aboutsummaryrefslogtreecommitdiffstats
path: root/examples/widgets/mainwindows/mdi/mdi.py
diff options
context:
space:
mode:
Diffstat (limited to 'examples/widgets/mainwindows/mdi/mdi.py')
-rw-r--r--examples/widgets/mainwindows/mdi/mdi.py195
1 files changed, 87 insertions, 108 deletions
diff --git a/examples/widgets/mainwindows/mdi/mdi.py b/examples/widgets/mainwindows/mdi/mdi.py
index a6ea6284d..c1fa01b8c 100644
--- a/examples/widgets/mainwindows/mdi/mdi.py
+++ b/examples/widgets/mainwindows/mdi/mdi.py
@@ -1,44 +1,6 @@
-
-#############################################################################
-##
-## Copyright (C) 2013 Riverbank Computing Limited.
-## Copyright (C) 2021 The Qt Company Ltd.
-## Contact: http://www.qt.io/licensing/
-##
-## This file is part of the Qt for Python examples of the Qt Toolkit.
-##
-## $QT_BEGIN_LICENSE:BSD$
-## You may use this file under the terms of the BSD license as follows:
-##
-## "Redistribution and use in source and binary forms, with or without
-## modification, are permitted provided that the following conditions are
-## met:
-## * Redistributions of source code must retain the above copyright
-## notice, this list of conditions and the following disclaimer.
-## * Redistributions in binary form must reproduce the above copyright
-## notice, this list of conditions and the following disclaimer in
-## the documentation and/or other materials provided with the
-## distribution.
-## * Neither the name of The Qt Company Ltd nor the names of its
-## contributors may be used to endorse or promote products derived
-## from this software without specific prior written permission.
-##
-##
-## THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
-## "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
-## LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
-## A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
-## OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
-## SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
-## LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
-## DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
-## THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
-## (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
-## OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
-##
-## $QT_END_LICENSE$
-##
-#############################################################################
+# Copyright (C) 2013 Riverbank Computing Limited.
+# Copyright (C) 2022 The Qt Company Ltd.
+# SPDX-License-Identifier: LicenseRef-Qt-Commercial OR BSD-3-Clause
"""PySide6 port of the widgets/mainwindows/mdi example from Qt v5.x, originating from PyQt"""
@@ -46,13 +8,13 @@ from argparse import ArgumentParser, RawTextHelpFormatter
from functools import partial
import sys
-from PySide6.QtCore import (QByteArray, QFile, QFileInfo, QPoint, QSettings,
- QSaveFile, QSize, QTextStream, Qt)
+from PySide6.QtCore import (QByteArray, QFile, QFileInfo, QSettings,
+ QSaveFile, QTextStream, Qt, Slot)
from PySide6.QtGui import QAction, QIcon, QKeySequence
from PySide6.QtWidgets import (QApplication, QFileDialog, QMainWindow,
- QMdiArea, QMessageBox, QTextEdit, QWidget)
+ QMdiArea, QMessageBox, QTextEdit)
-import mdi_rc
+import PySide6.QtExampleIcons # noqa: F401
class MdiChild(QTextEdit):
@@ -81,9 +43,8 @@ class MdiChild(QTextEdit):
return False
instr = QTextStream(file)
- QApplication.setOverrideCursor(Qt.WaitCursor)
- self.setPlainText(instr.readAll())
- QApplication.restoreOverrideCursor()
+ with QApplication.setOverrideCursor(Qt.WaitCursor):
+ self.setPlainText(instr.readAll())
self.set_current_file(fileName)
@@ -106,18 +67,17 @@ class MdiChild(QTextEdit):
def save_file(self, fileName):
error = None
- QApplication.setOverrideCursor(Qt.WaitCursor)
- file = QSaveFile(fileName)
- if file.open(QFile.WriteOnly | QFile.Text):
- outstr = QTextStream(file)
- outstr << self.toPlainText()
- if not file.commit():
+ with QApplication.setOverrideCursor(Qt.WaitCursor):
+ file = QSaveFile(fileName)
+ if file.open(QFile.WriteOnly | QFile.Text):
+ outstr = QTextStream(file)
+ outstr << self.toPlainText()
+ if not file.commit():
+ reason = file.errorString()
+ error = f"Cannot write file {fileName}:\n{reason}."
+ else:
reason = file.errorString()
- error = f"Cannot write file {fileName}:\n{reason}."
- else:
- reason = file.errorString()
- error = f"Cannot open file {fileName}:\n{reason}."
- QApplication.restoreOverrideCursor()
+ error = f"Cannot open file {fileName}:\n{reason}."
if error:
QMessageBox.warning(self, "MDI", error)
@@ -146,7 +106,7 @@ class MdiChild(QTextEdit):
f = self.user_friendly_current_file()
message = f"'{f}' has been modified.\nDo you want to save your changes?"
ret = QMessageBox.warning(self, "MDI", message,
- QMessageBox.Save | QMessageBox.Discard | QMessageBox.Cancel)
+ QMessageBox.Save | QMessageBox.Discard | QMessageBox.Cancel)
if ret == QMessageBox.Save:
return self.save()
@@ -196,11 +156,13 @@ class MainWindow(QMainWindow):
self.write_settings()
event.accept()
+ @Slot()
def new_file(self):
child = self.create_mdi_child()
child.new_file()
child.show()
+ @Slot()
def open(self):
file_name, _ = QFileDialog.getOpenFileName(self)
if file_name:
@@ -218,31 +180,38 @@ class MainWindow(QMainWindow):
else:
child.close()
+ @Slot()
def save(self):
if self.active_mdi_child() and self.active_mdi_child().save():
self.statusBar().showMessage("File saved", 2000)
+ @Slot()
def save_as(self):
if self.active_mdi_child() and self.active_mdi_child().save_as():
self.statusBar().showMessage("File saved", 2000)
+ @Slot()
def cut(self):
if self.active_mdi_child():
self.active_mdi_child().cut()
+ @Slot()
def copy(self):
if self.active_mdi_child():
self.active_mdi_child().copy()
+ @Slot()
def paste(self):
if self.active_mdi_child():
self.active_mdi_child().paste()
+ @Slot()
def about(self):
QMessageBox.about(self, "About MDI",
- "The <b>MDI</b> example demonstrates how to write multiple "
- "document interface applications using Qt.")
+ "The <b>MDI</b> example demonstrates how to write multiple "
+ "document interface applications using Qt.")
+ @Slot()
def update_menus(self):
has_mdi_child = (self.active_mdi_child() is not None)
self._save_act.setEnabled(has_mdi_child)
@@ -256,11 +225,12 @@ class MainWindow(QMainWindow):
self._previous_act.setEnabled(has_mdi_child)
self._separator_act.setVisible(has_mdi_child)
- has_selection = (self.active_mdi_child() is not None and
- self.active_mdi_child().textCursor().hasSelection())
+ has_selection = (self.active_mdi_child() is not None
+ and self.active_mdi_child().textCursor().hasSelection())
self._cut_act.setEnabled(has_selection)
self._copy_act.setEnabled(has_selection)
+ @Slot()
def update_window_menu(self):
self._window_menu.clear()
self._window_menu.addAction(self._close_act)
@@ -301,82 +271,85 @@ class MainWindow(QMainWindow):
def create_actions(self):
- icon = QIcon.fromTheme("document-new", QIcon(':/images/new.png'))
+ icon = QIcon.fromTheme(QIcon.ThemeIcon.DocumentNew)
self._new_act = QAction(icon, "&New", self,
- shortcut=QKeySequence.New, statusTip="Create a new file",
- triggered=self.new_file)
+ shortcut=QKeySequence.New, statusTip="Create a new file",
+ triggered=self.new_file)
- icon = QIcon.fromTheme("document-open", QIcon(':/images/open.png'))
+ icon = QIcon.fromTheme(QIcon.ThemeIcon.DocumentOpen)
self._open_act = QAction(icon, "&Open...", self,
- shortcut=QKeySequence.Open, statusTip="Open an existing file",
- triggered=self.open)
+ shortcut=QKeySequence.Open, statusTip="Open an existing file",
+ triggered=self.open)
- icon = QIcon.fromTheme("document-save", QIcon(':/images/save.png'))
+ icon = QIcon.fromTheme(QIcon.ThemeIcon.DocumentSave)
self._save_act = QAction(icon, "&Save", self,
- shortcut=QKeySequence.Save,
- statusTip="Save the document to disk", triggered=self.save)
+ shortcut=QKeySequence.Save,
+ statusTip="Save the document to disk", triggered=self.save)
self._save_as_act = QAction("Save &As...", self,
- shortcut=QKeySequence.SaveAs,
- statusTip="Save the document under a new name",
- triggered=self.save_as)
+ shortcut=QKeySequence.SaveAs,
+ statusTip="Save the document under a new name",
+ triggered=self.save_as)
- self._exit_act = QAction("E&xit", self, shortcut=QKeySequence.Quit,
- statusTip="Exit the application",
- triggered=QApplication.instance().closeAllWindows)
+ icon = QIcon.fromTheme(QIcon.ThemeIcon.ApplicationExit)
+ self._exit_act = QAction(icon, "E&xit", self, shortcut=QKeySequence.Quit,
+ statusTip="Exit the application",
+ triggered=QApplication.instance().closeAllWindows)
- icon = QIcon.fromTheme("edit-cut", QIcon(':/images/cut.png'))
+ icon = QIcon.fromTheme(QIcon.ThemeIcon.EditCut)
self._cut_act = QAction(icon, "Cu&t", self,
- shortcut=QKeySequence.Cut,
- statusTip="Cut the current selection's contents to the clipboard",
- triggered=self.cut)
+ shortcut=QKeySequence.Cut,
+ statusTip="Cut the current selection's contents to the clipboard",
+ triggered=self.cut)
- icon = QIcon.fromTheme("edit-copy", QIcon(':/images/copy.png'))
+ icon = QIcon.fromTheme(QIcon.ThemeIcon.EditCopy)
self._copy_act = QAction(icon, "&Copy", self,
- shortcut=QKeySequence.Copy,
- statusTip="Copy the current selection's contents to the clipboard",
- triggered=self.copy)
+ shortcut=QKeySequence.Copy,
+ statusTip="Copy the current selection's contents to the clipboard",
+ triggered=self.copy)
- icon = QIcon.fromTheme("edit-paste", QIcon(':/images/paste.png'))
+ icon = QIcon.fromTheme(QIcon.ThemeIcon.EditPaste)
self._paste_act = QAction(icon, "&Paste", self,
- shortcut=QKeySequence.Paste,
- statusTip="Paste the clipboard's contents into the current selection",
- triggered=self.paste)
+ shortcut=QKeySequence.Paste,
+ statusTip="Paste the clipboard's contents into the current "
+ "selection",
+ triggered=self.paste)
self._close_act = QAction("Cl&ose", self,
- statusTip="Close the active window",
- triggered=self._mdi_area.closeActiveSubWindow)
+ statusTip="Close the active window",
+ triggered=self._mdi_area.closeActiveSubWindow)
self._close_all_act = QAction("Close &All", self,
- statusTip="Close all the windows",
- triggered=self._mdi_area.closeAllSubWindows)
+ statusTip="Close all the windows",
+ triggered=self._mdi_area.closeAllSubWindows)
self._tile_act = QAction("&Tile", self, statusTip="Tile the windows",
- triggered=self._mdi_area.tileSubWindows)
+ triggered=self._mdi_area.tileSubWindows)
self._cascade_act = QAction("&Cascade", self,
- statusTip="Cascade the windows",
- triggered=self._mdi_area.cascadeSubWindows)
+ statusTip="Cascade the windows",
+ triggered=self._mdi_area.cascadeSubWindows)
self._next_act = QAction("Ne&xt", self, shortcut=QKeySequence.NextChild,
- statusTip="Move the focus to the next window",
- triggered=self._mdi_area.activateNextSubWindow)
+ statusTip="Move the focus to the next window",
+ triggered=self._mdi_area.activateNextSubWindow)
self._previous_act = QAction("Pre&vious", self,
- shortcut=QKeySequence.PreviousChild,
- statusTip="Move the focus to the previous window",
- triggered=self._mdi_area.activatePreviousSubWindow)
+ shortcut=QKeySequence.PreviousChild,
+ statusTip="Move the focus to the previous window",
+ triggered=self._mdi_area.activatePreviousSubWindow)
self._separator_act = QAction(self)
self._separator_act.setSeparator(True)
- self._about_act = QAction("&About", self,
- statusTip="Show the application's About box",
- triggered=self.about)
+ icon = QIcon.fromTheme(QIcon.ThemeIcon.HelpAbout)
+ self._about_act = QAction(icon, "&About", self,
+ statusTip="Show the application's About box",
+ triggered=self.about)
self._about_qt_act = QAction("About &Qt", self,
- statusTip="Show the Qt library's About box",
- triggered=QApplication.instance().aboutQt)
+ statusTip="Show the Qt library's About box",
+ triggered=QApplication.instance().aboutQt)
def create_menus(self):
self._file_menu = self.menuBar().addMenu("&File")
@@ -442,6 +415,7 @@ class MainWindow(QMainWindow):
return window
return None
+ @Slot()
def switch_layout_direction(self):
if self.layoutDirection() == Qt.LeftToRight:
QApplication.setLayoutDirection(Qt.RightToLeft)
@@ -461,6 +435,11 @@ if __name__ == '__main__':
options = argument_parser.parse_args()
app = QApplication(sys.argv)
+
+ icon_paths = QIcon.themeSearchPaths()
+ QIcon.setThemeSearchPaths(icon_paths + [":/qt-project.org/icons"])
+ QIcon.setFallbackThemeName("example_icons")
+
main_win = MainWindow()
for f in options.files:
main_win.load(f)