Completed scrolling in tile picker for level editor
[butaba-adventures.git] / leveleditor.py
old mode 100644 (file)
new mode 100755 (executable)
index 784199b..1fe96e1
@@ -1,8 +1,8 @@
-#!/usr/bin/env python3
+#!/usr/bin/env python
 
 # level designer gui - this is used to design level graphics
 # very rough and ready - main purpose is to allow quick game
-# design. inputting levels by hand array is very tough
+# design. inputting levels by hand array is very tedious
 
 import pygame
 import os.path
@@ -25,7 +25,7 @@ def draw_level (screen, leveldata, tileset):
                                j += 1
                        i += 1
 
-def display_menu (screen):
+def display_menu (screen, tileset, tilerow, tilecol):
        utility.put_text (screen, 490, 10, 10, (255,255,0), "p to pick tile")
        utility.put_text (screen, 490, 50, 10, (255,255,0), "w to wall (solid)")
        utility.put_text (screen, 490, 90, 10, (255,255,0), "<space> to place")
@@ -33,6 +33,10 @@ def display_menu (screen):
        utility.put_text (screen, 490, 170, 10, (255,255,0), "s to Save level")
        utility.put_text (screen, 490, 210, 10, (255,255,0), "q to Quit editor")
 
+       # currently selected tile
+       utility.put_text (screen, 490, 250, 10, (255,255,255), "Tile selected")
+       screen.blit (tileset, (490, 290), (tilecol*48, tilerow*48, 48, 48))
+
 # draw the tile cursor
 def draw_cursor (screen, currow, curcol):
        pygame.draw.rect (screen, (255,255,255), (curcol*48, currow*48, 48, 48), 1)
@@ -42,6 +46,152 @@ def make_wall (leveldata, row, col):
        # get the actual data in that place
        leveldata[row][col][2] = not leveldata[row][col][2]
 
+# place a tile at current spot
+def put_tile (leveldata, row, col, tilerow, tilecol):
+       leveldata[row][col][0] = tilerow
+       leveldata[row][col][1] = tilecol
+
+# picking a tile from the tileset
+def pick_tile (screen, tileset):
+       selrow, selcol = 0, 0
+
+       # total number of rows and columns
+       totalrows = tileset.get_height () / 48
+       totalcols = tileset.get_width () / 48
+
+       # implement scrolling by 480x480
+       # first get the number of pages to span across. If the width is
+       # exactly fitting in the page use totalwidth/480 else totalwidth/480+1
+       # (integer divison)
+       if tileset.get_width () % 480 == 0:
+               totalpages_cols = tileset.get_width () / 480
+       else:
+               totalpages_cols = tileset.get_width () / 480 + 1
+
+       if tileset.get_height () % 480 == 0:
+               totalpages_rows = tileset.get_height () / 480
+       else:
+               totalpages_rows = tileset.get_height () / 480 + 1
+
+       # set the current page
+       curpage_cols = 0
+       curpage_rows = 0
+
+       # cursor row and column
+       cursor_row = 0
+       cursor_col = 0
+
+       # the code for scrolling through the tileset is quite complicated here are the steps
+       # first we determine the total number of pages (number of row pages and col pages
+       # then when scrolling we check for two things:
+       # first horizontal scrolling:
+       # logic goes like this
+       # left arrow key movement:
+       # is the cursor col < 0 ? if so, is it the first page? if so, then set the
+       # cursor col to the last col of the last page. This unfortunately is not so easy
+       # because it need not be 10. So we determine the last col as follows:
+       # total width of the tileset image modulo 480 = this gives us a multiple of 48
+       # since we are using 48x48 tiles and the tileset file size is a multiple of 48.
+       # then we divide that value by 48 which gives us a number between 0 and 9.
+       # this is the last col. If it is not the first page, we simply set the cursor
+       # column to 9 and reduce the page by 1.
+       # right arrow movement:
+       # simply if it is the last col and last page we simply reset the
+       # page to 0 and the cursor col to 0. Otherwise page is incremented by 1
+       # and col is still set to 0. simple logic
+
+       # vertical scrolling using the same logic
+
+       while 1:
+               screen.fill (pygame.Color (0, 0, 0))
+               screen.blit (tileset, (0, 0), (curpage_cols * 480, curpage_rows * 480, 480, 480))
+               draw_cursor (screen, cursor_row, cursor_col)
+               pygame.display.update ()
+               for event in pygame.event.get ():
+                       if event.type == pygame.KEYDOWN:
+                               if event.key == pygame.K_ESCAPE:
+                                       return None
+                               elif event.key == pygame.K_SPACE or event.key == pygame.K_RETURN:
+                                       return selrow, selcol
+                               elif event.key == pygame.K_UP:
+                                       # reduce the selected row by 1
+                                       selrow -= 1
+                                       if selrow < 0:
+                                               selrow = totalrows - 1
+
+                                       # reduce the cursor row by 1
+                                       cursor_row -= 1
+                                       # if cursor row is < 0
+                                       if cursor_row < 0:
+                                               # reduce the page by 1
+                                               curpage_rows -= 1
+                                               if curpage_rows < 0:
+                                                       curpage_rows = totalpages_rows - 1
+                                                       if tileset.get_height () % 480 > 0 :
+                                                               # cursor row should be the last row - this is
+                                                               cursor_row = (tileset.get_height () % 480) / 48 - 1
+                                                       else:
+                                                               cursor_row = 9
+                                               else:
+                                                       cursor_row = 9
+
+                               elif event.key == pygame.K_DOWN:
+                                       # increase the selected row by 1
+                                       selrow += 1
+                                       if selrow >= totalrows:
+                                               selrow = 0
+
+                                       # increase the cursor row by 1
+                                       cursor_row += 1
+                                       # if cursor row is > 9
+                                       if ((tileset.get_height () % 480 > 0 and curpage_rows >= totalpages_rows - 1 and cursor_row >= (tileset.get_height () % 480) / 48)
+                                                       or cursor_row >= 10):
+                                               # increase the page by 1
+                                               curpage_rows += 1
+                                               # if the pages rows is >= totalpages_rows
+                                               if curpage_rows >= totalpages_rows:
+                                                       curpage_rows = 0
+                                                       cursor_row = 0
+                                               else:
+                                                       cursor_row = 0
+
+                               elif event.key == pygame.K_LEFT:
+                                       # decrease the selected col by 1
+                                       selcol -= 1
+                                       if selcol < 0:
+                                               selcol = totalcols - 1
+
+                                       # decrease the cursor col by 1
+                                       cursor_col -= 1
+                                       # if cursor col < 0
+                                       if cursor_col < 0:
+                                               curpage_cols -= 1
+                                               if curpage_cols < 0:
+                                                       curpage_cols = totalpages_cols - 1
+                                                       if tileset.get_width () % 480 > 0:
+                                                               cursor_col = (tileset.get_width () % 480) / 48 - 1
+                                                       else:
+                                                               cursor_col = 9
+                                               else:
+                                                       cursor_col = 9
+                               elif event.key == pygame.K_RIGHT:
+                                       selcol += 1
+                                       if selcol >= totalcols:
+                                               selcol = 0
+
+                                       # increase the cursor col by 1
+                                       cursor_col += 1
+                                       # if cursor col > 9
+                                       if ((tileset.get_width () % 480 > 0 and curpage_cols >= totalpages_cols - 1 and cursor_col >= (tileset.get_width () % 480) / 48)
+                                               or cursor_col >= 10):
+                                               curpage_cols += 1
+                                               if curpage_cols >= totalpages_cols:
+                                                       curpage_cols = 0
+                                                       cursor_col = 0
+                                               else:
+                                                       cursor_col = 0
+
+
 # the actual level editor
 def level_editor (fname):
        # load level data
