Resolve merge conflicts with master

This commit is contained in:
Lipu Fei 2019-11-06 12:01:49 +01:00
commit 7c36b6a8ba
67 changed files with 1716 additions and 171 deletions

View file

@ -87,9 +87,25 @@ Cura.MachineAction
}
}
}
Label
{
id: machineNameLabel
anchors.top: parent.top
anchors.left: parent.left
anchors.leftMargin: UM.Theme.getSize("default_margin").width
text: Cura.MachineManager.activeMachine.name
horizontalAlignment: Text.AlignHCenter
font: UM.Theme.getFont("large_bold")
color: UM.Theme.getColor("text")
renderType: Text.NativeRendering
}
UM.TabRow
{
id: tabBar
anchors.top: machineNameLabel.bottom
anchors.topMargin: UM.Theme.getSize("default_margin").height
width: parent.width
Repeater
{

View file

@ -48,9 +48,13 @@ class WindowsRemovableDrivePlugin(RemovableDrivePlugin.RemovableDrivePlugin):
drives = {}
bitmask = ctypes.windll.kernel32.GetLogicalDrives()
# Check possible drive letters, from A to Z
# Check possible drive letters, from C to Z
# Note: using ascii_uppercase because we do not want this to change with locale!
for letter in string.ascii_uppercase:
# Skip A and B, since those drives are typically reserved for floppy disks.
# Those drives can theoretically be reassigned but it's safer to not check them for removable drives.
# Windows will also behave weirdly even with some of its internal functions if you do this (e.g. search indexing doesn't search it).
# Users that have removable drives in A or B will just have to save to file and select the drive there.
for letter in string.ascii_uppercase[2:]:
drive = "{0}:/".format(letter)
# Do we really want to skip A and B?

View file

@ -155,25 +155,13 @@ Item
}
onPositionChanged: parent.onHandleDragged()
onPressed: sliderRoot.setActiveHandle(rangeHandle)
onPressed:
{
sliderRoot.setActiveHandle(rangeHandle)
sliderRoot.forceActiveFocus()
}
}
SimulationSliderLabel
{
id: rangleHandleLabel
height: sliderRoot.handleSize + UM.Theme.getSize("default_margin").height
x: parent.x - width - UM.Theme.getSize("default_margin").width
anchors.verticalCenter: parent.verticalCenter
target: Qt.point(sliderRoot.width, y + height / 2)
visible: sliderRoot.activeHandle == parent
// custom properties
maximumValue: sliderRoot.maximumValue
value: sliderRoot.upperValue
busy: UM.SimulationView.busy
setValue: rangeHandle.setValueManually // connect callback functions
}
}
onHeightChanged : {
@ -275,11 +263,12 @@ Item
{
id: upperHandleLabel
height: sliderRoot.handleSize + UM.Theme.getSize("default_margin").height
x: parent.x - parent.width - width
anchors.verticalCenter: parent.verticalCenter
target: Qt.point(sliderRoot.width, y + height / 2)
visible: sliderRoot.activeHandle == parent
height: sliderRoot.handleSize + UM.Theme.getSize("small_margin").height
anchors.bottom: parent.top
anchors.bottomMargin: UM.Theme.getSize("narrow_margin").height
anchors.horizontalCenter: parent.horizontalCenter
target: Qt.point(parent.width / 2, parent.top)
visible: sliderRoot.activeHandle == parent || sliderRoot.activeHandle == rangeHandle
// custom properties
maximumValue: sliderRoot.maximumValue
@ -384,11 +373,12 @@ Item
{
id: lowerHandleLabel
height: sliderRoot.handleSize + UM.Theme.getSize("default_margin").height
x: parent.x - parent.width - width
anchors.verticalCenter: parent.verticalCenter
target: Qt.point(sliderRoot.width + width, y + height / 2)
visible: sliderRoot.activeHandle == parent
height: sliderRoot.handleSize + UM.Theme.getSize("small_margin").height
anchors.top: parent.bottom
anchors.topMargin: UM.Theme.getSize("narrow_margin").height
anchors.horizontalCenter: parent.horizontalCenter
target: Qt.point(parent.width / 2, parent.bottom)
visible: sliderRoot.activeHandle == parent || sliderRoot.activeHandle == rangeHandle
// custom properties
maximumValue: sliderRoot.maximumValue
@ -397,4 +387,4 @@ Item
setValue: lowerHandle.setValueManually // connect callback functions
}
}
}
}

