[TabDeckEditor] Automatically sync view menu actions (#6522)

This commit is contained in:
RickyRister 2026-01-15 18:05:19 -08:00 committed by GitHub
parent 6213ccff48
commit 57e6c91689
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
11 changed files with 65 additions and 199 deletions

View file

@ -25,7 +25,6 @@ void DeckEditorCardDatabaseDockWidget::createDatabaseDisplayDock(AbstractTabDeck
setWidget(dockContents);
installEventFilter(deckEditor);
connect(this, &QDockWidget::topLevelChanged, deckEditor, &AbstractTabDeckEditor::dockTopLevelChanged);
// connect signals
connect(databaseDisplayWidget, &DeckEditorDatabaseDisplayWidget::cardChanged, deckEditor,

View file

@ -31,7 +31,6 @@ void DeckEditorCardInfoDockWidget::createCardInfoDock()
setWidget(cardInfoDockContents);
installEventFilter(deckEditor);
connect(this, &QDockWidget::topLevelChanged, deckEditor, &AbstractTabDeckEditor::dockTopLevelChanged);
}
void DeckEditorCardInfoDockWidget::updateCard(const ExactCard &_card)

View file

@ -46,7 +46,6 @@ DeckEditorDeckDockWidget::DeckEditorDeckDockWidget(AbstractTabDeckEditor *parent
setFeatures(QDockWidget::DockWidgetClosable | QDockWidget::DockWidgetFloatable | QDockWidget::DockWidgetMovable);
installEventFilter(deckEditor);
connect(this, &DeckEditorDeckDockWidget::topLevelChanged, deckEditor, &AbstractTabDeckEditor::dockTopLevelChanged);
createDeckDock();
}

View file

@ -80,7 +80,6 @@ void DeckEditorFilterDockWidget::createFiltersDock()
setWidget(filterDockContents);
installEventFilter(deckEditor);
connect(this, &QDockWidget::topLevelChanged, deckEditor, &AbstractTabDeckEditor::dockTopLevelChanged);
}
void DeckEditorFilterDockWidget::filterViewCustomContextMenu(const QPoint &point)

View file

@ -32,7 +32,6 @@ void DeckEditorPrintingSelectorDockWidget::createPrintingSelectorDock()
setWidget(printingSelectorDockContents);
installEventFilter(deckEditor);
connect(this, &QDockWidget::topLevelChanged, deckEditor, &AbstractTabDeckEditor::dockTopLevelChanged);
connect(printingSelector, &PrintingSelector::prevCardRequested, deckEditor->getDeckDockWidget(),
&DeckEditorDeckDockWidget::selectPrevCard);
connect(printingSelector, &PrintingSelector::nextCardRequested, deckEditor->getDeckDockWidget(),

View file

@ -77,16 +77,30 @@ AbstractTabDeckEditor::AbstractTabDeckEditor(TabSupervisor *_tabSupervisor) : Ta
&AbstractTabDeckEditor::refreshShortcuts);
}
void AbstractTabDeckEditor::registerDockWidget(QDockWidget *widget)
void AbstractTabDeckEditor::registerDockWidget(QMenu *_viewMenu, QDockWidget *widget)
{
QMenu *menu = viewMenu->addMenu(QString());
QMenu *menu = _viewMenu->addMenu(QString());
QAction *aVisible = menu->addAction(QString());
aVisible->setCheckable(true);
connect(aVisible, &QAction::triggered, this, &AbstractTabDeckEditor::dockVisibleTriggered);
QAction *aFloating = menu->addAction(QString());
aFloating->setCheckable(true);
connect(aFloating, &QAction::triggered, this, &AbstractTabDeckEditor::dockFloatingTriggered);
aFloating->setEnabled(false);
// user interaction
connect(aVisible, &QAction::triggered, widget, [widget](bool checked) { widget->setVisible(checked); });
connect(aFloating, &QAction::triggered, this, [widget](bool checked) { widget->setFloating(checked); });
// sync aFloating's enabled state with aVisible's checked state
connect(aVisible, &QAction::toggled, aFloating, [aFloating](bool checked) { aFloating->setEnabled(checked); });
// sync aFloating with dockWidget's floating state
connect(widget, &QDockWidget::topLevelChanged, aFloating,
[aFloating](bool topLevel) { aFloating->setChecked(topLevel); });
// sync aVisible with dockWidget's visible state
widget->installEventFilter(new DockWidgetVisibilityFilter(widget, aVisible));
dockToActions.insert(widget, {menu, aVisible, aFloating});
}
@ -594,3 +608,22 @@ bool AbstractTabDeckEditor::closeRequest()
return false;
return close();
}
DockWidgetVisibilityFilter::DockWidgetVisibilityFilter(QDockWidget *dockWidget, QAction *aVisible)
: QObject(dockWidget), dockWidget(dockWidget), aVisible(aVisible)
{
}
bool DockWidgetVisibilityFilter::eventFilter(QObject *o, QEvent *e)
{
if (o == dockWidget && !e->spontaneous()) {
if (e->type() == QEvent::Show) {
aVisible->setChecked(true);
}
if (e->type() == QEvent::Hide) {
aVisible->setChecked(false);
}
}
return false;
}