@@ -53,10 +203,11 @@ def level_editor (fname):
        screen = pygame.display.set_mode ((720, 512))
        pygame.display.set_caption ("Level editor")
        currow, curcol = 0, 0
+       tilerow, tilecol = 0, 0
 
        while 1:
                screen.fill (pygame.Color (0, 0, 0))
-               display_menu (screen)
+               display_menu (screen, tileset, tilerow, tilecol)
                draw_level (screen, leveldata, tileset)
                draw_cursor (screen, currow, curcol)
                pygame.display.update ()
@@ -65,6 +216,9 @@ def level_editor (fname):
                                if event.key == ord ("q"):
                                        pygame.quit ()
                                        return
+                               elif event.key == ord ("s"):
+                                       cPickle.dump (leveldata, file (fname, "w"))
+                                       print ("Level saved")
                                elif event.key == pygame.K_DOWN:
                                        currow += 1
                                        if currow > 9:
@@ -81,6 +235,13 @@ def level_editor (fname):
                                        curcol += 1
                                        if curcol > 9:
                                                curcol = 0
+                               elif event.key == pygame.K_SPACE or event.key == pygame.K_RETURN:
+                                       put_tile (leveldata, currow, curcol, tilerow, tilecol)
+                               elif event.key == ord ("p"):
+                                       tile = pick_tile (screen, tileset)
+                                       if tile is not None:
+                                               tilerow = tile[0]
+                                               tilecol = tile[1]
                                elif event.key == ord ("w"):
                                        make_wall (leveldata, currow, curcol)
 
@@ -107,7 +268,8 @@ def new_level ():
        level_editor (fname)
 
 def load_level ():
-       pass
+       fname = raw_input ("Level file to load: ")
+       level_editor (fname)
 
 def main ():
        while 1:
@@ -130,4 +292,4 @@ def main ():
 
 
 if __name__=="__main__":
-       main ()
\ No newline at end of file
+       main ()