1 | /**************************************************************************** |
2 | ** |
3 | ** Copyright (C) 2016 The Qt Company Ltd. |
4 | ** Contact: https://www.qt.io/licensing/ |
5 | ** |
6 | ** This file is part of the examples of the Qt Toolkit. |
7 | ** |
8 | ** $QT_BEGIN_LICENSE:BSD$ |
9 | ** Commercial License Usage |
10 | ** Licensees holding valid commercial Qt licenses may use this file in |
11 | ** accordance with the commercial license agreement provided with the |
12 | ** Software or, alternatively, in accordance with the terms contained in |
13 | ** a written agreement between you and The Qt Company. For licensing terms |
14 | ** and conditions see https://www.qt.io/terms-conditions. For further |
15 | ** information use the contact form at https://www.qt.io/contact-us. |
16 | ** |
17 | ** BSD License Usage |
18 | ** Alternatively, you may use this file under the terms of the BSD license |
19 | ** as follows: |
20 | ** |
21 | ** "Redistribution and use in source and binary forms, with or without |
22 | ** modification, are permitted provided that the following conditions are |
23 | ** met: |
24 | ** * Redistributions of source code must retain the above copyright |
25 | ** notice, this list of conditions and the following disclaimer. |
26 | ** * Redistributions in binary form must reproduce the above copyright |
27 | ** notice, this list of conditions and the following disclaimer in |
28 | ** the documentation and/or other materials provided with the |
29 | ** distribution. |
30 | ** * Neither the name of The Qt Company Ltd nor the names of its |
31 | ** contributors may be used to endorse or promote products derived |
32 | ** from this software without specific prior written permission. |
33 | ** |
34 | ** |
35 | ** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS |
36 | ** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT |
37 | ** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR |
38 | ** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT |
39 | ** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, |
40 | ** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT |
41 | ** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, |
42 | ** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY |
43 | ** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
44 | ** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |
45 | ** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE." |
46 | ** |
47 | ** $QT_END_LICENSE$ |
48 | ** |
49 | ****************************************************************************/ |
50 | |
51 | #include "locationdialog.h" |
52 | #include "mainwindow.h" |
53 | #include "settingstree.h" |
54 | |
55 | #include <QAction> |
56 | #include <QApplication> |
57 | #include <QFileDialog> |
58 | #include <QInputDialog> |
59 | #include <QLineEdit> |
60 | #include <QMenuBar> |
61 | #include <QMessageBox> |
62 | #include <QScreen> |
63 | #include <QStandardPaths> |
64 | #include <QStatusBar> |
65 | |
66 | MainWindow::MainWindow(QWidget *parent) : QMainWindow(parent) |
67 | , settingsTree(new SettingsTree) |
68 | { |
69 | setCentralWidget(settingsTree); |
70 | |
71 | createActions(); |
72 | |
73 | autoRefreshAct->setChecked(true); |
74 | fallbacksAct->setChecked(true); |
75 | |
76 | setWindowTitle(QCoreApplication::applicationName()); |
77 | const QRect availableGeometry = screen()->availableGeometry(); |
78 | adjustSize(); |
79 | move(ax: (availableGeometry.width() - width()) / 2, ay: (availableGeometry.height() - height()) / 2); |
80 | } |
81 | |
82 | void MainWindow::openSettings() |
83 | { |
84 | if (!locationDialog) |
85 | locationDialog = new LocationDialog(this); |
86 | |
87 | if (locationDialog->exec() != QDialog::Accepted) |
88 | return; |
89 | |
90 | SettingsPtr settings(new QSettings(locationDialog->format(), |
91 | locationDialog->scope(), |
92 | locationDialog->organization(), |
93 | locationDialog->application())); |
94 | |
95 | setSettingsObject(settings); |
96 | fallbacksAct->setEnabled(true); |
97 | } |
98 | |
99 | void MainWindow::openIniFile() |
100 | { |
101 | const QString directory = QStandardPaths::writableLocation(type: QStandardPaths::ConfigLocation); |
102 | const QString fileName = |
103 | QFileDialog::getOpenFileName(parent: this, caption: tr(s: "Open INI File" ), |
104 | dir: directory, filter: tr(s: "INI Files (*.ini *.conf)" )); |
105 | if (fileName.isEmpty()) |
106 | return; |
107 | |
108 | SettingsPtr settings(new QSettings(fileName, QSettings::IniFormat)); |
109 | |
110 | setSettingsObject(settings); |
111 | fallbacksAct->setEnabled(false); |
112 | } |
113 | |
114 | void MainWindow::openPropertyList() |
115 | { |
116 | const QString directory = QStandardPaths::writableLocation(type: QStandardPaths::ConfigLocation); |
117 | const QString fileName = |
118 | QFileDialog::getOpenFileName(parent: this, caption: tr(s: "Open Property List" ), |
119 | dir: directory, filter: tr(s: "Property List Files (*.plist)" )); |
120 | if (fileName.isEmpty()) |
121 | return; |
122 | |
123 | SettingsPtr settings(new QSettings(fileName, QSettings::NativeFormat)); |
124 | setSettingsObject(settings); |
125 | fallbacksAct->setEnabled(false); |
126 | } |
127 | |
128 | void MainWindow::openRegistryPath() |
129 | { |
130 | const QString path = |
131 | QInputDialog::getText(parent: this, title: tr(s: "Open Registry Path" ), |
132 | label: tr(s: "Enter the path in the Windows registry:" ), |
133 | echo: QLineEdit::Normal, text: "HKEY_CURRENT_USER\\" ); |
134 | if (path.isEmpty()) |
135 | return; |
136 | |
137 | SettingsPtr settings(new QSettings(path, QSettings::NativeFormat)); |
138 | |
139 | setSettingsObject(settings); |
140 | fallbacksAct->setEnabled(false); |
141 | } |
142 | |
143 | void MainWindow::about() |
144 | { |
145 | QMessageBox::about(parent: this, title: tr(s: "About Settings Editor" ), |
146 | text: tr(s: "The <b>Settings Editor</b> example shows how to access " |
147 | "application settings using Qt." )); |
148 | } |
149 | |
150 | void MainWindow::createActions() |
151 | { |
152 | QMenu * = menuBar()->addMenu(title: tr(s: "&File" )); |
153 | |
154 | QAction *openSettingsAct = fileMenu->addAction(text: tr(s: "&Open Application Settings..." ), object: this, slot: &MainWindow::openSettings); |
155 | openSettingsAct->setShortcuts(QKeySequence::Open); |
156 | |
157 | QAction *openIniFileAct = fileMenu->addAction(text: tr(s: "Open I&NI File..." ), object: this, slot: &MainWindow::openIniFile); |
158 | openIniFileAct->setShortcut(tr(s: "Ctrl+N" )); |
159 | |
160 | #ifdef Q_OS_MACOS |
161 | QAction *openPropertyListAct = fileMenu->addAction(tr("Open Apple &Property List..." ), this, &MainWindow::openPropertyList); |
162 | openPropertyListAct->setShortcut(tr("Ctrl+P" )); |
163 | #endif // Q_OS_MACOS |
164 | |
165 | #ifdef Q_OS_WIN |
166 | QAction *openRegistryPathAct = fileMenu->addAction(tr("Open Windows &Registry Path..." ), this, &MainWindow::openRegistryPath); |
167 | openRegistryPathAct->setShortcut(tr("Ctrl+G" )); |
168 | #endif // Q_OS_WIN |
169 | |
170 | fileMenu->addSeparator(); |
171 | |
172 | refreshAct = fileMenu->addAction(text: tr(s: "&Refresh" ), object: settingsTree, slot: &SettingsTree::refresh); |
173 | refreshAct->setShortcut(tr(s: "Ctrl+R" )); |
174 | refreshAct->setEnabled(false); |
175 | |
176 | fileMenu->addSeparator(); |
177 | |
178 | QAction *exitAct = fileMenu->addAction(text: tr(s: "E&xit" ), object: this, slot: &QWidget::close); |
179 | exitAct->setShortcuts(QKeySequence::Quit); |
180 | |
181 | QMenu * = menuBar()->addMenu(title: tr(s: "&Options" )); |
182 | |
183 | autoRefreshAct = optionsMenu->addAction(text: tr(s: "&Auto-Refresh" )); |
184 | autoRefreshAct->setShortcut(tr(s: "Ctrl+A" )); |
185 | autoRefreshAct->setCheckable(true); |
186 | autoRefreshAct->setEnabled(false); |
187 | connect(sender: autoRefreshAct, signal: &QAction::triggered, |
188 | receiver: settingsTree, slot: &SettingsTree::setAutoRefresh); |
189 | connect(sender: autoRefreshAct, signal: &QAction::triggered, |
190 | receiver: refreshAct, slot: &QAction::setDisabled); |
191 | |
192 | fallbacksAct = optionsMenu->addAction(text: tr(s: "&Fallbacks" )); |
193 | fallbacksAct->setShortcut(tr(s: "Ctrl+F" )); |
194 | fallbacksAct->setCheckable(true); |
195 | fallbacksAct->setEnabled(false); |
196 | connect(sender: fallbacksAct, signal: &QAction::triggered, |
197 | receiver: settingsTree, slot: &SettingsTree::setFallbacksEnabled); |
198 | |
199 | QMenu * = menuBar()->addMenu(title: tr(s: "&Help" )); |
200 | helpMenu->addAction(text: tr(s: "&About" ), object: this, slot: &MainWindow::about); |
201 | helpMenu->addAction(text: tr(s: "About &Qt" ), qApp, slot: &QCoreApplication::quit); |
202 | } |
203 | |
204 | void MainWindow::setSettingsObject(const SettingsPtr &settings) |
205 | { |
206 | settings->setFallbacksEnabled(fallbacksAct->isChecked()); |
207 | settingsTree->setSettingsObject(settings); |
208 | |
209 | refreshAct->setEnabled(true); |
210 | autoRefreshAct->setEnabled(true); |
211 | |
212 | QString niceName = QDir::cleanPath(path: settings->fileName()); |
213 | int pos = niceName.lastIndexOf(c: QLatin1Char('/')); |
214 | if (pos != -1) |
215 | niceName.remove(i: 0, len: pos + 1); |
216 | |
217 | if (!settings->isWritable()) |
218 | niceName = tr(s: "%1 (read only)" ).arg(a: niceName); |
219 | |
220 | setWindowTitle(tr(s: "%1 - %2" ).arg(args&: niceName, args: QCoreApplication::applicationName())); |
221 | statusBar()->showMessage(text: tr(s: "Opened \"%1\"" ).arg(a: QDir::toNativeSeparators(pathName: settings->fileName()))); |
222 | } |
223 | |