added support for storing multiple event definitions for global animations
authorHolger Schemel <info@artsoft.org>
Tue, 12 Mar 2019 20:22:02 +0000 (21:22 +0100)
committerHolger Schemel <info@artsoft.org>
Tue, 12 Mar 2019 21:00:19 +0000 (22:00 +0100)
src/anim.c
src/files.c
src/files.h
src/init.c
src/libgame/system.h
src/main.c
src/main.h

index 2234ebe48d8e55697a373947bb96990022733d0f..861364d727e4606a7ff284cb9f0893eb85a0f7c9 100644 (file)
@@ -14,6 +14,7 @@
 #include "anim.h"
 #include "main.h"
 #include "tools.h"
+#include "files.h"
 #include "events.h"
 #include "screens.h"
 
@@ -994,18 +995,20 @@ static boolean isClickablePart(struct GlobalAnimPartControlInfo *part, int mask)
   struct GraphicInfo *c = &part->control_info;
   int trigger_mask = ANIM_EVENT_ANIM_MASK | ANIM_EVENT_PART_MASK;
   int mask_anim_only = mask & ANIM_EVENT_ANIM_MASK;
+  int init_event = GetGlobalAnimEventValue(c->init_event, 0);
+  int anim_event = GetGlobalAnimEventValue(c->anim_event, 0);
 
   if (mask & ANIM_EVENT_ANY)
-    return (c->init_event & ANIM_EVENT_ANY ||
-           c->anim_event & ANIM_EVENT_ANY);
+    return (init_event & ANIM_EVENT_ANY ||
+           anim_event & ANIM_EVENT_ANY);
   else if (mask & ANIM_EVENT_SELF)
-    return (c->init_event & ANIM_EVENT_SELF ||
-           c->anim_event & ANIM_EVENT_SELF);
+    return (init_event & ANIM_EVENT_SELF ||
+           anim_event & ANIM_EVENT_SELF);
   else
-    return ((c->init_event & trigger_mask) == mask ||
-           (c->anim_event & trigger_mask) == mask ||
-           (c->init_event & trigger_mask) == mask_anim_only ||
-           (c->anim_event & trigger_mask) == mask_anim_only);
+    return ((init_event & trigger_mask) == mask ||
+           (anim_event & trigger_mask) == mask ||
+           (init_event & trigger_mask) == mask_anim_only ||
+           (anim_event & trigger_mask) == mask_anim_only);
 }
 
 static boolean isClickedPart(struct GlobalAnimPartControlInfo *part,
@@ -1070,8 +1073,8 @@ static int HandleGlobalAnim_Part(struct GlobalAnimPartControlInfo *part,
     part->anim_delay_counter =
       (c->anim_delay_fixed + GetSimpleRandom(c->anim_delay_random));
 
-    part->init_event_state = c->init_event;
-    part->anim_event_state = c->anim_event;
+    part->init_event_state = GetGlobalAnimEventValue(c->init_event, 0);
+    part->anim_event_state = GetGlobalAnimEventValue(c->anim_event, 0);
 
     part->initial_anim_sync_frame =
       (g->anim_global_sync ? 0 : anim_sync_frame + part->init_delay_counter);
index 4ac4563fee7dfd0fb9c3ab6494da719c95f56cca..1820761192872aace9e9a9867fbd0a82bb0e8997 100644 (file)
@@ -9941,6 +9941,79 @@ static int getElementFromToken(char *token)
   return EL_UNDEFINED;
 }
 
+void FreeGlobalAnimEventInfo(void)
+{
+  struct GlobalAnimEventInfo *gaei = &global_anim_event_info;
+
+  if (gaei->event_list == NULL)
+    return;
+
+  int i;
+
+  for (i = 0; i < gaei->num_event_lists; i++)
+  {
+    checked_free(gaei->event_list[i]->event_value);
+    checked_free(gaei->event_list[i]);
+  }
+
+  checked_free(gaei->event_list);
+
+  gaei->event_list = NULL;
+  gaei->num_event_lists = 0;
+}
+
+static int AddGlobalAnimEventList(void)
+{
+  struct GlobalAnimEventInfo *gaei = &global_anim_event_info;
+  int list_pos = gaei->num_event_lists++;
+
+  gaei->event_list = checked_realloc(gaei->event_list, gaei->num_event_lists *
+                                    sizeof(struct GlobalAnimEventListInfo *));
+
+  gaei->event_list[list_pos] =
+    checked_calloc(sizeof(struct GlobalAnimEventListInfo));
+
+  struct GlobalAnimEventListInfo *gaeli = gaei->event_list[list_pos];
+
+  gaeli->event_value = NULL;
+  gaeli->num_event_values = 0;
+
+  return list_pos;
+}
+
+static int AddGlobalAnimEventValue(int list_pos, int event_value)
+{
+  // do not add empty global animation events
+  if (event_value == ANIM_EVENT_NONE)
+    return list_pos;
+
+  // if list position is undefined, create new list
+  if (list_pos == ANIM_EVENT_UNDEFINED)
+    list_pos = AddGlobalAnimEventList();
+
+  struct GlobalAnimEventInfo *gaei = &global_anim_event_info;
+  struct GlobalAnimEventListInfo *gaeli = gaei->event_list[list_pos];
+  int value_pos = gaeli->num_event_values++;
+
+  gaeli->event_value = checked_realloc(gaeli->event_value,
+                                      gaeli->num_event_values * sizeof(int *));
+
+  gaeli->event_value[value_pos] = event_value;
+
+  return list_pos;
+}
+
+int GetGlobalAnimEventValue(int list_pos, int value_pos)
+{
+  if (list_pos == ANIM_EVENT_UNDEFINED)
+    return ANIM_EVENT_NONE;
+
+  struct GlobalAnimEventInfo *gaei = &global_anim_event_info;
+  struct GlobalAnimEventListInfo *gaeli = gaei->event_list[list_pos];
+
+  return gaeli->event_value[value_pos];
+}
+
 // This function checks if a string <s> of the format "string1, string2, ..."
 // exactly contains a string <s_contained>.
 
@@ -10152,6 +10225,9 @@ int get_parameter_value(char *value_raw, char *suffix, int type)
 
     // add optional "click:anim_X" or "click:anim_X.part_X" parameter
     result |= get_anim_parameter_value(value);
+
+    // final result is position in global animation event list
+    result = AddGlobalAnimEventValue(ANIM_EVENT_UNDEFINED, result);
   }
   else if (strEqual(suffix, ".init_event_action") ||
           strEqual(suffix, ".anim_event_action"))
