rnd-20030703-1-src
authorHolger Schemel <info@artsoft.org>
Thu, 3 Jul 2003 08:32:53 +0000 (10:32 +0200)
committerHolger Schemel <info@artsoft.org>
Sat, 30 Aug 2014 08:42:32 +0000 (10:42 +0200)
12 files changed:
src/conftime.h
src/editor.c
src/files.c
src/game.c
src/init.c
src/libgame/image.c
src/libgame/joystick.c
src/libgame/misc.h
src/libgame/system.c
src/libgame/system.h
src/main.c
src/main.h

index 6bc742d5806af6a1d4ac2a90bd4e35eab76241b1..aeb860a4561772379f08156a829bc514ecb9410a 100644 (file)
@@ -1 +1 @@
-#define COMPILE_DATE_STRING "[2003-07-02 10:20]"
+#define COMPILE_DATE_STRING "[2003-07-02 23:31]"
index f13b9bf1943267335541bc8369fef62c7086ad1b..dd757b0560755526e7be89a91d8c4904b0e49673 100644 (file)
@@ -20,6 +20,7 @@
 #include "tools.h"
 #include "files.h"
 #include "game.h"
+#include "init.h"
 #include "tape.h"
 
 
@@ -1286,6 +1287,10 @@ static struct
   }
 };
 
+static boolean can_explode_by_fire = FALSE;
+static boolean can_explode_smashed = FALSE;
+static boolean can_explode_impact = FALSE;
+
 static struct
 {
   int x, y;
@@ -1383,19 +1388,19 @@ static struct
   {
     ED_SETTINGS_XPOS(1),               ED_SETTINGS_YPOS(13),
     GADGET_ID_CUSTOM_EXPLODE_FIRE,
-    &custom_element_properties[EP_CAN_EXPLODE_BY_FIRE],
+    &can_explode_by_fire,
     "by fire",                         "element can explode by fire/explosion"
   },
   {
     ED_SETTINGS_XPOS(7),               ED_SETTINGS_YPOS(13),
     GADGET_ID_CUSTOM_EXPLODE_SMASH,
-    &custom_element_properties[EP_CAN_EXPLODE_SMASHED],
+    &can_explode_smashed,
     "smashed",                         "element can explode when smashed"
   },
   {
     ED_SETTINGS_XPOS(13),              ED_SETTINGS_YPOS(13),
     GADGET_ID_CUSTOM_EXPLODE_IMPACT,
-    &custom_element_properties[EP_CAN_EXPLODE_IMPACT],
+    &can_explode_impact,
     "impact",                          "element can explode on impact"
   },
 
@@ -1464,7 +1469,7 @@ static struct
   {
     ED_SETTINGS_XPOS(0),               ED_SETTINGS_YPOS(13),
     GADGET_ID_CUSTOM_USE_TEMPLATE,
-    &custom_element.use_template,
+    &level.use_custom_template,
     "use template",                    "use template for custom properties"
   },
 };
@@ -3613,6 +3618,9 @@ static void CopyCustomElementPropertiesToEditor(int element)
 {
   int i;
 
+  /* needed here to initialize combined element properties */
+  InitElementPropertiesEngine(level.game_version);
+
   custom_element = element_info[properties_element];
 
   for (i=0; i < NUM_ELEMENT_PROPERTIES; i++)
@@ -3621,76 +3629,88 @@ static void CopyCustomElementPropertiesToEditor(int element)
   for (i=0; i < NUM_CHANGE_EVENTS; i++)
     custom_element_change_events[i] = HAS_CHANGE_EVENT(element, i);
 
+  /* ---------- element settings: configure (custom elements) ------------- */
+
+  /* set accessible layer selectbox help value */
+  value_access_type =
+    (IS_WALKABLE(element) ? EP_WALKABLE :
+     IS_PASSABLE(element) ? EP_PASSABLE :
+     value_access_type);
+  value_access_layer =
+    (IS_ACCESSIBLE_OVER(element) ? EP_ACCESSIBLE_OVER :
+     IS_ACCESSIBLE_INSIDE(element) ? EP_ACCESSIBLE_INSIDE :
+     IS_ACCESSIBLE_UNDER(element) ? EP_ACCESSIBLE_UNDER :
+     value_access_layer);
+  custom_element_properties[EP_ACCESSIBLE] =
+    (IS_ACCESSIBLE_OVER(element) ||
+     IS_ACCESSIBLE_INSIDE(element) ||
+     IS_ACCESSIBLE_UNDER(element));
+
   /* set walk-to-object action selectbox help value */
   value_walk_to_action =
     (IS_DIGGABLE(element) ? EP_DIGGABLE :
      IS_COLLECTIBLE(element) ? EP_COLLECTIBLE :
      IS_PUSHABLE(element) ? EP_PUSHABLE :
-     EP_DIGGABLE);
+     value_walk_to_action);
   custom_element_properties[EP_WALK_TO_OBJECT] =
     (IS_DIGGABLE(element) ||
      IS_COLLECTIBLE(element) ||
      IS_PUSHABLE(element));
 
