//Copyright (c) 2022 Ultimaker B.V. //Cura is released under the terms of the LGPLv3 or higher. import QtQuick 2.2 import UM 1.5 as UM import Cura 1.0 as Cura Item { id: base UM.I18nCatalog { id: catalog; name: "cura"} height: childrenRect.height + UM.Theme.getSize("thick_margin").height property bool printerConnected: Cura.MachineManager.printerConnected property bool printerAcceptsCommands: printerConnected && Cura.MachineManager.printerOutputDevices[0].acceptsCommands property var activePrinter: printerConnected ? Cura.MachineManager.printerOutputDevices[0].activePrinter : null property var activePrintJob: activePrinter ? activePrinter.activePrintJob: null property real progress: { if(!printerConnected) { return 0 } if(activePrinter == null) { return 0 } if(activePrintJob == null) { return 0 } if(activePrintJob.timeTotal == 0) { return 0 // Prevent division by 0 } return activePrintJob.timeElapsed / activePrintJob.timeTotal * 100 } property int backendState: UM.Backend.state property bool showProgress: { // determine if we need to show the progress bar + percentage if(activePrintJob == null) { return false; } switch(base.activePrintJob.state) { case "printing": case "paused": case "pausing": case "resuming": return true; case "pre_print": // heating, etc. case "wait_cleanup": case "offline": case "abort": // note sure if this jobState actually occurs in the wild case "error": // after clicking abort you apparently get "error" case "ready": // ready to print or getting ready case "": // ready to print or getting ready default: return false; } } property variant statusColor: { if(!printerConnected || !printerAcceptsCommands || activePrinter == null) { return UM.Theme.getColor("text"); } switch(activePrinter.state) { case "maintenance": return UM.Theme.getColor("status_busy"); case "error": return UM.Theme.getColor("status_stopped"); } if(base.activePrintJob == null) { return UM.Theme.getColor("text"); } switch(base.activePrintJob.state) { case "printing": case "pre_print": case "wait_cleanup": case "pausing": case "resuming": return UM.Theme.getColor("status_busy"); case "ready": case "": return UM.Theme.getColor("status_ready"); case "paused": return UM.Theme.getColor("status_paused"); case "error": return UM.Theme.getColor("status_stopped"); case "offline": return UM.Theme.getColor("status_offline"); default: return UM.Theme.getColor("text"); } } property bool activity: CuraApplication.platformActivity; property string fileBaseName property string statusText: { if(!printerConnected) { return catalog.i18nc("@label:MonitorStatus", "Not connected to a printer"); } if(!printerAcceptsCommands) { return catalog.i18nc("@label:MonitorStatus", "Printer does not accept commands"); } var printerOutputDevice = Cura.MachineManager.printerOutputDevices[0] if(activePrinter == null) { return ""; } if(activePrinter.state == "maintenance") { return catalog.i18nc("@label:MonitorStatus", "In maintenance. Please check the printer"); } if(base.activePrintJob == null) { return " " } switch(base.activePrintJob.state) { case "offline": return catalog.i18nc("@label:MonitorStatus", "Lost connection with the printer"); case "printing": return catalog.i18nc("@label:MonitorStatus", "Printing..."); //TODO: Add text for case "pausing". case "paused": return catalog.i18nc("@label:MonitorStatus", "Paused"); //TODO: Add text for case "resuming". case "pre_print": return catalog.i18nc("@label:MonitorStatus", "Preparing..."); case "wait_cleanup": return catalog.i18nc("@label:MonitorStatus", "Please remove the print"); case "error": return printerOutputDevice.errorText; default: return " "; } } UM.Label { id: statusLabel width: parent.width - 2 * UM.Theme.getSize("thick_margin").width anchors.top: parent.top anchors.left: parent.left anchors.leftMargin: UM.Theme.getSize("thick_margin").width color: base.statusColor font: UM.Theme.getFont("large_bold") text: statusText } UM.Label { id: percentageLabel anchors.top: parent.top anchors.right: progressBar.right color: base.statusColor font: UM.Theme.getFont("large_bold") text: Math.round(progress) + "%" visible: showProgress } UM.ProgressBar { id: progressBar from: 0 to: 100 value: 0 //Doing this in an explicit binding since the implicit binding breaks on occasion. Binding { target: progressBar property: "value" value: base.progress } visible: showProgress indeterminate: { if(!printerConnected) { return false; } if(base.activePrintJob == null) { return false } switch(base.activePrintJob.state) { case "pausing": case "resuming": return true; default: return false; } } property string backgroundColor: UM.Theme.getColor("progressbar_background") property string controlColor: base.statusColor width: parent.width - 2 * UM.Theme.getSize("thick_margin").width height: UM.Theme.getSize("progressbar").height anchors.top: statusLabel.bottom anchors.topMargin: Math.round(UM.Theme.getSize("thick_margin").height / 4) anchors.left: parent.left anchors.leftMargin: UM.Theme.getSize("thick_margin").width } Row { id: buttonsRow height: abortButton.height anchors.top: progressBar.bottom anchors.topMargin: UM.Theme.getSize("thick_margin").height anchors.right: parent.right anchors.rightMargin: UM.Theme.getSize("thick_margin").width spacing: UM.Theme.getSize("default_margin").width Row { id: additionalComponentsRow spacing: UM.Theme.getSize("default_margin").width } Component.onCompleted: { buttonsRow.updateAdditionalComponents("monitorButtons") } Connections { target: CuraApplication function onAdditionalComponentsChanged() { buttonsRow.updateAdditionalComponents("monitorButtons") } } function updateAdditionalComponents (areaId) { if(areaId == "monitorButtons") { for (var component in CuraApplication.additionalComponents["monitorButtons"]) { CuraApplication.additionalComponents["monitorButtons"][component].parent = additionalComponentsRow } } } Cura.SecondaryButton { id: pauseResumeButton height: UM.Theme.getSize("save_button_save_to_button").height property bool userClicked: false property string lastJobState: "" visible: printerConnected && activePrinter != null &&activePrinter.canPause enabled: (!userClicked) && printerConnected && printerAcceptsCommands && activePrintJob != null && (["paused", "printing"].indexOf(activePrintJob.state) >= 0) text: { if (!printerConnected || activePrintJob == null) { return catalog.i18nc("@label", "Pause"); } if (activePrintJob.state == "paused") { return catalog.i18nc("@label", "Resume"); } else { return catalog.i18nc("@label", "Pause"); } } onClicked: { if(activePrintJob == null) { return // Do nothing! } if(activePrintJob.state == "paused") { activePrintJob.setState("print"); } else if(activePrintJob.state == "printing") { activePrintJob.setState("pause"); } } } Cura.SecondaryButton { id: abortButton visible: printerConnected && activePrinter != null && activePrinter.canAbort enabled: printerConnected && printerAcceptsCommands && activePrintJob != null && (["paused", "printing", "pre_print"].indexOf(activePrintJob.state) >= 0) height: UM.Theme.getSize("save_button_save_to_button").height text: catalog.i18nc("@label", "Abort Print") onClicked: confirmationDialog.open() } Cura.MessageDialog { id: confirmationDialog title: catalog.i18nc("@window:title", "Abort print") text: catalog.i18nc("@label", "Are you sure you want to abort the print?") standardButtons: Cura.MessageDialog.Yes | Cura.MessageDialog.No onAccepted: activePrintJob.setState("abort") } } }