DEADSOFTWARE

more monster tree cosmetix
[d2df-sdl.git] / src / game / g_monsters.pas
index 4a20c4853a01e09aa08920b90785922338a355d9..f5f69a93d5eea3b621a153db5d821dd334c49545 100644 (file)
@@ -93,6 +93,7 @@ type
   public
     FNoRespawn: Boolean;
     FFireTime: Integer;
+    trapCheckFrameId: DWord; // for `g_weapons.CheckTrap()`
 
     constructor Create(MonsterType: Byte; aID: Integer; ForcedUID: Integer = -1);
     destructor Destroy(); override;
@@ -195,6 +196,8 @@ function g_Mons_IsAnyAliveAt (x, y: Integer; width, height: Integer): Boolean;
 function g_Mons_ForEachAt (x, y: Integer; width, height: Integer; cb: TEachMonsterCB): Boolean;
 function g_Mons_ForEachAtAlive (x, y: Integer; width, height: Integer; cb: TEachMonsterCB): Boolean;
 
+function g_Mons_getNewTrapFrameId (): DWord;
+
 
 var
   gmon_debug_use_sqaccel: Boolean = true;
@@ -209,6 +212,11 @@ uses
   g_language, g_netmsg, z_aabbtree;
 
 
+// ////////////////////////////////////////////////////////////////////////// //
+var
+  monCheckTrapLastFrameId: DWord;
+
+
 // ////////////////////////////////////////////////////////////////////////// //
 type
   TDynAABBTreeMonsBase = specialize TDynAABBTreeBase<TMonster>;
@@ -484,6 +492,24 @@ begin
 end;
 
 
+function g_Mons_getNewTrapFrameId (): DWord;
+var
+  f: Integer;
+begin
+  Inc(monCheckTrapLastFrameId);
+  if monCheckTrapLastFrameId = 0 then
+  begin
+    // wraparound
+    monCheckTrapLastFrameId := 1;
+    for f := 0 to High(gMonsters) do
+    begin
+      if (gMonsters[f] <> nil) then gMonsters[f].trapCheckFrameId := 0;
+    end;
+  end;
+  result := monCheckTrapLastFrameId;
+end;
+
+
 var
   pt_x: Integer = 0;
   pt_xs: Integer = 1;
@@ -878,6 +904,7 @@ begin
 
   monsTree := TDynAABBTreeMons.Create();
   clearUidMap();
+  monCheckTrapLastFrameId := 0;
 end;
 
 procedure g_Monsters_FreeData();
@@ -1107,10 +1134,11 @@ procedure g_Monsters_Free();
 var
   a: Integer;
 begin
-  for a := 0 to High(gMonsters) do gMonsters[a].Free();
   monsTree.reset();
+  for a := 0 to High(gMonsters) do gMonsters[a].Free();
   gMonsters := nil;
   clearUidMap();
+  monCheckTrapLastFrameId := 0;
 end;
 
 function g_Monsters_Create(MonsterType: Byte; X, Y: Integer;
@@ -1625,6 +1653,7 @@ begin
 
   treeNode := -1;
   arrIdx := -1;
+  trapCheckFrameId := 0;
 
   if FMonsterType in [MONSTER_ROBO, MONSTER_BARREL] then
     FBloodKind := BLOOD_SPARKS
@@ -1900,10 +1929,13 @@ begin
 
   if (treeNode <> -1) then
   begin
-    {$IF DEFINED(D2F_DEBUG)}
-    e_WriteLog(Format('monster #%d(%u): removed from tree; nodeid=%d', [arrIdx, UID, treeNode]), MSG_NOTIFY);
-    {$ENDIF}
-    monsTree.removeObject(treeNode);
+    if monsTree.isValidId(treeNode) then
+    begin
+      {$IF DEFINED(D2F_DEBUG)}
+      e_WriteLog(Format('monster #%d(%u): removed from tree; nodeid=%d', [arrIdx, UID, treeNode]), MSG_NOTIFY);
+      {$ENDIF}
+      monsTree.removeObject(treeNode);
+    end;
   end;
 
   if (arrIdx <> -1) then