added (optional) main menu buttons to insert or play solution tape
authorHolger Schemel <info@artsoft.org>
Wed, 13 Jun 2018 22:57:40 +0000 (00:57 +0200)
committerHolger Schemel <info@artsoft.org>
Sun, 17 Jun 2018 22:02:50 +0000 (00:02 +0200)
There is a difference to the already existing tape buttons to insert
or play a solution tape in that the main menu buttons are only drawn
if the current level really has a solution tape, while the tape buttons
are always drawn, regardless if the level has a solution tape or not.

src/conf_gfx.c
src/main.h
src/screens.c
src/tape.c
src/tape.h

index 785b2e2ac03b1d852f6c74d1e97e18ec2ec2db15..20bb68308b27546d698cea883a529cc82c1d4c85 100644 (file)
@@ -6088,6 +6088,11 @@ struct ConfigInfo image_config[] =
   { "menu.button_level_number",                        UNDEFINED_FILENAME      },
   { "menu.button_level_number.active",         UNDEFINED_FILENAME      },
 
+  { "menu.button_insert_solution",             UNDEFINED_FILENAME      },
+  { "menu.button_insert_solution.active",      UNDEFINED_FILENAME      },
+  { "menu.button_play_solution",               UNDEFINED_FILENAME      },
+  { "menu.button_play_solution.active",                UNDEFINED_FILENAME      },
+
   { "menu.scrollbar",                          "RocksDC.png"           },
   { "menu.scrollbar.xpos",                     "8"                     },
   { "menu.scrollbar.ypos",                     "10"                    },
@@ -7908,6 +7913,11 @@ struct ConfigInfo image_config[] =
   { "main.button.next_level.x",                        "448"                   },
   { "main.button.next_level.y",                        "96"                    },
 
+  { "main.button.insert_solution.x",           "-1"                    },
+  { "main.button.insert_solution.y",           "-1"                    },
+  { "main.button.play_solution.x",             "-1"                    },
+  { "main.button.play_solution.y",             "-1"                    },
+
   { "main.text.name.x",                                "-1"                    },
   { "main.text.name.y",                                "-1"                    },
   { "main.text.name.width",                    "-1"                    },
index 6e4c5060077b32210f6fc6fb6b83e3239dee6785..b71bb3cef6ad46165484a3fff54cd67ed82556c3 100644 (file)
@@ -2642,6 +2642,9 @@ struct MenuMainButtonInfo
   struct MenuPosInfo first_level;
   struct MenuPosInfo last_level;
   struct MenuPosInfo level_number;
+
+  struct MenuPosInfo insert_solution;
+  struct MenuPosInfo play_solution;
 };
 
 struct MenuMainTextInfo
index 067f630aa2be16bc287964e6039def923020b006..200f725c27edc2ea348f530f3bdc54908366969c 100644 (file)
 #define SCREEN_CTRL_ID_NEXT_LEVEL      1
 #define SCREEN_CTRL_ID_PREV_PLAYER     2
 #define SCREEN_CTRL_ID_NEXT_PLAYER     3
-#define SCREEN_CTRL_ID_SCROLL_UP       4
-#define SCREEN_CTRL_ID_SCROLL_DOWN     5
-#define SCREEN_CTRL_ID_SCROLL_VERTICAL 6
+#define SCREEN_CTRL_ID_INSERT_SOLUTION 4
+#define SCREEN_CTRL_ID_PLAY_SOLUTION   5
+#define SCREEN_CTRL_ID_SCROLL_UP       6
+#define SCREEN_CTRL_ID_SCROLL_DOWN     7
+#define SCREEN_CTRL_ID_SCROLL_VERTICAL 8
 
-#define NUM_SCREEN_GADGETS             7
+#define NUM_SCREEN_GADGETS             9
 
-#define NUM_SCREEN_MENUBUTTONS         4
+#define NUM_SCREEN_MENUBUTTONS         6
 #define NUM_SCREEN_SCROLLBUTTONS       2
 #define NUM_SCREEN_SCROLLBARS          1
 
 #define SCREEN_MASK_MAIN               (1 << 0)