-  /* set consistency selectbox help value */
-  value_consistency =
-    (CAN_EXPLODE(element) ? EP_CAN_EXPLODE :
-     IS_INDESTRUCTIBLE(element) ? EP_INDESTRUCTIBLE :
-     EP_CAN_EXPLODE);
-  custom_element_properties[EP_EXPLODE_RESULT] =
-    (CAN_EXPLODE(element) ||
-     IS_INDESTRUCTIBLE(element));
+  /* set smash targets selectbox help value */
+  value_smash_targets =
+    (CAN_SMASH_EVERYTHING(element) ? EP_CAN_SMASH_EVERYTHING :
+     CAN_SMASH_ENEMIES(element) ? EP_CAN_SMASH_ENEMIES :
+     CAN_SMASH_PLAYER(element) ? EP_CAN_SMASH_PLAYER :
+     value_smash_targets);
+  custom_element_properties[EP_CAN_SMASH] =
+    (CAN_SMASH_EVERYTHING(element) ||
+     CAN_SMASH_ENEMIES(element) ||
+     CAN_SMASH_PLAYER(element));
 
   /* set deadliness selectbox help value */
   value_deadliness =
     (DONT_TOUCH(element) ? EP_DONT_TOUCH :
      DONT_COLLIDE_WITH(element) ? EP_DONT_COLLIDE_WITH :
      DONT_RUN_INTO(element) ? EP_DONT_RUN_INTO :
-     EP_DONT_RUN_INTO);
+     value_deadliness);
   custom_element_properties[EP_DEADLY] =
     (DONT_TOUCH(element) ||
      DONT_COLLIDE_WITH(element) ||
      DONT_RUN_INTO(element));
 
-  /* set smash targets selectbox help value */
-  value_smash_targets =
-    (CAN_SMASH_EVERYTHING(element) ? EP_CAN_SMASH_EVERYTHING :
-     CAN_SMASH_ENEMIES(element) ? EP_CAN_SMASH_ENEMIES :
-     CAN_SMASH_PLAYER(element) ? EP_CAN_SMASH_PLAYER :
-     EP_CAN_SMASH_PLAYER);
-  custom_element_properties[EP_CAN_SMASH] =
-    (CAN_SMASH_EVERYTHING(element) ||
-     CAN_SMASH_ENEMIES(element) ||
-     CAN_SMASH_PLAYER(element));
+  /* set consistency selectbox help value */
+  value_consistency =
+    (IS_INDESTRUCTIBLE(element) ? EP_INDESTRUCTIBLE :
+     CAN_EXPLODE(element) ? EP_CAN_EXPLODE :
+     value_consistency);
+  custom_element_properties[EP_EXPLODE_RESULT] =
+    (IS_INDESTRUCTIBLE(element) ||
+     CAN_EXPLODE(element));
 
-  /* set accessible layer selectbox help value */
-  value_access_type =
-    (IS_WALKABLE(element) ? EP_WALKABLE :
-     IS_PASSABLE(element) ? EP_PASSABLE :
-     EP_WALKABLE);
-  value_access_layer =
-    (IS_ACCESSIBLE_OVER(element) ? EP_ACCESSIBLE_OVER :
-     IS_ACCESSIBLE_INSIDE(element) ? EP_ACCESSIBLE_INSIDE :
-     IS_ACCESSIBLE_UNDER(element) ? EP_ACCESSIBLE_UNDER :
-     EP_ACCESSIBLE_OVER);
-  custom_element_properties[EP_ACCESSIBLE] =
-    (IS_ACCESSIBLE_OVER(element) ||
-     IS_ACCESSIBLE_INSIDE(element) ||
-     IS_ACCESSIBLE_UNDER(element));
+  /* special case: sub-settings dependent from main setting */
+  if (CAN_EXPLODE(element))
+  {
+    can_explode_by_fire = CAN_EXPLODE_BY_FIRE(element);
+    can_explode_smashed = CAN_EXPLODE_SMASHED(element);
+    can_explode_impact  = CAN_EXPLODE_IMPACT(element);
+  };
+
+  /* ---------- element settings: advanced (custom elements) --------------- */
 
   /* set change by player selectbox help value */
   value_change_player_action =
     (HAS_CHANGE_EVENT(element, CE_PUSHED_BY_PLAYER) ? CE_PUSHED_BY_PLAYER :
      HAS_CHANGE_EVENT(element, CE_PRESSED_BY_PLAYER) ? CE_PRESSED_BY_PLAYER :
      HAS_CHANGE_EVENT(element, CE_TOUCHED_BY_PLAYER) ? CE_TOUCHED_BY_PLAYER :
-     CE_TOUCHED_BY_PLAYER);
+     value_change_player_action);
 
-  /* set change by impact/smash selectbox help value */
+  /* set change by collision selectbox help value */
   value_change_collide_action =
     (HAS_CHANGE_EVENT(element, CE_SMASHED) ? CE_SMASHED :
      HAS_CHANGE_EVENT(element, CE_IMPACT) ? CE_IMPACT :
      HAS_CHANGE_EVENT(element, CE_COLLISION) ? CE_COLLISION :
-     CE_COLLISION);
+     value_change_collide_action);
 
   /* set change by other element action selectbox help value */
   value_change_other_action =
@@ -3701,7 +3721,7 @@ static void CopyCustomElementPropertiesToEditor(int element)
      HAS_CHANGE_EVENT(element, CE_OTHER_IS_EXPLODING) ? CE_OTHER_IS_EXPLODING :
      HAS_CHANGE_EVENT(element, CE_OTHER_IS_CHANGING) ? CE_OTHER_IS_CHANGING :
      HAS_CHANGE_EVENT(element, CE_OTHER_IS_TOUCHING) ? CE_OTHER_IS_TOUCHING :
-     CE_OTHER_IS_TOUCHING);
+     value_change_other_action);
 }
 
 static void CopyCustomElementPropertiesToGame(int element)
@@ -3710,6 +3730,20 @@ static void CopyCustomElementPropertiesToGame(int element)
 
   element_info[properties_element] = custom_element;
 
