rnd-20051228-2-src
[rocksndiamonds.git] / src / init.c
index f9dd0c1338bb8933f5bfeb18eb8bd7e2877ae277..cc3b23d57273030597f55e17e1c56df70179b9cb 100644 (file)
@@ -785,16 +785,23 @@ void InitElementSpecialGraphicInfo()
          element_info[i].graphic[ACTION_DEFAULT];
 }
 
-static int get_element_from_token(char *token)
+static int get_graphic_parameter_value(char *value_raw, char *suffix, int type)
 {
   int i;
   int x = 0;
 
+  if (type != TYPE_TOKEN)
+    return get_parameter_value(value_raw, suffix, type);
+
+  if (strcmp(value_raw, ARG_UNDEFINED) == 0)
+    return ARG_UNDEFINED_VALUE;
+
+  /* !!! OPTIMIZE THIS BY USING HASH !!! */
   for (i = 0; i < MAX_NUM_ELEMENTS; i++)
-    if (strcmp(element_info[i].token_name, token) == 0)
+    if (strcmp(element_info[i].token_name, value_raw) == 0)
       return i;
 
-#if 1
+  /* !!! OPTIMIZE THIS BY USING HASH !!! */
   for (i = 0; image_config[i].token != NULL; i++)
   {
     int len_config_value = strlen(image_config[i].value);
@@ -804,12 +811,11 @@ static int get_element_from_token(char *token)
        strcmp(image_config[i].value, UNDEFINED_FILENAME) != 0)
       continue;
 
-    if (strcmp(image_config[i].token, token) == 0)
+    if (strcmp(image_config[i].token, value_raw) == 0)
       return x;
 
     x++;
   }
-#endif
 
   return -1;
 }
@@ -830,39 +836,25 @@ static int get_scaled_graphic_height(int graphic)
   return original_height * scale_up_factor;
 }
 
