Howdy, Stranger!

It looks like you're new here. If you want to get involved, click one of these buttons!

Is there a function to generate possible x,y,w,h values for n rectangles to fit on phone screen?

in Questions Posts: 102

So basically i'm just trying to make a card game. I've got the prototype in Codea running on an Ipad in landscape mode, but I'm having difficulty figuring out what the card dimensions should be for an iphone in either landscape or portrait mode. Here is the project that i posted days ago (https://codea.io/talk/discussion/8198/card-game-dropbox-zip-file-no-installer#latest)

What i did do was make a big list by hand of x, y, x2, y2 values for each potential card, but only In ipad Landscape mode.

There are up to 16 cards, as well as one deck. So seventeen tables of x,y,x2, y2 values. REALLY don't want to rewrite this by hand for each possible screen orientation and device. I thought I could try making a function to generate this automatically, but no luck - is beyond my knowledge. help?

P.s. I haven't decided what width and height of cards would be good to fit on a phone screen. I was using 140 x 196 on the iPad, but on a phone screen (320x480) that will not fit. Maybe 70 x 98? The hard part is trying to figure out where everything should go. I don't want to use any magnification or scrolling, rather just have everythiing fit on screen. If not possible, then... well, function first, practicality after, with a function like that it would still make this easier

P.s.s. Do i have to program again for the dimensions of an iphone 6+ screen? Or is it automatically scaled up from a normal iphone screen?