+  /* ---------- element settings: configure (custom elements) ------------- */
+
+  /* set accessible property from checkbox and selectbox */
+  custom_element_properties[EP_WALKABLE_OVER] = FALSE;
+  custom_element_properties[EP_WALKABLE_INSIDE] = FALSE;
+  custom_element_properties[EP_WALKABLE_UNDER] = FALSE;
+  custom_element_properties[EP_PASSABLE_OVER] = FALSE;
+  custom_element_properties[EP_PASSABLE_INSIDE] = FALSE;
+  custom_element_properties[EP_PASSABLE_UNDER] = FALSE;
+  custom_element_properties[((value_access_type == EP_WALKABLE ?
+                             EP_WALKABLE_OVER : EP_PASSABLE_OVER) +
+                            (value_access_layer - EP_ACCESSIBLE_OVER))] =
+    custom_element_properties[EP_ACCESSIBLE];
+
   /* set walk-to-object property from checkbox and selectbox */
   custom_element_properties[EP_DIGGABLE] = FALSE;
   custom_element_properties[EP_COLLECTIBLE] = FALSE;
@@ -3717,11 +3751,12 @@ static void CopyCustomElementPropertiesToGame(int element)
   custom_element_properties[value_walk_to_action] =
     custom_element_properties[EP_WALK_TO_OBJECT];
 
-  /* set consistency property from checkbox and selectbox */
-  custom_element_properties[EP_CAN_EXPLODE] = FALSE;
-  custom_element_properties[EP_INDESTRUCTIBLE] = FALSE;
-  custom_element_properties[value_consistency] =
-    custom_element_properties[EP_EXPLODE_RESULT];
+  /* set smash property from checkbox and selectbox */
+  custom_element_properties[EP_CAN_SMASH_PLAYER] = FALSE;
+  custom_element_properties[EP_CAN_SMASH_ENEMIES] = FALSE;
+  custom_element_properties[EP_CAN_SMASH_EVERYTHING] = FALSE;
+  custom_element_properties[value_smash_targets] =
+    custom_element_properties[EP_CAN_SMASH];
 
   /* set deadliness property from checkbox and selectbox */
   custom_element_properties[EP_DONT_RUN_INTO] = FALSE;
@@ -3730,24 +3765,24 @@ static void CopyCustomElementPropertiesToGame(int element)
   custom_element_properties[value_deadliness] =
     custom_element_properties[EP_DEADLY];
 
-  /* set smash property from checkbox and selectbox */
-  custom_element_properties[EP_CAN_SMASH_PLAYER] = FALSE;
-  custom_element_properties[EP_CAN_SMASH_ENEMIES] = FALSE;
-  custom_element_properties[EP_CAN_SMASH_EVERYTHING] = FALSE;
-  custom_element_properties[value_smash_targets] =
-    custom_element_properties[EP_CAN_SMASH];
+  /* set consistency property from checkbox and selectbox */
+  custom_element_properties[EP_INDESTRUCTIBLE] = FALSE;
+  custom_element_properties[EP_CAN_EXPLODE] = FALSE;
+  custom_element_properties[EP_CAN_EXPLODE_BY_FIRE] = FALSE;
+  custom_element_properties[EP_CAN_EXPLODE_SMASHED] = FALSE;
+  custom_element_properties[EP_CAN_EXPLODE_IMPACT] = FALSE;
+  custom_element_properties[value_consistency] =
+    custom_element_properties[EP_EXPLODE_RESULT];
 
-  /* set accessible property from checkbox and selectbox */
-  custom_element_properties[EP_WALKABLE_OVER] = FALSE;
-  custom_element_properties[EP_WALKABLE_INSIDE] = FALSE;
-  custom_element_properties[EP_WALKABLE_UNDER] = FALSE;
-  custom_element_properties[EP_PASSABLE_OVER] = FALSE;
-  custom_element_properties[EP_PASSABLE_INSIDE] = FALSE;
-  custom_element_properties[EP_PASSABLE_UNDER] = FALSE;
-  custom_element_properties[((value_access_type == EP_WALKABLE ?
-                             EP_WALKABLE_OVER : EP_PASSABLE_OVER) +
-                            (value_access_layer - EP_ACCESSIBLE_OVER))] =
-    custom_element_properties[EP_ACCESSIBLE];
+  /* special case: sub-settings dependent from main setting */
+  if (custom_element_properties[EP_CAN_EXPLODE])
+  {
+    custom_element_properties[EP_CAN_EXPLODE_BY_FIRE] = can_explode_by_fire;
+    custom_element_properties[EP_CAN_EXPLODE_SMASHED] = can_explode_smashed;
+    custom_element_properties[EP_CAN_EXPLODE_IMPACT]  = can_explode_impact;
+  }
+
+  /* ---------- element settings: advanced (custom elements) --------------- */
 
   /* set player change event from checkbox and selectbox */
   custom_element_change_events[CE_TOUCHED_BY_PLAYER] = FALSE;
@@ -3756,7 +3791,7 @@ static void CopyCustomElementPropertiesToGame(int element)
   custom_element_change_events[value_change_player_action] =
     custom_element_change_events[CE_BY_PLAYER];
 
-  /* set player change event from checkbox and selectbox */
+  /* set collision change event from checkbox and selectbox */
   custom_element_change_events[CE_COLLISION] = FALSE;
   custom_element_change_events[CE_IMPACT] = FALSE;
   custom_element_change_events[CE_SMASHED] = FALSE;
@@ -3832,6 +3867,7 @@ void DrawLevelEd()
   redraw_mask |= REDRAW_ALL;
 
   ReinitializeElementListButtons();    /* only needed after setup changes */
+  ModifyEditorElementList();           /* may be needed for custom elements */
 
   UnmapTapeButtons();
   MapControlButtons();
