How can you have multiple "screens"

Hello! I’ve been wondering this for awhile how I can make multiple screens, for example, Lets say I want a world where you can step on a button, and by pressing the button your screen changes to the main menu.
Any suggestions?

Here’s a menu example.


displayMode(FULLSCREEN)
supportedOrientations(PORTRAIT)        -- set for portrait mode

function setup()
    func=menu
end

function draw()
    func()
end

function menu()
    background(0,0,200)  
    
    w=WIDTH/2            -- set width value
    eh=HEIGHT-400        -- set height of different options
    nh=HEIGHT-600        -- eh easy, nh normal, hh hard
    hh=HEIGHT-800
     
    fontSize(48)            -- set font size
    fill(255,0,0)            -- set font color
    
    menuTitle1="Main Menu"            -- main title
    menuTitle2="Select Option"    
    text(menuTitle1,w,HEIGHT-100)     -- display titles 
    text(menuTitle2,w,HEIGHT-200)      
 
    fill(0,255,0)           -- set easy values
    
    t1="Easy"
    text(t1,w,eh)
    w1,h1=textSize(t1)     -- width and height of easy text 
     
    t2="Normal"            -- set normal values
    text(t2,w,nh)
    w2,h2=textSize(t2)      -- width and height of normal text
    
    t3="Hard"                -- set hard values
    text(t3,w,hh)  
    w3,h3=textSize(t3)      -- width and height of hard text  
end

function easy()
    background(40,40,50)
    text("EASY screen",WIDTH/2,HEIGHT/2)
    text("tap screen for menu",WIDTH/2,HEIGHT/2-200)
end

function normal()
    background(40,40,50)
    text("NORMAL screen",WIDTH/2,HEIGHT/2)
    text("tap screen for menu",WIDTH/2,HEIGHT/2-200)
end

function hard()
    background(40,40,50)
    text("HARD screen",WIDTH/2,HEIGHT/2)
    text("tap screen for menu",WIDTH/2,HEIGHT/2-200)
end

function touched(t)
    if t.state==BEGAN then
        if func ~= menu then
            func=menu
            return
        end
        if func==menu then
            if t.x>w-w1/2 and t.x<w+w1/2 and t.y>eh-h1/2 and t.y<eh+h1/2 then
                func=easy
            end
            if t.x>w-w2/2 and t.x<w+w2/2 and t.y>nh-h2/2 and t.y<nh+h2/2 then
                func=normal
            end
            if t.x>w-w3/2 and t.x<w+w3/2 and t.y>hh-h3/2 and t.y<hh+h3/2 then
                func=hard
            end  
       end
    end  
end

Here’s some code I wrote a while ago that does this: http://coolcodea.wordpress.com/2013/05/04/47-game-template/

But those just look like menus, Are they just that are multiple screens?

is this that u said??
http://pastebin.com/NfRAmaYx

@Prynok The code I show above is an example of how to display different screens based on what button you tap. Since I don’t know exactly what you want to do with the different screens, I can only show screens that don’t really do anything. Since the screens don’t do anything, I just return back to the menu when you tap the screen. You would do whatever you want in the different screens and where you return to would depend on your code.

… but if you mean multiple screens like PIP, then you might wanna look at setContext() …

-delete-

I’ve got some code in my game (StackIt) that does menus, multiple screens, and transitions, but it’s heavily integrated with the rest of my code.

-delete-

  • Double post *

@Prynok - perhaps what’s confusing you is that in Codea there are no “screens”. There is one screen that is redrawing itself 60 times a second.

So if you want to show a menu, you draw a menu. If you want to play the game, you draw the game. That is why the examples you have been given have a variable that tells Codea what it should be drawing, ie whether it is a menu, the game etc.

So your draw code will look something like

function draw()
    if state=="Menu" then
        --code to draw menu
    elseif state=="Playing" then
        --code to draw game
    end

This is also a great place to use classes. You don’t want to draw the entire game in your main tab’s draw() function. Instead, you should have, at the very least, a Game object and a Menu object. Each one of those has a draw() function. In the Menu object, you’ll have code that draws the active menu items. In the Game object, you’ll have a table of things that get drawn. (Actually, you should have at least 2 tables: one for the background and one for dynamic objects and actors.)

So, building on Ignatz’s example, your main draw routine would look like:

function draw()
    if menu.active then
        menu:draw()
    elseif game.active then
        game:draw()
    else
        titleScreen:draw()
    end
end

Correction to @tomxp411’s code - Line 7 - titleScreen:draw()

yeah, the difference between : and . can be important. Every time I see that error trying to index nil, I know right what to go look for…

Oh that makes sense, thanks!

What I do is create a variable called “scene” and make an if statement in the draw function that’s “if scene == 1 then…(What to do for this scene)… elseif scene == 2 then…(What to do for this scene)…end” etc. I think that’s the simplest way. Now when you want to change your screen you just do “scene = (The scene #)”.

Classes are really good here instead of if() in draw simply because it’s easier to forward the execution to another “thing” to do - but it’s confusing to debug issues. I typically put together a main that consists of this:

--
-- main.lua
--

-- 0_GameTemplate
function setup()
        SetDisplayMode() --your own function

--GAME STATE DRIVER -- CAN ABSTRACT IN THE FUTURE
    -- define consts - these drive the game state
    --Note that I could have abstracted these 
    --into the GameFunctions file, but I want
    --to "see" the states.
    GAMESTATE_TITLE = 1
    GAMESTATE_PLAYING = 2
    -- put any screen states you want in here.
    GAMESTATE_SCREEN1 = 3
    GAMESTATE_SCREEN2 = 4
    GAMESTATE_ENDED = 5
    
    --these are the screens (classes) that are called when 
   --the game performs it's heartbeat
    --there should be one of these for each of the items above.
    GAMESTATES = { ScreenTitle, ScreenGame, nil, nil, ScreenEnd }
--note I don't have a SCREEN1 or SCREEN2, so 
--I assigned nil for now, These are Codea classes!

    --start at the default Title / Menu screen
    --note that this will occur fast, so if you are defer loading, 
--you'll have to 
    --be aware that all assets might not be loaded 
--before the Title screen renders.
    GAMESTATE = GAMESTATE_TITLE
 --END OF GAMESTATE DRIVER
   
    GameSetup()    --sets up game parameters. 
        --Not the same as the game state driver. Your custom variable setup

end


-- This function gets called once every frame
--this is the game's heartbeat.
function draw()
    background(0, 0, 0, 255) --clear background
    --state machine
    GAMESTATES[GAMESTATE]:draw()  --draw whatever the "Screen" should be
end

--any touches we get, forward on to the screen / class that needs them.
--note that this assumes that the default touch() is working!  
function touched(touch)
    --state machine - forward the touch!
    GAMESTATES[GAMESTATE]:touched(touch)      
end

GAMESTATES are the “screens”, basically, classes in Codea that handle their own draw() and touched(). Whenever you want to change the state of the game, change the value of the GAMESTATE variable to any of the constants, and the game will immediately jump / draw / touch in that state.

The biggest challenge with this is knowing how to safely switch states - clearing variables and making sure that you don’t jump into the middle of a game when you just finished doing high scores, for example. Careful variable use should help you avoid that.

I don’t know if this is the right place to go, but instead of having multiple screens in which the transitions quickly snap to the screen you wish to go to, couldn’t you also have a scene which the screen displays partially while you are in one section, and when you swipe or select a button the screen (slowly) shifts to reveal the other half of the scene.

I’m trying to refer to the screen in a game called Tiny Wings. I’m currently trying to code the effect using Codea.