-#define SCREEN_MASK_INPUT              (1 << 1)
+#define SCREEN_MASK_MAIN_HAS_SOLUTION  (1 << 1)
+#define SCREEN_MASK_INPUT              (1 << 2)
 
 /* graphic position and size values for buttons and scrollbars */
 #define SC_MENUBUTTON_XSIZE            TILEX
@@ -246,6 +249,8 @@ static void MapScreenMenuGadgets(int);
 static void MapScreenGadgets(int);
 static void MapScreenTreeGadgets(TreeInfo *);
 
+static void UpdateScreenMenuGadgets(int, boolean);
+
 static struct GadgetInfo *screen_gadget[NUM_SCREEN_GADGETS];
 
 static int info_mode = INFO_MODE_MAIN;
@@ -1658,6 +1663,7 @@ void DrawMainMenu()
   /* map gadgets for main menu screen */
   MapTapeButtons();
   MapScreenMenuGadgets(SCREEN_MASK_MAIN);
+  UpdateScreenMenuGadgets(SCREEN_MASK_MAIN_HAS_SOLUTION, hasSolutionTape());
 
   /* copy actual game door content to door double buffer for OpenDoor() */
   BlitBitmap(drawto, bitmap_db_door_1, DX, DY, DXSIZE, DYSIZE, 0, 0);
@@ -1929,6 +1935,8 @@ void HandleMainMenu_SelectLevel(int step, int direction, int selected_level_nr)
 
     SaveLevelSetup_SeriesInfo();
 
+    UpdateScreenMenuGadgets(SCREEN_MASK_MAIN_HAS_SOLUTION, hasSolutionTape());
+
     /* needed because DrawPreviewLevelInitial() takes some time */
     BackToFront();
     /* SyncDisplay(); */
@@ -7914,6 +7922,16 @@ static void getScreenMenuButtonPos(int *x, int *y, int gadget_id)
       *y = mSY + TILEY * MENU_SCREEN_START_YPOS;
       break;
 
+    case SCREEN_CTRL_ID_INSERT_SOLUTION:
+      *x = mSX + GDI_ACTIVE_POS(menu.main.button.insert_solution.x);
+      *y = mSY + GDI_ACTIVE_POS(menu.main.button.insert_solution.y);
+      break;
+
+    case SCREEN_CTRL_ID_PLAY_SOLUTION:
+      *x = mSX + GDI_ACTIVE_POS(menu.main.button.play_solution.x);
+      *y = mSY + GDI_ACTIVE_POS(menu.main.button.play_solution.y);
+      break;
+
     default:
       Error(ERR_EXIT, "unknown gadget ID %d", gadget_id);
   }
@@ -7956,6 +7974,20 @@ static struct
     SCREEN_MASK_INPUT,
     "next player"
   },
+  {
+    IMG_MENU_BUTTON_INSERT_SOLUTION, IMG_MENU_BUTTON_INSERT_SOLUTION_ACTIVE,
+    getScreenMenuButtonPos,
+    SCREEN_CTRL_ID_INSERT_SOLUTION,
+    SCREEN_MASK_MAIN_HAS_SOLUTION,
+    "insert solution tape"
+  },
+  {
+    IMG_MENU_BUTTON_PLAY_SOLUTION, IMG_MENU_BUTTON_PLAY_SOLUTION_ACTIVE,
+    getScreenMenuButtonPos,
+    SCREEN_CTRL_ID_PLAY_SOLUTION,
+    SCREEN_MASK_MAIN_HAS_SOLUTION,
+    "play solution tape"
+  },
 };
 
 static struct
@@ -8014,12 +8046,23 @@ static void CreateScreenMenubuttons()
     int gd_x1, gd_x2, gd_y1, gd_y2;
     int id = menubutton_info[i].gadget_id;
 
-    event_mask = GD_EVENT_PRESSED | GD_EVENT_REPEATED;
+    if (menubutton_info[i].screen_mask == SCREEN_MASK_MAIN_HAS_SOLUTION)
+      event_mask = GD_EVENT_RELEASED;
+    else
+      event_mask = GD_EVENT_PRESSED | GD_EVENT_REPEATED;
 
     menubutton_info[i].get_gadget_position(&x, &y, id);
 