View file

@ -20,9 +20,9 @@ UM.PointingRectangle {
property int startFrom: 1
target: Qt.point(parent.width, y + height / 2)
arrowSize: UM.Theme.getSize("default_arrow").width
arrowSize: UM.Theme.getSize("button_tooltip_arrow").height
height: parent.height
width: valueLabel.width + UM.Theme.getSize("default_margin").width
width: valueLabel.width
visible: false
color: UM.Theme.getColor("tool_panel_background")
@ -48,9 +48,9 @@ UM.PointingRectangle {
horizontalCenter: parent.horizontalCenter
}
width: ((maximumValue + 1).toString().length + 1) * 10 * screenScaleFactor
width: ((maximumValue + 1).toString().length + 1) * 8 * screenScaleFactor
text: sliderLabelRoot.value + startFrom // the current handle value, add 1 because layers is an array
horizontalAlignment: TextInput.AlignRight
horizontalAlignment: TextInput.AlignHCenter
// key bindings, work when label is currenctly focused (active handle in LayerSlider)
Keys.onUpPressed: sliderLabelRoot.setValue(sliderLabelRoot.value + ((event.modifiers & Qt.ShiftModifier) ? 10 : 1))
@ -58,7 +58,7 @@ UM.PointingRectangle {
style: TextFieldStyle {
textColor: UM.Theme.getColor("setting_control_text")
font: UM.Theme.getFont("default")
font: UM.Theme.getFont("small")
background: Item { }
}

View file

@ -29,14 +29,14 @@ Item
PathSlider
{
id: pathSlider
readonly property real preferredWidth: UM.Theme.getSize("slider_layerview_size").height // not a typo, should be as long as layerview slider
readonly property real margin: UM.Theme.getSize("default_margin").width
readonly property real pathSliderSafeWidth: pathSliderSafeXMax - pathSliderSafeXMin
height: UM.Theme.getSize("slider_handle").width
width: preferredWidth + margin * 2 < pathSliderSafeWidth ? preferredWidth : pathSliderSafeWidth - margin * 2
anchors.bottom: parent.bottom
anchors.bottomMargin: margin
@ -194,9 +194,8 @@ Item
LayerSlider
{
property var preferredHeight: UM.Theme.getSize("slider_layerview_size").height
property double heightMargin: UM.Theme.getSize("default_margin").height
property double heightMargin: UM.Theme.getSize("default_margin").height * 3 // extra margin to accomodate layer number tooltips
property double layerSliderSafeHeight: layerSliderSafeYMax - layerSliderSafeYMin
//todo incorporate margins in safeHeight?
id: layerSlider

View file

@ -1,11 +1,17 @@
// Copyright (c) 2018 Ultimaker B.V.
// Toolbox is released under the terms of the LGPLv3 or higher.
// Main window for the Toolbox
import QtQuick 2.2
import QtQuick.Dialogs 1.1
import QtQuick.Window 2.2
import UM 1.1 as UM
import "./pages"
import "./dialogs"
import "./components"
Window
{
id: base
@ -29,9 +35,16 @@ Window
Item
{
anchors.fill: parent
WelcomePage
{
visible: toolbox.viewPage === "welcome"
}
ToolboxHeader
{
id: header
visible: toolbox.viewPage !== "welcome"
}
Item

View file

@ -67,7 +67,7 @@ Item
width: UM.Theme.getSize("toolbox_thumbnail_small").width - UM.Theme.getSize("wide_margin").width
height: UM.Theme.getSize("toolbox_thumbnail_small").height - UM.Theme.getSize("wide_margin").width
fillMode: Image.PreserveAspectFit
source: model.icon_url || "../images/logobot.svg"
source: model.icon_url || "../../images/logobot.svg"
mipmap: true
}
UM.RecolorImage
@ -82,7 +82,7 @@ Item
sourceSize.height: height
visible: installedPackages != 0
color: (installedPackages >= packageCount) ? UM.Theme.getColor("primary") : UM.Theme.getColor("border")
source: "../images/installed_check.svg"
source: "../../images/installed_check.svg"
}
}
Item

View file

@ -23,7 +23,7 @@ Rectangle
height: UM.Theme.getSize("toolbox_thumbnail_large").height - 4 * UM.Theme.getSize("default_margin").height
width: UM.Theme.getSize("toolbox_thumbnail_large").height - 4 * UM.Theme.getSize("default_margin").height
fillMode: Image.PreserveAspectFit
source: model.icon_url || "../images/logobot.svg"
source: model.icon_url || "../../images/logobot.svg"
mipmap: true
anchors
{
@ -62,7 +62,7 @@ Rectangle
}
visible: installedPackages != 0
color: (installedPackages >= packageCount) ? UM.Theme.getColor("primary") : UM.Theme.getColor("border")
source: "../images/installed_check.svg"
source: "../../images/installed_check.svg"
}
SmallRatingWidget

View file

@ -14,7 +14,7 @@ import Cura 1.0 as Cura
UM.Dialog
{
// This dialog asks the user whether he/she wants to open a project file as a project or import models.
// This dialog asks the user to confirm he/she wants to uninstall materials/pprofiles which are currently in use
id: base
title: catalog.i18nc("@title:window", "Confirm uninstall") + toolbox.pluginToUninstall

View file

@ -6,6 +6,8 @@ import QtQuick.Controls 1.4
import QtQuick.Controls.Styles 1.4
import UM 1.1 as UM
import "../components"
Item
{
id: page
@ -31,7 +33,7 @@ Item
width: UM.Theme.getSize("toolbox_thumbnail_medium").width
height: UM.Theme.getSize("toolbox_thumbnail_medium").height
fillMode: Image.PreserveAspectFit
source: details.icon_url || "../images/logobot.svg"
source: details.icon_url || "../../images/logobot.svg"
mipmap: true
anchors
{

View file

@ -8,6 +8,8 @@ import UM 1.1 as UM
import Cura 1.1 as Cura
import "../components"
Item
{
id: page
@ -44,7 +46,7 @@ Item
{
anchors.fill: parent
fillMode: Image.PreserveAspectFit
source: details === null ? "" : (details.icon_url || "../images/logobot.svg")
source: details === null ? "" : (details.icon_url || "../../images/logobot.svg")
mipmap: true
}
}

View file

@ -5,6 +5,8 @@ import QtQuick 2.10
import QtQuick.Controls 2.3
import UM 1.1 as UM
import "../components"
ScrollView
{
clip: true

View file

@ -6,6 +6,8 @@ import QtQuick.Controls 2.3
import UM 1.1 as UM
import "../components"
ScrollView
{
id: page

View file

@ -0,0 +1,53 @@
// Copyright (c) 2018 Ultimaker B.V.
// Cura is released under the terms of the LGPLv3 or higher.
import QtQuick 2.7
import QtQuick.Controls 2.1
import QtQuick.Window 2.2
import UM 1.3 as UM
import Cura 1.1 as Cura
Column
{
id: welcomePage
spacing: UM.Theme.getSize("wide_margin").height
width: parent.width
height: childrenRect.height
anchors.centerIn: parent
Image
{
id: profileImage
fillMode: Image.PreserveAspectFit
source: "../../images/logobot.svg"
anchors.horizontalCenter: parent.horizontalCenter
width: Math.round(parent.width / 4)
}
Label
{
id: welcomeTextLabel
text: catalog.i18nc("@description", "Get plugins and materials verified by Ultimaker")
width: Math.round(parent.width / 2)
font: UM.Theme.getFont("default")
color: UM.Theme.getColor("text")
verticalAlignment: Text.AlignVCenter
horizontalAlignment: Text.AlignHCenter
anchors.horizontalCenter: parent.horizontalCenter
wrapMode: Label.WordWrap
renderType: Text.NativeRendering
}
Cura.PrimaryButton
{
id: loginButton
width: UM.Theme.getSize("account_button").width
height: UM.Theme.getSize("account_button").height
anchors.horizontalCenter: parent.horizontalCenter
text: catalog.i18nc("@button", "Sign in")
onClicked: Cura.API.account.login()
fixedWidthMode: true
}
}

View file

@ -86,7 +86,7 @@ class Toolbox(QObject, Extension):
# View page defines which type of page layout to use. For example,
# possible values include "overview", "detail" or "author".
self._view_page = "loading" # type: str
self._view_page = "welcome" # type: str
# Active package refers to which package is currently being downloaded,
# installed, or otherwise modified.
@ -105,7 +105,6 @@ class Toolbox(QObject, Extension):
self._restart_dialog_message = "" # type: str
self._application.initializationFinished.connect(self._onAppInitialized)
self._application.getCuraAPI().account.loginStateChanged.connect(self._updateRequestHeader)
self._application.getCuraAPI().account.accessTokenChanged.connect(self._updateRequestHeader)
# Signals:
@ -126,6 +125,16 @@ class Toolbox(QObject, Extension):
showLicenseDialog = pyqtSignal()
uninstallVariablesChanged = pyqtSignal()
## Go back to the start state (welcome screen or loading if no login required)
def _restart(self):
self._updateRequestHeader()
# For an Essentials build, login is mandatory
if not self._application.getCuraAPI().account.isLoggedIn and ApplicationMetadata.IsEnterpriseVersion:
self.setViewPage("welcome")
else:
self.setViewPage("loading")
self._fetchPackageData()
def _updateRequestHeader(self):
self._request_headers = [
(b"User-Agent",
@ -191,8 +200,11 @@ class Toolbox(QObject, Extension):
"packages": QUrl("{base_url}/packages".format(base_url = self._api_url))
}
# Request the latest and greatest!
self._fetchPackageData()
self._application.getCuraAPI().account.loginStateChanged.connect(self._restart)
if CuraApplication.getInstance().getPreferences().getValue("info/automatic_update_check"):
# Request the latest and greatest!
self._fetchPackageData()
def _fetchPackageData(self):
# Create the network manager:
@ -212,9 +224,9 @@ class Toolbox(QObject, Extension):
# Gather installed packages:
self._updateInstalledModels()
# Displays the toolbox
@pyqtSlot()
def browsePackages(self) -> None:
self._fetchPackageData()
def launch(self) -> None:
if not self._dialog:
self._dialog = self._createDialog("Toolbox.qml")
@ -223,6 +235,8 @@ class Toolbox(QObject, Extension):
Logger.log("e", "Unexpected error trying to create the 'Marketplace' dialog.")
return
self._restart()
self._dialog.show()
# Apply enabled/disabled state to installed plugins
@ -328,7 +342,7 @@ class Toolbox(QObject, Extension):
self._package_used_qualities = package_used_qualities
# Ask change to default material / profile
if self._confirm_reset_dialog is None:
self._confirm_reset_dialog = self._createDialog("ToolboxConfirmUninstallResetDialog.qml")
self._confirm_reset_dialog = self._createDialog("dialogs/ToolboxConfirmUninstallResetDialog.qml")
self.uninstallVariablesChanged.emit()
if self._confirm_reset_dialog is None:
Logger.log("e", "ToolboxConfirmUninstallResetDialog should have been initialized, but it is not. Not showing dialog and not uninstalling package.")

View file

@ -15,7 +15,6 @@ from cura.Settings.GlobalStack import GlobalStack
from .CloudApiClient import CloudApiClient
from .CloudOutputDevice import CloudOutputDevice
from ..Models.Http.CloudClusterResponse import CloudClusterResponse
from ..Messages.CloudPrinterDetectedMessage import CloudPrinterDetectedMessage
## The cloud output device manager is responsible for using the Ultimaker Cloud APIs to manage remote clusters.
@ -111,7 +110,6 @@ class CloudOutputDeviceManager:
)
self._remote_clusters[device.getId()] = device
self.discoveredDevicesChanged.emit()
self._checkIfNewClusterWasAdded(device.clusterData.cluster_id)
self._connectToActiveMachine()
def _onDiscoveredDeviceUpdated(self, cluster_data: CloudClusterResponse) -> None:
@ -183,11 +181,4 @@ class CloudOutputDeviceManager:
output_device_manager = CuraApplication.getInstance().getOutputDeviceManager()
if device.key not in output_device_manager.getOutputDeviceIds():
output_device_manager.addOutputDevice(device)
## Checks if Cura has a machine stack (printer) for the given cluster ID and shows a message if it hasn't.
def _checkIfNewClusterWasAdded(self, cluster_id: str) -> None:
container_registry = CuraApplication.getInstance().getContainerRegistry()
cloud_machines = container_registry.findContainersMetadata(**{self.META_CLUSTER_ID: "*"}) # all cloud machines
if not any(machine[self.META_CLUSTER_ID] == cluster_id for machine in cloud_machines):
CloudPrinterDetectedMessage().show()
output_device_manager.addOutputDevice(device)

View file

@ -1,45 +0,0 @@
# Copyright (c) 2019 Ultimaker B.V.
# Cura is released under the terms of the LGPLv3 or higher.
from UM import i18nCatalog
from UM.Message import Message
from cura.CuraApplication import CuraApplication
I18N_CATALOG = i18nCatalog("cura")
## Message shown when a new printer was added to your account but not yet in Cura.
class CloudPrinterDetectedMessage(Message):
# Singleton used to prevent duplicate messages of this type at the same time.
__is_visible = False
# Store in preferences to hide this message in the future.
_preference_key = "cloud/block_new_printers_popup"
def __init__(self) -> None:
super().__init__(
title=I18N_CATALOG.i18nc("@info:title", "New cloud printers found"),
text=I18N_CATALOG.i18nc("@info:message", "New printers have been found connected to your account, "
"you can find them in your list of discovered printers."),
lifetime=0,
dismissable=True,
option_state=False,
option_text=I18N_CATALOG.i18nc("@info:option_text", "Do not show this message again")
)
self.optionToggled.connect(self._onDontAskMeAgain)
CuraApplication.getInstance().getPreferences().addPreference(self._preference_key, False)
def show(self) -> None:
if CuraApplication.getInstance().getPreferences().getValue(self._preference_key):
return
if CloudPrinterDetectedMessage.__is_visible:
return
super().show()
CloudPrinterDetectedMessage.__is_visible = True
def hide(self, send_signal = True) -> None:
super().hide(send_signal)
CloudPrinterDetectedMessage.__is_visible = False
def _onDontAskMeAgain(self, checked: bool) -> None:
CuraApplication.getInstance().getPreferences().setValue(self._preference_key, checked)

View file

@ -325,7 +325,9 @@ class VersionUpgrade41to42(VersionUpgrade):
material_id = parser["containers"]["3"]
old_quality_id = parser["containers"]["2"]
if material_id in _creality_quality_per_material and old_quality_id in _creality_quality_per_material[material_id]:
parser["containers"]["2"] = _creality_quality_per_material[material_id][old_quality_id]
if definition_id == "creality_cr10_extruder_0": # We can't disambiguate between Creality CR-10 and Creality-CR10S since they share the same extruder definition. Have to go by the name.
if "cr-10s" in parser["metadata"].get("machine", "Creality CR-10").lower(): # Not perfect, since the user can change this name :(
parser["containers"]["2"] = _creality_quality_per_material[material_id][old_quality_id]
stack_copy = {} # type: Dict[str, str] # Make a copy so that we don't modify the dict we're iterating over.
stack_copy.update(parser["containers"])