Do not open card reveal windows when skipping in replays (#5157)

* create EventProcessingOption QFlag

* pass EventProcessingOption all the way down

* implement reveal skipping logic
This commit is contained in:
RickyRister 2024-11-08 17:06:23 -08:00 committed by GitHub
parent dd04c610ec
commit e894e78346
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
7 changed files with 58 additions and 22 deletions

View file

@ -93,7 +93,7 @@ void ReplayTimelineWidget::skipToTime(int newTime, bool doRewindBuffering)
if (isBackwardsSkip) { if (isBackwardsSkip) {
handleBackwardsSkip(doRewindBuffering); handleBackwardsSkip(doRewindBuffering);
} else { } else {
processNewEvents(); processNewEvents(FORWARD_SKIP);
} }
update(); update();
@ -130,7 +130,7 @@ void ReplayTimelineWidget::processRewind()
// process the rewind // process the rewind
currentEvent = 0; currentEvent = 0;
emit rewound(); emit rewound();
processNewEvents(); processNewEvents(BACKWARD_SKIP);
} }
QSize ReplayTimelineWidget::sizeHint() const QSize ReplayTimelineWidget::sizeHint() const
@ -147,17 +147,24 @@ void ReplayTimelineWidget::replayTimerTimeout()
{ {
currentTime += 200; currentTime += 200;
processNewEvents(); processNewEvents(NORMAL_PLAYBACK);
if (!(currentTime % 1000)) if (!(currentTime % 1000))
update(); update();
} }
/// Processes all unprocessed events up to the current time. /// Processes all unprocessed events up to the current time.
void ReplayTimelineWidget::processNewEvents() void ReplayTimelineWidget::processNewEvents(PlaybackMode playbackMode)
{ {
while ((currentEvent < replayTimeline.size()) && (replayTimeline[currentEvent] < currentTime)) { while ((currentEvent < replayTimeline.size()) && (replayTimeline[currentEvent] < currentTime)) {
emit processNextEvent(); Player::EventProcessingOptions options;
// backwards skip => always skip reveal windows
// forwards skip => skip reveal windows that don't happen within 10 seconds of the target
if (playbackMode == BACKWARD_SKIP || currentTime - replayTimeline[currentEvent] > 10000)
options |= Player::EventProcessingOption::SKIP_REVEAL_WINDOW;
emit processNextEvent(options);
++currentEvent; ++currentEvent;
} }
if (currentEvent == replayTimeline.size()) { if (currentEvent == replayTimeline.size()) {

View file

@ -1,6 +1,8 @@
#ifndef REPLAY_TIMELINE_WIDGET #ifndef REPLAY_TIMELINE_WIDGET
#define REPLAY_TIMELINE_WIDGET #define REPLAY_TIMELINE_WIDGET
#include "../../game/player/player.h"
#include <QList> #include <QList>
#include <QMouseEvent> #include <QMouseEvent>
#include <QWidget> #include <QWidget>
@ -12,11 +14,18 @@ class ReplayTimelineWidget : public QWidget
{ {
Q_OBJECT Q_OBJECT
signals: signals:
void processNextEvent(); void processNextEvent(Player::EventProcessingOptions options);
void replayFinished(); void replayFinished();
void rewound(); void rewound();
private: private:
enum PlaybackMode
{
NORMAL_PLAYBACK,
FORWARD_SKIP,
BACKWARD_SKIP
};
QTimer *replayTimer; QTimer *replayTimer;
static constexpr int BASE_REWIND_BUFFERING_TIMEOUT_MS = 180; static constexpr int BASE_REWIND_BUFFERING_TIMEOUT_MS = 180;
static constexpr int MAX_REWIND_BUFFERING_TIMEOUT_MS = 280; static constexpr int MAX_REWIND_BUFFERING_TIMEOUT_MS = 280;
@ -33,7 +42,7 @@ private:
void handleBackwardsSkip(bool doRewindBuffering); void handleBackwardsSkip(bool doRewindBuffering);
int calcRewindBufferingTimeout() const; int calcRewindBufferingTimeout() const;
void processRewind(); void processRewind();
void processNewEvents(); void processNewEvents(PlaybackMode playbackMode);
private slots: private slots:
void replayTimerTimeout(); void replayTimerTimeout();

View file

@ -614,9 +614,9 @@ void TabGame::closeRequest()
actLeaveGame(); actLeaveGame();
} }
void TabGame::replayNextEvent() void TabGame::replayNextEvent(Player::EventProcessingOptions options)
{ {
processGameEventContainer(replay->event_list(timelineWidget->getCurrentEvent()), nullptr); processGameEventContainer(replay->event_list(timelineWidget->getCurrentEvent()), nullptr, options);
} }
void TabGame::replayFinished() void TabGame::replayFinished()
@ -862,7 +862,9 @@ Player *TabGame::addPlayer(int playerId, const ServerInfo_User &info)
return newPlayer; return newPlayer;
} }
void TabGame::processGameEventContainer(const GameEventContainer &cont, AbstractClient *client) void TabGame::processGameEventContainer(const GameEventContainer &cont,
AbstractClient *client,
Player::EventProcessingOptions options)
{ {
const GameEventContext &context = cont.context(); const GameEventContext &context = cont.context();
messageLog->containerProcessingStarted(context); messageLog->containerProcessingStarted(context);
@ -937,7 +939,7 @@ void TabGame::processGameEventContainer(const GameEventContainer &cont, Abstract
qDebug() << "unhandled game event: invalid player id"; qDebug() << "unhandled game event: invalid player id";
break; break;
} }
player->processGameEvent(eventType, event, context); player->processGameEvent(eventType, event, context, options);
emitUserEvent(); emitUserEvent();
} }
} }
@ -1731,7 +1733,8 @@ void TabGame::createReplayDock()
// timeline widget // timeline widget
timelineWidget = new ReplayTimelineWidget; timelineWidget = new ReplayTimelineWidget;
timelineWidget->setTimeline(replayTimeline); timelineWidget->setTimeline(replayTimeline);
connect(timelineWidget, SIGNAL(processNextEvent()), this, SLOT(replayNextEvent())); connect(timelineWidget, SIGNAL(processNextEvent(Player::EventProcessingOptions)), this,
SLOT(replayNextEvent(Player::EventProcessingOptions)));
connect(timelineWidget, SIGNAL(replayFinished()), this, SLOT(replayFinished())); connect(timelineWidget, SIGNAL(replayFinished()), this, SLOT(replayFinished()));
connect(timelineWidget, &ReplayTimelineWidget::rewound, this, &TabGame::replayRewind); connect(timelineWidget, &ReplayTimelineWidget::rewound, this, &TabGame::replayRewind);

