From 089d1df0ff6b3ba6bd6eb20f5f8324f783361f13 Mon Sep 17 00:00:00 2001 From: novgorodschi catalin Date: Tue, 14 Jul 2026 14:03:31 +0300 Subject: [PATCH] Fix 3 bugs (spy dont die, hero error battle report and hospital cost) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 1. Spies — real bug, found. In calculateBattle, the block that calculates the attack power of spies had the hardcoded condition if ($i == 4 || $i == 14 || $i == 23 || $i == 44). Scouts of new tribes (52/64/74/82) did not enter the branch → attack power 0, so they all died no matter how many there were. Now the condition is in_array($i, $unitsbytype['scout']). With this, all four lists in Battle (cavalry, catapults, rams, scouts on attack + scouts on defense) are derived from unitsbytype. 2. Defender hero. I rebuilt the report CSV with dummy values ​​and confirmed that the indexes in Notice/1.tpl are correct (272 = hero present, 273 = hero dead) — so the problem was that $deadhero was ending up as 0 in the report, even though deadherodef was 1 in the battle result (that's why the hero actually died in the DB). Now $deadhero is taken directly from the battle result ($battlepart['deadherodef']), with $owndead['hero'] only as a fallback. 3. "Free" healing. The code called modifyResource(..., mode 0) exactly like training, so the resources were low — but at 100x speed and full storage (8M/8M in your captures) the difference is instantly invisible. I did find a real bug in this area though: modifyResource caps at 0 instead of failing, so if you don't have resources you heal for free. Now procHeal checks the stock and, if there are insufficient resources, automatically reduces the quantity to what you can afford (or cancels). --- GameEngine/Automation.php | 6 +++++- GameEngine/Battle.php | 4 ++-- GameEngine/Technology.php | 21 +++++++++++++++++++++ 3 files changed, 28 insertions(+), 3 deletions(-) diff --git a/GameEngine/Automation.php b/GameEngine/Automation.php index 54fbf414..5ded8603 100644 --- a/GameEngine/Automation.php +++ b/GameEngine/Automation.php @@ -3351,7 +3351,11 @@ class Automation { if (empty($alldead['hero'])) $alldead['hero'] = 0; if (empty($owndead['hero'])) $owndead['hero'] = 0; - $deadhero = $owndead['hero']; + // sursa autoritativa: rezultatul luptei (owndead['hero'] se poate pierde + // pe unele cai de executie, iar raportul afisa eroul aparator ca viu) + $deadhero = (int)(isset($battlepart['deadherodef']) && $battlepart['deadherodef'] > 0 + ? $battlepart['deadherodef'] + : $owndead['hero']); //Counting own total dead troops $ownDeadTroops = array_slice($owndead, 0, 10); diff --git a/GameEngine/Battle.php b/GameEngine/Battle.php index 3b45eec0..719d265f 100644 --- a/GameEngine/Battle.php +++ b/GameEngine/Battle.php @@ -485,7 +485,7 @@ class Battle { $conqureby, $defReinforcements = null) { - global $bid34, $bid35, $database; + global $bid34, $bid35, $database, $unitsbytype; /****************************************************************** * UNIT GROUP DEFINITIONS @@ -692,7 +692,7 @@ class Battle { global ${'u'.$i}; - if ($i == 4 || $i == 14 || $i == 23 || $i == 44) { + if (in_array($i, $unitsbytype['scout'])) { if ($scoutAB > 0) { diff --git a/GameEngine/Technology.php b/GameEngine/Technology.php index 5bb75afc..d2d454a7 100755 --- a/GameEngine/Technology.php +++ b/GameEngine/Technology.php @@ -136,6 +136,27 @@ class Technology { $each = (int)round($unitdata['time'] * $attri / SPEED); if($each < 1) $each = 1; + // nu vindeca gratis: modifyResource limiteaza la 0, deci verificam explicit stocul + $have = [(int)$village->awood, (int)$village->aclay, (int)$village->airon, (int)$village->acrop]; + { + if($have[0] < $wood || $have[1] < $clay || $have[2] < $iron || $have[3] < $crop) { + // resurse insuficiente: reducem cantitatea la cat isi permite jucatorul + $maxByRes = $amt; + foreach([['wood', $wood], ['clay', $clay], ['iron', $iron], ['crop', $crop]] as $k => $pair) { + if($pair[1] > 0) { + $possible = (int)floor($have[$k] * $amt / $pair[1]); + if($possible < $maxByRes) $maxByRes = $possible; + } + } + $amt = $maxByRes; + if($amt <= 0) return; + $wood = (int)ceil($unitdata['wood'] * $amt / 2); + $clay = (int)ceil($unitdata['clay'] * $amt / 2); + $iron = (int)ceil($unitdata['iron'] * $amt / 2); + $crop = (int)ceil($unitdata['crop'] * $amt / 2); + } + } + if($database->modifyResource($village->wid, $wood, $clay, $iron, $crop, 0)) { $database->deductWounded($village->wid, $unit, $amt); $database->healUnit($village->wid, $unit, $amt, $each);