-static void set_graphic_parameters(int graphic, int graphic_copy_from)
+static void set_graphic_parameters(int graphic)
 {
-  struct FileInfo *image = getImageListEntryFromImageID(graphic_copy_from);
+  struct FileInfo *image = getImageListEntryFromImageID(graphic);
   char **parameter_raw = image->parameter;
-  Bitmap *src_bitmap = getBitmapFromImageID(graphic_copy_from);
+  Bitmap *src_bitmap = getBitmapFromImageID(graphic);
   int parameter[NUM_GFX_ARGS];
   int anim_frames_per_row = 1, anim_frames_per_col = 1;
   int anim_frames_per_line = 1;
   int i;
 
-#if 1
-  if (graphic != graphic_copy_from)
-  {
-    graphic_info[graphic] = graphic_info[graphic_copy_from];
-
-    return;
-  }
-#endif
-
   /* if fallback to default artwork is done, also use the default parameters */
   if (image->fallback_to_default)
     parameter_raw = image->default_parameter;
 
   /* get integer values from string parameters */
   for (i = 0; i < NUM_GFX_ARGS; i++)
-  {
-    parameter[i] =
-      get_parameter_value(image_config_suffix[i].token, parameter_raw[i],
-                         image_config_suffix[i].type);
-
-    if (image_config_suffix[i].type == TYPE_TOKEN)
-      parameter[i] = get_element_from_token(parameter_raw[i]);
-  }
+    parameter[i] = get_graphic_parameter_value(parameter_raw[i],
+                                              image_config_suffix[i].token,
+                                              image_config_suffix[i].type);
 
   graphic_info[graphic].bitmap = src_bitmap;
 
@@ -1046,25 +1038,48 @@ static void set_graphic_parameters(int graphic, int graphic_copy_from)
   /* this is only used for drawing envelope graphics */
   graphic_info[graphic].draw_masked = parameter[GFX_ARG_DRAW_MASKED];
 
-#if 1
   /* optional graphic for cloning all graphics settings */
   if (parameter[GFX_ARG_CLONE_FROM] != ARG_UNDEFINED_VALUE)
     graphic_info[graphic].clone_from = parameter[GFX_ARG_CLONE_FROM];
-#else
-  /* optional graphic for cloning all graphics settings */
-  if (parameter[GFX_ARG_CLONE_FROM] != ARG_UNDEFINED_VALUE)
+}
+
+static void set_cloned_graphic_parameters(int graphic)
+{
+  int fallback_graphic = IMG_CHAR_EXCLAM;
+  int max_num_images = getImageListSize();
+  int clone_graphic = graphic_info[graphic].clone_from;
+  int num_references_followed = 1;
+
+  while (graphic_info[clone_graphic].clone_from != -1 &&
+        num_references_followed < max_num_images)
   {
-    if (parameter[GFX_ARG_CLONE_FROM] != -1)
-    {
-      int clone_graphic = parameter[GFX_ARG_CLONE_FROM];
+    clone_graphic = graphic_info[clone_graphic].clone_from;
 
-      graphic_info[graphic] = graphic_info[clone_graphic];
-      graphic_info[graphic].clone_from = clone_graphic;
+    num_references_followed++;
+  }
 
-      printf("::: %d -> %d\n", graphic, clone_graphic);
-    }
+  if (num_references_followed >= max_num_images)
+  {
+    Error(ERR_RETURN_LINE, "-");
+    Error(ERR_RETURN, "warning: error found in config file:");
+    Error(ERR_RETURN, "- config file: '%s'", getImageConfigFilename());
+    Error(ERR_RETURN, "- config token: '%s'", getTokenFromImageID(graphic));
+    Error(ERR_RETURN, "error: loop discovered when resolving cloned graphics");
+    Error(ERR_RETURN, "custom graphic rejected for this element/action");
+
+    if (graphic == fallback_graphic)
+      Error(ERR_EXIT, "fatal error: no fallback graphic available");
+
+    Error(ERR_RETURN, "fallback done to 'char_exclam' for this graphic");
+    Error(ERR_RETURN_LINE, "-");
+
+    graphic_info[graphic] = graphic_info[fallback_graphic];
+  }
+  else
+  {
+    graphic_info[graphic] = graphic_info[clone_graphic];
+    graphic_info[graphic].clone_from = clone_graphic;
   }
-#endif
 }
 
 static void InitGraphicInfo()
@@ -1101,53 +1116,14 @@ static void InitGraphicInfo()
   }
 #endif
 
-#if 1
   /* first set all graphic paramaters ... */
   for (i = 0; i < num_images; i++)
-  {
-    set_graphic_parameters(i, i);
-  }
+    set_graphic_parameters(i);
 
   /* ... then copy these parameters for cloned graphics */
   for (i = 0; i < num_images; i++)