View file

@ -2,6 +2,7 @@
#define TAB_GAME_H #define TAB_GAME_H
#include "../../client/tearoff_menu.h" #include "../../client/tearoff_menu.h"
#include "../../game/player/player.h"
#include "pb/event_leave.pb.h" #include "pb/event_leave.pb.h"
#include "pb/serverinfo_game.pb.h" #include "pb/serverinfo_game.pb.h"
#include "tab.h" #include "tab.h"
@ -47,7 +48,6 @@ class Event_Ping;
class Event_GameSay; class Event_GameSay;
class Event_Kicked; class Event_Kicked;
class Event_ReverseTurn; class Event_ReverseTurn;
class Player;
class CardZone; class CardZone;
class AbstractCardItem; class AbstractCardItem;
class CardItem; class CardItem;
@ -221,7 +221,7 @@ signals:
void openDeckEditor(const DeckLoader *deck); void openDeckEditor(const DeckLoader *deck);
void notIdle(); void notIdle();
private slots: private slots:
void replayNextEvent(); void replayNextEvent(Player::EventProcessingOptions options);
void replayFinished(); void replayFinished();
void replayPlayButtonToggled(bool checked); void replayPlayButtonToggled(bool checked);
void replayFastForwardButtonToggled(bool checked); void replayFastForwardButtonToggled(bool checked);
@ -307,7 +307,9 @@ public:
return activeCard; return activeCard;
} }
void processGameEventContainer(const GameEventContainer &cont, AbstractClient *client); void processGameEventContainer(const GameEventContainer &cont,
AbstractClient *client,
Player::EventProcessingOptions options);
PendingCommand *prepareGameCommand(const ::google::protobuf::Message &cmd); PendingCommand *prepareGameCommand(const ::google::protobuf::Message &cmd);
PendingCommand *prepareGameCommand(const QList<const ::google::protobuf::Message *> &cmdList); PendingCommand *prepareGameCommand(const QList<const ::google::protobuf::Message *> &cmdList);
public slots: public slots:

View file

@ -541,7 +541,7 @@ void TabSupervisor::processGameEventContainer(const GameEventContainer &cont)
{ {
TabGame *tab = gameTabs.value(cont.game_id()); TabGame *tab = gameTabs.value(cont.game_id());
if (tab) if (tab)
tab->processGameEventContainer(cont, qobject_cast<AbstractClient *>(sender())); tab->processGameEventContainer(cont, qobject_cast<AbstractClient *>(sender()), {});
else else
qDebug() << "gameEvent: invalid gameId"; qDebug() << "gameEvent: invalid gameId";
} }

View file