@@ -4257,7 +4293,7 @@ static void DrawCustomChangeTriggerArea()
 
   DrawElementBorder(area_sx, area_sy, MINI_TILEX, MINI_TILEY, TRUE);
   DrawMiniGraphicExt(drawto, gi->x, gi->y,
-                    el2edimg(custom_element.change.trigger));
+                    el2edimg(custom_element.change.trigger_element));
 
   MapDrawingArea(GADGET_ID_CUSTOM_CHANGE_TRIGGER);
 }
@@ -4796,6 +4832,16 @@ static void DrawPropertiesConfig()
   }
 }
 
+static void DrawPropertiesAdvancedDrawingAreas()
+{
+  DrawCustomGraphicElementArea();
+  DrawCustomChangeTargetArea();
+  DrawCustomChangeTriggerArea();
+  DrawCustomChangeContentArea();
+
+  redraw_mask |= REDRAW_FIELD;
+}
+
 static void DrawPropertiesAdvanced()
 {
   int i;
@@ -4822,10 +4868,7 @@ static void DrawPropertiesAdvanced()
   MapTextbuttonGadget(ED_TEXTBUTTON_ID_SAVE_AS_TEMPLATE);
 
   /* draw drawing area gadgets */
-  DrawCustomGraphicElementArea();
-  DrawCustomChangeTargetArea();
-  DrawCustomChangeContentArea();
-  DrawCustomChangeTriggerArea();
+  DrawPropertiesAdvancedDrawingAreas();
 }
 
 static void DrawElementName(int x, int y, int element)
@@ -5683,7 +5726,7 @@ static void HandleDrawingAreas(struct GadgetInfo *gi)
        }
        else if (id == GADGET_ID_CUSTOM_CHANGE_TRIGGER)
        {
-         custom_element.change.trigger = new_element;
+         custom_element.change.trigger_element = new_element;
          element_info[properties_element] = custom_element;
        }
        else if (id == GADGET_ID_RANDOM_BACKGROUND)
@@ -5801,7 +5844,7 @@ static void HandleDrawingAreas(struct GadgetInfo *gi)
       else if (id == GADGET_ID_CUSTOM_CHANGE_CONTENT)
        PickDrawingElement(button, custom_element.change.content[sx][sy]);
       else if (id == GADGET_ID_CUSTOM_CHANGE_TRIGGER)
-       PickDrawingElement(button, custom_element.change.trigger);
+       PickDrawingElement(button, custom_element.change.trigger_element);
       else if (id == GADGET_ID_RANDOM_BACKGROUND)
        PickDrawingElement(button, random_placement_background_element);
       else if (id >= GADGET_ID_ELEMENT_CONTENT_0 &&
@@ -5933,6 +5976,8 @@ static void HandleCheckbuttons(struct GadgetInfo *gi)
   {
     ModifyEditorElementList();
     RedrawDrawingElements();
+
+    DrawPropertiesAdvancedDrawingAreas();
   }
 }
 
@@ -6547,7 +6592,7 @@ static void HandleDrawingAreaInfo(struct GadgetInfo *gi)
                getElementInfoText(custom_element.change.content[sx][sy]));
     else if (id == GADGET_ID_CUSTOM_CHANGE_TRIGGER)
       DrawTextF(INFOTEXT_XPOS - SX, INFOTEXT_YPOS - SY, FONT_TEXT_2, "%s",
-               getElementInfoText(custom_element.change.trigger));
+               getElementInfoText(custom_element.change.trigger_element));
     else if (id == GADGET_ID_RANDOM_BACKGROUND)
       DrawTextF(INFOTEXT_XPOS - SX, INFOTEXT_YPOS - SY, FONT_TEXT_2, "%s",
                getElementInfoText(random_placement_background_element));
index a86507f36d90a642d2ec542963ac98bcba55f91c..ebdd7afd2ed5970fa84aea0addce539a7511ed58 100644 (file)
 #define CHUNK_SIZE_NONE                -1      /* do not write chunk size    */
 #define FILE_VERS_CHUNK_SIZE   8       /* size of file version chunk */
 #define LEVEL_HEADER_SIZE      80      /* size of level file header  */
-#define LEVEL_HEADER_UNUSED    14      /* unused level header bytes  */
+#define LEVEL_HEADER_UNUSED    13      /* unused level header bytes  */
 #define LEVEL_CHUNK_CNT2_SIZE  160     /* size of level CNT2 chunk   */
 #define LEVEL_CHUNK_CNT2_UNUSED        11      /* unused CNT2 chunk bytes    */
+#define LEVEL_CPART_CUS3_SIZE  102     /* size of CUS3 chunk part    */
+#define LEVEL_CPART_CUS3_UNUSED        16      /* unused CUS3 bytes / part   */
 #define TAPE_HEADER_SIZE       20      /* size of tape file header   */
 #define TAPE_HEADER_UNUSED     3       /* unused tape header bytes   */
 
+#define LEVEL_CHUNK_CUS3_SIZE(x) (2 + x * LEVEL_CPART_CUS3_SIZE)
+
 /* file identifier strings */
 #define LEVEL_COOKIE_TMPL      "ROCKSNDIAMONDS_LEVEL_FILE_VERSION_x.x"
 #define TAPE_COOKIE_TMPL       "ROCKSNDIAMONDS_TAPE_FILE_VERSION_x.x"
@@ -73,6 +77,8 @@ static void setLevelInfoToDefaults()
   level.gravity = FALSE;
   level.em_slippery_gems = FALSE;
 
+  level.use_custom_template = FALSE;
+
   for(i=0; i<MAX_LEVEL_NAME_LEN; i++)
     level.name[i] = '\0';
   for(i=0; i<MAX_LEVEL_AUTHOR_LEN; i++)
