#ifndef COCKATRICE_TAB_ARCHIDEKT_H #define COCKATRICE_TAB_ARCHIDEKT_H #include "../../interface/widgets/cards/card_size_widget.h" #include "../../interface/widgets/quick_settings/settings_button_widget.h" #include "../../tab.h" #include #include #include #include #include #include #include #include /** Base API link for Archidekt deck search */ inline QString archidektApiLink = "https://archidekt.com/api/decks/v3/?name="; /** * @brief Tab for browsing, searching, and filtering Archidekt decks. * * This class provides a comprehensive interface for querying decks from the Archidekt API. * Users can filter decks by name, owner, included cards, commanders, deck tags, colors, EDH bracket, * and formats. It also provides sorting and pagination, as well as a card size adjustment widget. */ class TabArchidekt : public Tab { Q_OBJECT public: /** * @brief Construct a new TabArchidekt object * @param _tabSupervisor Parent tab supervisor responsible for tab management and callbacks * * Initializes the network manager, creates all UI components, sets up layouts, * connects signals and slots, and triggers an initial fetch of top decks. */ explicit TabArchidekt(TabSupervisor *_tabSupervisor); /** * @brief Update all UI text to reflect the current language or translation * * This function re-applies translations to all labels, buttons, and placeholders. * It should be called after a language change. */ void retranslateUi() override; /** * @brief Construct the search URL from all current filters * @return QString Fully constructed URL including all query parameters * * The search URL is dynamically built using the state of all filter widgets. * Parameters included: * - Deck name * - Owner * - Included cards * - Commander cards * - Deck tag * - Colors and logical AND requirement * - Formats * - EDH bracket * - Packages toggle * - Sorting field and direction * - Pagination (page and page size) */ QString buildSearchUrl(); /** * @brief Trigger a search using the current filters * * Sends a network request to the Archidekt API using the URL generated by buildSearchUrl(). * Updates the current page display with results asynchronously. */ void doSearch(); /** * @brief Retrieve the tab display text * @return QString Human-readable title for the tab * * If a card is pre-selected (cardToQuery), its name is appended to the tab title. */ QString getTabText() const override { auto cardName = cardToQuery.isNull() ? QString() : cardToQuery->getName(); return tr("Archidekt: ") + cardName; } /** * @brief Get the card size slider widget * @return CardSizeWidget* Pointer to the card size adjustment slider * * Allows external code to read or manipulate the current card size or hook up the sliders signals. */ CardSizeWidget *getCardSizeSlider() { return cardSizeSlider; } /** @brief Network manager for handling API requests */ QNetworkAccessManager *networkManager; public slots: /** * @brief Process a network reply containing JSON data * @param reply QNetworkReply object with the API response * * Determines whether the response corresponds to a top decks query or a single deck, * and dispatches it to the appropriate handler. */ void processApiJson(QNetworkReply *reply); /** * @brief Handle a JSON response containing multiple decks * @param reply QJsonObject containing top deck listings * * Clears the previous page display and creates a new display widget for the results. */ void processTopDecksResponse(QJsonObject reply); /** * @brief Handle a JSON response for a single deck * @param reply QJsonObject containing deck data * * Clears the previous page display and creates a new display widget for the deck details. */ void processDeckResponse(QJsonObject reply); /** * @brief Pretty-print a QJsonValue for debugging * @param value The JSON value to print * @param indentLevel The indentation depth (number of levels) */ void prettyPrintJson(const QJsonValue &value, int indentLevel); /** * @brief Navigate to a specified page URL * @param url The URL to request * * Typically called when a navigation button is clicked in a deck listing. */ void actNavigatePage(QString url); /** * @brief Fetch top decks from the Archidekt API * * Called on initialization to populate the initial page display. */ void getTopDecks(); private: // --------------------------------------------------------------------- // Layout Containers // --------------------------------------------------------------------- QWidget *container; ///< Root container for the entire tab QVBoxLayout *mainLayout; ///< Outer vertical layout containing navigation and page display QWidget *navigationContainer; ///< Container for all navigation/filter controls QHBoxLayout *navigationLayout; ///< Layout for horizontal arrangement of filter widgets QWidget *currentPageDisplay; ///< Widget containing the currently displayed deck(s) QVBoxLayout *currentPageLayout; ///< Layout for deck display widgets // --------------------------------------------------------------------- // Sorting Controls // --------------------------------------------------------------------- QComboBox *orderByCombo; ///< Dropdown for selecting the sort field QPushButton *orderDirButton; ///< Toggle button for ascending/descending sort // --------------------------------------------------------------------- // Color Filters // --------------------------------------------------------------------- QSet activeColors; ///< Set of currently active mana colors QCheckBox *logicalAndCheck; ///< Require ALL selected colors instead of ANY // --------------------------------------------------------------------- // Format Filters // --------------------------------------------------------------------- QLabel *formatLabel; ///< Label displaying "Formats" SettingsButtonWidget *formatSettingsWidget; ///< Collapsible widget containing format checkboxes QVector formatChecks; ///< Individual checkboxes for each format // --------------------------------------------------------------------- // EDH Bracket / Package Toggle // --------------------------------------------------------------------- QComboBox *edhBracketCombo; ///< Dropdown for EDH bracket selection QCheckBox *packagesCheck; ///< Toggle for searching card packages instead of full decks // --------------------------------------------------------------------- // Basic Search Fields // --------------------------------------------------------------------- QLineEdit *nameField; ///< Input for deck name filter QLineEdit *ownerField; ///< Input for owner name filter // --------------------------------------------------------------------- // Card Filters // --------------------------------------------------------------------- QLineEdit *cardsField; ///< Input for cards included in the deck (comma-separated) QLineEdit *commandersField; ///< Input for commander cards (comma-separated) // --------------------------------------------------------------------- // Deck Tag // --------------------------------------------------------------------- QLineEdit *deckTagNameField; ///< Input for deck tag filtering // --------------------------------------------------------------------- // Search Trigger // --------------------------------------------------------------------- QPushButton *searchPushButton; ///< Button to trigger the search manually // --------------------------------------------------------------------- // UI Settings (Card Size) // --------------------------------------------------------------------- SettingsButtonWidget *settingsButton; ///< Container for additional UI settings CardSizeWidget *cardSizeSlider; ///< Slider to adjust card size in results // --------------------------------------------------------------------- // Minimum Cards in Deck // --------------------------------------------------------------------- QLabel *minDeckSizeLabel; ///< Label for minimum number of cards per deck QSpinBox *minDeckSizeSpin; ///< Spinner to select minimum deck size // --------------------------------------------------------------------- // Pagination // --------------------------------------------------------------------- QSpinBox *pageSpin; ///< Spinner to select the page number for results // --------------------------------------------------------------------- // Optional Context // --------------------------------------------------------------------- CardInfoPtr cardToQuery; ///< Optional pre-selected card for initial filtering }; #endif // COCKATRICE_TAB_ARCHIDEKT_H