diff --git a/plugins/UM3NetworkPrinting/resources/qml/CameraButton.qml b/plugins/UM3NetworkPrinting/resources/qml/CameraButton.qml index 6f054f9c19..bf7690ac37 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/CameraButton.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/CameraButton.qml @@ -9,12 +9,14 @@ import Cura 1.0 as Cura Rectangle { id: base + + property var enabled: true + property var iconSource: null; - color: "#0a0850" // TODO: Theme! + color: UM.Theme.getColor("monitor_icon_primary") height: width; radius: Math.round(0.5 * width); width: 24 * screenScaleFactor; - property var enabled: true UM.RecolorImage { id: icon; @@ -22,7 +24,7 @@ Rectangle { horizontalCenter: parent.horizontalCenter; verticalCenter: parent.verticalCenter; } - color: UM.Theme.getColor("primary_text"); + color: UM.Theme.getColor("monitor_icon_accent"); height: width; source: iconSource; width: Math.round(parent.width / 2); diff --git a/plugins/UM3NetworkPrinting/resources/qml/ExpandableCard.qml b/plugins/UM3NetworkPrinting/resources/qml/ExpandableCard.qml index d4c123652d..c839e52892 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/ExpandableCard.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/ExpandableCard.qml @@ -6,10 +6,11 @@ import QtQuick.Controls 2.0 import UM 1.3 as UM import Cura 1.0 as Cura -// TODO: Theme & documentation! -// The expandable component has 3 major sub components: -// * The headerItem Always visible and should hold some info about what happens if the component is expanded -// * The popupItem The content that needs to be shown if the component is expanded. +/** + * The expandable component has 3 major sub components: + * - The headerItem Always visible and should hold some info about what happens if the component is expanded + * - The popupItem The content that needs to be shown if the component is expanded. + */ Item { id: base @@ -17,10 +18,10 @@ Item property bool expanded: false property bool enabled: true property var borderWidth: 1 - property color borderColor: "#CCCCCC" - property color headerBackgroundColor: "white" - property color headerHoverColor: "#e8f2fc" - property color drawerBackgroundColor: "white" + property color borderColor: UM.Theme.getColor("monitor_card_border") + property color headerBackgroundColor: UM.Theme.getColor("monitor_icon_accent") + property color headerHoverColor: UM.Theme.getColor("monitor_card_hover") + property color drawerBackgroundColor: UM.Theme.getColor("monitor_icon_accent") property alias headerItem: header.children property alias drawerItem: drawer.children diff --git a/plugins/UM3NetworkPrinting/resources/qml/GenericPopUp.qml b/plugins/UM3NetworkPrinting/resources/qml/GenericPopUp.qml new file mode 100644 index 0000000000..74d9377f3e --- /dev/null +++ b/plugins/UM3NetworkPrinting/resources/qml/GenericPopUp.qml @@ -0,0 +1,227 @@ +// Copyright (c) 2018 Ultimaker B.V. +// Cura is released under the terms of the LGPLv3 or higher. + +import QtQuick 2.2 +import QtQuick.Controls 2.0 +import QtQuick.Controls.Styles 1.4 +import QtQuick.Dialogs 1.1 +import QtGraphicalEffects 1.0 +import UM 1.3 as UM + +/** + * This is a generic pop-up element which can be supplied with a target and a content item. The + * content item will appear to the left, right, above, or below the target depending on the value of + * the direction property + */ +Popup +{ + id: base + + /** + * The target item is what the pop-up is "tied" to, usually a button + */ + property var target + + /** + * Which direction should the pop-up "point"? + * Possible values include: + * - "up" + * - "down" + * - "left" + * - "right" + */ + property string direction: "down" + + /** + * We save the default direction so that if a pop-up was flipped but later has space (i.e. it + * moved), we can unflip it back to the default direction. + */ + property string originalDirection: "" + + /** + * Should the popup close when you click outside it? For example, this is + * disabled by the InfoBlurb component since it's opened and closed using mouse + * hovers, not clicks. + */ + property bool closeOnClick: true + + /** + * Use white for context menus, dark grey for info blurbs! + */ + property var color: "#ffffff" // TODO: Theme! + + Component.onCompleted: + { + recalculatePosition() + + // Set the direction here so it's only set once and never mutated + originalDirection = (' ' + direction).slice(1) + } + + background: Item + { + anchors.fill: parent + + DropShadow + { + anchors.fill: pointedRectangle + color: UM.Theme.getColor("monitor_shadow") + radius: UM.Theme.getSize("monitor_shadow_radius").width + source: pointedRectangle + transparentBorder: true + verticalOffset: 2 * screenScaleFactor + } + + Item + { + id: pointedRectangle + anchors + { + horizontalCenter: parent.horizontalCenter + verticalCenter: parent.verticalCenter + } + height: parent.height - 10 * screenScaleFactor // Because of the shadow + width: parent.width - 10 * screenScaleFactor // Because of the shadow + + Rectangle + { + id: point + anchors + { + horizontalCenter: + { + switch(direction) + { + case "left": + return bloop.left + case "right": + return bloop.right + default: + return bloop.horizontalCenter + } + } + verticalCenter: + { + switch(direction) + { + case "up": + return bloop.top + case "down": + return bloop.bottom + default: + return bloop.verticalCenter + } + } + } + color: base.color + height: 12 * screenScaleFactor + transform: Rotation + { + angle: 45 + origin.x: point.width / 2 + origin.y: point.height / 2 + } + width: height + } + + Rectangle + { + id: bloop + anchors + { + fill: parent + leftMargin: direction == "left" ? 8 * screenScaleFactor : 0 + rightMargin: direction == "right" ? 8 * screenScaleFactor : 0 + topMargin: direction == "up" ? 8 * screenScaleFactor : 0 + bottomMargin: direction == "down" ? 8 * screenScaleFactor : 0 + } + color: base.color + width: parent.width + } + } + } + + visible: false + onClosed: visible = false + onOpened: + { + // Flip orientation if necessary + recalculateOrientation() + + // Fix position if necessary + recalculatePosition() + + // Show the pop up + visible = true + } + closePolicy: closeOnClick ? Popup.CloseOnPressOutside : Popup.NoAutoClose + + clip: true + + padding: UM.Theme.getSize("monitor_shadow_radius").width + topPadding: direction == "up" ? padding + 8 * screenScaleFactor : padding + bottomPadding: direction == "down" ? padding + 8 * screenScaleFactor : padding + leftPadding: direction == "left" ? padding + 8 * screenScaleFactor : padding + rightPadding: direction == "right" ? padding + 8 * screenScaleFactor : padding + + function recalculatePosition() { + + // Stupid pop-up logic causes the pop-up to resize, so let's compute what it SHOULD be + const realWidth = contentItem.implicitWidth + leftPadding + rightPadding + const realHeight = contentItem.implicitHeight + topPadding + bottomPadding + + var centered = { + x: target.x + target.width / 2 - realWidth / 2, + y: target.y + target.height / 2 - realHeight / 2 + } + + switch(direction) + { + case "left": + x = target.x + target.width + y = centered.y + break + case "right": + x = target.x - realWidth + y = centered.y + break + case "up": + x = centered.x + y = target.y + target.height + break + case "down": + x = centered.x + y = target.y - realHeight + break + } + } + + function recalculateOrientation() { + var availableSpace + var targetPosition = target.mapToItem(monitorFrame, 0, 0) + + // Stupid pop-up logic causes the pop-up to resize, so let's compute what it SHOULD be + const realWidth = contentItem.implicitWidth + leftPadding + rightPadding + const realHeight = contentItem.implicitHeight + topPadding + bottomPadding + + switch(originalDirection) + { + case "up": + availableSpace = monitorFrame.height - (targetPosition.y + target.height) + direction = availableSpace < realHeight ? "down" : originalDirection + break + case "down": + availableSpace = targetPosition.y + direction = availableSpace < realHeight ? "up" : originalDirection + break + case "right": + availableSpace = targetPosition.x + direction = availableSpace < realWidth ? "left" : originalDirection + break + case "left": + availableSpace = monitorFrame.width - (targetPosition.x + target.width) + direction = availableSpace < realWidth ? "right" : originalDirection + break + } + } +} diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorBuildplateConfiguration.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorBuildplateConfiguration.qml index 192a5a7f76..d1a0c207c5 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/MonitorBuildplateConfiguration.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorBuildplateConfiguration.qml @@ -41,7 +41,7 @@ Item anchors.centerIn: parent height: parent.height width: height - color: buildplateIcon.visible > 0 ? "transparent" : "#eeeeee" // TODO: Theme! + color: buildplateIcon.visible > 0 ? "transparent" : UM.Theme.getColor("monitor_skeleton_loading") radius: Math.floor(height / 2) } @@ -49,7 +49,7 @@ Item { id: buildplateIcon anchors.centerIn: parent - color: "#0a0850" // TODO: Theme! (Standard purple) + color: UM.Theme.getColor("monitor_icon_primary") height: parent.height source: "../svg/icons/buildplate.svg" width: height @@ -60,7 +60,7 @@ Item Label { id: buildplateLabel - color: "#191919" // TODO: Theme! + color: UM.Theme.getColor("monitor_text_primary") elide: Text.ElideRight font: UM.Theme.getFont("default") // 12pt, regular text: buildplate ? buildplate : "" diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorCarousel.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorCarousel.qml index de24ee5a8c..0d7a177dd3 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/MonitorCarousel.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorCarousel.qml @@ -49,12 +49,12 @@ Item GradientStop { position: 0.0 - color: "#fff6f6f6" // TODO: Theme! + color: UM.Theme.getColor("monitor_stage_background") } GradientStop { position: 1.0 - color: "#66f6f6f6" // TODO: Theme! + color: UM.Theme.getColor("monitor_stage_background_fade") } } } @@ -82,9 +82,9 @@ Item onClicked: navigateTo(currentIndex - 1) background: Rectangle { - color: leftButton.hovered ? "#e8f2fc" : "#ffffff" // TODO: Theme! + color: leftButton.hovered ? UM.Theme.getColor("monitor_card_hover") : UM.Theme.getColor("monitor_card_background") border.width: 1 * screenScaleFactor // TODO: Theme! - border.color: "#cccccc" // TODO: Theme! + border.color: UM.Theme.getColor("monitor_card_border") radius: 2 * screenScaleFactor // TODO: Theme! } contentItem: Item @@ -97,7 +97,7 @@ Item height: width // TODO: Theme! sourceSize.width: width // TODO: Theme! sourceSize.height: width // TODO: Theme! - color: "#152950" // TODO: Theme! + color: UM.Theme.getColor("monitor_text_primary") source: UM.Theme.getIcon("arrow_left") } } @@ -161,9 +161,9 @@ Item hoverEnabled: true background: Rectangle { - color: rightButton.hovered ? "#e8f2fc" : "#ffffff" // TODO: Theme! + color: rightButton.hovered ? UM.Theme.getColor("monitor_card_hover") : UM.Theme.getColor("monitor_card_background") border.width: 1 * screenScaleFactor // TODO: Theme! - border.color: "#cccccc" // TODO: Theme! + border.color: UM.Theme.getColor("monitor_card_border") radius: 2 * screenScaleFactor // TODO: Theme! } contentItem: Item @@ -176,7 +176,7 @@ Item height: width // TODO: Theme! sourceSize.width: width // TODO: Theme! sourceSize.height: width // TODO: Theme! - color: "#152950" // TODO: Theme! + color: UM.Theme.getColor("monitor_text_primary") source: UM.Theme.getIcon("arrow_right") } } @@ -204,12 +204,12 @@ Item GradientStop { position: 0.0 - color: "#66f6f6f6" // TODO: Theme! + color: UM.Theme.getColor("monitor_stage_background_fade") } GradientStop { position: 1.0 - color: "#fff6f6f6" // TODO: Theme! + color: UM.Theme.getColor("monitor_stage_background") } } } @@ -238,7 +238,7 @@ Item { background: Rectangle { - color: model.index == currentIndex ? "#777777" : "#d8d8d8" // TODO: Theme! + color: model.index == currentIndex ? UM.Theme.getColor("monitor_carousel_dot_current") : UM.Theme.getColor("monitor_carousel_dot") radius: Math.floor(width / 2) width: 12 * screenScaleFactor // TODO: Theme! height: width // TODO: Theme! diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorContextMenu.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorContextMenu.qml new file mode 100644 index 0000000000..771bd4b8cf --- /dev/null +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorContextMenu.qml @@ -0,0 +1,182 @@ +// Copyright (c) 2018 Ultimaker B.V. +// Cura is released under the terms of the LGPLv3 or higher. + +import QtQuick 2.3 +import QtQuick.Controls 2.0 +import QtQuick.Dialogs 1.1 +import UM 1.3 as UM + +/** + * A MonitorInfoBlurb is an extension of the GenericPopUp used to show static information (vs. interactive context + * menus). It accepts some text (text), an item to link to to (target), and a specification of which side of the target + * to appear on (direction). It also sets the GenericPopUp's color to black, to differentiate itself from a menu. + */ +Item +{ + property alias target: popUp.target + + property var printJob: null + + GenericPopUp + { + id: popUp + + // Which way should the pop-up point? Default is up, but will flip when required + direction: "up" + + // Use dark grey for info blurbs and white for context menus + color: UM.Theme.getColor("monitor_context_menu") + + contentItem: Item + { + id: contentWrapper + implicitWidth: childrenRect.width + implicitHeight: menuItems.height + UM.Theme.getSize("default_margin").height + + Column + { + id: menuItems + width: 144 * screenScaleFactor + + anchors + { + top: parent.top + topMargin: Math.floor(UM.Theme.getSize("default_margin").height / 2) + } + + spacing: Math.floor(UM.Theme.getSize("default_margin").height / 2) + + PrintJobContextMenuItem { + onClicked: { + sendToTopConfirmationDialog.visible = true; + popUp.close(); + } + text: catalog.i18nc("@label", "Move to top"); + visible: { + if (printJob && (printJob.state == "queued" || printJob.state == "error") && !isAssigned(printJob)) { + if (OutputDevice && OutputDevice.queuedPrintJobs[0]) { + return OutputDevice.queuedPrintJobs[0].key != printJob.key; + } + } + return false; + } + } + + PrintJobContextMenuItem { + onClicked: { + deleteConfirmationDialog.visible = true; + popUp.close(); + } + text: catalog.i18nc("@label", "Delete"); + visible: { + if (!printJob) { + return false; + } + var states = ["queued", "error", "sent_to_printer"]; + return states.indexOf(printJob.state) !== -1; + } + } + + PrintJobContextMenuItem { + enabled: visible && !(printJob.state == "pausing" || printJob.state == "resuming"); + onClicked: { + if (printJob.state == "paused") { + printJob.setState("print"); + popUp.close(); + return; + } + if (printJob.state == "printing") { + printJob.setState("pause"); + popUp.close(); + return; + } + } + text: { + if (!printJob) { + return ""; + } + switch(printJob.state) { + case "paused": + return catalog.i18nc("@label", "Resume"); + case "pausing": + return catalog.i18nc("@label", "Pausing..."); + case "resuming": + return catalog.i18nc("@label", "Resuming..."); + default: + catalog.i18nc("@label", "Pause"); + } + } + visible: { + if (!printJob) { + return false; + } + var states = ["printing", "pausing", "paused", "resuming"]; + return states.indexOf(printJob.state) !== -1; + } + } + + PrintJobContextMenuItem { + enabled: visible && printJob.state !== "aborting"; + onClicked: { + abortConfirmationDialog.visible = true; + popUp.close(); + } + text: printJob && printJob.state == "aborting" ? catalog.i18nc("@label", "Aborting...") : catalog.i18nc("@label", "Abort"); + visible: { + if (!printJob) { + return false; + } + var states = ["pre_print", "printing", "pausing", "paused", "resuming"]; + return states.indexOf(printJob.state) !== -1; + } + } + } + } + } + + MessageDialog { + id: sendToTopConfirmationDialog + Component.onCompleted: visible = false + icon: StandardIcon.Warning + onYes: OutputDevice.sendJobToTop(printJob.key) + standardButtons: StandardButton.Yes | StandardButton.No + text: printJob && printJob.name ? catalog.i18nc("@label %1 is the name of a print job.", "Are you sure you want to move %1 to the top of the queue?").arg(printJob.name) : "" + title: catalog.i18nc("@window:title", "Move print job to top") + } + + MessageDialog { + id: deleteConfirmationDialog + Component.onCompleted: visible = false + icon: StandardIcon.Warning + onYes: OutputDevice.deleteJobFromQueue(printJob.key) + standardButtons: StandardButton.Yes | StandardButton.No + text: printJob && printJob.name ? catalog.i18nc("@label %1 is the name of a print job.", "Are you sure you want to delete %1?").arg(printJob.name) : "" + title: catalog.i18nc("@window:title", "Delete print job") + } + + MessageDialog { + id: abortConfirmationDialog + Component.onCompleted: visible = false + icon: StandardIcon.Warning + onYes: printJob.setState("abort") + standardButtons: StandardButton.Yes | StandardButton.No + text: printJob && printJob.name ? catalog.i18nc("@label %1 is the name of a print job.", "Are you sure you want to abort %1?").arg(printJob.name) : "" + title: catalog.i18nc("@window:title", "Abort print") + } + + function switchPopupState() { + popUp.visible ? popUp.close() : popUp.open() + } + function open() { + popUp.open() + } + function close() { + popUp.close() + } + function isAssigned(job) { + if (!job) { + return false; + } + return job.assignedPrinter ? true : false; + } +} diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorContextMenuButton.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorContextMenuButton.qml new file mode 100644 index 0000000000..3e4f1839b6 --- /dev/null +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorContextMenuButton.qml @@ -0,0 +1,31 @@ +// Copyright (c) 2018 Ultimaker B.V. +// Cura is released under the terms of the LGPLv3 or higher. + +import QtQuick 2.3 +import QtQuick.Controls 2.0 +import UM 1.3 as UM +import Cura 1.0 as Cura + +Button +{ + id: base + background: Rectangle + { + color: UM.Theme.getColor("viewport_background") // TODO: Theme! + height: base.height + opacity: base.down || base.hovered ? 1 : 0 + radius: Math.round(0.5 * width) + width: base.width + } + contentItem: Label { + color: UM.Theme.getColor("monitor_text_primary") + font.pixelSize: 32 * screenScaleFactor + horizontalAlignment: Text.AlignHCenter + text: base.text + verticalAlignment: Text.AlignVCenter + } + height: width + hoverEnabled: enabled + text: "\u22EE" //Unicode Three stacked points. + width: 36 * screenScaleFactor // TODO: Theme! +} \ No newline at end of file diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorExtruderConfiguration.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorExtruderConfiguration.qml index 17c0fa8651..4079f23b0a 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/MonitorExtruderConfiguration.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorExtruderConfiguration.qml @@ -36,7 +36,7 @@ Item MonitorIconExtruder { id: extruderIcon - color: "#eeeeee" // TODO: Theme! + color: UM.Theme.getColor("monitor_skeleton_loading") position: 0 } @@ -48,7 +48,7 @@ Item left: extruderIcon.right leftMargin: 12 * screenScaleFactor // TODO: Theme! } - color: materialLabel.visible > 0 ? "transparent" : "#eeeeee" // TODO: Theme! + color: materialLabel.visible > 0 ? "transparent" : UM.Theme.getColor("monitor_skeleton_loading") height: 18 * screenScaleFactor // TODO: Theme! width: Math.max(materialLabel.contentWidth, 60 * screenScaleFactor) // TODO: Theme! radius: 2 * screenScaleFactor // TODO: Theme! @@ -57,7 +57,7 @@ Item { id: materialLabel - color: "#191919" // TODO: Theme! + color: UM.Theme.getColor("monitor_text_primary") elide: Text.ElideRight font: UM.Theme.getFont("default") // 12pt, regular text: "" @@ -77,7 +77,7 @@ Item left: materialLabelWrapper.left bottom: parent.bottom } - color: printCoreLabel.visible > 0 ? "transparent" : "#eeeeee" // TODO: Theme! + color: printCoreLabel.visible > 0 ? "transparent" : UM.Theme.getColor("monitor_skeleton_loading") height: 18 * screenScaleFactor // TODO: Theme! width: Math.max(printCoreLabel.contentWidth, 36 * screenScaleFactor) // TODO: Theme! radius: 2 * screenScaleFactor // TODO: Theme! @@ -86,7 +86,7 @@ Item { id: printCoreLabel - color: "#191919" // TODO: Theme! + color: UM.Theme.getColor("monitor_text_primary") elide: Text.ElideRight font: UM.Theme.getFont("default_bold") // 12pt, bold text: "" diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorIconExtruder.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorIconExtruder.qml index f7d123ada7..c3e78317c5 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/MonitorIconExtruder.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorIconExtruder.qml @@ -39,6 +39,7 @@ Item { id: positionLabel font: UM.Theme.getFont("small") + color: UM.Theme.getColor("monitor_text_primary") height: Math.round(size / 2) horizontalAlignment: Text.AlignHCenter text: position + 1 diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorInfoBlurb.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorInfoBlurb.qml new file mode 100644 index 0000000000..21000b8bff --- /dev/null +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorInfoBlurb.qml @@ -0,0 +1,53 @@ +// Copyright (c) 2018 Ultimaker B.V. +// Cura is released under the terms of the LGPLv3 or higher. + +import QtQuick 2.3 +import QtQuick.Controls 2.0 +import UM 1.3 as UM + +/** + * A MonitorInfoBlurb is an extension of the GenericPopUp used to show static information (vs. interactive context + * menus). It accepts some text (text), an item to link to to (target), and a specification of which side of the target + * to appear on (direction). It also sets the GenericPopUp's color to black, to differentiate itself from a menu. + */ +Item +{ + property alias text: innerLabel.text + property alias target: popUp.target + property alias direction: popUp.direction + + GenericPopUp + { + id: popUp + + // Which way should the pop-up point? Default is up, but will flip when required + direction: "up" + + // Use dark grey for info blurbs and white for context menus + color: UM.Theme.getColor("monitor_tooltip") + + contentItem: Item + { + id: contentWrapper + implicitWidth: childrenRect.width + implicitHeight: innerLabel.contentHeight + 2 * innerLabel.padding + Label + { + id: innerLabel + padding: 12 * screenScaleFactor // TODO: Theme! + text: "" + wrapMode: Text.WordWrap + width: 240 * screenScaleFactor // TODO: Theme! + color: UM.Theme.getColor("monitor_tooltip_text") + font: UM.Theme.getFont("default") + } + } + } + + function open() { + popUp.open() + } + function close() { + popUp.close() + } +} diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorPrintJobCard.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorPrintJobCard.qml index f2b9c3cff7..c7588b83bc 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/MonitorPrintJobCard.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorPrintJobCard.qml @@ -4,6 +4,7 @@ import QtQuick 2.2 import QtQuick.Controls 2.0 import UM 1.3 as UM +import Cura 1.0 as Cura /** * A Print Job Card is essentially just a filled-in Expandable Card item. All @@ -21,13 +22,17 @@ Item // The print job which all other data is derived from property var printJob: null + // If the printer is a cloud printer or not. Other items base their enabled state off of this boolean. In the future + // they might not need to though. + property bool cloudConnection: Cura.MachineManager.activeMachineHasActiveCloudConnection + width: parent.width height: childrenRect.height ExpandableCard { enabled: printJob != null - borderColor: printJob.configurationChanges.length !== 0 ? "#f5a623" : "#CCCCCC" // TODO: Theme! + borderColor: printJob && printJob.configurationChanges.length !== 0 ? UM.Theme.getColor("warning") : UM.Theme.getColor("monitor_card_border") headerItem: Row { height: 48 * screenScaleFactor // TODO: Theme! @@ -49,7 +54,7 @@ Item width: 216 * screenScaleFactor // TODO: Theme! (Should match column size) Rectangle { - color: "#eeeeee" + color: UM.Theme.getColor("monitor_skeleton_loading") width: Math.round(parent.width / 2) height: parent.height visible: !printJob @@ -57,7 +62,7 @@ Item Label { text: printJob && printJob.name ? printJob.name : "" - color: "#374355" + color: UM.Theme.getColor("monitor_text_primary") elide: Text.ElideRight font: UM.Theme.getFont("medium") // 14pt, regular visible: printJob @@ -75,7 +80,7 @@ Item width: 216 * screenScaleFactor // TODO: Theme! (Should match column size) Rectangle { - color: "#eeeeee" + color: UM.Theme.getColor("monitor_skeleton_loading") width: Math.round(parent.width / 3) height: parent.height visible: !printJob @@ -83,7 +88,7 @@ Item Label { text: printJob ? OutputDevice.formatDuration(printJob.timeTotal) : "" - color: "#374355" + color: UM.Theme.getColor("monitor_text_primary") elide: Text.ElideRight font: UM.Theme.getFont("medium") // 14pt, regular visible: printJob @@ -102,7 +107,7 @@ Item Rectangle { - color: "#eeeeee" + color: UM.Theme.getColor("monitor_skeleton_loading") width: 72 * screenScaleFactor // TODO: Theme! height: parent.height visible: !printJob @@ -112,7 +117,7 @@ Item { id: printerAssignmentLabel anchors.verticalCenter: parent.verticalCenter - color: "#374355" + color: UM.Theme.getColor("monitor_text_primary") elide: Text.ElideRight font: UM.Theme.getFont("medium") // 14pt, regular text: { @@ -176,7 +181,7 @@ Item { id: printerConfiguration anchors.verticalCenter: parent.verticalCenter - buildplate: "Glass" + buildplate: catalog.i18nc("@label", "Glass") configurations: [ base.printJob.configuration.extruderConfigurations[0], @@ -186,7 +191,7 @@ Item } Label { text: printJob && printJob.owner ? printJob.owner : "" - color: "#374355" // TODO: Theme! + color: UM.Theme.getColor("monitor_text_primary") elide: Text.ElideRight font: UM.Theme.getFont("medium") // 14pt, regular anchors.top: printerConfiguration.top @@ -198,18 +203,52 @@ Item } } - PrintJobContextMenu + MonitorContextMenuButton { - id: contextButton + id: contextMenuButton anchors { - right: parent.right; + right: parent.right rightMargin: 8 * screenScaleFactor // TODO: Theme! top: parent.top topMargin: 8 * screenScaleFactor // TODO: Theme! } - printJob: base.printJob width: 32 * screenScaleFactor // TODO: Theme! height: 32 * screenScaleFactor // TODO: Theme! + enabled: !cloudConnection + onClicked: enabled ? contextMenu.switchPopupState() : {} + visible: + { + if (!printJob) { + return false + } + var states = ["queued", "error", "sent_to_printer", "pre_print", "printing", "pausing", "paused", "resuming"] + return states.indexOf(printJob.state) !== -1 + } + } + + MonitorContextMenu + { + id: contextMenu + printJob: base.printJob ? base.printJob : null + target: contextMenuButton + } + + // For cloud printing, add this mouse area over the disabled contextButton to indicate that it's not available + MouseArea + { + id: contextMenuDisabledButtonArea + anchors.fill: contextMenuButton + hoverEnabled: contextMenuButton.visible && !contextMenuButton.enabled + onEntered: contextMenuDisabledInfo.open() + onExited: contextMenuDisabledInfo.close() + enabled: !contextMenuButton.enabled + } + + MonitorInfoBlurb + { + id: contextMenuDisabledInfo + text: catalog.i18nc("@info", "These options are not available because you are monitoring a cloud printer.") + target: contextMenuButton } } \ No newline at end of file diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorPrintJobPreview.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorPrintJobPreview.qml index d0bad63258..a392571757 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/MonitorPrintJobPreview.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorPrintJobPreview.qml @@ -19,7 +19,7 @@ Item Rectangle { anchors.fill: parent - color: printJob ? "transparent" : "#eeeeee" // TODO: Theme! + color: printJob ? "transparent" : UM.Theme.getColor("monitor_skeleton_loading") radius: 8 // TODO: Theme! Image { diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorPrintJobProgressBar.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorPrintJobProgressBar.qml index d5d4705a36..2ba70268b2 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/MonitorPrintJobProgressBar.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorPrintJobProgressBar.qml @@ -34,15 +34,15 @@ Item { background: Rectangle { - color: "#f5f5f5" // TODO: Theme! - implicitHeight: visible ? 8 * screenScaleFactor : 0 // TODO: Theme! + color: UM.Theme.getColor("monitor_progress_bar_empty") + implicitHeight: visible ? 12 * screenScaleFactor : 0 // TODO: Theme! implicitWidth: 180 * screenScaleFactor // TODO: Theme! radius: 2 * screenScaleFactor // TODO: Theme! } progress: Rectangle { id: progressItem; - color: printJob && printJob.isActive ? "#3282ff" : "#CCCCCC" // TODO: Theme! + color: printJob && printJob.isActive ? UM.Theme.getColor("monitor_progress_bar_fill") : UM.Theme.getColor("monitor_progress_bar_deactive") radius: 2 * screenScaleFactor // TODO: Theme! } } @@ -56,7 +56,7 @@ Item leftMargin: 18 * screenScaleFactor // TODO: Theme! } text: printJob ? Math.round(printJob.progress * 100) + "%" : "0%" - color: printJob && printJob.isActive ? "#374355" : "#babac1" // TODO: Theme! + color: printJob && printJob.isActive ? UM.Theme.getColor("monitor_text_primary") : UM.Theme.getColor("monitor_text_disabled") width: contentWidth font: UM.Theme.getFont("medium") // 14pt, regular @@ -72,7 +72,7 @@ Item left: percentLabel.right leftMargin: 18 * screenScaleFactor // TODO: Theme! } - color: "#374355" // TODO: Theme! + color: UM.Theme.getColor("monitor_text_primary") font: UM.Theme.getFont("medium") // 14pt, regular text: { diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorPrinterCard.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorPrinterCard.qml index facfaaaaaf..e56e22e40f 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/MonitorPrinterCard.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorPrinterCard.qml @@ -5,15 +5,14 @@ import QtQuick 2.3 import QtQuick.Controls 2.0 import QtQuick.Dialogs 1.1 import UM 1.3 as UM +import Cura 1.0 as Cura /** - * A Printer Card is has two main components: the printer portion and the print - * job portion, the latter being paired in the UI when a print job is paired - * a printer in-cluster. + * A Printer Card is has two main components: the printer portion and the print job portion, the latter being paired in + * the UI when a print job is paired a printer in-cluster. * - * NOTE: For most labels, a fixed height with vertical alignment is used to make - * layouts more deterministic (like the fixed-size textboxes used in original - * mock-ups). This is also a stand-in for CSS's 'line-height' property. Denoted + * NOTE: For most labels, a fixed height with vertical alignment is used to make layouts more deterministic (like the + * fixed-size textboxes used in original mock-ups). This is also a stand-in for CSS's 'line-height' property. Denoted * with '// FIXED-LINE-HEIGHT:'. */ Item @@ -25,11 +24,14 @@ Item property var borderSize: 1 * screenScaleFactor // TODO: Theme, and remove from here - // If the printer card's controls are enabled. This is used by the carousel - // to prevent opening the context menu or camera while the printer card is not - // "in focus" + // If the printer card's controls are enabled. This is used by the carousel to prevent opening the context menu or + // camera while the printer card is not "in focus" property var enabled: true + // If the printer is a cloud printer or not. Other items base their enabled state off of this boolean. In the future + // they might not need to though. + property bool cloudConnection: Cura.MachineManager.activeMachineHasActiveCloudConnection + width: 834 * screenScaleFactor // TODO: Theme! height: childrenRect.height @@ -37,10 +39,10 @@ Item { id: background anchors.fill: parent - color: "#FFFFFF" // TODO: Theme! + color: UM.Theme.getColor("monitor_card_background") border { - color: "#CCCCCC" // TODO: Theme! + color: UM.Theme.getColor("monitor_card_border") width: borderSize // TODO: Remove once themed } radius: 2 * screenScaleFactor // TODO: Theme! @@ -69,7 +71,7 @@ Item id: printerImage width: 108 * screenScaleFactor // TODO: Theme! height: 108 * screenScaleFactor // TODO: Theme! - color: printer ? "transparent" : "#eeeeee" // TODO: Theme! + color: printer ? "transparent" : UM.Theme.getColor("monitor_skeleton_loading") radius: 8 // TODO: Theme! Image { @@ -93,8 +95,7 @@ Item Rectangle { id: printerNameLabel - // color: "#414054" // TODO: Theme! - color: printer ? "transparent" : "#eeeeee" // TODO: Theme! + color: printer ? "transparent" : UM.Theme.getColor("monitor_skeleton_loading") height: 18 * screenScaleFactor // TODO: Theme! width: parent.width radius: 2 * screenScaleFactor // TODO: Theme! @@ -102,7 +103,7 @@ Item Label { text: printer && printer.name ? printer.name : "" - color: "#414054" // TODO: Theme! + color: UM.Theme.getColor("monitor_text_primary") elide: Text.ElideRight font: UM.Theme.getFont("large") // 16pt, bold width: parent.width @@ -116,7 +117,7 @@ Item Rectangle { - color: "#eeeeee" // TODO: Theme! + color: UM.Theme.getColor("monitor_skeleton_loading") height: 18 * screenScaleFactor // TODO: Theme! radius: 2 * screenScaleFactor // TODO: Theme! visible: !printer @@ -156,16 +157,11 @@ Item } height: 72 * screenScaleFactor // TODO: Theme!te theRect's x property } - - // TODO: Make this work. - PropertyAnimation { target: printerConfiguration; property: "visible"; to: 0; loops: Animation.Infinite; duration: 500 } } - - - PrintJobContextMenu + MonitorContextMenuButton { - id: contextButton + id: contextMenuButton anchors { right: parent.right @@ -173,15 +169,49 @@ Item top: parent.top topMargin: 12 * screenScaleFactor // TODO: Theme! } - printJob: printer ? printer.activePrintJob : null width: 36 * screenScaleFactor // TODO: Theme! height: 36 * screenScaleFactor // TODO: Theme! - enabled: base.enabled - visible: printer + enabled: !cloudConnection + + onClicked: enabled ? contextMenu.switchPopupState() : {} + visible: + { + if (!printer || !printer.activePrintJob) { + return false + } + var states = ["queued", "error", "sent_to_printer", "pre_print", "printing", "pausing", "paused", "resuming"] + return states.indexOf(printer.activePrintJob.state) !== -1 + } } + + MonitorContextMenu + { + id: contextMenu + printJob: printer ? printer.activePrintJob : null + target: contextMenuButton + } + + // For cloud printing, add this mouse area over the disabled contextButton to indicate that it's not available + MouseArea + { + id: contextMenuDisabledButtonArea + anchors.fill: contextMenuButton + hoverEnabled: contextMenuButton.visible && !contextMenuButton.enabled + onEntered: contextMenuDisabledInfo.open() + onExited: contextMenuDisabledInfo.close() + enabled: !contextMenuButton.enabled + } + + MonitorInfoBlurb + { + id: contextMenuDisabledInfo + text: catalog.i18nc("@info", "These options are not available because you are monitoring a cloud printer.") + target: contextMenuButton + } + CameraButton { - id: cameraButton; + id: cameraButton anchors { right: parent.right @@ -190,9 +220,27 @@ Item bottomMargin: 20 * screenScaleFactor // TODO: Theme! } iconSource: "../svg/icons/camera.svg" - enabled: base.enabled + enabled: !cloudConnection visible: printer } + + // For cloud printing, add this mouse area over the disabled cameraButton to indicate that it's not available + MouseArea + { + id: cameraDisabledButtonArea + anchors.fill: cameraButton + hoverEnabled: cameraButton.visible && !cameraButton.enabled + onEntered: cameraDisabledInfo.open() + onExited: cameraDisabledInfo.close() + enabled: !cameraButton.enabled + } + + MonitorInfoBlurb + { + id: cameraDisabledInfo + text: catalog.i18nc("@info", "The webcam is not available because you are monitoring a cloud printer.") + target: cameraButton + } } @@ -220,7 +268,7 @@ Item } border { - color: printer && printer.activePrintJob && printer.activePrintJob.configurationChanges.length > 0 ? "#f5a623" : "transparent" // TODO: Theme! + color: printer && printer.activePrintJob && printer.activePrintJob.configurationChanges.length > 0 ? UM.Theme.getColor("warning") : "transparent" // TODO: Theme! width: borderSize // TODO: Remove once themed } color: "transparent" // TODO: Theme! @@ -246,7 +294,7 @@ Item { verticalCenter: parent.verticalCenter } - color: printer ? "#414054" : "#aaaaaa" // TODO: Theme! + color: printer ? UM.Theme.getColor("monitor_text_primary") : UM.Theme.getColor("monitor_text_disabled") font: UM.Theme.getFont("large_bold") // 16pt, bold text: { if (!printer) { @@ -299,10 +347,10 @@ Item Label { id: printerJobNameLabel - color: printer && printer.activePrintJob && printer.activePrintJob.isActive ? "#414054" : "#babac1" // TODO: Theme! + color: printer && printer.activePrintJob && printer.activePrintJob.isActive ? UM.Theme.getColor("monitor_text_primary") : UM.Theme.getColor("monitor_text_disabled") elide: Text.ElideRight font: UM.Theme.getFont("large") // 16pt, bold - text: printer && printer.activePrintJob ? printer.activePrintJob.name : "Untitled" // TODO: I18N + text: printer && printer.activePrintJob ? printer.activePrintJob.name : catalog.i18nc("@label", "Untitled") width: parent.width // FIXED-LINE-HEIGHT: @@ -319,10 +367,10 @@ Item topMargin: 6 * screenScaleFactor // TODO: Theme! left: printerJobNameLabel.left } - color: printer && printer.activePrintJob && printer.activePrintJob.isActive ? "#53657d" : "#babac1" // TODO: Theme! + color: printer && printer.activePrintJob && printer.activePrintJob.isActive ? UM.Theme.getColor("monitor_text_primary") : UM.Theme.getColor("monitor_text_disabled") elide: Text.ElideRight font: UM.Theme.getFont("default") // 12pt, regular - text: printer && printer.activePrintJob ? printer.activePrintJob.owner : "Anonymous" // TODO: I18N + text: printer && printer.activePrintJob ? printer.activePrintJob.owner : catalog.i18nc("@label", "Anonymous") width: parent.width // FIXED-LINE-HEIGHT: @@ -348,7 +396,7 @@ Item verticalCenter: parent.verticalCenter } font: UM.Theme.getFont("default") - text: "Requires configuration changes" + text: catalog.i18nc("@label:status", "Requires configuration changes") visible: printer && printer.activePrintJob && printer.activePrintJob.configurationChanges.length > 0 && !printerStatus.visible // FIXED-LINE-HEIGHT: @@ -368,13 +416,13 @@ Item } background: Rectangle { - color: "#d8d8d8" // TODO: Theme! + color: UM.Theme.getColor("monitor_secondary_button_shadow") radius: 2 * screenScaleFactor // Todo: Theme! Rectangle { anchors.fill: parent anchors.bottomMargin: 2 * screenScaleFactor // TODO: Theme! - color: detailsButton.hovered ? "#e4e4e4" : "#f0f0f0" // TODO: Theme! + color: detailsButton.hovered ? UM.Theme.getColor("monitor_secondary_button_hover") : UM.Theme.getColor("monitor_secondary_button") radius: 2 * screenScaleFactor // Todo: Theme! } } @@ -382,9 +430,9 @@ Item { anchors.fill: parent anchors.bottomMargin: 2 * screenScaleFactor // TODO: Theme! - color: "#1e66d7" // TODO: Theme! + color: UM.Theme.getColor("monitor_secondary_button_text") font: UM.Theme.getFont("medium") // 14pt, regular - text: "Details" // TODO: I18NC! + text: catalog.i18nc("@action:button","Details"); verticalAlignment: Text.AlignVCenter horizontalAlignment: Text.AlignHCenter height: 18 * screenScaleFactor // TODO: Theme! diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorPrinterConfiguration.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorPrinterConfiguration.qml index debc8b7959..dbe085e18e 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/MonitorPrinterConfiguration.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorPrinterConfiguration.qml @@ -37,7 +37,7 @@ Item MonitorExtruderConfiguration { - color: modelData && modelData.activeMaterial ? modelData.activeMaterial.color : "#eeeeee" // TODO: Theme! + color: modelData && modelData.activeMaterial ? modelData.activeMaterial.color : UM.Theme.getColor("monitor_skeleton_loading") material: modelData && modelData.activeMaterial ? modelData.activeMaterial.name : "" position: modelData && typeof(modelData.position) === "number" ? modelData.position : -1 // Use negative one to create empty extruder number printCore: modelData ? modelData.hotendID : "" diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorPrinterPill.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorPrinterPill.qml index 2408089e1e..2aeecd5a92 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/MonitorPrinterPill.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorPrinterPill.qml @@ -32,14 +32,14 @@ Item Rectangle { id: background anchors.fill: parent - color: printerNameLabel.visible ? "#e4e4f2" : "#eeeeee"// TODO: Theme! + color: printerNameLabel.visible ? UM.Theme.getColor("monitor_printer_family_tag") : UM.Theme.getColor("monitor_skeleton_loading") radius: 2 * screenScaleFactor // TODO: Theme! } Label { id: printerNameLabel anchors.centerIn: parent - color: "#535369" // TODO: Theme! + color: UM.Theme.getColor("monitor_text_primary") text: tagText font.pointSize: 10 // TODO: Theme! visible: text !== "" diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorQueue.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorQueue.qml index f2dc09de95..c9996849fb 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/MonitorQueue.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorQueue.qml @@ -22,7 +22,7 @@ Item left: queuedPrintJobs.left top: parent.top } - color: UM.Theme.getColor("text") + color: UM.Theme.getColor("monitor_text_primary") font: UM.Theme.getFont("large") text: catalog.i18nc("@label", "Queued") } @@ -42,7 +42,7 @@ Item { id: externalLinkIcon anchors.verticalCenter: manageQueueLabel.verticalCenter - color: UM.Theme.getColor("text_link") + color: UM.Theme.getColor("monitor_text_link") source: UM.Theme.getIcon("external_link") width: 16 * screenScaleFactor // TODO: Theme! (Y U NO USE 18 LIKE ALL OTHER ICONS?!) height: 16 * screenScaleFactor // TODO: Theme! (Y U NO USE 18 LIKE ALL OTHER ICONS?!) @@ -56,9 +56,9 @@ Item leftMargin: 6 * screenScaleFactor // TODO: Theme! verticalCenter: externalLinkIcon.verticalCenter } - color: UM.Theme.getColor("text_link") + color: UM.Theme.getColor("monitor_text_link") font: UM.Theme.getFont("default") // 12pt, regular - linkColor: UM.Theme.getColor("text_link") + linkColor: UM.Theme.getColor("monitor_text_link") text: catalog.i18nc("@label link to connect manager", "Manage queue in Cura Connect") renderType: Text.NativeRendering } @@ -94,7 +94,7 @@ Item Label { text: catalog.i18nc("@label", "Print jobs") - color: "#666666" + color: UM.Theme.getColor("monitor_text_primary") elide: Text.ElideRight font: UM.Theme.getFont("medium") // 14pt, regular anchors.verticalCenter: parent.verticalCenter @@ -108,7 +108,7 @@ Item Label { text: catalog.i18nc("@label", "Total print time") - color: "#666666" + color: UM.Theme.getColor("monitor_text_primary") elide: Text.ElideRight font: UM.Theme.getFont("medium") // 14pt, regular anchors.verticalCenter: parent.verticalCenter @@ -122,7 +122,7 @@ Item Label { text: catalog.i18nc("@label", "Waiting for") - color: "#666666" + color: UM.Theme.getColor("monitor_text_primary") elide: Text.ElideRight font: UM.Theme.getFont("medium") // 14pt, regular anchors.verticalCenter: parent.verticalCenter diff --git a/plugins/UM3NetworkPrinting/resources/qml/MonitorStage.qml b/plugins/UM3NetworkPrinting/resources/qml/MonitorStage.qml index 8723e6f46e..59cbda7172 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/MonitorStage.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/MonitorStage.qml @@ -11,7 +11,7 @@ import QtGraphicalEffects 1.0 // This is the root component for the monitor stage. Component { - Item + Rectangle { id: monitorFrame @@ -24,6 +24,7 @@ Component } } width: maximumWidth + color: UM.Theme.getColor("monitor_stage_background") // Enable keyboard navigation. NOTE: This is done here so that we can also potentially // forward to the queue items in the future. (Deleting selected print job, etc.) @@ -36,24 +37,6 @@ Component name: "cura" } - LinearGradient - { - anchors.fill: parent - gradient: Gradient - { - GradientStop - { - position: 0.0 - color: "#f6f6f6" // TODO: Theme! - } - GradientStop - { - position: 1.0 - color: "#ffffff" // TODO: Theme! - } - } - } - Item { id: printers diff --git a/plugins/UM3NetworkPrinting/resources/qml/PrintJobContextMenu.qml b/plugins/UM3NetworkPrinting/resources/qml/PrintJobContextMenu.qml deleted file mode 100644 index 5c5c892dad..0000000000 --- a/plugins/UM3NetworkPrinting/resources/qml/PrintJobContextMenu.qml +++ /dev/null @@ -1,274 +0,0 @@ -// Copyright (c) 2018 Ultimaker B.V. -// Cura is released under the terms of the LGPLv3 or higher. - -import QtQuick 2.2 -import QtQuick.Controls 2.0 -import QtQuick.Controls.Styles 1.4 -import QtQuick.Dialogs 1.1 -import QtGraphicalEffects 1.0 -import UM 1.3 as UM - -Item { - id: root; - property var printJob: null; - property var started: isStarted(printJob); - property var assigned: isAssigned(printJob); - property var enabled: true - - Button { - id: button; - background: Rectangle { - color: UM.Theme.getColor("viewport_background"); // TODO: Theme! - height: button.height; - opacity: button.down || button.hovered ? 1 : 0; - radius: Math.round(0.5 * width); - width: button.width; - } - contentItem: Label { - color: UM.Theme.getColor("monitor_context_menu_dots"); - font.pixelSize: 32 * screenScaleFactor; - horizontalAlignment: Text.AlignHCenter; - text: button.text; - verticalAlignment: Text.AlignVCenter; - } - height: width; - hoverEnabled: base.enabled - onClicked: base.enabled ? parent.switchPopupState() : {} - text: "\u22EE"; //Unicode; Three stacked points. - visible: { - if (!printJob) { - return false; - } - var states = ["queued", "sent_to_printer", "pre_print", "printing", "pausing", "paused", "resuming"]; - return states.indexOf(printJob.state) !== -1; - } - width: 36 * screenScaleFactor; // TODO: Theme! - } - - Popup { - id: popup; - background: Item { - anchors.fill: parent; - - DropShadow { - anchors.fill: pointedRectangle; - color: UM.Theme.getColor("monitor_shadow"); - radius: UM.Theme.getSize("monitor_shadow_radius").width; - source: pointedRectangle; - transparentBorder: true; - verticalOffset: 2 * screenScaleFactor; - } - - Item { - id: pointedRectangle; - anchors { - horizontalCenter: parent.horizontalCenter; - verticalCenter: parent.verticalCenter; - } - height: parent.height - 10 * screenScaleFactor; // Because of the shadow - width: parent.width - 10 * screenScaleFactor; // Because of the shadow - - Rectangle { - id: point; - anchors { - right: bloop.right; - rightMargin: 24 * screenScaleFactor; - } - color: UM.Theme.getColor("monitor_context_menu_background"); - height: 14 * screenScaleFactor; - transform: Rotation { - angle: 45; - } - width: 14 * screenScaleFactor; - y: 1 * screenScaleFactor; - } - - Rectangle { - id: bloop; - anchors { - bottom: parent.bottom; - bottomMargin: 8 * screenScaleFactor; // Because of the shadow - top: parent.top; - topMargin: 8 * screenScaleFactor; // Because of the shadow + point - } - color: UM.Theme.getColor("monitor_context_menu_background"); - width: parent.width; - } - } - } - clip: true; - closePolicy: Popup.CloseOnPressOutside; - contentItem: Column { - id: popupOptions; - anchors { - top: parent.top; - topMargin: UM.Theme.getSize("default_margin").height + 10 * screenScaleFactor; // Account for the point of the box - } - height: childrenRect.height + spacing * popupOptions.children.length + UM.Theme.getSize("default_margin").height; - spacing: Math.floor(UM.Theme.getSize("default_margin").height / 2); - width: parent.width; - - PrintJobContextMenuItem { - onClicked: { - sendToTopConfirmationDialog.visible = true; - popup.close(); - } - text: catalog.i18nc("@label", "Move to top"); - visible: { - if (printJob && printJob.state == "queued" && !assigned) { - if (OutputDevice && OutputDevice.queuedPrintJobs[0]) { - return OutputDevice.queuedPrintJobs[0].key != printJob.key; - } - } - return false; - } - } - - PrintJobContextMenuItem { - onClicked: { - deleteConfirmationDialog.visible = true; - popup.close(); - } - text: catalog.i18nc("@label", "Delete"); - visible: { - if (!printJob) { - return false; - } - var states = ["queued", "sent_to_printer"]; - return states.indexOf(printJob.state) !== -1; - } - } - - PrintJobContextMenuItem { - enabled: visible && !(printJob.state == "pausing" || printJob.state == "resuming"); - onClicked: { - if (printJob.state == "paused") { - printJob.setState("print"); - popup.close(); - return; - } - if (printJob.state == "printing") { - printJob.setState("pause"); - popup.close(); - return; - } - } - text: { - if (!printJob) { - return ""; - } - switch(printJob.state) { - case "paused": - return catalog.i18nc("@label", "Resume"); - case "pausing": - return catalog.i18nc("@label", "Pausing..."); - case "resuming": - return catalog.i18nc("@label", "Resuming..."); - default: - catalog.i18nc("@label", "Pause"); - } - } - visible: { - if (!printJob) { - return false; - } - var states = ["printing", "pausing", "paused", "resuming"]; - return states.indexOf(printJob.state) !== -1; - } - } - - PrintJobContextMenuItem { - enabled: visible && printJob.state !== "aborting"; - onClicked: { - abortConfirmationDialog.visible = true; - popup.close(); - } - text: printJob && printJob.state == "aborting" ? catalog.i18nc("@label", "Aborting...") : catalog.i18nc("@label", "Abort"); - visible: { - if (!printJob) { - return false; - } - var states = ["pre_print", "printing", "pausing", "paused", "resuming"]; - return states.indexOf(printJob.state) !== -1; - } - } - } - enter: Transition { - NumberAnimation { - duration: 75; - property: "visible"; - } - } - exit: Transition { - NumberAnimation { - duration: 75; - property: "visible"; - } - } - height: contentItem.height + 2 * padding; - onClosed: visible = false; - onOpened: visible = true; - padding: UM.Theme.getSize("monitor_shadow_radius").width; - transformOrigin: Popup.Top; - visible: false; - width: 182 * screenScaleFactor; - x: (button.width - width) + 26 * screenScaleFactor; - y: button.height + 5 * screenScaleFactor; // Because shadow - } - - MessageDialog { - id: sendToTopConfirmationDialog; - Component.onCompleted: visible = false; - icon: StandardIcon.Warning; - onYes: OutputDevice.sendJobToTop(printJob.key); - standardButtons: StandardButton.Yes | StandardButton.No; - text: printJob && printJob.name ? catalog.i18nc("@label %1 is the name of a print job.", "Are you sure you want to move %1 to the top of the queue?").arg(printJob.name) : ""; - title: catalog.i18nc("@window:title", "Move print job to top"); - } - - MessageDialog { - id: deleteConfirmationDialog; - Component.onCompleted: visible = false; - icon: StandardIcon.Warning; - onYes: OutputDevice.deleteJobFromQueue(printJob.key); - standardButtons: StandardButton.Yes | StandardButton.No; - text: printJob && printJob.name ? catalog.i18nc("@label %1 is the name of a print job.", "Are you sure you want to delete %1?").arg(printJob.name) : ""; - title: catalog.i18nc("@window:title", "Delete print job"); - } - - MessageDialog { - id: abortConfirmationDialog; - Component.onCompleted: visible = false; - icon: StandardIcon.Warning; - onYes: printJob.setState("abort"); - standardButtons: StandardButton.Yes | StandardButton.No; - text: printJob && printJob.name ? catalog.i18nc("@label %1 is the name of a print job.", "Are you sure you want to abort %1?").arg(printJob.name) : ""; - title: catalog.i18nc("@window:title", "Abort print"); - } - - // Utils - function switchPopupState() { - popup.visible ? popup.close() : popup.open(); - } - function isStarted(job) { - if (!job) { - return false; - } - return ["pre_print", "printing", "pausing", "paused", "resuming", "aborting"].indexOf(job.state) !== -1; - } - function isAssigned(job) { - if (!job) { - return false; - } - return job.assignedPrinter ? true : false; - } - function getMenuLength() { - var visible = 0; - for (var i = 0; i < popupOptions.children.length; i++) { - if (popupOptions.children[i].visible) { - visible++; - } - } - return visible; - } -} diff --git a/plugins/UM3NetworkPrinting/resources/qml/PrintJobContextMenuItem.qml b/plugins/UM3NetworkPrinting/resources/qml/PrintJobContextMenuItem.qml index eea8fac3e1..67c82db320 100644 --- a/plugins/UM3NetworkPrinting/resources/qml/PrintJobContextMenuItem.qml +++ b/plugins/UM3NetworkPrinting/resources/qml/PrintJobContextMenuItem.qml @@ -9,10 +9,10 @@ import UM 1.3 as UM Button { background: Rectangle { opacity: parent.down || parent.hovered ? 1 : 0; - color: UM.Theme.getColor("monitor_context_menu_highlight"); + color: UM.Theme.getColor("monitor_context_menu_hover") } contentItem: Label { - color: enabled ? UM.Theme.getColor("text") : UM.Theme.getColor("text_inactive"); + color: enabled ? UM.Theme.getColor("monitor_text_primary") : UM.Theme.getColor("monitor_text_disabled"); text: parent.text horizontalAlignment: Text.AlignLeft; verticalAlignment: Text.AlignVCenter; diff --git a/plugins/UM3NetworkPrinting/src/ClusterUM3OutputDevice.py b/plugins/UM3NetworkPrinting/src/ClusterUM3OutputDevice.py index b48f9380e1..052dd0b979 100644 --- a/plugins/UM3NetworkPrinting/src/ClusterUM3OutputDevice.py +++ b/plugins/UM3NetworkPrinting/src/ClusterUM3OutputDevice.py @@ -13,6 +13,7 @@ from UM.FileHandler.WriteFileJob import WriteFileJob # To call the file writer from UM.Logger import Logger from UM.Settings.ContainerRegistry import ContainerRegistry from UM.i18n import i18nCatalog +from UM.Qt.Duration import Duration, DurationFormat from UM.Message import Message from UM.Scene.SceneNode import SceneNode # For typing. @@ -346,6 +347,10 @@ class ClusterUM3OutputDevice(NetworkedPrinterOutputDevice): def getDateCompleted(self, time_remaining: int) -> str: return formatDateCompleted(time_remaining) + @pyqtSlot(int, result = str) + def formatDuration(self, seconds: int) -> str: + return Duration(seconds).getDisplayString(DurationFormat.Format.Short) + @pyqtSlot(str) def sendJobToTop(self, print_job_uuid: str) -> None: # This function is part of the output device (and not of the printjob output model) as this type of operation diff --git a/plugins/USBPrinting/USBPrinterOutputDevice.py b/plugins/USBPrinting/USBPrinterOutputDevice.py index 89903b06f4..2b516fb553 100644 --- a/plugins/USBPrinting/USBPrinterOutputDevice.py +++ b/plugins/USBPrinting/USBPrinterOutputDevice.py @@ -55,6 +55,7 @@ class USBPrinterOutputDevice(PrinterOutputDevice): self._update_thread = Thread(target = self._update, daemon = True) self._last_temperature_request = None # type: Optional[int] + self._firmware_idle_count = 0 self._is_printing = False # A print is being sent. diff --git a/resources/qml/Menus/ConfigurationMenu/ConfigurationItem.qml b/resources/qml/Menus/ConfigurationMenu/ConfigurationItem.qml index 058c1ff4c2..296ae62366 100644 --- a/resources/qml/Menus/ConfigurationMenu/ConfigurationItem.qml +++ b/resources/qml/Menus/ConfigurationMenu/ConfigurationItem.qml @@ -218,7 +218,8 @@ Button { if(isValidMaterial) { - Cura.MachineManager.applyRemoteConfiguration(configuration); + toggleContent() + Cura.MachineManager.applyRemoteConfiguration(configuration) } } } diff --git a/resources/qml/Preferences/ProfilesPage.qml b/resources/qml/Preferences/ProfilesPage.qml index f23a04d800..52c69b780e 100644 --- a/resources/qml/Preferences/ProfilesPage.qml +++ b/resources/qml/Preferences/ProfilesPage.qml @@ -173,6 +173,7 @@ Item id: createQualityDialog title: catalog.i18nc("@title:window", "Create Profile") object: "" + explanation: catalog.i18nc("@info", "Please provide a name for this profile.") onAccepted: { base.newQualityNameToSelect = newName; // We want to switch to the new profile once it's created diff --git a/resources/themes/cura-dark/theme.json b/resources/themes/cura-dark/theme.json index 6b29073475..6211320f10 100644 --- a/resources/themes/cura-dark/theme.json +++ b/resources/themes/cura-dark/theme.json @@ -215,24 +215,40 @@ "toolbox_header_button_text_inactive": [128, 128, 128, 255], "toolbox_header_button_text_hovered": [255, 255, 255, 255], - "monitor_card_background_inactive": [43, 48, 52, 255], - "monitor_card_background": [43, 48, 52, 255], - "monitor_context_menu_background": [80, 84, 87, 255], - "monitor_context_menu_dots": [0, 167, 233, 255], - "monitor_context_menu_highlight": [0, 167, 233, 255], - "monitor_image_overlay": [255, 255, 255, 255], - "monitor_lining_heavy": [255, 255, 255, 255], - "monitor_lining_light": [102, 102, 102, 255], - "monitor_pill_background": [102, 102, 102, 255], + "monitor_printer_family_tag": [86, 86, 106, 255], + "monitor_text_primary": [229, 229, 229, 255], + "monitor_text_disabled": [102, 102, 102, 255], + "monitor_text_link": [103, 160, 252, 255], + "monitor_icon_primary": [229, 229, 229, 255], + "monitor_icon_accent": [51, 53, 54, 255], + + "monitor_secondary_button_hover": [80, 80, 80, 255], + "monitor_secondary_button": [92, 92, 92, 255], + "monitor_secondary_button_text": [250, 250, 250, 255], + "monitor_secondary_button_shadow": [74, 74, 74, 255], + + "monitor_card_border": [102, 102, 102, 255], + "monitor_card_background": [51, 53, 54, 255], + "monitor_card_hover": [84, 89, 95, 255], + + "monitor_stage_background": [30, 36, 39, 255], + "monitor_stage_background_fade": [30, 36, 39, 102], + + "monitor_progress_bar_fill": [50, 130, 255, 255], + "monitor_progress_bar_deactive": [102, 102, 102, 255], + "monitor_progress_bar_empty": [67, 67, 67, 255], + + "monitor_tooltip": [25, 25, 25, 255], + "monitor_tooltip_text": [229, 229, 229, 255], + "monitor_context_menu": [67, 67, 67, 255], + "monitor_context_menu_hover": [30, 102, 215, 255], + + "monitor_skeleton_loading": [102, 102, 102, 255], "monitor_placeholder_image": [102, 102, 102, 255], - "monitor_printer_icon": [255, 255, 255, 255], - "monitor_progress_background_text": [102, 102, 102, 255], - "monitor_progress_background": [80, 84, 87, 255], - "monitor_progress_fill_inactive": [216, 216, 216, 255], - "monitor_progress_fill_text": [0, 0, 0, 255], - "monitor_progress_fill": [216, 216, 216, 255], - "monotir_printer_icon_inactive": [154, 154, 154, 255], - "monitor_skeleton_fill": [31, 36, 39, 255], - "monitor_skeleton_fill_dark": [31, 36, 39, 255] + "monitor_image_overlay": [0, 0, 0, 255], + "monitor_shadow": [4, 10, 13, 255], + + "monitor_carousel_dot": [119, 119, 119, 255], + "monitor_carousel_dot_current": [216, 216, 216, 255] } } diff --git a/resources/themes/cura-light/theme.json b/resources/themes/cura-light/theme.json index 6e76080c3e..3d5aba7477 100644 --- a/resources/themes/cura-light/theme.json +++ b/resources/themes/cura-light/theme.json @@ -400,27 +400,41 @@ "favorites_header_text_hover": [31, 36, 39, 255], "favorites_row_selected": [196, 239, 255, 255], - "monitor_card_background_inactive": [240, 240, 240, 255], + "monitor_printer_family_tag": [228, 228, 242, 255], + "monitor_text_primary": [65, 64, 84, 255], + "monitor_text_disabled": [238, 238, 238, 255], + "monitor_text_link": [50, 130, 255, 255], + "monitor_icon_primary": [10, 8, 80, 255], + "monitor_icon_accent": [255, 255, 255, 255], + + "monitor_secondary_button_hover": [228, 228, 228, 255], + "monitor_secondary_button": [240, 240, 240, 255], + "monitor_secondary_button_text": [30, 102, 215, 255], + "monitor_secondary_button_shadow": [216, 216, 216, 255], + + "monitor_card_border": [192, 193, 194, 255], "monitor_card_background": [255, 255, 255, 255], - "monitor_context_menu_background": [255, 255, 255, 255], - "monitor_context_menu_dots": [154, 154, 154, 255], - "monitor_context_menu_highlight": [245, 245, 245, 255], - "monitor_image_overlay": [0, 0, 0, 255], - "monitor_lining_heavy": [0, 0, 0, 255], - "monitor_lining_light": [230, 230, 230, 255], - "monitor_pill_background": [245, 245, 245, 255], + "monitor_card_hover": [232, 242, 252, 255], + + "monitor_stage_background": [246, 246, 246, 255], + "monitor_stage_background_fade": [246, 246, 246, 102], + + "monitor_progress_bar_fill": [50, 130, 255, 255], + "monitor_progress_bar_deactive": [192, 193, 194, 255], + "monitor_progress_bar_empty": [245, 245, 245, 255], + + "monitor_tooltip": [25, 25, 25, 255], + "monitor_tooltip_text": [255, 255, 255, 255], + "monitor_context_menu": [255, 255, 255, 255], + "monitor_context_menu_hover": [245, 245, 245, 255], + + "monitor_skeleton_loading": [238, 238, 238, 255], "monitor_placeholder_image": [230, 230, 230, 255], - "monitor_printer_icon_inactive": [154, 154, 154, 255], - "monitor_printer_icon": [50, 130, 255, 255], - "monitor_progress_background_text": [0,0,0,255], - "monitor_progress_background": [245, 245, 245, 255], - "monitor_progress_fill_inactive": [154, 154, 154, 255], - "monitor_progress_fill_text": [255,255,255,255], - "monitor_progress_fill": [50, 130, 255, 255], - "monitor_shadow": [0, 0, 0, 63], - "monitor_skeleton_fill": [245, 245, 245, 255], - "monitor_skeleton_fill_dark": [216, 216, 216, 255], - "monitor_text_inactive": [154, 154, 154, 255] + "monitor_image_overlay": [0, 0, 0, 255], + "monitor_shadow": [220, 220, 220, 255], + + "monitor_carousel_dot": [216, 216, 216, 255], + "monitor_carousel_dot_current": [119, 119, 119, 255] }, "sizes": {