Comments

  • Posts: 71

    To make the cards scale with the screen size, you could just use the variables WIDTH and HEIGHT. WIDTH/18 could be the width of a card and HEIGHT/16 could be the height of the same card. Just put everything that might change on a different size screen in terms of WIDTH and HEIGHT.

  • dave1707dave1707 Mod
    Posts: 6,397

    @xThomas See the discussion I show below. I have a program in there that scales the screen for different sizes. You can look at that to see how I did it.

    https://codea.io/talk/discussion/8026/best-way-to-scale-ui-elements-for-all-screen-sizes
    
  • dave1707dave1707 Mod
    edited March 19 Posts: 6,397

    @xThomas I modified my original code to include the iPad Pro, the 38mm Watch, and the 42mm Watch. Since I don't have an iPad Pro, the 42mm or 38mm Watch, I'm not sure if this show the correct information for those sizes. If anyone has one of them, let me know if there's a problem.

    displayMode(FULLSCREEN)
    
    function setup()  
        device={"iPad Pro","iPad Air","iPhone7 Plus","iPhone7","iPhone 5","Watch 42mm","Watch 38mm"}
        rectMode(CENTER)
        fontSize(40)
        font("Baskerville-Italic")
        x=300
        y=100
        xv=3
        yv=3
        dev=1
        if WIDTH<HEIGHT then
            tab={vec2(1024,1366),vec2(768,1024),vec2(414,736),
                    vec2(375,667),vec2(320,568),vec2(156,195),vec2(136,170)}
        else
            tab={vec2(1366,1024),vec2(1024,768),vec2(736,414),
                    vec2(667,375),vec2(568,320),vec2(195,156),vec2(170,136)}
        end 
        wm=WIDTH
        hm=HEIGHT 
    end
    
    function orientationChanged()
        setup()
    end
    
    function draw()
        background(0)
        fill(255)   
        stroke(255)
        strokeWidth(3)
    
        -- same code for all devices
        w=tab[dev].x    -- width of device from table
        h=tab[dev].y    -- height of device from table
        mw=wm     -- largest width of all devices
        mh=hm     -- largest height of all devices
        ar=(w/h)/(mw/mh)    -- aspect ratio
    
        scale(w/mw,h/mh)    -- scale of device to largest screen
    
        sprite("Planet Cute:Character Pink Girl",x,y,101,171*ar)
        sprite("Planet Cute:Character Cat Girl",100,600,101,171*ar)
    
        text("Tap screen to show different device sizes.",mw*.38,mh*.25)
        text(device[dev],mw*.2,mh*.45)
        text(tab[dev].x.."  "..tab[dev].y,mw*.2,mh*.4)
    
        noFill()
        ellipse(mw/2,mh/2,50,50*ar)
        ellipse(mw*.75,mh*.75,100,100*ar)
    
        line(mw/2,mh/2,0,mh)
        line(mw*.75,mh*.75,200,100)
    
        rect(mw/2,mh/2,mw,mh)
        rect(200,100,100,100*ar)
        -- end of same code for all devices
    
        -- calculate motion of sprite
        x=x+xv
        y=y+yv
        if x>=mw or x<=0 then
            xv=-xv
        end
        if y>=mh or y<=0 then
            yv=-yv
        end    
    end
    
    function touched(t) -- display different device size
        if t.state==BEGAN then
            dev=dev+1
            if dev>#device then
                dev=1
            end
        end
    end
    
  • Posts: 102

    @dave1707 sorry it took so long to get back to u, but cool. Any ideas on how i can improve my own piece of code before i take a longer look at implementing yours? It should be self explanatory, but if it isn't, and I might not have explained my problem very well, im still trying to make the function that can set the x,y x2 and y2 positions in a table so i draw cards and handle touch. But it's kind of hard for me, i'm not really used to this math,but i think it is necessary so i can implement it into my card game, where right now it's all set by hand. I am not good at this :( (to be clear, the problem is that it doesn't look good right now, but its fully playable)

    -- Attempting to make a function for set of playing cards with even spacing in between them. that can auto reaize itself for different orientation changes
    
    -- it kind of works but doesnt work right
    
    
    playingFields = {}
    
    function setcards()
        print "setting card positions!?"
        local w, h = 180, 240
        local sw, sh = 20, 28
        local x, y, x2, y2
        local j = 0
        local k = 1
        y = HEIGHT - h - sh
        y2 = HEIGHT - sh
        local tx, ty
        local yy, yy2
        local wrapwidth = WIDTH - 20
        local ywrap = 0
        local shy = 1
        for i = 1,16 do
            x = w * j + sw * k
            x2 = w * k + sw * k
            yy = y - (h * ywrap) - (sh * shy)
            yy2 = y2 - (h * ywrap) - (sh * shy)
            if x2 > wrapwidth then
                --print(" exceeded wrapwidth, wrapping to next line ")
                j = 0
                k = 1
                x = w * j + sw * k
                x2 = w * k + sw * k
                ywrap = ywrap + 1
                yy = y - (h * ywrap) - (sh * shy)
                yy2 = y2 - (h * ywrap) - (sh * shy)
                shy = shy + 1
            end
            tx = x + w/2
            ty = yy + h/2
            playingFields[i] = {x = x, x2 = x2, y = yy, y2 = yy2, tx = tx, ty = ty}
            playingFields[i][0] = i
    
            k, j = k + 1, j + 1
    
           -- print("("..x..", "..yy..")", "("..x2..", "..yy2..")")
         --   print("ywrap ="..ywrap)
        end
    end
    
    function setup()
        setcards()
    
    end
    
    function orientationChanged( newO )
        setcards()
    end
    function draw()
        background(40,40,50)
        for i,v in ipairs(playingFields) do
           -- fill(16*i)
            pushStyle()
            rectMode(CORNERS)
            stroke(0,252,0)
            strokeWidth(3)
            fill(168)
            rect(v.x, v.y, v.x2, v.y2)
            popStyle()
            pushStyle()
            fontSize(32)
            font("Arial")
            fill(252,252)
            text(v[0], v.tx, v.ty)
            popStyle()
        end
    end
    
    
  • dave1707dave1707 Mod
    Posts: 6,397

    @xThomas How many cards across and down are you trying to fit on the screen.

  • dave1707dave1707 Mod
    Posts: 6,397

    @xThomas I don't think my original code would work for cards. Here is a different version to place cards on different size screens. I don't know how many cards you want on the screen, so I set this so you can change the number of cards across and down. You can also change the spacing size in between the cards. I'm just simulating different screen sizes, but you would have to change some of the code to use the WIDTH and HEIGHT of the actual device screen.

    displayMode(FULLSCREEN)
    supportedOrientations(LANDSCAPE_ANY)
    
    function setup()  
        rectMode(CENTER)
        dev=1
        device={"iPad Pro","iPad Air","iPhone7 Plus","iPhone7","iPhone 5"}
        tab={vec2(1366,1024),vec2(1024,768),vec2(736,414),vec2(667,375),vec2(568,320)}
    
        xCards=8    -- number of cards across
        yCards=4    -- number of cards down
        spacing=4   -- spacing between cards
    end
    
    function draw()
        background(0)    
        -- set screen size, change code to use actual screen size
        currW=tab[dev].x
        currH=tab[dev].y
    
        -- determine card size based on screen size
        sx=(currW-spacing*(xCards+1))//xCards
        sy=(currH-spacing*(yCards+1))//yCards
    
        drawCards()
    
        -- draw screen outline, not needed for actual device.
        noFill()
        stroke(255)
        strokeWidth(3)
        rect(currW/2,currH/2,currW,currH)  
    
        -- display text, not needed for actual device 
        fill(255)   
        text(device[dev],WIDTH/2,HEIGHT-25)
        text(tab[dev].x.." x "..tab[dev].y,WIDTH/2,HEIGHT-50)
        text("Cards = "..xCards.." across by "..yCards.." down",WIDTH/2,HEIGHT-75)
        text("Tap screen to change screen size",WIDTH/2,HEIGHT-100)
    end
    
    function touched(t) -- display different device size
        if t.state==BEGAN then
            dev=dev+1
            if dev>#device then
                dev=1
            end
        end
    end
    
    function drawCards()
        fill(255,255,255,80)
        for x=1,xCards do
            for y=1,yCards do
                rect(x*sx+x*spacing-sx/2,y*sy+y*spacing-sy/2,sx,sy)
            end
        end
    end
    
  • Posts: 213

    I have been starting to use a different form for making my apps universal, so I will share my old technique of making any app universal. All you have to do is create an image in the setup(), then setContext() of the entire draw(). Be careful not to use WIDTH and HEIGHT, for they will mess it up. Make variables called WIDTHw and HEIGHTh and make them equal to normal size screen. Here's an example:

    -- Universal
    supportedOrientations(CurrentOrientation)
    displayMode(OVERLAY)
    function setup()
        if CurrentOrientation==LANDSCAPE_LEFT or CurrentOrientation==LANDSCAPE_RIGHT then
            WIDTHw=1024
            HEIGHTh=768
        else
            WIDTHw=768
            HEIGHTh=1024
        end
        output.clear()
        parameter.clear()
        print("This is an example of making an app universal!")
        GIMG=image(WIDTHw,HEIGHTh)
        GSize=vec2(WIDTH,HEIGHT)
        parameter.number("Width of Device",1,WIDTHw,WIDTHw,function(a)
            GSize.x=a
        end)
        parameter.number("Height of Device",1,HEIGHTh,HEIGHTh,function(t)
            GSize.y=t
        end)
        print"Drag the parameters to change the size of the screen."
        print("It looks a bit distorted, but it works for 2D and 3D")
    end
    
    -- This function gets called once every frame
    function draw()
        background(0)
        setContext(GIMG,true)
        pushMatrix()pushStyle()
        background(255)
        rectMode(CENTER)
        fill(229, 98, 98, 195)
        stroke(167, 223, 137, 202)
        strokeWidth(10)
        rect(WIDTHw/2,HEIGHTh/2,(vec2(WIDTHw,HEIGHTh)*3/4):unpack())
        sprite("SpaceCute:Rocketship",WIDTHw/2,HEIGHTh/2)
        fill(0)
        fontSize(80)
        textAlign(CENTER)
        font("AcademyEngravedLetPlain")
        textMode(CENTER)
        text("Developing\nFor Dummies",WIDTHw/2,HEIGHTh*3/4)
        fontSize(30)
        font("Zapfino")
        text("Author\n|Da Baller|",WIDTHw/2,HEIGHTh/4)
        popMatrix()popStyle()
        setContext()
        pushMatrix()pushStyle()
        spriteMode(CENTER)
        sprite(GIMG,GSize.x/2,GSize.y/2,GSize:unpack())
        popMatrix()popStyle()
    end
    
  • dave1707dave1707 Mod
    Posts: 6,397

    @CamelCoder Does that work if you have a lot of objects moving around the screen.

  • Posts: 213

    @dave1707 yeah, in fact, it runs at almost the same FPS, except, 3D buffer will slow it down just a tiny bit, maybe like .5 FPS. If you haven't downloaded my apps, that's what I used for it. My app, Mazoo: The Ultimate 3D Maze, is 3D and works on all devices properly. It's just a bit slow on old devices, but that doesn't have to do anything with the setContext()

  • dave1707dave1707 Mod
    Posts: 6,397

    @CamelCoder I tried it with moving sprites and it works fine. Great Job. But like you said, any sprites I use are distorted. There should be a way to calculate an aspect ratio with yours so sprites, circles, or squares remain correct.

Sign In or Register to comment.