View file

@ -169,9 +169,6 @@ public slots:
/** @brief Shows the printing selector dock. Pure virtual. */
virtual void showPrintingSelector() = 0;
/** @brief Slot for when a dock's top-level state changes. Pure virtual. */
virtual void dockTopLevelChanged(bool topLevel) = 0;
signals:
/** @brief Emitted when a deck should be opened in a new editor tab. */
void openDeckEditor(const LoadedDeck &deck);
@ -246,12 +243,6 @@ protected slots:
/** @brief Handles dock close events. */
void closeEvent(QCloseEvent *event) override;
/** @brief Slot triggered when a dock visibility changes. Pure virtual. */
virtual void dockVisibleTriggered() = 0;
/** @brief Slot triggered when a dock floating state changes. Pure virtual. */
virtual void dockFloatingTriggered() = 0;
private:
/** @brief Sets the deck for this tab.
* @param _deck The deck object.
@ -289,7 +280,7 @@ protected:
* @brief registers a QDockWidget as a managed dock widget. Creates the associated actions and menu, adds them to
* the viewMenu, and connects those actions to the tab's slots.
*/
void registerDockWidget(QDockWidget *widget);
void registerDockWidget(QMenu *_viewMenu, QDockWidget *widget);
/** @brief Confirms deck open action based on settings and modified state.
* @param openInSameTabIfBlank Whether to reuse same tab if blank.
@ -316,4 +307,19 @@ protected:
QMap<QDockWidget *, DockActions> dockToActions;
};
/**
* This filter syncs the dock widget's visibility with the viewMenu visibility action's check state.
*/
class DockWidgetVisibilityFilter : public QObject
{
Q_OBJECT
QDockWidget *dockWidget;
QAction *aVisible;
public:
explicit DockWidgetVisibilityFilter(QDockWidget *dockWidget, QAction *aVisible);
bool eventFilter(QObject *o, QEvent *e) override;
};
#endif // TAB_GENERIC_DECK_EDITOR_H

View file

