#pragma once #include "core/workspace/ProjectWorkspace.h" #include "main_window/RecentProjectHistory.h" #include #include #include #include #include #include #include class ToolOptionPopup; class QAction; class QCheckBox; class QComboBox; class QDockWidget; class QFormLayout; class QLabel; class QMenu; class QFrame; class QIcon; class QPushButton; class QSlider; class QStackedWidget; class QToolButton; class QTreeWidget; class QTreeWidgetItem; class QWidget; class EditorCanvas; class TimelineWidget; namespace gui { class BackgroundPropertySection; class EntityPropertySection; class ToolPropertySection; class EntityIntroPopup; class ResourceLibraryDock; } namespace core::library { class ResourceLibraryProvider; class FakeResourceLibraryProvider; class OnlineResourceLibraryProvider; } class MainWindow : public QMainWindow { Q_OBJECT public: explicit MainWindow(QWidget* parent = nullptr); protected: bool eventFilter(QObject* watched, QEvent* event) override; private slots: // 文件菜单槽函数 void onNewProject(); void onOpenProject(); void onSaveProject(); void onCloseProject(); // 编辑菜单槽函数 void onUndo(); void onRedo(); void onCopyObject(); void onPasteObject(); // 帮助菜单槽函数 void onAbout(); void onComputeDepth(); void onTogglePlay(bool on); void onInsertCombinedKey(); // 位置 + userScale void onProjectTreeItemClicked(QTreeWidgetItem* item, int column); private: void computeDepthAsync(); // UI 状态分三种: // - Welcome:未打开项目。只显示欢迎页,其它 dock 一律隐藏,视图开关禁用。 // - Editor:已打开项目。显示编辑页,按默认规则显示 dock,同时允许用户通过“视图”菜单控制。 // - Preview:预览展示。用于全流程完成后的展示(要求:项目已打开且背景不为空)。 enum class UiMode { Welcome, Editor, Preview }; void createMenus(); // 菜单和工具栏 void createFileMenu(); // 文件菜单 void createEditMenu(); // 编辑菜单 void createHelpMenu(); // 帮助菜单 void createViewMenu(); // 视图菜单 void createWindowMenu(); // 窗口菜单(资源库等) void createProjectTreeDock(); void createTimelineDock(); void createResourceLibraryDock(); void refreshProjectTree(); void updateUiEnabledState(); // 更新“可用性/勾选/默认显隐”,不要做业务逻辑 void applyUiMode(UiMode mode); // 统一控制 welcome/editor 两态的显隐策略 UiMode currentUiMode() const; // 根据 workspace 状态推导 void syncCanvasViewMenuFromState(); void showProjectRootContextMenu(const QPoint& globalPos); void showBackgroundContextMenu(const QPoint& globalPos); void rebuildCentralPages(); void showWelcomePage(); void showEditorPage(); void showPreviewPage(); void refreshWelcomeRecentList(); void openProjectFromPath(const QString& dir); void refreshPreviewPage(); void refreshEditorPage(); void applyTimelineFromProject(); void updateTimelineTracks(); void refreshDopeSheet(); void setPreviewRequested(bool preview); void syncPreviewPlaybackBar(); QStackedWidget* m_centerStack = nullptr; QWidget* m_pageWelcome = nullptr; QTreeWidget* m_welcomeRecentTree = nullptr; QLabel* m_welcomeRecentEmptyLabel = nullptr; QWidget* m_pageEditor = nullptr; QWidget* m_canvasHost = nullptr; QFrame* m_floatingModeDock = nullptr; QFrame* m_floatingToolDock = nullptr; QComboBox* m_modeSelector = nullptr; QStackedWidget* m_propertyStack = nullptr; gui::BackgroundPropertySection* m_bgPropertySection = nullptr; gui::EntityPropertySection* m_entityPropertySection = nullptr; gui::ToolPropertySection* m_toolPropertySection = nullptr; QToolButton* m_btnCreateEntity = nullptr; ToolOptionPopup* m_createEntityPopup = nullptr; QToolButton* m_btnToggleDepthOverlay = nullptr; EditorCanvas* m_editorCanvas = nullptr; QTreeWidget* m_projectTree = nullptr; QDockWidget* m_dockProjectTree = nullptr; QDockWidget* m_dockProperties = nullptr; QDockWidget* m_dockTimeline = nullptr; QDockWidget* m_dockResourceLibrary = nullptr; QTreeWidgetItem* m_itemBackground = nullptr; QAction* m_actionUndo = nullptr; QAction* m_actionRedo = nullptr; QAction* m_actionCopy = nullptr; QAction* m_actionPaste = nullptr; QAction* m_actionToggleProjectTree = nullptr; QAction* m_actionToggleProperties = nullptr; QAction* m_actionToggleTimeline = nullptr; QAction* m_actionToggleResourceLibrary = nullptr; QAction* m_actionEnterPreview = nullptr; QAction* m_actionBackToEditor = nullptr; QAction* m_actionCanvasWorldAxes = nullptr; QAction* m_actionCanvasAxisValues = nullptr; QAction* m_actionCanvasGrid = nullptr; QAction* m_actionCanvasCheckerboard = nullptr; QAction* m_actionCanvasDepthOverlay = nullptr; QAction* m_actionCanvasGizmoLabels = nullptr; core::ProjectWorkspace m_workspace; RecentProjectHistory m_recentHistory; bool m_previewRequested = false; /// 因右侧栏过窄自动收起;用户通过视图菜单再次打开时清除 bool m_rightDocksNarrowHidden = false; QPointF m_lastWorldPos; int m_lastWorldZ = -1; bool m_hasSelectedEntity = false; bool m_hasSelectedTool = false; bool m_syncingTreeSelection = false; int m_selectedEntityDepth = 0; QPointF m_selectedEntityOrigin; QString m_selectedEntityId; QString m_selectedToolId; QString m_selectedEntityDisplayNameCache; QString m_bgAbsCache; QString m_bgSizeTextCache; // 项目树“眼睛”:仅用于画布临时隐藏(不持久化、不进时间轴) QSet m_tempHiddenEntityIds; QSet m_tempHiddenToolIds; void updateStatusBarText(); void syncCreateEntityToolButtonTooltip(); void refreshPropertyPanel(); void refreshEntityPropertyPanelFast(); void syncProjectTreeFromCanvasSelection(); bool m_timelineScrubbing = false; bool m_entityDragging = false; QTimer* m_propertySyncTimer = nullptr; int m_currentFrame = 0; bool m_playing = false; QTimer* m_playTimer = nullptr; TimelineWidget* m_timeline = nullptr; QToolButton* m_btnPlay = nullptr; QComboBox* m_schemeSelector = nullptr; // 时间轴区间选择(用于逐帧贴图动画) int m_timelineRangeStart = -1; int m_timelineRangeEnd = -1; QCheckBox* m_chkAutoKeyframe = nullptr; // 旧版 DopeSheet 已移除,这里保留占位便于后续扩展区间 UI(如自定义小部件) QTreeWidget* m_dopeTree = nullptr; QPushButton* m_btnDopeDeleteKey = nullptr; gui::EntityIntroPopup* m_entityIntroPopup = nullptr; QFrame* m_previewPlaybackBar = nullptr; QToolButton* m_previewBtnPlay = nullptr; QToolButton* m_previewBtnPause = nullptr; gui::ResourceLibraryDock* m_resourceLibraryDockWidget = nullptr; core::library::ResourceLibraryProvider* m_resourceLibraryProvider = nullptr; };