Тёмная тема
#include <lib_Basic.cpp> #include <SFML/Graphics.hpp> ' #include <SFML/Window.hpp> ' #include <SFML/Audio.hpp> ' #include <SFML/Network.hpp> ' #include <SFML/System.hpp> CONST GAMEWIDTH AS INTEGER = 640 CONST GAMEHEIGHT AS INTEGER = 480 CONST CENTERTILE AS INTEGER = 16 CONST SIZETILE AS INTEGER = 32 CONST FLIPSPEED AS INTEGER = 2'8 CONST MAPSIZEX AS INTEGER = 8 CONST MAPSIZEY AS INTEGER = 14 CONST MAPPOSITIONX AS INTEGER = 192 CONST MAPPOSITIONY AS INTEGER = 16 DIM map[MAPSIZEX][MAPSIZEY] AS INTEGER DIM t1x AS INTEGER DIM t1y AS INTEGER DIM t2x AS INTEGER DIM t2y AS INTEGER DIM selection_done AS INTEGER = 0 DIM mouse_left_state AS INTEGER DIM mouse_position AS sf.Vector2i DIM mx AS INTEGER 'for test DIM my AS INTEGER 'for test DIM helpx AS INTEGER = -1 DIM helpy AS INTEGER = -1 DIM SCORE AS LONG = 0 DIM LEVEL AS INTEGER = 7 'min = 7; max = 16 DIM GameOver AS BOOLEAN = FALSE FUNCTION pred(BYVAL mapx AS INTEGER, BYVAL mapy AS INTEGER, BYVAL t AS INTEGER) AS BOOLEAN IF mapx >= 0 AND mapx <= MAPSIZEX - 1 THEN IF mapy >= 0 AND mapy <= MAPSIZEY - 1 THEN IF t = map[mapx][mapy] THEN RETURN TRUE END IF END IF END IF RETURN FALSE END FUNCTION FUNCTION EndGame(BYVAL x AS INTEGER, BYVAL y AS INTEGER) AS BOOLEAN DIM t AS INTEGER t = map[x][y] IF t = 0 THEN helpx = -1 helpy = -1 RETURN FALSE END IF IF pred(x, y + 1, t) = TRUE THEN IF pred(x, y + 3, t) = TRUE THEN helpx = x helpy = y + 3 RETURN FALSE END IF IF pred(x - 1, y + 2, t) = TRUE THEN helpx = x - 1 helpy = y + 2 RETURN FALSE END IF IF pred(x + 1, y + 2, t) = TRUE THEN helpx = x + 1 helpy = y + 2 RETURN FALSE END IF IF pred(x, y - 2, t) = TRUE THEN helpx = x helpy = y - 2 RETURN FALSE END IF IF pred(x - 1, y - 1, t) = TRUE THEN helpx = x - 1 helpy = y - 1 RETURN FALSE END IF IF pred(x + 1, y - 1, t) = TRUE THEN helpx = x + 1 helpy = y - 1 RETURN FALSE END IF END IF IF pred(x, y + 2, t) = TRUE THEN IF pred(x - 1, y + 1, t) = TRUE THEN helpx = x - 1 helpy = y + 1 RETURN FALSE END IF IF pred(x + 1, y + 1, t) = TRUE THEN helpx = x + 1 helpy = y + 1 RETURN FALSE END IF END IF IF pred(x + 1, y, t) = TRUE THEN IF pred(x + 3, y, t) = TRUE THEN helpx = x + 3 helpy = y RETURN FALSE END IF IF pred(x + 2, y - 1, t) = TRUE THEN helpx = x + 2 helpy = y - 1 RETURN FALSE END IF IF pred(x + 2, y + 1, t) = TRUE THEN helpx = x + 2 helpy = y + 1 RETURN FALSE END IF IF pred(x - 2, y, t) = TRUE THEN helpx = x - 2 helpy = y RETURN FALSE END IF IF pred(x - 1, y - 1, t) = TRUE THEN helpx = x - 1 helpy = y - 1 RETURN FALSE END IF IF pred(x - 1, y + 1, t) = TRUE THEN helpx = x - 1 helpy = y + 1 RETURN FALSE END IF END IF IF pred(x + 2, y, t) = TRUE THEN IF pred(x + 1, y - 1, t) = TRUE THEN helpx = x + 1 helpy = y - 1 RETURN FALSE END IF IF pred(x + 1, y + 1, t) = TRUE THEN helpx = x + 1 helpy = y + 1 RETURN FALSE END IF END IF helpx = -1 helpy = -1 RETURN TRUE END FUNCTION FUNCTION CountTile(BYVAL x AS INTEGER, BYVAL y AS INTEGER, BYVAL ty AS INTEGER, BYVAL dir AS INTEGER, BYREF cn AS INTEGER) AS BOOLEAN cn = 0 SELECT CASE dir CASE 0 'Up DO WHILE (y > 0) IF map[x][y] = ty THEN cn = cn + 1 ELSE RETURN (cn > 2) END IF y = y - 1 LOOP RETURN (cn > 2) CASE 1 'Right DO WHILE (x < MAPSIZEX) IF map[x][y] = ty THEN cn = cn + 1 ELSE RETURN (cn > 2) END IF x = x + 1 LOOP RETURN (cn > 2) CASE 2 'Down DO WHILE (y < MAPSIZEY) IF map[x][y] = ty THEN cn = cn + 1 ELSE RETURN (cn > 2) END IF y = y + 1 LOOP RETURN (cn > 2) CASE 3 'Left DO WHILE (x > 0) IF map[x][y] = ty THEN cn = cn + 1 ELSE RETURN (cn > 2) END IF x = x - 1 LOOP RETURN (cn > 2) END SELECT cn = 0 RETURN FALSE END FUNCTION FUNCTION CausesPop() AS BOOLEAN DIM x AS INTEGER DIM y AS INTEGER DIM tl AS INTEGER DIM tlc AS INTEGER FOR y = 0 TO MAPSIZEY - 1 FOR x = 0 TO MAPSIZEX - 1 tl = map[x][y] IF tl > 0 THEN IF CountTile(x, y, tl, 0, tlc) THEN RETURN TRUE ELSE IF CountTile(x, y, tl, 1, tlc) THEN RETURN TRUE ELSE IF CountTile(x, y, tl, 2, tlc) THEN RETURN TRUE ELSE IF CountTile(x, y, tl, 3, tlc) THEN RETURN TRUE END IF END IF END IF END IF END IF NEXT x NEXT y RETURN FALSE END FUNCTION FUNCTION Switch(BYVAL x0 AS INTEGER, BYVAL y0 AS INTEGER, BYVAL x1 AS INTEGER, BYVAL y1 AS INTEGER) AS BOOLEAN DIM a AS INTEGER a = map[x0][y0] map[x0][y0] = map[x1][y1] map[x1][y1] = a IF CausesPop() = TRUE THEN RETURN TRUE END IF a = map[x0][y0] map[x0][y0] = map[x1][y1] map[x1][y1] = a RETURN FALSE END FUNCTION SUB UpdateSelection(BYVAL mpx AS INTEGER, BYVAL mpy AS INTEGER, BYVAL isButtonPressed AS BOOLEAN) IF mpx >= MAPPOSITIONX AND mpx <= MAPPOSITIONX + (SIZETILE * MAPSIZEX) THEN IF mpy >= MAPPOSITIONY AND mpy <= MAPPOSITIONY + (SIZETILE * MAPSIZEY) THEN DIM dx AS INTEGER DIM dy AS INTEGER IF (isButtonPressed = TRUE) THEN mx = INT((mpx - MAPPOSITIONX) / SIZETILE) my = INT((mpy - MAPPOSITIONY) / SIZETILE) SELECT CASE mouse_left_state CASE 0 t1x = mx t1y = my mouse_left_state = 1 CASE 2 t2x = mx t2y = my mouse_left_state = 3 END SELECT ELSE SELECT CASE mouse_left_state CASE 1 mouse_left_state = 2 CASE 3 dx = ABS(t2x - t1x) dy = ABS(t2y - t1y) IF dx = 1 AND dy = 0 THEN selection_done = 1 ELSE IF dx = 0 AND dy = 1 THEN selection_done = 1 END IF END IF mouse_left_state = 0 IF (dx > 1 OR dy > 1) OR (dx = 0 AND dy = 0) OR (dx = 1 AND dy = 1) THEN mouse_left_state = 1 t1x = t2x t1y = t2y END IF END SELECT END IF END IF END IF END SUB SUB KillTiles(BYVAL x AS INTEGER, BYVAL y AS INTEGER, BYVAL c AS INTEGER, BYVAL dir AS INTEGER) SELECT CASE c CASE 3 SCORE = SCORE + 3 CASE 4 SCORE = SCORE + 10 CASE IS > 4 SCORE = SCORE + 50 END SELECT DIM d AS INTEGER FOR d = 0 TO c - 1 SELECT CASE dir CASE 0 map[x][y] = 0 y = y - 1 CASE 1 map[x][y] = 0 x = x + 1 CASE 2 map[x][y] = 0 y = y + 1 CASE 3 map[x][y] = 0 x = x - 1 END SELECT NEXT d END SUB SUB FillGrid() DIM x AS INTEGER DIM y AS INTEGER DIM tl AS INTEGER DIM tlc AS INTEGER FOR x = 0 TO MAPSIZEX - 1 IF map[x][0] = 0 THEN map[x][0] = ((RND() % LEVEL) + 1) END IF NEXT x FOR y = MAPSIZEY - 2 TO 0 STEP -1 FOR x = 0 TO MAPSIZEX - 1 IF map[x][y] > 0 THEN IF map[x][y + 1] = 0 THEN map[x][y + 1] = map[x][y] map[x][y] = 0 END IF END IF NEXT x NEXT y FOR y = 0 TO MAPSIZEY - 1 FOR x = 0 TO MAPSIZEX - 1 tl = map[x][y] IF tl > 0 THEN IF CountTile(x, y, tl, 0, tlc) = TRUE THEN KillTiles (x, y, tlc, 0) ELSE IF CountTile(x, y, tl, 1, tlc) = TRUE THEN KillTiles (x, y, tlc, 1) ELSE IF CountTile(x, y, tl, 2, tlc) = TRUE THEN KillTiles (x, y, tlc, 2) ELSE IF CountTile(x, y, tl, 3, tlc) = TRUE THEN KillTiles (x, y, tlc, 3) END IF END IF END IF END IF END IF NEXT x NEXT y END SUB FUNCTION main(BYVAL COMMANDCOUNT AS INTEGER, BYPTR COMMAND[] AS CHAR) AS INTEGER setlocale(LC_ALL, "RUS") RANDOMIZE() DIM Clock AS sf.Clock DIM x1 AS INTEGER DIM x2 AS INTEGER DIM y1 AS INTEGER DIM y2 AS INTEGER DIM Center_X AS INTEGER DIM Center_Y AS INTEGER DIM size1 AS FLOAT DIM size2 AS FLOAT DIM mt1 AS INTEGER DIM mt2 AS INTEGER DIM Do_Swap_Tiles AS BOOLEAN = FALSE DIM move_blocks AS INTEGER DIM move_axis AS INTEGER SET window(sf.VideoMode(GAMEWIDTH, GAMEHEIGHT, 32), "Match-three", sf.Style.Titlebar | sf.Style.Close) AS sf.RenderWindow window.setVerticalSyncEnabled(true) DIM font AS sf.Font IF NOT(font.loadFromFile("resources/sansation.ttf")) THEN RETURN EXIT_FAILURE END IF DIM debugMessage AS sf.Text debugMessage.setFont(font) debugMessage.setCharacterSize(14) debugMessage.setPosition(5.f, 355.f) debugMessage.setFillColor(sf.Color.White) DIM scoreMessage AS sf.Text scoreMessage.setFont(font) scoreMessage.setCharacterSize(14) scoreMessage.setPosition(5.f, 2.f) scoreMessage.setStyle(sf.Text.Bold); scoreMessage.setFillColor(sf.Color.White) DIM GameOverMessage AS sf.Text GameOverMessage.setFont(font) GameOverMessage.setCharacterSize(70) GameOverMessage.setPosition(115.f, 195.f) GameOverMessage.setStyle(sf.Text.Bold); GameOverMessage.setFillColor(sf.Color.White) GameOverMessage.setString("GAME OVER") DIM tileSet AS sf.Texture tileSet.loadFromFile("resources/blocks2.png") DIM tile(tileSet) AS sf.Sprite DIM textureback AS sf.Texture textureback.loadFromFile("resources/back.png") DIM spback(textureback) AS sf.Sprite DIM textureselect AS sf.Texture textureselect.loadFromFile("resources/select.png") DIM spselect(textureselect) AS sf.Sprite DIM texturehelp AS sf.Texture texturehelp.loadFromFile("resources/help.png") DIM sphelp(texturehelp) AS sf.Sprite DO WHILE (window.isOpen()) DIM event AS sf.Event DO WHILE (window.pollEvent(event)) IF ((event.type = sf.Event.Closed) OR ((event.type = sf.Event.KeyPressed) AND (event.key.code = sf.Keyboard.Escape))) THEN window.close() EXIT DO END IF LOOP IF selection_done = 0 THEN FillGrid() END IF window.clear(sf.Color(0, 0, 0)) window.draw(spback) GameOver = TRUE 'DrawGrid DIM x AS INTEGER DIM y AS INTEGER FOR y = 0 TO MAPSIZEY - 1 FOR x = 0 TO MAPSIZEX - 1 IF GameOver = TRUE THEN GameOver = EndGame(x, y) IF selection_done <> 0 THEN IF map[x][y] > 0 THEN IF (x = t1x AND y = t1y) OR (x = t2x AND y = t2y) THEN ELSE tile.setTextureRect(sf.IntRect(((map[x][y]) - 1) * SIZETILE, 0, SIZETILE, SIZETILE)) tile.setPosition(MAPPOSITIONX + x * SIZETILE, MAPPOSITIONY + y * SIZETILE) window.draw(tile) END IF END IF ELSE IF map[x][y] > 0 THEN tile.setTextureRect(sf.IntRect(((map[x][y]) - 1) * SIZETILE, 0, SIZETILE, SIZETILE)) tile.setPosition(MAPPOSITIONX + x * SIZETILE, MAPPOSITIONY + y * SIZETILE) window.draw(tile) END IF END IF NEXT x NEXT y IF GameOver = TRUE THEN mouse_left_state = -1 IF selection_done <> 0 THEN Do_Swap_Tiles = FALSE IF selection_done = 1 THEN move_blocks = SIZETILE selection_done = 2 x1 = MAPPOSITIONX + t1x * SIZETILE x2 = MAPPOSITIONX + t2x * SIZETILE y1 = MAPPOSITIONY + t1y * SIZETILE y2 = MAPPOSITIONY + t2y * SIZETILE Center_X = ((x2 - x1) / 2) + x1 Center_Y = ((y2 - y1) / 2) + y1 IF t1y = t2y THEN IF t1x > t2x THEN mt1 = map[t2x][t2y] mt2 = map[t1x][t1y] ELSE mt1 = map[t1x][t1y] mt2 = map[t2x][t2y] END IF ELSE IF t1y > t2y THEN mt1 = map[t2x][t2y] mt2 = map[t1x][t1y] ELSE mt1 = map[t1x][t1y] mt2 = map[t2x][t2y] END IF END IF move_axis = 1 IF t1y = t2y THEN move_axis = 0 END IF IF selection_done = 2 THEN IF move_blocks < 0 THEN IF Switch(t1x, t1y, t2x, t2y) = TRUE THEN selection_done = 0 mouse_left_state = 0 t1x = t2x t1y = t2y ELSE selection_done = 3 SCORE = SCORE - 5 END IF ELSE Do_Swap_Tiles = TRUE move_blocks = move_blocks - FLIPSPEED END IF END IF IF selection_done = 3 THEN IF move_blocks >= SIZETILE THEN selection_done = 0 Do_Swap_Tiles = TRUE ELSE move_blocks = move_blocks + FLIPSPEED Do_Swap_Tiles = TRUE END IF mouse_left_state = 0 END IF ELSE 'UpdateSelection mouse_position = sf.Mouse.getPosition(window) UpdateSelection(mouse_position.x, mouse_position.y, sf.Mouse.isButtonPressed(sf.Mouse.Left)) END IF IF Do_Swap_Tiles = TRUE THEN SELECT CASE move_axis CASE 0 'x tile.setTextureRect(sf.IntRect((mt1 - 1) * SIZETILE, 0, SIZETILE, SIZETILE)) tile.setPosition(Center_X + CENTERTILE - move_blocks, Center_Y) window.draw(tile) tile.setTextureRect(sf.IntRect((mt2 - 1) * SIZETILE, 0, SIZETILE, SIZETILE)) tile.setPosition(Center_X - CENTERTILE + move_blocks, Center_Y) window.draw(tile) CASE 1 'y tile.setTextureRect(sf.IntRect((mt1 - 1) * SIZETILE, 0, SIZETILE, SIZETILE)) tile.setPosition(Center_X, Center_Y + CENTERTILE - move_blocks) window.draw(tile) tile.setTextureRect(sf.IntRect((mt2 - 1) * SIZETILE, 0, SIZETILE, SIZETILE)) tile.setPosition(Center_X, Center_Y - CENTERTILE + move_blocks) window.draw(tile) END SELECT END IF IF selection_done = 0 THEN IF mouse_left_state <> 0 THEN IF GameOver = FALSE THEN spselect.setPosition(MAPPOSITIONX + t1x * SIZETILE, MAPPOSITIONY + t1y * SIZETILE) window.draw(spselect) END IF END IF IF GameOver = FALSE THEN sphelp.setPosition(MAPPOSITIONX + helpx * SIZETILE, MAPPOSITIONY + helpy * SIZETILE) window.draw(sphelp) END IF END IF 'FPS DIM Framerate AS sf.Time = Clock.getElapsedTime() Clock.restart() 'info for test debugMessage.setString("FPS " + STR(1.f / Framerate.asSeconds()) + "\n" _ + "selection_done = " + STR(selection_done) + "\n" _ + "x = " + STR(mouse_position.x) + " y = " + STR(mouse_position.y) + "\n" _ + "mx = " + STR(INT((mouse_position.x - MAPPOSITIONX) / SIZETILE)) + " my = " + STR(INT((mouse_position.y - MAPPOSITIONY) / SIZETILE)) + "\n" _ + "mouse_left_state = " + STR(mouse_left_state) + "\n" _ + "map[mx][my] = " + STR(map[mx][my]) + "\n" _ + "t1x = " + STR(t1x) + " t1y = " + STR(t1y) + "\n" _ + "t2x = " + STR(t2x) + " t2y = " + STR(t2y) + "\n" _ ) IF SCORE > 100 THEN LEVEL = 8 IF SCORE > 200 THEN LEVEL = 9 IF SCORE > 300 THEN LEVEL = 10 IF SCORE > 500 THEN LEVEL = 11 IF SCORE > 600 THEN LEVEL = 12 IF SCORE > 700 THEN LEVEL = 13 IF SCORE > 800 THEN LEVEL = 14 IF SCORE > 900 THEN LEVEL = 15 IF SCORE > 1000 THEN LEVEL = 16 scoreMessage.setString("LEVEL " + STR(LEVEL - 6) + "\n" + "SCORE " + STR(SCORE) + "\n") window.draw(debugMessage) window.draw(scoreMessage) IF GameOver = TRUE THEN window.draw(GameOverMessage) END IF window.display() LOOP RETURN 0 END FUNCTION