|
6 | 6 | #include "Ext/Building/Body.h" |
7 | 7 | #include <Ext/Event/Body.h> |
8 | 8 |
|
| 9 | +#include <BeaconManagerClass.h> |
| 10 | + |
9 | 11 | #include <unordered_map> |
| 12 | +#include <algorithm> |
| 13 | +#include <utility> |
10 | 14 |
|
11 | 15 | // Trigger power recalculation on gain/loss of any techno, not just buildings. |
12 | 16 | DEFINE_HOOK_AGAIN(0x5025F0, HouseClass_RegisterGain, 0x5) // RegisterLoss |
@@ -681,3 +685,72 @@ DEFINE_HOOK(0x45063F, BuildingClass_UpdateRepairSell_PlayerAutoRepair, 0x6) |
681 | 685 | } |
682 | 686 |
|
683 | 687 | #pragma endregion |
| 688 | + |
| 689 | +#pragma region BeaconOrder |
| 690 | + |
| 691 | +DEFINE_HOOK(0x43131B, BeaconManagerClass_DeleteBeacon_RecordOrder, 0x5) |
| 692 | +{ |
| 693 | + GET(int, beaconIdx, EBX); |
| 694 | + GET(int, houseIdx, ECX); |
| 695 | + |
| 696 | + const auto pHouse = HouseClass::Array.GetItem(houseIdx); |
| 697 | + const auto pExt = HouseExt::ExtMap.Find(pHouse); |
| 698 | + |
| 699 | + const int oldValue = std::exchange(pExt->BeaconsPlacedOrder[beaconIdx], 0); |
| 700 | + |
| 701 | + if (oldValue != 0) |
| 702 | + { |
| 703 | + for (int i = 0; i < 3; ++i) |
| 704 | + { |
| 705 | + if (i != beaconIdx && pExt->BeaconsPlacedOrder[i] > oldValue) |
| 706 | + --pExt->BeaconsPlacedOrder[i]; |
| 707 | + } |
| 708 | + } |
| 709 | + |
| 710 | + return 0; |
| 711 | +} |
| 712 | + |
| 713 | +DEFINE_HOOK_AGAIN(0x430E5D, BeaconManagerClass_PlaceBeacon_RecordOrder, 0x5) |
| 714 | +DEFINE_HOOK(0x430C64, BeaconManagerClass_PlaceBeacon_RecordOrder, 0x5) |
| 715 | +{ |
| 716 | + GET(int, beaconIdx, EAX); |
| 717 | + GET(int, houseIdx, EBX); |
| 718 | + |
| 719 | + const auto pHouse = HouseClass::Array.GetItem(houseIdx); |
| 720 | + const auto pExt = HouseExt::ExtMap.Find(pHouse); |
| 721 | + |
| 722 | + const int maxVal = std::max({ pExt->BeaconsPlacedOrder[0], pExt->BeaconsPlacedOrder[1], pExt->BeaconsPlacedOrder[2] }); |
| 723 | + pExt->BeaconsPlacedOrder[beaconIdx] = maxVal + 1; |
| 724 | + |
| 725 | + return 0; |
| 726 | +} |
| 727 | + |
| 728 | +DEFINE_HOOK(0x4AC9B2, MouseClass_ToggleBeaconMode_AllUsed, 0x6) |
| 729 | +{ |
| 730 | + GET(bool, canPlace, EAX); |
| 731 | + |
| 732 | + if (canPlace) |
| 733 | + return 0x4AC9B8; |
| 734 | + |
| 735 | + const auto pHouse = HouseClass::CurrentPlayer; |
| 736 | + const auto pExt = HouseExt::ExtMap.Find(pHouse); |
| 737 | + |
| 738 | + for (int i = 0; i < 3; ++i) |
| 739 | + { |
| 740 | + if (pExt->BeaconsPlacedOrder[i] == 1) |
| 741 | + { |
| 742 | + auto pManager = &BeaconManagerClass::Instance; |
| 743 | + auto pBeacon = pManager->Beacons[pHouse->ArrayIndex][i]; |
| 744 | + // Select and delete beacon. |
| 745 | + // If you don't select the beacon, the game will not send the IPX packet. |
| 746 | + MapClass::UnselectAll(); |
| 747 | + pBeacon->Bitfield |= 2; |
| 748 | + pManager->DeleteBeacon(-1, -1); |
| 749 | + break; |
| 750 | + } |
| 751 | + } |
| 752 | + |
| 753 | + return 0x4AC9B8; |
| 754 | +} |
| 755 | + |
| 756 | +#pragma endregion |
0 commit comments