@ -2341,7 +2341,7 @@ void Player::eventDrawCards(const Event_DrawCards &event)
emit logDrawCards(this, event.number(), _deck->getCards().size() == 0); emit logDrawCards(this, event.number(), _deck->getCards().size() == 0);
} }
void Player::eventRevealCards(const Event_RevealCards &event) void Player::eventRevealCards(const Event_RevealCards &event, EventProcessingOptions options)
{ {
CardZone *zone = zones.value(QString::fromStdString(event.zone_name())); CardZone *zone = zones.value(QString::fromStdString(event.zone_name()));
if (!zone) { if (!zone) {
@ -2388,7 +2388,7 @@ void Player::eventRevealCards(const Event_RevealCards &event)
showZoneView = false; showZoneView = false;
} }
} }
if (showZoneView && !cardList.isEmpty()) { if (!options.testFlag(SKIP_REVEAL_WINDOW) && showZoneView && !cardList.isEmpty()) {
static_cast<GameScene *>(scene())->addRevealedZoneView(this, zone, cardList, event.grant_write_access()); static_cast<GameScene *>(scene())->addRevealedZoneView(this, zone, cardList, event.grant_write_access());
} }
@ -2415,7 +2415,10 @@ void Player::eventChangeZoneProperties(const Event_ChangeZoneProperties &event)
} }
} }
void Player::processGameEvent(GameEvent::GameEventType type, const GameEvent &event, const GameEventContext &context) void Player::processGameEvent(GameEvent::GameEventType type,
const GameEvent &event,
const GameEventContext &context,
EventProcessingOptions options)
{ {
switch (type) { switch (type) {
case GameEvent::GAME_SAY: case GameEvent::GAME_SAY:
@ -2470,7 +2473,7 @@ void Player::processGameEvent(GameEvent::GameEventType type, const GameEvent &ev
eventDrawCards(event.GetExtension(Event_DrawCards::ext)); eventDrawCards(event.GetExtension(Event_DrawCards::ext));
break; break;
case GameEvent::REVEAL_CARDS: case GameEvent::REVEAL_CARDS:
eventRevealCards(event.GetExtension(Event_RevealCards::ext)); eventRevealCards(event.GetExtension(Event_RevealCards::ext), options);
break; break;
case GameEvent::CHANGE_ZONE_PROPERTIES: case GameEvent::CHANGE_ZONE_PROPERTIES:
eventChangeZoneProperties(event.GetExtension(Event_ChangeZoneProperties::ext)); eventChangeZoneProperties(event.GetExtension(Event_ChangeZoneProperties::ext));

View file

@ -226,6 +226,13 @@ private slots:
void initSayMenu(); void initSayMenu();
public:
enum EventProcessingOption
{
SKIP_REVEAL_WINDOW = 0x0001
};
Q_DECLARE_FLAGS(EventProcessingOptions, EventProcessingOption)
private: private:
TabGame *game; TabGame *game;
QMenu *sbMenu, *countersMenu, *sayMenu, *createPredefinedTokenMenu, *mRevealLibrary, *mLendLibrary, *mRevealTopCard, QMenu *sbMenu, *countersMenu, *sayMenu, *createPredefinedTokenMenu, *mRevealLibrary, *mLendLibrary, *mRevealTopCard,
@ -332,7 +339,7 @@ private:
void eventDestroyCard(const Event_DestroyCard &event); void eventDestroyCard(const Event_DestroyCard &event);
void eventAttachCard(const Event_AttachCard &event); void eventAttachCard(const Event_AttachCard &event);
void eventDrawCards(const Event_DrawCards &event); void eventDrawCards(const Event_DrawCards &event);
void eventRevealCards(const Event_RevealCards &event); void eventRevealCards(const Event_RevealCards &event, EventProcessingOptions options);
void eventChangeZoneProperties(const Event_ChangeZoneProperties &event); void eventChangeZoneProperties(const Event_ChangeZoneProperties &event);
void cmdSetTopCard(Command_MoveCard &cmd); void cmdSetTopCard(Command_MoveCard &cmd);
void cmdSetBottomCard(Command_MoveCard &cmd); void cmdSetBottomCard(Command_MoveCard &cmd);
@ -470,7 +477,10 @@ public:
void processPlayerInfo(const ServerInfo_Player &info); void processPlayerInfo(const ServerInfo_Player &info);
void processCardAttachment(const ServerInfo_Player &info); void processCardAttachment(const ServerInfo_Player &info);
void processGameEvent(GameEvent::GameEventType type, const GameEvent &event, const GameEventContext &context); void processGameEvent(GameEvent::GameEventType type,
const GameEvent &event,
const GameEventContext &context,
EventProcessingOptions options);
PendingCommand *prepareGameCommand(const ::google::protobuf::Message &cmd); PendingCommand *prepareGameCommand(const ::google::protobuf::Message &cmd);
PendingCommand *prepareGameCommand(const QList<const ::google::protobuf::Message *> &cmdList); PendingCommand *prepareGameCommand(const QList<const ::google::protobuf::Message *> &cmdList);
@ -480,6 +490,8 @@ public:
void setLastToken(CardInfoPtr cardInfo); void setLastToken(CardInfoPtr cardInfo);
}; };
Q_DECLARE_OPERATORS_FOR_FLAGS(Player::EventProcessingOptions)
class AnnotationDialog : public QInputDialog class AnnotationDialog : public QInputDialog
{ {
Q_OBJECT Q_OBJECT