@@ -99,8 +105,6 @@ static void setLevelInfoToDefaults()
   {
     int element = EL_CUSTOM_START + i;
 
-    element_info[element].use_template = FALSE;
-
     element_info[element].use_gfx_element = FALSE;
     element_info[element].gfx_element = EL_EMPTY_SPACE;
 
@@ -121,23 +125,21 @@ static void setLevelInfoToDefaults()
        element_info[element].content[x][y] = EL_EMPTY_SPACE;
 
     element_info[element].change.events = CE_BITMASK_DEFAULT;
+    element_info[element].change.target_element = EL_EMPTY_SPACE;
 
     element_info[element].change.delay_fixed = 0;
     element_info[element].change.delay_random = 0;
     element_info[element].change.delay_frames = -1;    /* use default */
 
-    element_info[element].change.trigger = EL_EMPTY_SPACE;
-
-    element_info[element].change.target_element = EL_EMPTY_SPACE;
+    element_info[element].change.trigger_element = EL_EMPTY_SPACE;
 
+    element_info[element].change.explode = FALSE;
     element_info[element].change.use_content = FALSE;
     element_info[element].change.only_complete = FALSE;
     element_info[element].change.use_random_change = FALSE;
     element_info[element].change.random = 0;
     element_info[element].change.power = CP_NON_DESTRUCTIVE;
 
-    element_info[element].change.explode = FALSE;
-
     for(x=0; x<3; x++)
       for(y=0; y<3; y++)
        element_info[element].change.content[x][y] = EL_EMPTY_SPACE;
@@ -240,6 +242,8 @@ static int LoadLevel_HEAD(FILE *file, int chunk_size, struct LevelInfo *level)
   level->encoding_16bit_field  = (fgetc(file) == 1 ? TRUE : FALSE);
   level->em_slippery_gems      = (fgetc(file) == 1 ? TRUE : FALSE);
 
+  level->use_custom_template   = (fgetc(file) == 1 ? TRUE : FALSE);
+
   ReadUnusedBytesFromFile(file, LEVEL_HEADER_UNUSED);
 
   return chunk_size;
@@ -418,6 +422,87 @@ static int LoadLevel_CUS2(FILE *file, int chunk_size, struct LevelInfo *level)
   return chunk_size;
 }
 
+static int LoadLevel_CUS3(FILE *file, int chunk_size, struct LevelInfo *level)
+{
+  int num_changed_custom_elements = getFile16BitBE(file);
+  int chunk_size_expected = LEVEL_CHUNK_CUS3_SIZE(num_changed_custom_elements);
+  int i, x, y;
+
+  if (chunk_size_expected != chunk_size)
+  {
+    ReadUnusedBytesFromFile(file, chunk_size - 2);
+    return chunk_size_expected;
+  }
+
+  for (i=0; i < num_changed_custom_elements; i++)
+  {
+    int element = getFile16BitBE(file);
+
+    if (!IS_CUSTOM_ELEMENT(element))
+    {
+      Error(ERR_WARN, "invalid custom element number %d", element);
+
+      element = EL_DEFAULT;    /* dummy element used for artwork config */
+    }
+
+    Properties[element][EP_BITFIELD_BASE] = getFile32BitBE(file);
+
+    /* some free bytes for future properties and padding */
+    ReadUnusedBytesFromFile(file, 7);
+
+    element_info[element].use_gfx_element = getFile8Bit(file);
+    element_info[element].gfx_element =
+      checkLevelElement(getFile16BitBE(file));
+
+    element_info[element].score = getFile8Bit(file);
+    element_info[element].gem_count = getFile8Bit(file);
+
+    element_info[element].push_delay_fixed = getFile16BitBE(file);
+    element_info[element].push_delay_random = getFile16BitBE(file);
+    element_info[element].move_delay_fixed = getFile16BitBE(file);
+    element_info[element].move_delay_random = getFile16BitBE(file);
+
+    element_info[element].move_pattern = getFile16BitBE(file);
+    element_info[element].move_direction_initial = getFile8Bit(file);
+    element_info[element].move_stepsize = getFile8Bit(file);
+
+    for(y=0; y<3; y++)
+      for(x=0; x<3; x++)
+       element_info[element].content[x][y] =
+         checkLevelElement(getFile16BitBE(file));
+
+    element_info[element].change.events = getFile32BitBE(file);
+
+    element_info[element].change.target_element =
+      checkLevelElement(getFile16BitBE(file));
+
+    element_info[element].change.delay_fixed = getFile16BitBE(file);
+    element_info[element].change.delay_random = getFile16BitBE(file);
+    element_info[element].change.delay_frames = getFile16BitBE(file);
+
+    element_info[element].change.trigger_element =
+      checkLevelElement(getFile16BitBE(file));
+
+    element_info[element].change.explode = getFile8Bit(file);
+    element_info[element].change.use_content = getFile8Bit(file);
+    element_info[element].change.only_complete = getFile8Bit(file);
+    element_info[element].change.use_random_change = getFile8Bit(file);
+
+    element_info[element].change.random = getFile8Bit(file);
+    element_info[element].change.power = getFile8Bit(file);
+
+    for(y=0; y<3; y++)
+      for(x=0; x<3; x++)
+       element_info[element].change.content[x][y] =
+         checkLevelElement(getFile16BitBE(file));
+
+    /* some free bytes for future properties and padding */
+    ReadUnusedBytesFromFile(file, LEVEL_CPART_CUS3_UNUSED);
+  }
+
+  return chunk_size;
+}
+
 void LoadLevelFromFilename(char *filename)
 {
   char cookie[MAX_LINE_LEN];
@@ -498,6 +583,7 @@ void LoadLevelFromFilename(char *filename)
       { "CNT2", LEVEL_CHUNK_CNT2_SIZE, LoadLevel_CNT2 },
       { "CUS1", -1,                    LoadLevel_CUS1 },
       { "CUS2", -1,                    LoadLevel_CUS2 },
+      { "CUS3", -1,                    LoadLevel_CUS3 },
       {  NULL,  0,                     NULL }
     };
 