index 031349f774039a1051bf5e860563bac446eecb7f..6af3a1486d5194c3c15c932adf6d1cb619e982b5 100644 (file)
@@ -86,6 +86,9 @@ void ConvertLevels(void);
 void CreateLevelSketchImages(void);
 void CreateCustomElementImages(char *);
 
+void FreeGlobalAnimEventInfo(void);
+int GetGlobalAnimEventValue(int, int);
+
 int get_parameter_value(char *, char *, int);
 
 #endif // FILES_H
index 683bacdb44dcf328f2ce18389100ffe4a809de46..d3b33ec219b723d71da1cd2011f07267fe7b2407 100644 (file)
@@ -1301,8 +1301,8 @@ static void set_graphic_parameters_ext(int graphic, int *parameter,
   g->anim_delay_random = 0;
   g->post_delay_fixed = 0;
   g->post_delay_random = 0;
-  g->init_event = ANIM_EVENT_DEFAULT;
-  g->anim_event = ANIM_EVENT_DEFAULT;
+  g->init_event = ANIM_EVENT_UNDEFINED;
+  g->anim_event = ANIM_EVENT_UNDEFINED;
   g->init_event_action = -1;
   g->anim_event_action = -1;
   g->draw_masked = FALSE;
@@ -1723,6 +1723,8 @@ static void InitGraphicInfo(void)
     -1
   };
 
+  FreeGlobalAnimEventInfo();
+
   checked_free(graphic_info);
 
   graphic_info = checked_calloc(num_images * sizeof(struct GraphicInfo));
index 50dc573630763b6f3459a795a7f1b72e1898a217..7b45b057fd7e894a5629dbb7b0599a3e3b491877 100644 (file)
 #define STYLE_DEFAULT          STYLE_NONE
 
 // values for special global animation events
+#define ANIM_EVENT_UNDEFINED   -1
 #define ANIM_EVENT_NONE                0
 #define ANIM_EVENT_SELF                (1 << 16)
 #define ANIM_EVENT_ANY         (1 << 17)
index 28eaf6494ceff2328cca6c0603dcf53cd5d91a28..59faa000e1ccb64b15051c6a1dc8cd2ee5fa7f12 100644 (file)
@@ -7568,6 +7568,11 @@ struct GlobalAnimNameInfo global_anim_name_info[NUM_GLOBAL_ANIM_TOKENS + 1] =
   { NULL                       }
 };
 
+struct GlobalAnimEventInfo global_anim_event_info =
+{
+  NULL, 0
+};
+
 
 // ----------------------------------------------------------------------------
 // music token prefix definitions
index 4ae3c627eb648f0d11f1e49f8f66920b9578b05c..93874a7e974a57883f29df82c51f02e9abb3adbe 100644 (file)
@@ -3412,6 +3412,18 @@ struct GlobalAnimInfo
   int music[NUM_GLOBAL_ANIM_PARTS_ALL][NUM_SPECIAL_GFX_ARGS];
 };
 
+struct GlobalAnimEventListInfo
+{
+  int *event_value;
+  int num_event_values;
+};
+
+struct GlobalAnimEventInfo
+{
+  struct GlobalAnimEventListInfo **event_list;
+  int num_event_lists;
+};
+
 struct GraphicInfo
 {
   Bitmap **bitmaps;            // bitmaps in all required sizes
@@ -3701,6 +3713,7 @@ extern struct TokenIntPtrInfo     image_config_vars[];
 extern struct FontInfo         font_info[];
 extern struct GlobalAnimInfo   global_anim_info[];
 extern struct GlobalAnimNameInfo global_anim_name_info[];
+extern struct GlobalAnimEventInfo global_anim_event_info;
 extern struct MusicPrefixInfo  music_prefix_info[];
 extern struct GraphicInfo      *graphic_info;
 extern struct SoundInfo               *sound_info;