1 /*
2 * mainwindow.h
3 * Copyright 2008-2015, Thorbjørn Lindeijer <thorbjorn@lindeijer.nl>
4 * Copyright 2008, Roderic Morris <roderic@ccs.neu.edu>
5 * Copyright 2009-2010, Jeff Bland <jksb@member.fsf.org>
6 * Copyright 2010-2011, Stefan Beller <stefanbeller@googlemail.com>
7 *
8 * This file is part of Tiled.
9 *
10 * This program is free software; you can redistribute it and/or modify it
11 * under the terms of the GNU General Public License as published by the Free
12 * Software Foundation; either version 2 of the License, or (at your option)
13 * any later version.
14 *
15 * This program is distributed in the hope that it will be useful, but WITHOUT
16 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
17 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
18 * more details.
19 *
20 * You should have received a copy of the GNU General Public License along with
21 * this program. If not, see <http://www.gnu.org/licenses/>.
22 */
23
24 #pragma once
25
26 #include "clipboardmanager.h"
27 #include "document.h"
28 #include "preferences.h"
29 #include "preferencesdialog.h"
30 #include "project.h"
31 #include "session.h"
32
33 #include <QMainWindow>
34 #include <QPointer>
35 #include <QSessionManager>
36
37 class QComboBox;
38 class QLabel;
39
40 namespace Ui {
41 class MainWindow;
42 }
43
44 namespace Tiled {
45
46 class FileFormat;
47 class TileLayer;
48
49 class AutomappingManager;
50 class ConsoleDock;
51 class DocumentManager;
52 class Editor;
53 class IssuesDock;
54 class LocatorWidget;
55 class MapDocument;
56 class MapDocumentActionHandler;
57 class MapEditor;
58 class MapScene;
59 class MapView;
60 class ObjectTypesEditor;
61 class ProjectDock;
62 class ProjectModel;
63 class TilesetDocument;
64 class TilesetEditor;
65 class Zoomable;
66
67 /**
68 * The main editor window.
69 *
70 * Represents the main user interface, including the menu bar. It keeps track
71 * of the current file and is also the entry point of all menu actions.
72 */
73 class MainWindow : public QMainWindow
74 {
75 Q_OBJECT
76
77 public:
78 MainWindow(QWidget *parent = nullptr, Qt::WindowFlags flags = {});
79 ~MainWindow() override;
80
81 void commitData(QSessionManager &manager);
82
83 void initializeSession();
84
85 /**
86 * Opens the given file. When opened successfully, the file is added to the
87 * list of recent files.
88 *
89 * When a \a format is given, it is used to open the file. Otherwise, a
90 * format is searched using MapFormat::supportsFile.
91 *
92 * @return whether the file was successfully opened
93 */
94 bool openFile(const QString &fileName, FileFormat *fileFormat = nullptr);
95
96 bool addRecentProjectsActions(QMenu *menu) const;
97
98 static MainWindow *instance();
99
100 protected:
101 bool event(QEvent *event) override;
102
103 void closeEvent(QCloseEvent *event) override;
104 void changeEvent(QEvent *event) override;
105
106 void keyPressEvent(QKeyEvent *) override;
107 void keyReleaseEvent(QKeyEvent *) override;
108
109 void dragEnterEvent(QDragEnterEvent *) override;
110 void dropEvent(QDropEvent *) override;
111
112 void resizeEvent(QResizeEvent *) override;
113
114 private:
115 void newMap();
116 void openFileDialog();
117 void openFileInProject();
118 bool saveFile();
119 bool saveFileAs();
120 void saveAll();
121 void export_(); // 'export' is a reserved word
122 bool exportDocument(Document *document);
123 void exportAs();
124 void exportAsImage();
125 void reload();
126 void closeFile();
127 bool closeAllFiles();
128
129 void openProject();
130 bool openProjectFile(const QString &fileName);
131 void saveProjectAs();
132 void closeProject();
133 bool switchProject(Project project);
134 void restoreSession();
135 void projectProperties();
136
137 void cut();
138 void copy();
139 void paste();
140 void pasteInPlace();
141 void delete_();
142 void openPreferences();
143 void openCrashReporterPopup();
144 void openProjectExtensionsPopup();
145
146 void showPopup(QWidget *widget);
147 void updatePopupGeometry(QSize size);
148
149 void labelVisibilityActionTriggered(QAction *action);
150 void zoomIn();
151 void zoomOut();
152 void zoomNormal();
153 void fitInView();
154 void setFullScreen(bool fullScreen);
155 void toggleClearView(bool clearView);
156 void setLayoutLocked(bool locked);
157 void resetToDefaultLayout();
158
159 bool newTileset(const QString &path = QString());
160 void reloadTilesetImages();
161 void addExternalTileset();
162 void resizeMap();
163 void offsetMap();
164 void editMapProperties();
165
166 void editTilesetProperties();
167
168 void updateWindowTitle();
169 void updateActions();
170 void updateZoomable();
171 void updateZoomActions();
172 void openDocumentation();
173 void openForum();
174 void showDonationPopup();
175 void aboutTiled();
176 void openRecentFile();
177 void reopenClosedFile();
178 void openRecentProject();
179
180 void documentChanged(Document *document);
181 void documentSaved(Document *document);
182 void closeDocument(int index);
183
184 void currentEditorChanged(Editor *editor);
185
186 void reloadError(const QString &error);
187 void autoMappingError(bool automatic);
188 void autoMappingWarning(bool automatic);
189
190 void onObjectTypesEditorClosed();
191
192 void ensureHasBorderInFullScreen();
193
194 /**
195 * Asks the user whether the given \a mapDocument should be saved, when
196 * necessary. If it needs to ask, also makes sure that it is the current
197 * document.
198 *
199 * @return <code>true</code> when any unsaved data is either discarded or
200 * saved, <code>false</code> when the user cancelled or saving
201 * failed.
202 */
203 bool confirmSave(Document *document);
204
205 /**
206 * Checks all maps for changes, if so, ask if to save these changes.
207 *
208 * @return <code>true</code> when any unsaved data is either discarded or
209 * saved, <code>false</code> when the user cancelled or saving
210 * failed.
211 */
212 bool confirmAllSave();
213
214 bool confirmSaveWorld(const QString &fileName);
215
216 void writeSettings();
217 void readSettings();
218
219 void updateRecentFilesMenu();
220 void updateRecentProjectsMenu();
221 void updateViewsAndToolbarsMenu();
222
223 void retranslateUi();
224
225 void exportMapAs(MapDocument *mapDocument);
226 void exportTilesetAs(TilesetDocument *tilesetDocument);
227
228 QList<QDockWidget*> allDockWidgets() const;
229 QList<QToolBar*> allToolBars() const;
230
231 Ui::MainWindow *mUi;
232 Document *mDocument = nullptr;
233 Zoomable *mZoomable = nullptr;
234 MapDocumentActionHandler *mActionHandler;
235 ConsoleDock *mConsoleDock;
236 ProjectDock *mProjectDock;
237 IssuesDock *mIssuesDock;
238 ObjectTypesEditor *mObjectTypesEditor;
239 QPointer<LocatorWidget> mLocatorWidget;
240 QPointer<QWidget> mPopupWidget;
241 double mPopupWidgetShowProgress = 1.0;
242
243 QAction *mRecentFiles[Preferences::MaxRecentFiles];
244
245 QMenu *mLayerMenu;
246 QMenu *mNewLayerMenu;
247 QMenu *mGroupLayerMenu;
248 QMenu *mViewsAndToolbarsMenu;
249 QAction *mViewsAndToolbarsAction;
250 QAction *mShowObjectTypesEditor;
251
252 QAction *mResetToDefaultLayout;
253 QAction *mLockLayout;
254
255 void setupQuickStamps();
256
257 AutomappingManager *mAutomappingManager;
258 DocumentManager *mDocumentManager;
259 MapEditor *mMapEditor;
260 TilesetEditor *mTilesetEditor;
261 QList<QWidget*> mEditorStatusBarWidgets;
262
263 QPointer<PreferencesDialog> mPreferencesDialog;
264
265 QMap<QMainWindow*, QByteArray> mMainWindowStates;
266
267 SessionOption<QStringList> mLoadedWorlds { "loadedWorlds" };
268
269 static MainWindow *mInstance;
270 };
271
instance()272 inline MainWindow *MainWindow::instance()
273 {
274 Q_ASSERT(mInstance);
275 return mInstance;
276 }
277
278 } // namespace Tiled
279