@@ -668,6 +754,8 @@ static void SaveLevel_HEAD(FILE *file, struct LevelInfo *level)
   fputc((level->encoding_16bit_field ? 1 : 0), file);
   fputc((level->em_slippery_gems ? 1 : 0), file);
 
+  fputc((level->use_custom_template ? 1 : 0), file);
+
   WriteUnusedBytesToFile(file, LEVEL_HEADER_UNUSED);
 }
 
@@ -762,6 +850,7 @@ static void SaveLevel_CNT2(FILE *file, struct LevelInfo *level, int element)
        putFile16BitBE(file, content_array[i][x][y]);
 }
 
+#if 0
 static void SaveLevel_CUS1(FILE *file, struct LevelInfo *level,
                           int num_changed_custom_elements)
 {
@@ -788,7 +877,9 @@ static void SaveLevel_CUS1(FILE *file, struct LevelInfo *level,
   if (check != num_changed_custom_elements)    /* should not happen */
     Error(ERR_WARN, "inconsistent number of custom element properties");
 }
+#endif
 
+#if 0
 static void SaveLevel_CUS2(FILE *file, struct LevelInfo *level,
                           int num_changed_custom_elements)
 {
@@ -815,13 +906,88 @@ static void SaveLevel_CUS2(FILE *file, struct LevelInfo *level,
   if (check != num_changed_custom_elements)    /* should not happen */
     Error(ERR_WARN, "inconsistent number of custom target elements");
 }
+#endif
+
+static void SaveLevel_CUS3(FILE *file, struct LevelInfo *level,
+                          int num_changed_custom_elements)
+{
+  int i, x, y, check = 0;
+
+  putFile16BitBE(file, num_changed_custom_elements);
+
+  for (i=0; i < NUM_CUSTOM_ELEMENTS; i++)
+  {
+    int element = EL_CUSTOM_START + i;
+
+    if (Properties[element][EP_BITFIELD_BASE] != EP_BITMASK_DEFAULT)
+    {
+      if (check < num_changed_custom_elements)
+      {
+       putFile16BitBE(file, element);
+       putFile32BitBE(file, Properties[element][EP_BITFIELD_BASE]);
+
+       /* some free bytes for future properties and padding */
+       WriteUnusedBytesToFile(file, 7);
+
+       putFile8Bit(file, element_info[element].use_gfx_element);
+       putFile16BitBE(file, element_info[element].gfx_element);
+
+       putFile8Bit(file, element_info[element].score);
+       putFile8Bit(file, element_info[element].gem_count);
+
+       putFile16BitBE(file, element_info[element].push_delay_fixed);
+       putFile16BitBE(file, element_info[element].push_delay_random);
+       putFile16BitBE(file, element_info[element].move_delay_fixed);
+       putFile16BitBE(file, element_info[element].move_delay_random);
+
+       putFile16BitBE(file, element_info[element].move_pattern);
+       putFile8Bit(file, element_info[element].move_direction_initial);
+       putFile8Bit(file, element_info[element].move_stepsize);
+
+       for(y=0; y<3; y++)
+         for(x=0; x<3; x++)
+           putFile16BitBE(file, element_info[element].content[x][y]);
+
+       putFile32BitBE(file, element_info[element].change.events);
+
+       putFile16BitBE(file, element_info[element].change.target_element);
+
+       putFile16BitBE(file, element_info[element].change.delay_fixed);
+       putFile16BitBE(file, element_info[element].change.delay_random);
+       putFile16BitBE(file, element_info[element].change.delay_frames);
+
+       putFile16BitBE(file, element_info[element].change.trigger_element);
+
+       putFile8Bit(file, element_info[element].change.explode);
+       putFile8Bit(file, element_info[element].change.use_content);
+       putFile8Bit(file, element_info[element].change.only_complete);
+       putFile8Bit(file, element_info[element].change.use_random_change);
+
+       putFile8Bit(file, element_info[element].change.random);
+       putFile8Bit(file, element_info[element].change.power);
+
+       for(y=0; y<3; y++)
+         for(x=0; x<3; x++)
+           putFile16BitBE(file, element_info[element].change.content[x][y]);
+
+       /* some free bytes for future properties and padding */
+       WriteUnusedBytesToFile(file, LEVEL_CPART_CUS3_UNUSED);
+      }
+
+      check++;
+    }
+  }
+
+  if (check != num_changed_custom_elements)    /* should not happen */
+    Error(ERR_WARN, "inconsistent number of custom element properties");
+}
 
 void SaveLevel(int level_nr)
 {
   char *filename = getLevelFilename(level_nr);
   int body_chunk_size;
-  int num_changed_custom_elements1 = 0;
-  int num_changed_custom_elements2 = 0;
+  int num_changed_custom_elements = 0;
+  int level_chunk_CUS3_size;
   int i, x, y;
   FILE *file;
 
@@ -858,15 +1024,11 @@ void SaveLevel(int level_nr)
   body_chunk_size =
     level.fieldx * level.fieldy * (level.encoding_16bit_field ? 2 : 1);
 
-  /* check for non-standard custom elements and calculate "CUS1" chunk size */
+  /* check for non-standard custom elements and calculate "CUS3" chunk size */
   for (i=0; i < NUM_CUSTOM_ELEMENTS; i++)
     if (Properties[EL_CUSTOM_START +i][EP_BITFIELD_BASE] != EP_BITMASK_DEFAULT)
-      num_changed_custom_elements1++;
-
-  /* check for non-standard custom elements and calculate "CUS2" chunk size */
-  for (i=0; i < NUM_CUSTOM_ELEMENTS; i++)
-    if (element_info[EL_CUSTOM_START + i].change.target_element != EL_EMPTY)
-      num_changed_custom_elements2++;
+      num_changed_custom_elements++;
+  level_chunk_CUS3_size = LEVEL_CHUNK_CUS3_SIZE(num_changed_custom_elements);
 
   putFileChunkBE(file, "RND1", CHUNK_SIZE_UNDEFINED);
   putFileChunkBE(file, "CAVE", CHUNK_SIZE_NONE);
@@ -896,16 +1058,10 @@ void SaveLevel(int level_nr)
     SaveLevel_CNT2(file, &level, EL_BD_AMOEBA);
   }
 
-  if (num_changed_custom_elements1 > 0)
-  {
-    putFileChunkBE(file, "CUS1", 2 + num_changed_custom_elements1 * 6);
-    SaveLevel_CUS1(file, &level, num_changed_custom_elements1);
-  }
-
-  if (num_changed_custom_elements2 > 0)
+  if (num_changed_custom_elements > 0)
   {
-    putFileChunkBE(file, "CUS2", 2 + num_changed_custom_elements2 * 4);
-    SaveLevel_CUS2(file, &level, num_changed_custom_elements2);
+    putFileChunkBE(file, "CUS3", level_chunk_CUS3_size);
+    SaveLevel_CUS3(file, &level, num_changed_custom_elements);
   }
 
   fclose(file);
index 1a143d4f706fec53a9f0ecc2839baef22fe846f6..1b6251b62491bf23a2f579e6764e536e0e7ec38e 100644 (file)
@@ -846,7 +846,7 @@ static void InitGameEngine()
   /* add trigger events from element change event properties */
   for (i=0; i<MAX_NUM_ELEMENTS; i++)
     if (HAS_CHANGE_EVENT(i, CE_BY_OTHER))
-      trigger_events[element_info[i].change.trigger] |=
+      trigger_events[element_info[i].change.trigger_element] |=
        element_info[i].change.events;
 
   /* ---------- initialize push delay -------------------------------------- */
@@ -5329,7 +5329,7 @@ static boolean CheckTriggeredElementChange(int trigger_element,
   for (i=0; i<MAX_NUM_ELEMENTS; i++)
   {
     if (!CAN_CHANGE(i) || !HAS_CHANGE_EVENT(i, trigger_event) ||
-       element_info[i].change.trigger != trigger_element)
+       element_info[i].change.trigger_element != trigger_element)
       continue;
 
     for (y=0; y<lev_fieldy; y++) for (x=0; x<lev_fieldx; x++)
@@ -6444,13 +6444,13 @@ void TestIfElementTouchesCustomElement(int x, int y)
       continue;
 
     if (center_is_custom &&
-       Feld[xx][yy] == element_info[Feld[x][y]].change.trigger)
+       Feld[xx][yy] == element_info[Feld[x][y]].change.trigger_element)
     {
       CheckElementChange(x, y, Feld[x][y], CE_OTHER_IS_TOUCHING);
     }
 
     if (IS_CUSTOM_ELEMENT(Feld[xx][yy]) &&
-       Feld[x][y] == element_info[Feld[xx][yy]].change.trigger)
+       Feld[x][y] == element_info[Feld[xx][yy]].change.trigger_element)
     {
       CheckElementChange(xx, yy, Feld[xx][yy], CE_OTHER_IS_TOUCHING);
     }
index 25f6137ef2b045aff4ccf666edc2e9e7e7654851..7e4b1727863b3c5ffd3b1cd59a9da024e5fdae19 100644 (file)
@@ -645,7 +645,7 @@ static void set_graphic_parameters(int graphic, char **parameter_raw)
     anim_frames_per_col = src_bitmap->height / graphic_info[graphic].height;
   }
 
