Closed astronik00 closed 1 year ago
@astronik00
Получилось такое окно:
Вывел отдельно переменные для изменения текстов:
@pavelparfishov
А как передать текст содержимого ошибки из другого окна? Или например, как передать код ошибки на окно предупреждения, а в зависимости от него выбрать нужные строки (из массива ошибок, например, который бы хранился в окне)?
@pavelparfishov В принципе, можно и без передачи ошибки между окнами, но тогда придется создавать подобное окно на каждое возможное предупреждение.
Для передачи текста из одного QML-окна в другое можно использовать сигналы и слоты.
Пример: У нас есть QML-окно MainWindow.qml с кнопкой, при нажатии на которую открывается второе окно SecondWindow.qml, в котором мы хотим отобразить текст, переданный из MainWindow.qml.
В MainWindow.qml нужно объявить сигнал и обработчик нажатия на кнопку:
import QtQuick 2.0
Item {
signal textToPass(string text)
Button {
text: "Open second window"
onClicked: {
textToPass("Hello from Main Window!")
}
}
}
В SecondWindow.qml нужно объявить слот для принятия сигнала и отобразить переданный текст:
import QtQuick 2.0
Item {
id: secondWindow
property string textToDisplay: ""
Connections {
target: main
onTextToPass: {
secondWindow.textToDisplay = text;
secondWindow.visible = true;
}
}
Text {
text: secondWindow.textToDisplay
}
}
Здесь мы объявляем свойство textToDisplay, которое будет использоваться для отображения текста в окне. В блоке Connections мы подключаем сигнал textToPass из MainWindow.qml к слоту onTextToPass и передаем текст в свойство textToDisplay. Кроме того, мы делаем окно видимым, чтобы отобразить переданный текст.
Обратите внимание, что мы используем идентификатор main в Connections, который должен быть установлен в корневом элементе ApplicationWindow в файле main.qml:
import QtQuick 2.0
ApplicationWindow {
id: main
width: 640
height: 480
visible: true
// ...
SecondWindow {
visible: false
}
}
Здесь мы добавляем в ApplicationWindow компонент SecondWindow, который мы будем использовать для отображения переданного текста. Обратите внимание, что мы устанавливаем свойство visible в false, чтобы окно не отображалось по умолчанию.
Думаешь, стоит такую логику в разметке интерфейса реализовывать? Можно конечно if-ами попытаться это сделать, но тогда придется постоянно в qml-файл лезть, чтобы добавить информацию по новой ошибке. Мне кажется, что лучше сделать массивы в .py файле или .json или .csv, и при обработке ошибки в .py-файле просто передавать нужные тексты в окно предупреждений.
Пример передачи названия кнопки из Python в QML:
from PyQt5.QtCore import QObject, pyqtProperty, pyqtSignal, pyqtSlot
from PyQt5.QtGui import QGuiApplication
from PyQt5.QtQml import QQmlApplicationEngine
import sys
class ButtonTextProvider(QObject):
def __init__(self, parent=None):
super().__init__(parent)
self._button_text = ""
@pyqtProperty(str, notify=buttonTextChanged)
def buttonText(self):
return self._button_text
@buttonText.setter
def buttonText(self, text):
self._button_text = text
self.buttonTextChanged.emit()
buttonTextChanged = pyqtSignal()
if __name__ == "__main__":
app = QGuiApplication(sys.argv)
engine = QQmlApplicationEngine()
# создаем экземпляр класса ButtonTextProvider и передаем его в QML
button_text_provider = ButtonTextProvider()
engine.rootContext().setContextProperty("buttonTextProvider", button_text_provider)
# получаем текст кнопки из переменной Python
button_text = "Нажми меня"
# устанавливаем текст кнопки в свойство buttonText объекта ButtonTextProvider
button_text_provider.buttonText = button_text
# запускаем приложение
engine.load("main.qml")
if not engine.rootObjects():
sys.exit(-1)
sys.exit(app.exec_())
Думаешь, стоит такую логику в разметке интерфейса реализовывать?
А это на какое из двух сообщений? Не понимаю, о какой конкретно
Я так-то думаю, что можно создать один класс ошибки, у которой было бы название, текст, а также значения кнопок (последнее не очень красиво звучит для класса, а может и норм), и просто передавать в новое окно ошибку, а дальше:
button_ok_text = MyCustomError.button_ok_text
button_close_text = MyCustomError.button_close_text
@astronik00 Привет) Вот так получилось сделать:
В QML он вот так подтягивается:
Text {
text: myText.text
anchors.centerIn: parent
}
Мне сложно понять логику, не начав разбирать документацию Qt и QML. Так сделать можно или нельзя?
class CustomException(Exception):
def __init__(self, title: str, description: str, ok: str, cancel: str) -> None:
self.title = title
self.description = description
self.ok = ok
self.cancel = cancel
где-то выкинули ошибку:
if a == 1:
raise CustomException("a == 1", "А оказалось равно 1, это ужасно", "Да", "Нет")
и где-то в файле:
try:
pass
except CustomException as e:
# вызов окна предупреждения с передачей e.title, e.description, e.ok, e.cancel
@astronik00 Как получилось сделать:
Тексты для элементов хранятся в словаре. Подтягиваются по ключу.
Используется класс, который наследуется от QObject, чтобы с QML взаимодействовать. Одновременно от Exception и QObject он наследоваться не может :( . Критично, что он не от Exception наследуется? Или это был просто возможный вариант реализации?
@pavelparfishov К сожалению, это обязательно, чтобы можно было выбросить питоновский Exception и использовать его в блоке try-catch.
@astronik00 Попробовал по-другому (создал еще один класс).
Класс для Exception'ов:
class CustomException(Exception):
def __init__(self, error_info: Tuple[str, str, str, str]) -> None:
super().__init__(error_info[1])
self.error_info = ErrorInfo(*error_info)
Так норм?
@pavelparfishov а класс ErrorInfo откуда берется?
а ты можешь это выложить в свою ветку? я примерно поняла, но все еще не очень этот самый ErrorInfo - это как Model, которую ты создал на View ошибки, который подтягивается по названию error_info?
если все работает, то думаю, что такой вариант пойдет
@astronik00 Класс ErrorInfo я создал. Наследуется от QObject, чтобы с QML взаимодействовать. Выложил в ветку 3 файла.
@pavelparfishov
Я посмотрела. Тогда будем создавать таким образом ошибки. Само окно выглядит симпатично.
@pavelparfishov
Вот еще вспомнила.
self._error_name = _error_name
self._error_text = _error_text
Я думаю error
_name уже излишне, стоит просто оставить name и text
Design
Требования: программист
Краткое описание
Необходимо создать окно предупреждения по общей структуре, в которое можно было бы передать текст предупреждения, а также текст кнопок.
Функциональные требования или иные документы
Пример:
На окне должны быть четыре элемента: название, развернутый текст, кнопка 1, кнопка 2. Ситуации, которые нужно рассмотреть:
Более конкретный и подходящий под ситуацию текст реализовать самостоятельно. Расширять список, если будут обнаружены еще ситуации.
Обобщенное решение
Выходной результат
Файл окна QML. В MR загрузить скриншот работы.