@ -54,11 +54,11 @@ void TabDeckEditor::createMenus()
viewMenu = new QMenu(this);
registerDockWidget(cardInfoDockWidget);
registerDockWidget(cardDatabaseDockWidget);
registerDockWidget(deckDockWidget);
registerDockWidget(filterDockWidget);
registerDockWidget(printingSelectorDockWidget);
registerDockWidget(viewMenu, cardInfoDockWidget);
registerDockWidget(viewMenu, cardDatabaseDockWidget);
registerDockWidget(viewMenu, deckDockWidget);
registerDockWidget(viewMenu, filterDockWidget);
registerDockWidget(viewMenu, printingSelectorDockWidget);
if (SettingsCache::instance().getOverrideAllCardArtWithPersonalPreference()) {
dockToActions[printingSelectorDockWidget].menu->setEnabled(false);
@ -130,7 +130,6 @@ void TabDeckEditor::showPrintingSelector()
{
printingSelectorDockWidget->printingSelector->setCard(cardInfoDockWidget->cardInfo->getCard().getCardPtr());
printingSelectorDockWidget->printingSelector->updateDisplay();
dockToActions[printingSelectorDockWidget].aVisible->setChecked(true);
printingSelectorDockWidget->setVisible(true);
}
@ -152,19 +151,9 @@ void TabDeckEditor::loadLayout()
if (SettingsCache::instance().getOverrideAllCardArtWithPersonalPreference()) {
if (!printingSelectorDockWidget->isHidden()) {
printingSelectorDockWidget->setHidden(true);
dockToActions[printingSelectorDockWidget].aVisible->setChecked(true);
}
}
for (auto it = dockToActions.begin(); it != dockToActions.end(); ++it) {
QDockWidget *dockWidget = it.key();
const DockActions &actions = it.value();
actions.aVisible->setChecked(!dockWidget->isHidden());
actions.aFloating->setEnabled(actions.aVisible->isChecked());
actions.aFloating->setChecked(dockWidget->isFloating());
}
cardInfoDockWidget->setMinimumSize(layouts.getDeckEditorCardSize());
cardInfoDockWidget->setMaximumSize(layouts.getDeckEditorCardSize());
@ -185,23 +174,13 @@ void TabDeckEditor::loadLayout()
*/
void TabDeckEditor::restartLayout()
{
// Update menu checkboxes
for (auto it = dockToActions.begin(); it != dockToActions.end(); ++it) {
QDockWidget *dockWidget = it.key();
const DockActions &actions = it.value();
actions.aVisible->setEnabled(true);
actions.aFloating->setEnabled(false);
// Show/hide and reset floating
// Show/hide and reset floating
for (auto dockWidget : dockToActions.keys()) {
dockWidget->setVisible(true);
dockWidget->setFloating(false);
}
// Printing selector special case
dockToActions[printingSelectorDockWidget].aVisible->setChecked(
!SettingsCache::instance().getOverrideAllCardArtWithPersonalPreference());
printingSelectorDockWidget->setVisible(!SettingsCache::instance().getOverrideAllCardArtWithPersonalPreference());
addDockWidget(Qt::LeftDockWidgetArea, cardDatabaseDockWidget);
@ -230,51 +209,6 @@ void TabDeckEditor::freeDocksSize()
}
}
/** @brief Handles dock visibility toggling from menu actions. */
void TabDeckEditor::dockVisibleTriggered()
{
QObject *o = sender();
for (auto it = dockToActions.begin(); it != dockToActions.end(); ++it) {
QDockWidget *dockWidget = it.key();
const DockActions &actions = it.value();
if (o == actions.aVisible) {
dockWidget->setHidden(!actions.aVisible->isChecked());
actions.aFloating->setEnabled(actions.aVisible->isChecked());
return;
}
}
}
/** @brief Handles dock floating toggling from menu actions. */
void TabDeckEditor::dockFloatingTriggered()
{
QObject *o = sender();
for (auto it = dockToActions.begin(); it != dockToActions.end(); ++it) {
QDockWidget *dockWidget = it.key();
const DockActions &actions = it.value();
if (o == actions.aFloating) {
dockWidget->setFloating(actions.aFloating->isChecked());
return;
}
}
}
/** @brief Syncs menu state with dock floating changes. */
void TabDeckEditor::dockTopLevelChanged(bool topLevel)
{
QObject *o = sender();
auto dockWidget = qobject_cast<QDockWidget *>(o);
if (dockToActions.contains(dockWidget)) {
DockActions actions = dockToActions.value(dockWidget);
actions.aFloating->setChecked(topLevel);
}
}
/**
* @brief Handles close/hide events to update menu state and save layout.
* @param o Object sending the event.
@ -283,15 +217,6 @@ void TabDeckEditor::dockTopLevelChanged(bool topLevel)
*/
bool TabDeckEditor::eventFilter(QObject *o, QEvent *e)
{
if (e->type() == QEvent::Close) {
auto dockWidget = qobject_cast<QDockWidget *>(o);
if (dockToActions.contains(dockWidget)) {
DockActions actions = dockToActions.value(dockWidget);
actions.aVisible->setChecked(false);
actions.aFloating->setEnabled(false);
}
}
if (o == this && e->type() == QEvent::Hide) {
LayoutsSettings &layouts = SettingsCache::instance().layouts();
layouts.setDeckEditorLayoutState(saveState());

View file

@ -70,9 +70,6 @@ protected slots:
/** @brief Handles dock visibility, floating, and top-level changes. */
bool eventFilter(QObject *o, QEvent *e) override;
void dockVisibleTriggered() override;
void dockFloatingTriggered() override;
void dockTopLevelChanged(bool topLevel) override;
public:
/**

View file

@ -97,10 +97,10 @@ void TabDeckEditorVisual::createMenus()
viewMenu = new QMenu(this);
registerDockWidget(cardInfoDockWidget);
registerDockWidget(deckDockWidget);
registerDockWidget(filterDockWidget);
registerDockWidget(printingSelectorDockWidget);
registerDockWidget(viewMenu, cardInfoDockWidget);
registerDockWidget(viewMenu, deckDockWidget);
registerDockWidget(viewMenu, filterDockWidget);
registerDockWidget(viewMenu, printingSelectorDockWidget);
if (SettingsCache::instance().getOverrideAllCardArtWithPersonalPreference()) {
dockToActions[printingSelectorDockWidget].menu->setEnabled(false);
@ -241,7 +241,6 @@ void TabDeckEditorVisual::showPrintingSelector()
{
printingSelectorDockWidget->printingSelector->setCard(cardInfoDockWidget->cardInfo->getCard().getCardPtr());
printingSelectorDockWidget->printingSelector->updateDisplay();
dockToActions[printingSelectorDockWidget].aVisible->setChecked(true);
printingSelectorDockWidget->setVisible(true);
}
@ -283,19 +282,9 @@ void TabDeckEditorVisual::loadLayout()
if (SettingsCache::instance().getOverrideAllCardArtWithPersonalPreference()) {
if (!printingSelectorDockWidget->isHidden()) {
printingSelectorDockWidget->setHidden(true);
dockToActions[printingSelectorDockWidget].aVisible->setChecked(false);
}
}
for (auto it = dockToActions.begin(); it != dockToActions.end(); ++it) {
QDockWidget *dockWidget = it.key();
const DockActions &actions = it.value();
actions.aVisible->setChecked(dockWidget->isHidden());
actions.aFloating->setEnabled(actions.aVisible->isChecked());
actions.aFloating->setChecked(dockWidget->isFloating());
}
cardInfoDockWidget->setMinimumSize(layouts.getDeckEditorCardSize());
cardInfoDockWidget->setMaximumSize(layouts.getDeckEditorCardSize());
@ -314,20 +303,10 @@ void TabDeckEditorVisual::loadLayout()
/** @brief Resets the layout to default positions and dock states. */
void TabDeckEditorVisual::restartLayout()
{
for (auto it = dockToActions.begin(); it != dockToActions.end(); ++it) {
QDockWidget *dockWidget = it.key();
const DockActions &actions = it.value();
actions.aFloating->setEnabled(false);
for (auto dockWidget : dockToActions.keys()) {
dockWidget->setFloating(false);
}
dockToActions[cardInfoDockWidget].aVisible->setChecked(true);
dockToActions[deckDockWidget].aVisible->setChecked(true);
dockToActions[filterDockWidget].aVisible->setChecked(false);
dockToActions[printingSelectorDockWidget].aVisible->setChecked(
!SettingsCache::instance().getOverrideAllCardArtWithPersonalPreference());
deckDockWidget->setVisible(true);
cardInfoDockWidget->setVisible(true);
filterDockWidget->setVisible(false);
@ -377,15 +356,6 @@ void TabDeckEditorVisual::retranslateUi()
*/
bool TabDeckEditorVisual::eventFilter(QObject *o, QEvent *e)
{
if (e->type() == QEvent::Close) {
auto dockWidget = qobject_cast<QDockWidget *>(o);
if (dockToActions.contains(dockWidget)) {
DockActions actions = dockToActions.value(dockWidget);
actions.aVisible->setChecked(false);
actions.aFloating->setEnabled(false);
}
}
if (o == this && e->type() == QEvent::Hide) {
LayoutsSettings &layouts = SettingsCache::instance().layouts();
layouts.setDeckEditorLayoutState(saveState());
@ -397,47 +367,3 @@ bool TabDeckEditorVisual::eventFilter(QObject *o, QEvent *e)
}
return false;
}
/** @brief Toggles dock visibility based on the corresponding menu action. */
void TabDeckEditorVisual::dockVisibleTriggered()
{
QObject *o = sender();
for (auto it = dockToActions.begin(); it != dockToActions.end(); ++it) {
QDockWidget *dockWidget = it.key();
const DockActions &actions = it.value();
if (o == actions.aVisible) {
dockWidget->setHidden(!actions.aVisible->isChecked());
actions.aFloating->setEnabled(actions.aVisible->isChecked());
return;
}
}
}
/** @brief Toggles dock floating state based on the corresponding menu action. */
void TabDeckEditorVisual::dockFloatingTriggered()
{
QObject *o = sender();
for (auto it = dockToActions.begin(); it != dockToActions.end(); ++it) {
QDockWidget *dockWidget = it.key();
const DockActions &actions = it.value();
if (o == actions.aFloating) {
dockWidget->setFloating(actions.aFloating->isChecked());
return;
}
}
}
/** @brief Updates menu checkboxes when a dock's top-level/floating state changes. */
void TabDeckEditorVisual::dockTopLevelChanged(bool topLevel)
{
QObject *o = sender();
auto dockWidget = qobject_cast<QDockWidget *>(o);
if (dockToActions.contains(dockWidget)) {
DockActions actions = dockToActions.value(dockWidget);
actions.aFloating->setChecked(topLevel);
}
}

View file

@ -84,22 +84,6 @@ protected slots:
*/
bool eventFilter(QObject *o, QEvent *e) override;
/**
* @brief Triggered when a dock visibility menu item is clicked.
*/
void dockVisibleTriggered() override;
/**
* @brief Triggered when a dock floating menu item is clicked.
*/
void dockFloatingTriggered() override;
/**
* @brief Triggered when a dock top-level state changes.
* @param topLevel True if the dock became floating.
*/
void dockTopLevelChanged(bool topLevel) override;
protected:
TabDeckEditorVisualTabWidget *tabContainer; ///< Tab container holding different visual widgets.