From 2ca774bd7e318ea853a975fcb5cb2b5fdcbaaeb5 Mon Sep 17 00:00:00 2001 From: Marco Matthies <71844+marcom@users.noreply.github.com> Date: Thu, 23 May 2024 19:54:11 +0200 Subject: [PATCH] Untabify main.qml, config.qml --- src/config.qml | 452 ++++++++++++++++++++++++------------------------- src/main.qml | 316 +++++++++++++++++----------------- 2 files changed, 384 insertions(+), 384 deletions(-) diff --git a/src/config.qml b/src/config.qml index 713e4e0..3d8711f 100644 --- a/src/config.qml +++ b/src/config.qml @@ -18,237 +18,237 @@ ApplicationWindow { visible: true ColumnLayout { - id: generalSettings - anchors.top: parent.top - anchors.left: parent.left - anchors.leftMargin: 20 - anchors.topMargin: 20 - spacing: 8 - - Text { - text: "General Settings:" - horizontalAlignment: Text.AlignCenter - font.bold: true - } - - RowLayout { - Label { text: "Configuration file:" } - Label { - text: conf.userconfigfile - font.italic: true - } - Button { - text: "Select..." - onClicked: conffileChooser.open() - } - FileDialog { - id: conffileChooser - defaultSuffix: "toml" - fileMode: FileDialog.SaveFile - nameFilters: ["Configuration files (*.toml)"] - onAccepted: conf.userconfigfile = selectedFile - } - } - - RowLayout { - Label { text: "Output folder:" } - Label { - text: conf.outdir - font.italic: true - } - Button { - text: "Select..." - onClicked: outdirChooser.open() - } - FolderDialog { - id: outdirChooser - selectedFolder: conf.outdir - onAccepted: conf.outdir = selectedFolder - } - } - - //XXX Not all regions have data available! - // (currently, only Jena is fully configured) - RowLayout { - Label { text: "Region:" } - ComboBox { - currentIndex: 3 - model: ["Bodensee", "Eichsfeld", "Hohenlohe", "Jena", - "Oberrhein", "Thüringer Becken"] - onCurrentIndexChanged: conf.region = currentText - } - } - - RowLayout { - Label { text: "Crop model:" } - ComboBox { - currentIndex: 0 - model: ["ALMaSS", "AquaCrop"] - onCurrentIndexChanged: conf.cropmodel = currentText - } - } - - RowLayout { //TODO how can I enable multi-species selection? - Label { text: "Species:" } - ComboBox { - currentIndex: 0 - model: ["Skylark", "Wolpertinger"] - onCurrentIndexChanged: conf.species = currentText - } - } - - //XXX For which years do I actually have data? - RowLayout { - Label { text: "Start date:" } - SpinBox { - Layout.maximumWidth: 100 - from: 1 - to: 31 - value: conf.startdateday - editable: true - wrap: true - onValueModified: conf.startdateday = value - } - SpinBox { - Layout.maximumWidth: 100 - from: 1 - to: 12 - value: conf.startdatemonth - editable: true - wrap: true - onValueModified: conf.startdatemonth = value - } - SpinBox { - Layout.maximumWidth: 100 - from: 2000 - to: 2050 - value: conf.startdateyear - editable: true - wrap: true - textFromValue: function(value) { return Number(value).toString(); } - onValueModified: conf.startdateyear = value - } - } - - RowLayout { - Label { text: "End date:" } - SpinBox { - Layout.maximumWidth: 100 - from: 1 - to: 31 - value: conf.enddateday - editable: true - wrap: true - onValueModified: conf.enddateday = value - } - SpinBox { - Layout.maximumWidth: 100 - from: 1 - to: 12 - value: conf.enddatemonth - editable: true - wrap: true - onValueModified: conf.enddatemonth = value - } - SpinBox { - Layout.maximumWidth: 100 - from: 2000 - to: 2050 - value: conf.enddateyear - editable: true - wrap: true - textFromValue: function(value) { return Number(value).toString(); } - onValueModified: conf.enddateyear = value - } - } + id: generalSettings + anchors.top: parent.top + anchors.left: parent.left + anchors.leftMargin: 20 + anchors.topMargin: 20 + spacing: 8 + + Text { + text: "General Settings:" + horizontalAlignment: Text.AlignCenter + font.bold: true + } + + RowLayout { + Label { text: "Configuration file:" } + Label { + text: conf.userconfigfile + font.italic: true + } + Button { + text: "Select..." + onClicked: conffileChooser.open() + } + FileDialog { + id: conffileChooser + defaultSuffix: "toml" + fileMode: FileDialog.SaveFile + nameFilters: ["Configuration files (*.toml)"] + onAccepted: conf.userconfigfile = selectedFile + } + } + + RowLayout { + Label { text: "Output folder:" } + Label { + text: conf.outdir + font.italic: true + } + Button { + text: "Select..." + onClicked: outdirChooser.open() + } + FolderDialog { + id: outdirChooser + selectedFolder: conf.outdir + onAccepted: conf.outdir = selectedFolder + } + } + + //XXX Not all regions have data available! + // (currently, only Jena is fully configured) + RowLayout { + Label { text: "Region:" } + ComboBox { + currentIndex: 3 + model: ["Bodensee", "Eichsfeld", "Hohenlohe", "Jena", + "Oberrhein", "Thüringer Becken"] + onCurrentIndexChanged: conf.region = currentText + } + } + + RowLayout { + Label { text: "Crop model:" } + ComboBox { + currentIndex: 0 + model: ["ALMaSS", "AquaCrop"] + onCurrentIndexChanged: conf.cropmodel = currentText + } + } + + RowLayout { //TODO how can I enable multi-species selection? + Label { text: "Species:" } + ComboBox { + currentIndex: 0 + model: ["Skylark", "Wolpertinger"] + onCurrentIndexChanged: conf.species = currentText + } + } + + //XXX For which years do I actually have data? + RowLayout { + Label { text: "Start date:" } + SpinBox { + Layout.maximumWidth: 100 + from: 1 + to: 31 + value: conf.startdateday + editable: true + wrap: true + onValueModified: conf.startdateday = value + } + SpinBox { + Layout.maximumWidth: 100 + from: 1 + to: 12 + value: conf.startdatemonth + editable: true + wrap: true + onValueModified: conf.startdatemonth = value + } + SpinBox { + Layout.maximumWidth: 100 + from: 2000 + to: 2050 + value: conf.startdateyear + editable: true + wrap: true + textFromValue: function(value) { return Number(value).toString(); } + onValueModified: conf.startdateyear = value + } + } + + RowLayout { + Label { text: "End date:" } + SpinBox { + Layout.maximumWidth: 100 + from: 1 + to: 31 + value: conf.enddateday + editable: true + wrap: true + onValueModified: conf.enddateday = value + } + SpinBox { + Layout.maximumWidth: 100 + from: 1 + to: 12 + value: conf.enddatemonth + editable: true + wrap: true + onValueModified: conf.enddatemonth = value + } + SpinBox { + Layout.maximumWidth: 100 + from: 2000 + to: 2050 + value: conf.enddateyear + editable: true + wrap: true + textFromValue: function(value) { return Number(value).toString(); } + onValueModified: conf.enddateyear = value + } + } } ColumnLayout { - id: advancedSettings - anchors.top: parent.top - anchors.right: parent.right - anchors.left: generalSettings.right - anchors.rightMargin: 20 - anchors.topMargin: 20 - anchors.leftMargin: 20 - spacing: 8 - - Text { - text: "Advanced Settings:" - horizontalAlignment: Text.AlignCenter - font.bold: true - } - - RowLayout { - Label { text: "Random seed:" } - SpinBox { - from: 0 - to: 2147483647 - value: 2 - editable: true - onValueModified: conf.seed = value - } - } - - RowLayout { - Label { text: "Log level:" } - ComboBox { - currentIndex: 2 - model: ["debug", "info", "warn"] - onCurrentIndexChanged: conf.loglevel = currentText - } - } - - RowLayout { - Label { text: "Processors:" } - SpinBox { - from: 1 - to: 8 - value: conf.processors - editable: true - onValueModified: conf.processors = value - } - } - - CheckBox { - checked: conf.csvoutput - text: "Write CSV output" - onClicked: conf.csvoutput = checked - } - - //TODO add config options for: - // farmmodel - // targetspecies - // insectmodel + id: advancedSettings + anchors.top: parent.top + anchors.right: parent.right + anchors.left: generalSettings.right + anchors.rightMargin: 20 + anchors.topMargin: 20 + anchors.leftMargin: 20 + spacing: 8 + + Text { + text: "Advanced Settings:" + horizontalAlignment: Text.AlignCenter + font.bold: true + } + + RowLayout { + Label { text: "Random seed:" } + SpinBox { + from: 0 + to: 2147483647 + value: 2 + editable: true + onValueModified: conf.seed = value + } + } + + RowLayout { + Label { text: "Log level:" } + ComboBox { + currentIndex: 2 + model: ["debug", "info", "warn"] + onCurrentIndexChanged: conf.loglevel = currentText + } + } + + RowLayout { + Label { text: "Processors:" } + SpinBox { + from: 1 + to: 8 + value: conf.processors + editable: true + onValueModified: conf.processors = value + } + } + + CheckBox { + checked: conf.csvoutput + text: "Write CSV output" + onClicked: conf.csvoutput = checked + } + + //TODO add config options for: + // farmmodel + // targetspecies + // insectmodel } footer: ToolBar { - RowLayout { - anchors.right: parent.right - layoutDirection: Qt.RightToLeft - - Button { - text: "Start new simulation" - onClicked: { - //TODO show splash - Julia.writeconfig() - Julia.newsimulation() - configWindow.close() - } - } - - Button { - text: "Save configuration" - onClicked: { - Julia.writeconfig() - configWindow.close() - } - } - - Button { - text: "Cancel" - onClicked: configWindow.close() - } - } + RowLayout { + anchors.right: parent.right + layoutDirection: Qt.RightToLeft + + Button { + text: "Start new simulation" + onClicked: { + //TODO show splash + Julia.writeconfig() + Julia.newsimulation() + configWindow.close() + } + } + + Button { + text: "Save configuration" + onClicked: { + Julia.writeconfig() + configWindow.close() + } + } + + Button { + text: "Cancel" + onClicked: configWindow.close() + } + } } } diff --git a/src/main.qml b/src/main.qml index 81d00d2..c047a52 100644 --- a/src/main.qml +++ b/src/main.qml @@ -18,201 +18,201 @@ ApplicationWindow { visible: true menuBar: MenuBar { - Menu { - title: "&Simulation" - Action { - text: "&New Simulation" - onTriggered: { vars.launching = true } //TODO select config file - } - Action { - text: "&Configure Simulation" - onTriggered: { Julia.configwindow() } - } - Action { - text: "&Load Saved State" - onTriggered: { loadFileChooser.open() } - } - Action { - text: "&Save Current State" - onTriggered: { saveFileChooser.open() } - } - MenuSeparator { } - Action { - text: "&Quit" - onTriggered: { mainWindow.close() } - } - } - Menu { - title: "&Data" - Action { - text: "Show &Population Graph" - onTriggered: { populationGraph.visible = true } - } - Action { - text: "Save &Simulation Output" - onTriggered: { Julia.saveoutput() } - } - } - Menu { - title: "&Help" - Action { - text: "&Documentation" - onTriggered: { Qt.openUrlExternally("https://persefone-model.eu/documentation") } - } - Action { - text: "&Website" - onTriggered: { Qt.openUrlExternally("https://persefone-model.eu/") } - } - Action { - text: "&About" - onTriggered: { aboutDialog.open() } - } - } + Menu { + title: "&Simulation" + Action { + text: "&New Simulation" + onTriggered: { vars.launching = true } //TODO select config file + } + Action { + text: "&Configure Simulation" + onTriggered: { Julia.configwindow() } + } + Action { + text: "&Load Saved State" + onTriggered: { loadFileChooser.open() } + } + Action { + text: "&Save Current State" + onTriggered: { saveFileChooser.open() } + } + MenuSeparator { } + Action { + text: "&Quit" + onTriggered: { mainWindow.close() } + } + } + Menu { + title: "&Data" + Action { + text: "Show &Population Graph" + onTriggered: { populationGraph.visible = true } + } + Action { + text: "Save &Simulation Output" + onTriggered: { Julia.saveoutput() } + } + } + Menu { + title: "&Help" + Action { + text: "&Documentation" + onTriggered: { Qt.openUrlExternally("https://persefone-model.eu/documentation") } + } + Action { + text: "&Website" + onTriggered: { Qt.openUrlExternally("https://persefone-model.eu/") } + } + Action { + text: "&About" + onTriggered: { aboutDialog.open() } + } + } } // visualise the model map and the locations of animals MakieViewport { - id: mapviewport - anchors.fill: parent - renderFunction: render_map_callback + id: mapviewport + anchors.fill: parent + renderFunction: render_map_callback } // the main control bar, with pause/step/run buttons, the progress // bar and a speed slider footer: ToolBar { - RowLayout { - //TODO change button texts to icons - // (https://doc.qt.io/qt-6/qtquickcontrols-icons.html) - id: controlBar - anchors.fill: parent - Layout.alignment: Qt.AlignVCenter - Layout.fillWidth: true - // anchors.topMargin: 5 //FIXME - // anchors.bottomMargin: 5 - Button { - id: backButton - text: "<" - ToolTip.text: "Back" - ToolTip.visible: hovered - onClicked: { Julia.previousstep() } - } - Button { - id: stepButton - text: ">" - ToolTip.text: "Step" - ToolTip.visible: hovered - onClicked: { Julia.nextstep() } - } - Button { - id: runButton - text: vars.runbuttontext - ToolTip.text: vars.runbuttontip - ToolTip.visible: hovered - onClicked: { vars.running = !vars.running } - } - ProgressBar { - id: progressBar - value: vars.progress - Layout.fillWidth: true - ToolTip.text: "Simulation progress" - ToolTip.visible: hovered - } - Slider { - id: speedSlider - from: 0.0 - to: 2.0 - value: vars.delay - stepSize: 0.1 - snapMode: Slider.SnapAlways - ToolTip.text: "Time delay between updates" - ToolTip.visible: hovered - onValueChanged: vars.delay = value - } - Text { - id: dateText - text: Julia.datestring() - //width: //TODO - } - } + RowLayout { + //TODO change button texts to icons + // (https://doc.qt.io/qt-6/qtquickcontrols-icons.html) + id: controlBar + anchors.fill: parent + Layout.alignment: Qt.AlignVCenter + Layout.fillWidth: true + // anchors.topMargin: 5 //FIXME + // anchors.bottomMargin: 5 + Button { + id: backButton + text: "<" + ToolTip.text: "Back" + ToolTip.visible: hovered + onClicked: { Julia.previousstep() } + } + Button { + id: stepButton + text: ">" + ToolTip.text: "Step" + ToolTip.visible: hovered + onClicked: { Julia.nextstep() } + } + Button { + id: runButton + text: vars.runbuttontext + ToolTip.text: vars.runbuttontip + ToolTip.visible: hovered + onClicked: { vars.running = !vars.running } + } + ProgressBar { + id: progressBar + value: vars.progress + Layout.fillWidth: true + ToolTip.text: "Simulation progress" + ToolTip.visible: hovered + } + Slider { + id: speedSlider + from: 0.0 + to: 2.0 + value: vars.delay + stepSize: 0.1 + snapMode: Slider.SnapAlways + ToolTip.text: "Time delay between updates" + ToolTip.visible: hovered + onValueChanged: vars.delay = value + } + Text { + id: dateText + text: Julia.datestring() + //width: //TODO + } + } } // extra windows MessageDialog { - id: aboutDialog - text: "Persefone.jl Desktop" - informativeText: "A mechanistic model of agricultural landscapes \ + id: aboutDialog + text: "Persefone.jl Desktop" + informativeText: "A mechanistic model of agricultural landscapes \ and ecosystems in Europe.\n\n\ © 2023 Daniel Vedder, Lea Kolb, Guy Pe'er\n\ Distributed under the MIT license." } FileDialog { - id: loadFileChooser - defaultSuffix: "dat" - nameFilters: ["Save files (*.dat)"] - onAccepted: { Julia.loadsimulation(selectedFile.toString()) } + id: loadFileChooser + defaultSuffix: "dat" + nameFilters: ["Save files (*.dat)"] + onAccepted: { Julia.loadsimulation(selectedFile.toString()) } } FileDialog { - id: saveFileChooser - defaultSuffix: "dat" - fileMode: FileDialog.SaveFile - nameFilters: ["Save files (*.dat)"] - onAccepted: { Julia.savesimulation(selectedFile.toString()) } + id: saveFileChooser + defaultSuffix: "dat" + fileMode: FileDialog.SaveFile + nameFilters: ["Save files (*.dat)"] + onAccepted: { Julia.savesimulation(selectedFile.toString()) } } Window { - id: populationGraph - title: "Population Graph" - width: 512 - height: 512 - visible: false + id: populationGraph + title: "Population Graph" + width: 512 + height: 512 + visible: false - MakieViewport { - id: plotviewport - anchors.fill: parent - renderFunction: render_plot_callback - } + MakieViewport { + id: plotviewport + anchors.fill: parent + renderFunction: render_plot_callback + } } Popup { - id: splashPopup - parent: Overlay.overlay - closePolicy: Popup.NoAutoClose - modal: true - padding: 0 + id: splashPopup + parent: Overlay.overlay + closePolicy: Popup.NoAutoClose + modal: true + padding: 0 - width: 600 - height: 250 - x: Math.round((parent.width - width) / 2) - y: Math.round((parent.height - height) / 2) + width: 600 + height: 250 + x: Math.round((parent.width - width) / 2) + y: Math.round((parent.height - height) / 2) - Image { - anchors.fill: parent - source: "persefonejl_logo_v3_splash.png" - } + Image { + anchors.fill: parent + source: "persefonejl_logo_v3_splash.png" + } } // set up connections and signals to update the simulation and the display Connections { - target: timer - function onTimeout() { vars.ticks += 1 } + target: timer + function onTimeout() { vars.ticks += 1 } } JuliaSignals { - signal updateMakie() - onUpdateMakie: { - dateText.text = Julia.datestring(); - mapviewport.update(); - plotviewport.update(); - } - signal showSplash() - onShowSplash: { - splashPopup.open() - } - signal closeSplash() - onCloseSplash: { - splashPopup.close() - } + signal updateMakie() + onUpdateMakie: { + dateText.text = Julia.datestring(); + mapviewport.update(); + plotviewport.update(); + } + signal showSplash() + onShowSplash: { + splashPopup.open() + } + signal closeSplash() + onCloseSplash: { + splashPopup.close() + } } } -- GitLab