-  {
     if (graphic_info[i].clone_from != -1)
-    {
-      int clone_graphic = graphic_info[i].clone_from;
-
-      if (graphic_info[clone_graphic].clone_from != -1)
-      {
-       Error(ERR_RETURN_LINE, "-");
-       Error(ERR_RETURN, "warning: error found in config file:");
-       Error(ERR_RETURN, "- config file: '%s'", getImageConfigFilename());
-       Error(ERR_RETURN, "- config token: '%s'", getTokenFromImageID(i));
-       Error(ERR_RETURN,
-             "error: cannot clone from already cloned graphic '%s'",
-             getTokenFromImageID(clone_graphic));
-       Error(ERR_RETURN, "custom graphic rejected for this element/action");
-
-       if (i == fallback_graphic)
-         Error(ERR_EXIT, "fatal error: no fallback graphic available");
-
-       Error(ERR_RETURN, "fallback done to 'char_exclam' for this graphic");
-       Error(ERR_RETURN_LINE, "-");
-
-       set_graphic_parameters(i, fallback_graphic);
-      }
-      else
-      {
-       graphic_info[i] = graphic_info[clone_graphic];
-       graphic_info[i].clone_from = clone_graphic;
-
-#if 0
-       printf("::: graphic %d ['%s'] is cloned from %d ['%s']\n",
-              i, getTokenFromImageID(i),
-              clone_graphic, getTokenFromImageID(clone_graphic));
-#endif
-      }
-    }
-  }
-#endif
+      set_cloned_graphic_parameters(i);
 
   for (i = 0; i < num_images; i++)
   {
@@ -1156,46 +1132,20 @@ static void InitGraphicInfo()
     int first_frame, last_frame;
     int src_bitmap_width, src_bitmap_height;
 
-#if 0
-    printf("::: image # %d: '%s' ['%s']\n",
-          i, image->token, getTokenFromImageID(i));
-#endif
-
-#if 0
-    set_graphic_parameters(i, i);
-#endif
-
     /* now check if no animation frames are outside of the loaded image */
 
-#if 0
-    if (graphic_info[i].bitmap == NULL)
-      Error(ERR_WARN, "no bitmap for graphic %d ['%s']",
-           i, getTokenFromImageID(i));
-#endif
-
     if (graphic_info[i].bitmap == NULL)
       continue;                /* skip check for optional images that are undefined */
 
-#if 1
     /* get final bitmap size (with scaling, but without small images) */
     src_bitmap_width  = graphic_info[i].src_image_width;
     src_bitmap_height = graphic_info[i].src_image_height;
-#else
-    /* get final bitmap size (with scaling, but without small images) */
-    src_bitmap_width  = get_scaled_graphic_width(i);
-    src_bitmap_height = get_scaled_graphic_height(i);
 
-    if (graphic_info[i].clone_from != -1)
-    {
-      int clone_graphic = graphic_info[i].clone_from;
-
-      src_bitmap_width  = get_scaled_graphic_width(clone_graphic);
-      src_bitmap_height = get_scaled_graphic_height(clone_graphic);
-    }
-#endif
+    /* check if first animation frame is inside specified bitmap */
 
     first_frame = 0;
     getGraphicSource(i, first_frame, &src_bitmap, &src_x, &src_y);
+
     if (src_x < 0 || src_y < 0 ||
        src_x + TILEX > src_bitmap_width ||
        src_y + TILEY > src_bitmap_height)
@@ -1216,11 +1166,14 @@ static void InitGraphicInfo()
       Error(ERR_RETURN, "fallback done to 'char_exclam' for this graphic");
       Error(ERR_RETURN_LINE, "-");
 
-      set_graphic_parameters(i, fallback_graphic);
+      graphic_info[i] = graphic_info[fallback_graphic];
     }
 
+    /* check if last animation frame is inside specified bitmap */
+
     last_frame = graphic_info[i].anim_frames - 1;
     getGraphicSource(i, last_frame, &src_bitmap, &src_x, &src_y);
+
     if (src_x < 0 || src_y < 0 ||
        src_x + TILEX > src_bitmap_width ||
        src_y + TILEY > src_bitmap_height)
@@ -1241,7 +1194,7 @@ static void InitGraphicInfo()
       Error(ERR_RETURN, "fallback done to 'char_exclam' for this graphic");
       Error(ERR_RETURN_LINE, "-");
 
-      set_graphic_parameters(i, fallback_graphic);
+      graphic_info[i] = graphic_info[fallback_graphic];
     }
 
 #if defined(TARGET_X11_NATIVE_PERFORMANCE_WORKAROUND)
@@ -1431,7 +1384,8 @@ static void set_sound_parameters(int sound, char **parameter_raw)
   /* get integer values from string parameters */
   for (i = 0; i < NUM_SND_ARGS; i++)
     parameter[i] =
