Cockatrice/libcockatrice_game/libcockatrice/game/zones/view_zone_logic.h
BruebachL ff393b8990
[Game] Connect zone dump response before sending the request (#7711)
ZoneViewZone::initializeCards() connected PendingCommand::finished only after ZoneViewZoneLogic::requestZoneDump() had already sent the command. Local games process the dump synchronously, so finished was emitted before the view connected and the library/sideboard view stayed empty.

Split requestZoneDump() into prepareZoneDump() and sendZoneDump(), and connect before sending, matching the TabRoom prepare/send convention.

Co-authored-by: Lukas Brübach <Bruebach.Lukas@bdosecurity.de>
2026-11-01 12:49:35 +01:00

111 lines
3 KiB
C++

/**
* @file view_zone_logic.h
* @ingroup GameLogicZones
*/
//! \todo Document this file.
#ifndef COCKATRICE_VIEW_ZONE_LOGIC_H
#define COCKATRICE_VIEW_ZONE_LOGIC_H
#include "card_zone_logic.h"
#include <qtmetamacros.h>
class PlayerLogic;
class QObject;
class PendingCommand;
class IInterfaceSettingsProvider;
class ZoneViewZoneLogic : public CardZoneLogic
{
Q_OBJECT
signals:
void addToViews();
void removeFromViews();
void closeView();
private:
CardZoneLogic *origZone;
int numberCards;
bool revealZone, writeableRevealZone;
bool isReversed;
// Borrowed settings provider (owned by the application). Null outside the client, in which case views stay open.
IInterfaceSettingsProvider *interfaceSettings;
public:
enum CardAction
{
INITIALIZE,
ADD_CARD,
REMOVE_CARD
};
ZoneViewZoneLogic(PlayerLogic *_player,
CardZoneLogic *_origZone,
int _numberCards,
bool _revealZone,
bool _writeableRevealZone,
bool _isReversed,
IInterfaceSettingsProvider *interfaceSettings = nullptr,
QObject *parent = nullptr);
bool prepareAddCard(int x);
void removeCard(int position, bool toNewZone);
void updateCardIds(CardAction action);
/**
* @brief Asks the graphics view showing this zone to close itself.
*
* Logic code has no handle on the view, so it goes through the logic object the view was built from.
*/
void requestClose();
/** @brief Removes all cards from the view, without touching anything else. Used in replay rewind */
void clearCards();
[[nodiscard]] bool getCloseEmptyCardView() const;
int getNumberCards() const
{
return numberCards;
}
bool getRevealZone() const
{
return revealZone;
}
bool getWriteableRevealZone() const
{
return writeableRevealZone;
}
void setWriteableRevealZone(bool _writeableRevealZone);
bool getIsReversed() const
{
return isReversed;
}
CardZoneLogic *getOriginalZone() const
{
return origZone;
}
/**
* @brief Builds the zone-dump command for this view without sending it.
* @return The pending command, or nullptr when there is no zone to dump.
*
* Keeps command construction in game/ so graphics views don't reach
* through the player into PlayerActions to set it up. The response can
* arrive synchronously (local games), so callers must connect to
* PendingCommand::finished before calling sendZoneDump().
*/
PendingCommand *prepareZoneDump();
/**
* @brief Sends a command returned by prepareZoneDump().
* @param pendingCommand The prepared command; nullptr is ignored.
*/
void sendZoneDump(PendingCommand *pendingCommand);
protected:
void addCardImpl(CardState *card, int x, int y) override;
};
#endif // COCKATRICE_VIEW_ZONE_LOGIC_H