-  /* correct x or y offset dependant of vertical or horizontal frame order */
+  /* correct x or y offset dependent of vertical or horizontal frame order */
   if (parameter[GFX_ARG_VERTICAL])     /* frames are ordered vertically */
   {
     graphic_info[graphic].offset_y =
@@ -2521,7 +2521,7 @@ void InitElementPropertiesEngine(int engine_version)
   InitElementPropertiesStatic();
 #endif
 
-  /* set all special, combined or engine dependant element properties */
+  /* set all special, combined or engine dependent element properties */
   for (i=0; i < MAX_NUM_ELEMENTS; i++)
   {
 #if 0
@@ -3133,7 +3133,7 @@ void ReloadCustomArtwork()
 
   /* custom level artwork configured in level series configuration file
      always overrides custom level artwork stored in level series directory
-     and (level independant) custom artwork configured in setup menue */
+     and (level independent) custom artwork configured in setup menue */
   if (leveldir_current->graphics_set != NULL)
     gfx_new_identifier = leveldir_current->graphics_set;
   if (leveldir_current->sounds_set != NULL)
@@ -3298,7 +3298,7 @@ void CloseAllAndExit(int exit_value)
   FreeTileClipmasks();
 
   CloseVideoDisplay();
-  ClosePlatformDependantStuff();
+  ClosePlatformDependentStuff();
 
   exit(exit_value);
 }
index c841ffed244c9fc66fecc62feda0c463a59120df..4e30f4c1a4e7792980fa0f90e2fca0da1a7ef855 100644 (file)
@@ -699,7 +699,7 @@ int Read_PCX_to_Pixmap(Display *display, Window window, GC gc, char *filename,
 
 
 /* ========================================================================= */
-/* PLATFORM INDEPENDANT IMAGE FUNCTIONS                                      */
+/* PLATFORM INDEPENDENT IMAGE FUNCTIONS                                      */
 /* ========================================================================= */
 
 struct ImageInfo
index 06ac654162e43f38da9f24b483d8d9de64db2691..32efad6f840fdccaf7d3fb224c8563db3fdf5caa 100644 (file)
@@ -20,7 +20,7 @@
 
 
 /* ========================================================================= */
-/* platform dependant joystick functions                                     */
+/* platform dependent joystick functions                                     */
 /* ========================================================================= */
 
 #if defined(PLATFORM_UNIX) && !defined(TARGET_SDL)
@@ -97,7 +97,7 @@ boolean UnixReadJoystick(int fd, int *x, int *y, boolean *b1, boolean *b2)
 
 
 /* ========================================================================= */
-/* platform independant joystick functions                                   */
+/* platform independent joystick functions                                   */
 /* ========================================================================= */
 
 #define TRANSLATE_JOYSYMBOL_TO_JOYNAME 0
index cec93e978139ede92653396b5f5f78b786e1a4cb..7fd0a1a5b83e25c9df3860f1fbf6d7b72beed304 100644 (file)
@@ -123,6 +123,8 @@ void putFileVersion(FILE *, int);
 void ReadUnusedBytesFromFile(FILE *, unsigned long);
 void WriteUnusedBytesToFile(FILE *, unsigned long);
 
+#define getFile8Bit(f)        fgetc(f)
+#define putFile8Bit(f,x)      fputc(x, f)
 #define getFile16BitBE(f)     getFile16BitInteger(f,BYTE_ORDER_BIG_ENDIAN)
 #define getFile16BitLE(f)     getFile16BitInteger(f,BYTE_ORDER_LITTLE_ENDIAN)
 #define putFile16BitBE(f,x)   putFile16BitInteger(f,x,BYTE_ORDER_BIG_ENDIAN)
index d2e5e38f40be8fcf749f708b42d5d3f1b8cb635f..bfa9966bb0eb742f7f370247ffb181f86dede637 100644 (file)
@@ -107,7 +107,7 @@ void InitExitFunction(void (*exit_function)(int))
 #endif
 }
 
-void InitPlatformDependantStuff(void)
+void InitPlatformDependentStuff(void)
 {
 #if defined(PLATFORM_MSDOS)
   _fmode = O_BINARY;
@@ -120,7 +120,7 @@ void InitPlatformDependantStuff(void)
 #endif
 }
 
-void ClosePlatformDependantStuff(void)
+void ClosePlatformDependentStuff(void)
 {
 #if defined(PLATFORM_MSDOS)
   dumpErrorFile();
index 399e1e65e7318cc66911aa4b9c41f8ad7c826bdd..d5f4457f48f45219ee63ada6cd2deb1f6bdc8ff8 100644 (file)
@@ -700,8 +700,8 @@ void InitProgramInfo(char *, char *, char *, char *, char *, char *, char *,
                     char *, char *, char *, int);
 
 void InitExitFunction(void (*exit_function)(int));
-void InitPlatformDependantStuff(void);
-void ClosePlatformDependantStuff(void);
+void InitPlatformDependentStuff(void);
+void ClosePlatformDependentStuff(void);
 
 void InitGfxFieldInfo(int, int, int, int, int, int, int, int, Bitmap *);
 void InitGfxDoor1Info(int, int, int, int);
index 13c7245db65052c095fcea62f1775167638cd7af..dc2c783438227082168a5dc1012e58895531d186 100644 (file)
@@ -3114,7 +3114,7 @@ int main(int argc, char *argv[])
                  COOKIE_PREFIX, FILENAME_PREFIX, GAME_VERSION_ACTUAL);
 
   InitExitFunction(CloseAllAndExit);
-  InitPlatformDependantStuff();
+  InitPlatformDependentStuff();
 
   GetOptions(argv);
   OpenAll();
index 8dd07973ad26d5f8f2a833535f325c44ced666a7..7e70d87fc4a15a1d79fcb368a03d85b7a2027ebc 100644 (file)
@@ -1085,6 +1085,8 @@ struct LevelInfo
   boolean gravity;
   boolean em_slippery_gems;    /* EM style "gems slip from wall" behaviour */
 
+  boolean use_custom_template; /* use custom properties from template file */
+
   boolean no_level_file;
 };
 
@@ -1175,13 +1177,13 @@ struct ElementChangeInfo
 {
   unsigned long events;                /* bitfield for change events */
 
+  short target_element;                /* target element after change */
+
   int delay_fixed;             /* added frame delay before changed (fixed) */
   int delay_random;            /* added frame delay before changed (random) */
   int delay_frames;            /* either 1 (frames) or 50 (seconds; 50 fps) */
 
-  short trigger;               /* custom element triggering change */
-
-  short target_element;                /* target element after change */
+  short trigger_element;       /* custom element triggering change */
 
   int content[3][3];           /* new elements after extended change */
   boolean use_content;         /* use extended change content */
@@ -1220,8 +1222,6 @@ struct ElementInfo
 
   /* ---------- special element property values ---------- */
 
-  boolean use_template;                /* use all properties from template file */
-
   boolean use_gfx_element;
   short gfx_element;           /* optional custom graphic element */