Monopoly — Portage moderne 0.1.0
Portage moderne C/C++23 du Monopoly de 1999
Loading...
Searching...
No Matches
AuctionUI.cpp
Go to the documentation of this file.
1#include "AuctionUI.hpp"
2
3#include "IBarLayout.hpp"
4
5#include <algorithm>
6#include <limits>
7
9{
10 namespace
11 {
12 constexpr std::uint8_t AuctionHouse = 40;
13 constexpr std::uint8_t AuctionHotel = 41;
14 constexpr std::uint32_t ValidPlayerMask =
15 (1u << rules::MaxPlayers) - 1u;
16
17 [[nodiscard]] std::uint32_t playerMask(std::int64_t value) noexcept
18 {
19 return static_cast<std::uint32_t>(value) & ValidPlayerMask;
20 }
21
22 [[nodiscard]] int propertyForSale(std::int64_t square) noexcept
23 {
24 if (square == AuctionHouse) return 28;
25 if (square == AuctionHotel) return 29;
26 if (square < 0 || square >= static_cast<std::int64_t>(rules::SquareCount))
27 return -1;
28 return ibar::layout::propertyIndex(static_cast<int>(square));
29 }
30
31 void initializeLayout(State& state, rules::PlayerNumber numberOfPlayers) noexcept
32 {
33 state.backdropCenterX.fill(0);
34 const int count = std::min<int>(numberOfPlayers, rules::MaxPlayers);
35 const int spacingWidth = count > 4 ? BackdropSmallWidth : 201;
36 state.backdropWidth = count > 4 ? BackdropSmallWidth : BackdropBigWidth;
37 const int spacing = (800 - count * spacingWidth) / (count + 1);
38 for (int player = 0; player < count; ++player)
39 state.backdropCenterX[static_cast<std::size_t>(player)] =
40 spacing + player * (spacingWidth + spacing) + spacingWidth / 2;
41 }
42 }
43
44 void reset(State& state) noexcept
45 {
46 state = {};
47 }
48
50 State& state,
52 const actions::Message& message,
54 {
55 RuleUpdate update{};
56
57 if (message.action == actions::Type::NotifyAreYouThere)
58 {
59 if (message.numberC == static_cast<std::int64_t>(
61 {
62 state.rollCallPlayers = playerMask(message.numberA);
63 state.rollCallSerial = message.numberB;
64 }
65 return update;
66 }
67
68 if (message.action != actions::Type::NotifyAuctionGoing &&
69 message.action != actions::Type::NotifyNewHighBid)
70 return update;
71
72 state.playersAllowedInAuction = playerMask(message.numberE);
73 state.highestBid = message.numberB;
74
75 if (message.action == actions::Type::NotifyAuctionGoing)
76 {
78 return update;
79
80 switch (message.numberD)
81 {
82 case 1:
83 state.nextPennyBags = PennyBagsState::GoingOnce;
84 state.pennyBagsSwitch = true;
85 break;
86 case 2:
87 state.nextPennyBags = PennyBagsState::GoingTwice;
88 state.pennyBagsSwitch = true;
89 break;
90 case 3:
91 state.nextPennyBags = PennyBagsState::Sold;
92 state.pennyBagsSwitch = true;
93 state.thirdGoingReceived = true;
94 break;
95 default:
96 break;
97 }
98 return update;
99 }
100
101 if (message.numberA == rules::BankPlayer)
102 {
103 initializeLayout(state, gameState.numberOfPlayers);
104 state.bids.fill(0);
105 state.highestBidder.reset();
106 state.playersAllowedToBid = playerMask(message.numberE);
107 state.propertyForSale = propertyForSale(message.numberC);
108
110 state.thirdGoingReceived)
111 {
113 state.formerView = desiredView;
114 state.nextPennyBags = PennyBagsState::Intro;
115 state.pennyBagsSwitch = true;
116 state.thirdGoingReceived = false;
117 update.requestedBackdrop = display::Screen2D::Auction;
118 update.auctionStarted = true;
119 }
120 return update;
121 }
122
123 if (message.numberA >= 0 &&
124 message.numberA < rules::BankPlayer)
125 {
126 const auto player = static_cast<rules::PlayerNumber>(message.numberA);
127 state.bids[player] = state.highestBid;
128 state.highestBidder = player;
130 state.pennyBagsSwitch = true;
131 }
132
133 return update;
134 }
135
137 const State& state,
138 rules::PlayerNumber numberOfPlayers,
140 rules::PlayerNumber player) noexcept
141 {
143 player >= numberOfPlayers || player >= rules::MaxPlayers)
144 return false;
145 return (state.playersAllowedToBid & (1u << player)) != 0;
146 }
147
148 std::optional<BidRequest> planBid(
149 const State& state,
150 rules::PlayerNumber numberOfPlayers,
152 const uimsg::Message& message,
153 std::uint32_t localHumanMask) noexcept
154 {
155 if (message.type != uimsg::Type::MouseLeftDown ||
157 return std::nullopt;
158
159 const int x = static_cast<int>(message.numberA);
160 const int y = static_cast<int>(message.numberB);
162 return std::nullopt;
163
164 const auto count = std::min<rules::PlayerNumber>(
165 numberOfPlayers, rules::MaxPlayers);
166 for (rules::PlayerNumber player = 0; player < count; ++player)
167 {
168 const auto bit = 1u << player;
169 if ((localHumanMask & bit) == 0 ||
170 !playerPanelWanted(state, numberOfPlayers, desiredView, player))
171 continue;
172
173 const int firstBillX = state.backdropCenterX[player] -
174 BillTrayWidth / 2 + 2;
175 for (std::uint8_t bill = 0;
177 {
178 const int left = firstBillX + BillWidth * bill;
179 const int right = left + BillWidth;
180 if (x < left || x >= right) continue;
181 const auto increment = BillDenominations[bill];
182 if (state.highestBid >
183 std::numeric_limits<std::int64_t>::max() - increment)
184 return std::nullopt;
185 return BidRequest{player, state.highestBid + increment, bill};
186 }
187 }
188 return std::nullopt;
189 }
190}
std::size_t count
std::atomic< float > left
std::atomic< float > right
unsigned state
unsigned index
std::uint16_t value
Definition Timers.cpp:16
constexpr int BillTrayWidth
Definition AuctionUI.hpp:22
constexpr std::size_t BillCount
Definition AuctionUI.hpp:15
constexpr int BackdropBigWidth
Definition AuctionUI.hpp:21
constexpr int BackdropSmallWidth
Definition AuctionUI.hpp:20
constexpr int BillHeight
Definition AuctionUI.hpp:24
constexpr int BillTraysY
Definition AuctionUI.hpp:28
bool playerPanelWanted(const State &state, rules::PlayerNumber numberOfPlayers, display::Screen2D desiredView, rules::PlayerNumber player) noexcept
constexpr int BillWidth
Definition AuctionUI.hpp:23
std::optional< BidRequest > planBid(const State &state, rules::PlayerNumber numberOfPlayers, display::Screen2D desiredView, const uimsg::Message &message, std::uint32_t localHumanMask) noexcept
void reset(State &state) noexcept
Definition AuctionUI.cpp:44
RuleUpdate processRuleMessage(State &state, const rules::GameState &gameState, const actions::Message &message, display::Screen2D desiredView) noexcept
Definition AuctionUI.cpp:49
constexpr std::array< std::int64_t, BillCount > BillDenominations
Definition AuctionUI.hpp:16
int propertyIndex(int square) noexcept
constexpr PlayerNumber BankPlayer
Definition RuleTypes.hpp:15
std::uint8_t PlayerNumber
Definition RuleTypes.hpp:12
constexpr std::size_t SquareCount
Definition RuleTypes.hpp:24
constexpr PlayerNumber MaxPlayers
Definition RuleTypes.hpp:14