-    width = SC_MENUBUTTON_XSIZE;
-    height = SC_MENUBUTTON_YSIZE;
+    if (menubutton_info[i].screen_mask == SCREEN_MASK_MAIN_HAS_SOLUTION)
+    {
+      width  = graphic_info[menubutton_info[i].gfx_pressed].width;
+      height = graphic_info[menubutton_info[i].gfx_pressed].height;
+    }
+    else
+    {
+      width = SC_MENUBUTTON_XSIZE;
+      height = SC_MENUBUTTON_YSIZE;
+    }
 
     gfx_unpressed = menubutton_info[i].gfx_unpressed;
     gfx_pressed   = menubutton_info[i].gfx_pressed;
@@ -8228,6 +8271,33 @@ void MapScreenMenuGadgets(int screen_mask)
       MapGadget(screen_gadget[menubutton_info[i].gadget_id]);
 }
 
+void UnmapScreenMenuGadgets(int screen_mask)
+{
+  int i;
+
+  for (i = 0; i < NUM_SCREEN_MENUBUTTONS; i++)
+  {
+    if (screen_mask & menubutton_info[i].screen_mask)
+    {
+      UnmapGadget(screen_gadget[menubutton_info[i].gadget_id]);
+
+      if (screen_mask & SCREEN_MASK_MAIN_HAS_SOLUTION)
+       DrawBackground(screen_gadget[menubutton_info[i].gadget_id]->x,
+                      screen_gadget[menubutton_info[i].gadget_id]->y,
+                      screen_gadget[menubutton_info[i].gadget_id]->width,
+                      screen_gadget[menubutton_info[i].gadget_id]->height);
+    }
+  }
+}
+
+void UpdateScreenMenuGadgets(int screen_mask, boolean map_gadgets)
+{
+  if (map_gadgets)
+    MapScreenMenuGadgets(screen_mask);
+  else
+    UnmapScreenMenuGadgets(screen_mask);
+}
+
 void MapScreenGadgets(int num_entries)
 {
   int i;
@@ -8273,6 +8343,14 @@ static void HandleScreenGadgets(struct GadgetInfo *gi)
       HandleSetupScreen_Input_Player(step, +1);
       break;
 
+    case SCREEN_CTRL_ID_INSERT_SOLUTION:
+      InsertSolutionTape();
+      break;
+
+    case SCREEN_CTRL_ID_PLAY_SOLUTION:
+      PlaySolutionTape();
+      break;
+
     case SCREEN_CTRL_ID_SCROLL_UP:
       if (game_status == GAME_MODE_LEVELS)
        HandleChooseLevelSet(0,0, 0, -1 * SCROLL_LINE, MB_MENU_MARK);
index f75bc897e6f4579f1908050253b3ce1c0c2c3f01..1e072cd4ffa567c9543e5999d10db07c52ce3eaf 100644 (file)
@@ -1079,12 +1079,18 @@ void TapeQuickLoad()
   }
 }
 
-boolean InsertSolutionTape()
+boolean hasSolutionTape()
 {
+  boolean tape_file_exists = fileExists(getSolutionTapeFilename(level_nr));
   boolean level_has_tape = (level.game_engine_type == GAME_ENGINE_TYPE_SP &&
                            level.native_sp_level->demo.is_available);
 
-  if (!fileExists(getSolutionTapeFilename(level_nr)) && !level_has_tape)
+  return (tape_file_exists || level_has_tape);
+}
+
+boolean InsertSolutionTape()
+{
+  if (!hasSolutionTape())
   {
     Request("No solution tape for this level!", REQ_CONFIRM);
 
index 0924395c0e11a089784c3664044681a230422ff1..e7f4da6e1cc88ee1d1a489235d53d542b1614165 100644 (file)
@@ -233,6 +233,8 @@ unsigned int GetTapeLengthFrames(void);
 unsigned int GetTapeLengthSeconds(void);
 void TapeQuickSave(void);
 void TapeQuickLoad(void);
+
+boolean hasSolutionTape();
 boolean InsertSolutionTape(void);
 boolean PlaySolutionTape(void);