-      get_parameter_value(sound_config_suffix[i].token, parameter_raw[i],
+      get_parameter_value(parameter_raw[i],
+                         sound_config_suffix[i].token,
                          sound_config_suffix[i].type);
 
   /* explicit loop mode setting in configuration overrides default value */
@@ -1608,7 +1562,8 @@ static void set_music_parameters(int music, char **parameter_raw)
   /* get integer values from string parameters */
   for (i = 0; i < NUM_MUS_ARGS; i++)
     parameter[i] =
-      get_parameter_value(music_config_suffix[i].token, parameter_raw[i],
+      get_parameter_value(parameter_raw[i],
+                         music_config_suffix[i].token,
                          music_config_suffix[i].type);
 
   /* explicit loop mode setting in configuration overrides default value */
@@ -1995,6 +1950,10 @@ void InitElementPropertiesStatic()
     EL_GATE_2_GRAY,
     EL_GATE_3_GRAY,
     EL_GATE_4_GRAY,
+    EL_GATE_1_GRAY_ACTIVE,
+    EL_GATE_2_GRAY_ACTIVE,
+    EL_GATE_3_GRAY_ACTIVE,
+    EL_GATE_4_GRAY_ACTIVE,
     EL_EM_GATE_1,
     EL_EM_GATE_2,
     EL_EM_GATE_3,
@@ -2003,6 +1962,10 @@ void InitElementPropertiesStatic()
     EL_EM_GATE_2_GRAY,
     EL_EM_GATE_3_GRAY,
     EL_EM_GATE_4_GRAY,
+    EL_EM_GATE_1_GRAY_ACTIVE,
+    EL_EM_GATE_2_GRAY_ACTIVE,
+    EL_EM_GATE_3_GRAY_ACTIVE,
+    EL_EM_GATE_4_GRAY_ACTIVE,
     EL_EMC_GATE_5,
     EL_EMC_GATE_6,
     EL_EMC_GATE_7,
@@ -2011,6 +1974,10 @@ void InitElementPropertiesStatic()
     EL_EMC_GATE_6_GRAY,
     EL_EMC_GATE_7_GRAY,
     EL_EMC_GATE_8_GRAY,
+    EL_EMC_GATE_5_GRAY_ACTIVE,
+    EL_EMC_GATE_6_GRAY_ACTIVE,
+    EL_EMC_GATE_7_GRAY_ACTIVE,
+    EL_EMC_GATE_8_GRAY_ACTIVE,
     EL_SWITCHGATE_OPEN,
     EL_SWITCHGATE_OPENING,
     EL_SWITCHGATE_CLOSED,
@@ -2255,6 +2222,10 @@ void InitElementPropertiesStatic()
     EL_GATE_2_GRAY,
     EL_GATE_3_GRAY,
     EL_GATE_4_GRAY,
+    EL_GATE_1_GRAY_ACTIVE,
+    EL_GATE_2_GRAY_ACTIVE,
+    EL_GATE_3_GRAY_ACTIVE,
+    EL_GATE_4_GRAY_ACTIVE,
     EL_PENGUIN,
     EL_PIG,
     EL_DRAGON,
@@ -2292,6 +2263,10 @@ void InitElementPropertiesStatic()
     EL_EM_GATE_2_GRAY,
     EL_EM_GATE_3_GRAY,
     EL_EM_GATE_4_GRAY,
+    EL_EM_GATE_1_GRAY_ACTIVE,
+    EL_EM_GATE_2_GRAY_ACTIVE,
+    EL_EM_GATE_3_GRAY_ACTIVE,
+    EL_EM_GATE_4_GRAY_ACTIVE,
     EL_EMC_GATE_5,
     EL_EMC_GATE_6,
     EL_EMC_GATE_7,
@@ -2300,6 +2275,10 @@ void InitElementPropertiesStatic()
     EL_EMC_GATE_6_GRAY,
     EL_EMC_GATE_7_GRAY,
     EL_EMC_GATE_8_GRAY,
+    EL_EMC_GATE_5_GRAY_ACTIVE,
+    EL_EMC_GATE_6_GRAY_ACTIVE,
+    EL_EMC_GATE_7_GRAY_ACTIVE,
+    EL_EMC_GATE_8_GRAY_ACTIVE,
     EL_SWITCHGATE_OPEN,
     EL_TIMEGATE_OPEN,
     -1
@@ -2393,6 +2372,10 @@ void InitElementPropertiesStatic()
     EL_EM_GATE_2_GRAY,
     EL_EM_GATE_3_GRAY,
     EL_EM_GATE_4_GRAY,
+    EL_EM_GATE_1_GRAY_ACTIVE,
+    EL_EM_GATE_2_GRAY_ACTIVE,
+    EL_EM_GATE_3_GRAY_ACTIVE,
+    EL_EM_GATE_4_GRAY_ACTIVE,
     EL_EMC_GATE_5,
     EL_EMC_GATE_6,
     EL_EMC_GATE_7,
@@ -2401,6 +2384,10 @@ void InitElementPropertiesStatic()
     EL_EMC_GATE_6_GRAY,
     EL_EMC_GATE_7_GRAY,
     EL_EMC_GATE_8_GRAY,
+    EL_EMC_GATE_5_GRAY_ACTIVE,
+    EL_EMC_GATE_6_GRAY_ACTIVE,
+    EL_EMC_GATE_7_GRAY_ACTIVE,
+    EL_EMC_GATE_8_GRAY_ACTIVE,
     EL_SWITCHGATE_OPEN,
     EL_TIMEGATE_OPEN,
 
@@ -2549,6 +2536,7 @@ void InitElementPropertiesStatic()
     EL_BALLOON_SWITCH_UP,
     EL_BALLOON_SWITCH_DOWN,
     EL_BALLOON_SWITCH_ANY,
+    EL_BALLOON_SWITCH_NONE,
     EL_LAMP,
     EL_TIME_ORB_FULL,
     EL_EMC_MAGIC_BALL_SWITCH,
@@ -2751,6 +2739,10 @@ void InitElementPropertiesStatic()
     EL_GATE_2_GRAY,
     EL_GATE_3_GRAY,
     EL_GATE_4_GRAY,
+    EL_GATE_1_GRAY_ACTIVE,
+    EL_GATE_2_GRAY_ACTIVE,
+    EL_GATE_3_GRAY_ACTIVE,
+    EL_GATE_4_GRAY_ACTIVE,
     EL_EM_GATE_1,
     EL_EM_GATE_2,
     EL_EM_GATE_3,
@@ -2759,6 +2751,10 @@ void InitElementPropertiesStatic()
     EL_EM_GATE_2_GRAY,
     EL_EM_GATE_3_GRAY,
     EL_EM_GATE_4_GRAY,
+    EL_EM_GATE_1_GRAY_ACTIVE,
+    EL_EM_GATE_2_GRAY_ACTIVE,
+    EL_EM_GATE_3_GRAY_ACTIVE,
+    EL_EM_GATE_4_GRAY_ACTIVE,
     EL_EXIT_CLOSED,
     EL_EXIT_OPENING,
     EL_EXIT_OPEN,
@@ -2935,6 +2931,10 @@ void InitElementPropertiesStatic()
     EL_GATE_2_GRAY,
     EL_GATE_3_GRAY,
     EL_GATE_4_GRAY,
+    EL_GATE_1_GRAY_ACTIVE,
+    EL_GATE_2_GRAY_ACTIVE,
+    EL_GATE_3_GRAY_ACTIVE,
+    EL_GATE_4_GRAY_ACTIVE,
     EL_EM_GATE_1,
     EL_EM_GATE_2,
     EL_EM_GATE_3,
@@ -2943,6 +2943,10 @@ void InitElementPropertiesStatic()
     EL_EM_GATE_2_GRAY,
     EL_EM_GATE_3_GRAY,
     EL_EM_GATE_4_GRAY,
+    EL_EM_GATE_1_GRAY_ACTIVE,
+    EL_EM_GATE_2_GRAY_ACTIVE,
+    EL_EM_GATE_3_GRAY_ACTIVE,
+    EL_EM_GATE_4_GRAY_ACTIVE,
     EL_SWITCHGATE_OPEN,
     EL_SWITCHGATE_OPENING,
     EL_SWITCHGATE_CLOSED,
@@ -3058,6 +3062,10 @@ void InitElementPropertiesStatic()
     EL_GATE_2_GRAY,
     EL_GATE_3_GRAY,
     EL_GATE_4_GRAY,
+    EL_GATE_1_GRAY_ACTIVE,
+    EL_GATE_2_GRAY_ACTIVE,
+    EL_GATE_3_GRAY_ACTIVE,
+    EL_GATE_4_GRAY_ACTIVE,
     EL_EM_GATE_1,
     EL_EM_GATE_2,
     EL_EM_GATE_3,
@@ -3066,6 +3074,10 @@ void InitElementPropertiesStatic()
     EL_EM_GATE_2_GRAY,
     EL_EM_GATE_3_GRAY,
     EL_EM_GATE_4_GRAY,
+    EL_EM_GATE_1_GRAY_ACTIVE,
+    EL_EM_GATE_2_GRAY_ACTIVE,
+    EL_EM_GATE_3_GRAY_ACTIVE,
+    EL_EM_GATE_4_GRAY_ACTIVE,
     EL_EMC_GATE_5,
     EL_EMC_GATE_6,
     EL_EMC_GATE_7,
@@ -3074,6 +3086,10 @@ void InitElementPropertiesStatic()
     EL_EMC_GATE_6_GRAY,
     EL_EMC_GATE_7_GRAY,
     EL_EMC_GATE_8_GRAY,
+    EL_EMC_GATE_5_GRAY_ACTIVE,
+    EL_EMC_GATE_6_GRAY_ACTIVE,
+    EL_EMC_GATE_7_GRAY_ACTIVE,
+    EL_EMC_GATE_8_GRAY_ACTIVE,
     -1
   };
 
@@ -3167,6 +3183,10 @@ void InitElementPropertiesStatic()
     EL_GATE_2_GRAY,
     EL_GATE_3_GRAY,
     EL_GATE_4_GRAY,
+    EL_GATE_1_GRAY_ACTIVE,
+    EL_GATE_2_GRAY_ACTIVE,
+    EL_GATE_3_GRAY_ACTIVE,
+    EL_GATE_4_GRAY_ACTIVE,
     EL_EM_GATE_1,
     EL_EM_GATE_2,
     EL_EM_GATE_3,
@@ -3175,6 +3195,10 @@ void InitElementPropertiesStatic()
     EL_EM_GATE_2_GRAY,
     EL_EM_GATE_3_GRAY,
     EL_EM_GATE_4_GRAY,
+    EL_EM_GATE_1_GRAY_ACTIVE,
+    EL_EM_GATE_2_GRAY_ACTIVE,
+    EL_EM_GATE_3_GRAY_ACTIVE,
+    EL_EM_GATE_4_GRAY_ACTIVE,
     EL_EMC_GATE_5,
     EL_EMC_GATE_6,
     EL_EMC_GATE_7,
@@ -3183,6 +3207,10 @@ void InitElementPropertiesStatic()
     EL_EMC_GATE_6_GRAY,
     EL_EMC_GATE_7_GRAY,
     EL_EMC_GATE_8_GRAY,
+    EL_EMC_GATE_5_GRAY_ACTIVE,
+    EL_EMC_GATE_6_GRAY_ACTIVE,
+    EL_EMC_GATE_7_GRAY_ACTIVE,
+    EL_EMC_GATE_8_GRAY_ACTIVE,
     EL_DYNAMITE,
     EL_INVISIBLE_STEELWALL,
     EL_INVISIBLE_WALL,