-- Learn to Program with Singe -- Lesson 7: A Game dofile("Singe/Framework.singe") local PLAYER_WIDTH = 40 local PLAYER_HEIGHT = 8 local PLAYER_SPEED = 4 local PLAYER_MARGIN = 4 local BLOCK_SIZE = 12 local BLOCK_SPEED = 1.5 local BLOCK_FASTER = 0.05 local SPAWN_FRAMES = 40 local START_LIVES = 3 local TEXT_COLUMNS = overlayGetWidth() // overlayGetFontWidth() local screenWidth = overlayGetWidth() local screenHeight = overlayGetHeight() local playerY = screenHeight - PLAYER_HEIGHT - PLAYER_MARGIN local playerX = (screenWidth - PLAYER_WIDTH) / 2 local goingLeft = false local goingRight = false local blocks = {} local blockSpeed = BLOCK_SPEED local spawnTimer = 0 local score = 0 local lives = START_LIVES local state = "waiting" function drawGame() colorForeground(80, 255, 160) overlayBox(playerX, playerY, playerX + PLAYER_WIDTH - 1, playerY + PLAYER_HEIGHT - 1) colorForeground(255, 90, 90) for i, block in ipairs(blocks) do overlayBox(block.x, block.y, block.x + BLOCK_SIZE - 1, block.y + BLOCK_SIZE - 1) end overlayPrint(1, 1, "SCORE " .. score .. " LIVES " .. lives) end function drawOverText() printCentered(7, "GAME OVER") printCentered(9, "PRESS SPACE TO PLAY AGAIN") end function drawWaitingText() printCentered(6, "DODGE THE BLOCKS") printCentered(8, "ARROW KEYS TO MOVE") printCentered(10, "PRESS SPACE TO START") end function printCentered(row, text) overlayPrint(math.floor((TEXT_COLUMNS - #text) / 2), row, text) end function spawnBlock() local block = {} block.x = math.random(0, screenWidth - BLOCK_SIZE) block.y = -BLOCK_SIZE table.insert(blocks, block) end function startGame() playerX = (screenWidth - PLAYER_WIDTH) / 2 blocks = {} blockSpeed = BLOCK_SPEED spawnTimer = 0 score = 0 lives = START_LIVES state = "playing" end function updatePlaying() if goingLeft then playerX = playerX - PLAYER_SPEED end if goingRight then playerX = playerX + PLAYER_SPEED end if playerX < 0 then playerX = 0 elseif playerX > screenWidth - PLAYER_WIDTH then playerX = screenWidth - PLAYER_WIDTH end spawnTimer = spawnTimer - 1 if spawnTimer <= 0 then spawnBlock() spawnTimer = SPAWN_FRAMES end for i = #blocks, 1, -1 do local block = blocks[i] block.y = block.y + blockSpeed if collideRects(block.x, block.y, BLOCK_SIZE, BLOCK_SIZE, playerX, playerY, PLAYER_WIDTH, PLAYER_HEIGHT) then table.remove(blocks, i) lives = lives - 1 if lives == 0 then state = "over" end elseif block.y > screenHeight then table.remove(blocks, i) score = score + 1 blockSpeed = blockSpeed + BLOCK_FASTER end end end function onInputPressed(what) if what == SWITCH_LEFT then goingLeft = true elseif what == SWITCH_RIGHT then goingRight = true elseif what == SWITCH_BUTTON1 and state ~= "playing" then startGame() end end function onInputReleased(what) if what == SWITCH_LEFT then goingLeft = false elseif what == SWITCH_RIGHT then goingRight = false end end function onOverlayUpdate() if state == "playing" then updatePlaying() end overlayClear() drawGame() if state == "waiting" then drawWaitingText() elseif state == "over" then drawOverText() end return OVERLAY_UPDATED end