Merge pull request #17954 from Ultimaker/CURA-7812-decrease-Qml-singletons

CURA-7812-decrease-Qml-singletons
This commit is contained in:
Erwan MATHIEU 2024-01-12 11:09:54 +01:00 committed by GitHub
commit 0fe682470a
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
12 changed files with 96 additions and 40 deletions

View File

@ -3,10 +3,11 @@
from typing import List, cast from typing import List, cast
from PyQt6.QtCore import QObject, QUrl, QMimeData from PyQt6.QtCore import QObject, QUrl, pyqtSignal, pyqtProperty
from PyQt6.QtGui import QDesktopServices from PyQt6.QtGui import QDesktopServices
from PyQt6.QtWidgets import QApplication from PyQt6.QtWidgets import QApplication
from UM.Application import Application
from UM.Event import CallFunctionEvent from UM.Event import CallFunctionEvent
from UM.FlameProfiler import pyqtSlot from UM.FlameProfiler import pyqtSlot
from UM.Math.Vector import Vector from UM.Math.Vector import Vector
@ -37,6 +38,10 @@ class CuraActions(QObject):
def __init__(self, parent: QObject = None) -> None: def __init__(self, parent: QObject = None) -> None:
super().__init__(parent) super().__init__(parent)
self._operation_stack = Application.getInstance().getOperationStack()
self._operation_stack.changed.connect(self._onUndoStackChanged)
undoStackChanged = pyqtSignal()
@pyqtSlot() @pyqtSlot()
def openDocumentation(self) -> None: def openDocumentation(self) -> None:
# Starting a web browser from a signal handler connected to a menu will crash on windows. # Starting a web browser from a signal handler connected to a menu will crash on windows.
@ -45,6 +50,25 @@ class CuraActions(QObject):
event = CallFunctionEvent(self._openUrl, [QUrl("https://ultimaker.com/en/resources/manuals/software?utm_source=cura&utm_medium=software&utm_campaign=dropdown-documentation")], {}) event = CallFunctionEvent(self._openUrl, [QUrl("https://ultimaker.com/en/resources/manuals/software?utm_source=cura&utm_medium=software&utm_campaign=dropdown-documentation")], {})
cura.CuraApplication.CuraApplication.getInstance().functionEvent(event) cura.CuraApplication.CuraApplication.getInstance().functionEvent(event)
@pyqtProperty(bool, notify=undoStackChanged)
def canUndo(self):
return self._operation_stack.canUndo()
@pyqtProperty(bool, notify=undoStackChanged)
def canRedo(self):
return self._operation_stack.canRedo()
@pyqtSlot()
def undo(self):
self._operation_stack.undo()
@pyqtSlot()
def redo(self):
self._operation_stack.redo()
def _onUndoStackChanged(self):
self.undoStackChanged.emit()
@pyqtSlot() @pyqtSlot()
def openBugReportPage(self) -> None: def openBugReportPage(self) -> None:
event = CallFunctionEvent(self._openUrl, [QUrl("https://github.com/Ultimaker/Cura/issues/new/choose")], {}) event = CallFunctionEvent(self._openUrl, [QUrl("https://github.com/Ultimaker/Cura/issues/new/choose")], {})

View File

@ -15,13 +15,13 @@ import numpy
from PyQt6.QtCore import QObject, QTimer, QUrl, QUrlQuery, pyqtSignal, pyqtProperty, QEvent, pyqtEnum, QCoreApplication, \ from PyQt6.QtCore import QObject, QTimer, QUrl, QUrlQuery, pyqtSignal, pyqtProperty, QEvent, pyqtEnum, QCoreApplication, \
QByteArray QByteArray
from PyQt6.QtGui import QColor, QIcon from PyQt6.QtGui import QColor, QIcon
from PyQt6.QtQml import qmlRegisterUncreatableType, qmlRegisterUncreatableMetaObject, qmlRegisterSingletonType, qmlRegisterType from PyQt6.QtQml import qmlRegisterUncreatableMetaObject, qmlRegisterSingletonType, qmlRegisterType
from PyQt6.QtWidgets import QMessageBox from PyQt6.QtWidgets import QMessageBox
import UM.Util import UM.Util
import cura.Settings.cura_empty_instance_containers import cura.Settings.cura_empty_instance_containers
from UM.Application import Application from UM.Application import Application
from UM.Decorators import override from UM.Decorators import override, deprecated
from UM.FlameProfiler import pyqtSlot from UM.FlameProfiler import pyqtSlot
from UM.Logger import Logger from UM.Logger import Logger
from UM.Math.AxisAlignedBox import AxisAlignedBox from UM.Math.AxisAlignedBox import AxisAlignedBox
@ -191,7 +191,7 @@ class CuraApplication(QtApplication):
self.empty_container = None # type: EmptyInstanceContainer self.empty_container = None # type: EmptyInstanceContainer
self.empty_definition_changes_container = None # type: EmptyInstanceContainer self.empty_definition_changes_container = None # type: EmptyInstanceContainer
self.empty_variant_container = None # type: EmptyInstanceContainer self.empty_variant_container = None # type: EmptyInstanceContainer
self.empty_intent_container = None # type: EmptyInstanceContainer self.empty_intent_container = None # type: EmptyInstanceContainer
self.empty_material_container = None # type: EmptyInstanceContainer self.empty_material_container = None # type: EmptyInstanceContainer
self.empty_quality_container = None # type: EmptyInstanceContainer self.empty_quality_container = None # type: EmptyInstanceContainer
self.empty_quality_changes_container = None # type: EmptyInstanceContainer self.empty_quality_changes_container = None # type: EmptyInstanceContainer
@ -1138,6 +1138,10 @@ class CuraApplication(QtApplication):
return cast(MachineActionManager.MachineActionManager, self._machine_action_manager) return cast(MachineActionManager.MachineActionManager, self._machine_action_manager)
@pyqtSlot(result = QObject)
def getMachineActionManagerQml(self)-> MachineActionManager.MachineActionManager:
return cast(QObject, self._machine_action_manager)
@pyqtSlot(result = QObject) @pyqtSlot(result = QObject)
def getMaterialManagementModel(self) -> MaterialManagementModel: def getMaterialManagementModel(self) -> MaterialManagementModel:
if not self._material_management_model: if not self._material_management_model:
@ -1150,7 +1154,8 @@ class CuraApplication(QtApplication):
self._quality_management_model = QualityManagementModel(parent = self) self._quality_management_model = QualityManagementModel(parent = self)
return self._quality_management_model return self._quality_management_model
def getSimpleModeSettingsManager(self, *args): @pyqtSlot(result=QObject)
def getSimpleModeSettingsManager(self)-> SimpleModeSettingsManager:
if self._simple_mode_settings_manager is None: if self._simple_mode_settings_manager is None:
self._simple_mode_settings_manager = SimpleModeSettingsManager() self._simple_mode_settings_manager = SimpleModeSettingsManager()
return self._simple_mode_settings_manager return self._simple_mode_settings_manager
@ -1193,16 +1198,43 @@ class CuraApplication(QtApplication):
return self._print_information return self._print_information
def getQualityProfilesDropDownMenuModel(self, *args, **kwargs): @pyqtSlot(result=QObject)
def getQualityProfilesDropDownMenuModel(self, *args, **kwargs)-> QualityProfilesDropDownMenuModel:
if self._quality_profile_drop_down_menu_model is None: if self._quality_profile_drop_down_menu_model is None:
self._quality_profile_drop_down_menu_model = QualityProfilesDropDownMenuModel(self) self._quality_profile_drop_down_menu_model = QualityProfilesDropDownMenuModel(self)
return self._quality_profile_drop_down_menu_model return self._quality_profile_drop_down_menu_model
def getCustomQualityProfilesDropDownMenuModel(self, *args, **kwargs): @pyqtSlot(result=QObject)
def getCustomQualityProfilesDropDownMenuModel(self, *args, **kwargs)->CustomQualityProfilesDropDownMenuModel:
if self._custom_quality_profile_drop_down_menu_model is None: if self._custom_quality_profile_drop_down_menu_model is None:
self._custom_quality_profile_drop_down_menu_model = CustomQualityProfilesDropDownMenuModel(self) self._custom_quality_profile_drop_down_menu_model = CustomQualityProfilesDropDownMenuModel(self)
return self._custom_quality_profile_drop_down_menu_model return self._custom_quality_profile_drop_down_menu_model
@deprecated("SimpleModeSettingsManager is deprecated and will be removed in major SDK release, Use getSimpleModeSettingsManager() instead", since = "5.7.0")
def getSimpleModeSettingsManagerWrapper(self, *args, **kwargs):
return self.getSimpleModeSettingsManager()
@deprecated("MachineActionManager is deprecated and will be removed in major SDK release, Use getMachineActionManager() instead", since="5.7.0")
def getMachineActionManagerWrapper(self, *args, **kwargs):
return self.getMachineActionManager()
@deprecated("QualityManagementModel is deprecated and will be removed in major SDK release, Use getQualityManagementModel() instead", since="5.7.0")
def getQualityManagementModelWrapper(self, *args, **kwargs):
return self.getQualityManagementModel()
@deprecated("MaterialManagementModel is deprecated and will be removed in major SDK release, Use getMaterialManagementModel() instead", since = "5.7.0")
def getMaterialManagementModelWrapper(self, *args, **kwargs):
return self.getMaterialManagementModel()
@deprecated("QualityProfilesDropDownMenuModel is deprecated and will be removed in major SDK release, Use getQualityProfilesDropDownMenuModel() instead", since = "5.7.0")
def getQualityProfilesDropDownMenuModelWrapper(self, *args, **kwargs):
return self.getQualityProfilesDropDownMenuModel()
@deprecated("CustomQualityProfilesDropDownMenuModel is deprecated and will be removed in major SDK release, Use getCustomQualityProfilesDropDownMenuModel() instead", since = "5.7.0")
def getCustomQualityProfilesDropDownMenuModelWrapper(self, *args, **kwargs):
return self.getCustomQualityProfilesDropDownMenuModel()
def getCuraAPI(self, *args, **kwargs) -> "CuraAPI": def getCuraAPI(self, *args, **kwargs) -> "CuraAPI":
return self._cura_API return self._cura_API
@ -1231,8 +1263,8 @@ class CuraApplication(QtApplication):
qmlRegisterSingletonType(MachineManager, "Cura", 1, 0, self.getMachineManager, "MachineManager") qmlRegisterSingletonType(MachineManager, "Cura", 1, 0, self.getMachineManager, "MachineManager")
qmlRegisterSingletonType(IntentManager, "Cura", 1, 6, self.getIntentManager, "IntentManager") qmlRegisterSingletonType(IntentManager, "Cura", 1, 6, self.getIntentManager, "IntentManager")
qmlRegisterSingletonType(SettingInheritanceManager, "Cura", 1, 0, self.getSettingInheritanceManager, "SettingInheritanceManager") qmlRegisterSingletonType(SettingInheritanceManager, "Cura", 1, 0, self.getSettingInheritanceManager, "SettingInheritanceManager")
qmlRegisterSingletonType(SimpleModeSettingsManager, "Cura", 1, 0, self.getSimpleModeSettingsManager, "SimpleModeSettingsManager") qmlRegisterSingletonType(SimpleModeSettingsManager, "Cura", 1, 0, self.getSimpleModeSettingsManagerWrapper, "SimpleModeSettingsManager")
qmlRegisterSingletonType(MachineActionManager.MachineActionManager, "Cura", 1, 0, self.getMachineActionManager, "MachineActionManager") qmlRegisterSingletonType(MachineActionManager.MachineActionManager, "Cura", 1, 0, self.getMachineActionManagerWrapper, "MachineActionManager")
self.processEvents() self.processEvents()
qmlRegisterType(NetworkingUtil, "Cura", 1, 5, "NetworkingUtil") qmlRegisterType(NetworkingUtil, "Cura", 1, 5, "NetworkingUtil")
@ -1257,16 +1289,14 @@ class CuraApplication(QtApplication):
qmlRegisterType(FavoriteMaterialsModel, "Cura", 1, 0, "FavoriteMaterialsModel") qmlRegisterType(FavoriteMaterialsModel, "Cura", 1, 0, "FavoriteMaterialsModel")
qmlRegisterType(GenericMaterialsModel, "Cura", 1, 0, "GenericMaterialsModel") qmlRegisterType(GenericMaterialsModel, "Cura", 1, 0, "GenericMaterialsModel")
qmlRegisterType(MaterialBrandsModel, "Cura", 1, 0, "MaterialBrandsModel") qmlRegisterType(MaterialBrandsModel, "Cura", 1, 0, "MaterialBrandsModel")
qmlRegisterSingletonType(QualityManagementModel, "Cura", 1, 0, self.getQualityManagementModel, "QualityManagementModel") qmlRegisterSingletonType(QualityManagementModel, "Cura", 1, 0, self.getQualityManagementModelWrapper,"QualityManagementModel")
qmlRegisterSingletonType(MaterialManagementModel, "Cura", 1, 5, self.getMaterialManagementModel, "MaterialManagementModel") qmlRegisterSingletonType(MaterialManagementModel, "Cura", 1, 5, self.getMaterialManagementModelWrapper,"MaterialManagementModel")
self.processEvents() self.processEvents()
qmlRegisterType(DiscoveredPrintersModel, "Cura", 1, 0, "DiscoveredPrintersModel") qmlRegisterType(DiscoveredPrintersModel, "Cura", 1, 0, "DiscoveredPrintersModel")
qmlRegisterType(DiscoveredCloudPrintersModel, "Cura", 1, 7, "DiscoveredCloudPrintersModel") qmlRegisterType(DiscoveredCloudPrintersModel, "Cura", 1, 7, "DiscoveredCloudPrintersModel")
qmlRegisterSingletonType(QualityProfilesDropDownMenuModel, "Cura", 1, 0, qmlRegisterSingletonType(QualityProfilesDropDownMenuModel, "Cura", 1, 0, self.getQualityProfilesDropDownMenuModelWrapper, "QualityProfilesDropDownMenuModel")
self.getQualityProfilesDropDownMenuModel, "QualityProfilesDropDownMenuModel") qmlRegisterSingletonType(CustomQualityProfilesDropDownMenuModel, "Cura", 1, 0, self.getCustomQualityProfilesDropDownMenuModelWrapper, "CustomQualityProfilesDropDownMenuModel")
qmlRegisterSingletonType(CustomQualityProfilesDropDownMenuModel, "Cura", 1, 0,
self.getCustomQualityProfilesDropDownMenuModel, "CustomQualityProfilesDropDownMenuModel")
qmlRegisterType(NozzleModel, "Cura", 1, 0, "NozzleModel") qmlRegisterType(NozzleModel, "Cura", 1, 0, "NozzleModel")
qmlRegisterType(IntentModel, "Cura", 1, 6, "IntentModel") qmlRegisterType(IntentModel, "Cura", 1, 6, "IntentModel")
qmlRegisterType(IntentCategoryModel, "Cura", 1, 6, "IntentCategoryModel") qmlRegisterType(IntentCategoryModel, "Cura", 1, 6, "IntentCategoryModel")

View File

@ -25,7 +25,7 @@ UM.TooltipArea
onClicked: onClicked:
{ {
addedSettingsModel.setVisible(model.key, checked); addedSettingsModel.setVisible(model.key, checked);
UM.ActiveTool.forceUpdate(); UM.Controller.forceUpdate();
} }
} }

View File

@ -23,7 +23,7 @@ Item
readonly property string infillMeshType: "infill_mesh" readonly property string infillMeshType: "infill_mesh"
readonly property string antiOverhangMeshType: "anti_overhang_mesh" readonly property string antiOverhangMeshType: "anti_overhang_mesh"
property var currentMeshType: UM.ActiveTool.properties.getValue("MeshType") property var currentMeshType: UM.Controller.properties.getValue("MeshType")
// Update the view every time the currentMeshType changes // Update the view every time the currentMeshType changes
onCurrentMeshTypeChanged: onCurrentMeshTypeChanged:
@ -56,7 +56,7 @@ Item
function setMeshType(type) function setMeshType(type)
{ {
UM.ActiveTool.setProperty("MeshType", type) UM.Controller.setProperty("MeshType", type)
updateMeshTypeCheckedState(type) updateMeshTypeCheckedState(type)
} }
@ -224,7 +224,7 @@ Item
visibilityHandler: Cura.PerObjectSettingVisibilityHandler visibilityHandler: Cura.PerObjectSettingVisibilityHandler
{ {
id: visibility_handler id: visibility_handler
selectedObjectId: UM.ActiveTool.properties.getValue("SelectedObjectId") selectedObjectId: UM.Controller.properties.getValue("SelectedObjectId")
} }
// For some reason the model object is updated after removing him from the memory and // For some reason the model object is updated after removing him from the memory and
@ -320,7 +320,7 @@ Item
{ {
id: provider id: provider
containerStackId: UM.ActiveTool.properties.getValue("ContainerID") containerStackId: UM.Controller.properties.getValue("ContainerID")
key: model.key key: model.key
watchedProperties: [ "value", "enabled", "validationState" ] watchedProperties: [ "value", "enabled", "validationState" ]
storeIndex: 0 storeIndex: 0
@ -330,7 +330,7 @@ Item
UM.SettingPropertyProvider UM.SettingPropertyProvider
{ {
id: inheritStackProvider id: inheritStackProvider
containerStackId: UM.ActiveTool.properties.getValue("ContainerID") containerStackId: UM.Controller.properties.getValue("ContainerID")
key: model.key key: model.key
watchedProperties: [ "limit_to_extruder" ] watchedProperties: [ "limit_to_extruder" ]
} }
@ -381,22 +381,22 @@ Item
Connections Connections
{ {
target: UM.ActiveTool target: UM.Controller
function onPropertiesChanged() function onPropertiesChanged()
{ {
// the values cannot be bound with UM.ActiveTool.properties.getValue() calls, // the values cannot be bound with UM.Controller.properties.getValue() calls,
// so here we connect to the signal and update the those values. // so here we connect to the signal and update the those values.
if (typeof UM.ActiveTool.properties.getValue("SelectedObjectId") !== "undefined") if (typeof UM.Controller.properties.getValue("SelectedObjectId") !== "undefined")
{ {
const selectedObjectId = UM.ActiveTool.properties.getValue("SelectedObjectId") const selectedObjectId = UM.Controller.properties.getValue("SelectedObjectId")
if (addedSettingsModel.visibilityHandler.selectedObjectId != selectedObjectId) if (addedSettingsModel.visibilityHandler.selectedObjectId != selectedObjectId)
{ {
addedSettingsModel.visibilityHandler.selectedObjectId = selectedObjectId addedSettingsModel.visibilityHandler.selectedObjectId = selectedObjectId
} }
} }
if (typeof UM.ActiveTool.properties.getValue("ContainerID") !== "undefined") if (typeof UM.Controller.properties.getValue("ContainerID") !== "undefined")
{ {
const containerId = UM.ActiveTool.properties.getValue("ContainerID") const containerId = UM.Controller.properties.getValue("ContainerID")
if (provider.containerStackId !== containerId) if (provider.containerStackId !== containerId)
{ {
provider.containerStackId = containerId provider.containerStackId = containerId

View File

@ -120,8 +120,8 @@ Item
text: catalog.i18nc("@action:inmenu menubar:edit", "&Undo") text: catalog.i18nc("@action:inmenu menubar:edit", "&Undo")
icon.name: "edit-undo" icon.name: "edit-undo"
shortcut: StandardKey.Undo shortcut: StandardKey.Undo
onTriggered: UM.OperationStack.undo() onTriggered: CuraActions.undo()
enabled: UM.OperationStack.canUndo enabled: CuraActions.canUndo
} }
Action Action
@ -130,8 +130,8 @@ Item
text: catalog.i18nc("@action:inmenu menubar:edit", "&Redo") text: catalog.i18nc("@action:inmenu menubar:edit", "&Redo")
icon.name: "edit-redo" icon.name: "edit-redo"
shortcut: StandardKey.Redo shortcut: StandardKey.Redo
onTriggered: UM.OperationStack.redo() onTriggered: CuraActions.redo()
enabled: UM.OperationStack.canRedo enabled: CuraActions.canRedo
} }
Action Action

View File

@ -58,7 +58,7 @@ UM.Dialog
UM.Label UM.Label
{ {
id: version id: version
text: catalog.i18nc("@label","version: %1").arg(UM.Application.version) text: catalog.i18nc("@label","version: %1").arg(CuraApplication.version())
font: UM.Theme.getFont("large_bold") font: UM.Theme.getFont("large_bold")
color: UM.Theme.getColor("button_text") color: UM.Theme.getColor("button_text")
anchors.right : logo.right anchors.right : logo.right

View File

@ -12,6 +12,7 @@ import Cura 1.0 as Cura
UM.ManagementPage UM.ManagementPage
{ {
id: base id: base
property var machineActionManager: CuraApplication.getMachineActionManagerQml()
Item { enabled: false; UM.I18nCatalog { id: catalog; name: "cura"} } Item { enabled: false; UM.I18nCatalog { id: catalog; name: "cura"} }
title: catalog.i18nc("@title:tab", "Printers") title: catalog.i18nc("@title:tab", "Printers")
@ -58,10 +59,11 @@ UM.ManagementPage
anchors.fill: parent anchors.fill: parent
spacing: UM.Theme.getSize("default_margin").height spacing: UM.Theme.getSize("default_margin").height
Repeater Repeater
{ {
id: machineActionRepeater id: machineActionRepeater
model: base.currentItem ? Cura.MachineActionManager.getSupportedActions(Cura.MachineManager.getDefinitionByMachineId(base.currentItem.id)) : null model: base.currentItem ? machineActionManager.getSupportedActions(Cura.MachineManager.getDefinitionByMachineId(base.currentItem.id)) : null
Item Item
{ {

View File

@ -160,7 +160,7 @@ Item
ProfileWarningReset ProfileWarningReset
{ {
id: profileWarningReset id: profileWarningReset
width: childrenRect.width width: parent.width
anchors.right: parent.right anchors.right: parent.right
anchors.verticalCenter: parent.verticalCenter anchors.verticalCenter: parent.verticalCenter
fullWarning: false fullWarning: false

View File

@ -187,7 +187,7 @@ Popup
//Add all the custom profiles. //Add all the custom profiles.
Repeater Repeater
{ {
model: Cura.CustomQualityProfilesDropDownMenuModel model: CuraApplication.getCustomQualityProfilesDropDownMenuModel()
MenuButton MenuButton
{ {
onClicked: Cura.MachineManager.setQualityChangesGroup(model.quality_changes_group) onClicked: Cura.MachineManager.setQualityChangesGroup(model.quality_changes_group)

View File

@ -11,7 +11,7 @@ import "../Dialogs"
Item Item
{ {
property bool fullWarning: true // <- Can you see the warning icon and the text, or is it just the buttons? property bool fullWarning: true // <- Can you see the warning icon and the text, or is it just the buttons?
property var simpleModeSettingsManager :CuraApplication.getSimpleModeSettingsManager()
height: visible ? UM.Theme.getSize("action_button_icon").height : 0 height: visible ? UM.Theme.getSize("action_button_icon").height : 0
width: visible ? childrenRect.width: 0 width: visible ? childrenRect.width: 0
visible: Cura.MachineManager.hasUserSettings || (fullWarning && Cura.MachineManager.hasCustomQuality) visible: Cura.MachineManager.hasUserSettings || (fullWarning && Cura.MachineManager.hasCustomQuality)
@ -96,7 +96,7 @@ Item
State State
{ {
name: "custom settings changed" name: "custom settings changed"
when: Cura.SimpleModeSettingsManager.isProfileCustomized when: simpleModeSettingsManager.isProfileCustomized
PropertyChanges PropertyChanges
{ {
target: warning target: warning

View File

@ -223,7 +223,7 @@ SettingItem
cursorShape: Qt.IBeamCursor cursorShape: Qt.IBeamCursor
onPressed: { onPressed:(mouse)=> {
if (!input.activeFocus) if (!input.activeFocus)
{ {
base.focusGainedByClick = true base.focusGainedByClick = true

View File

@ -203,7 +203,7 @@ Item
x: UM.Theme.getSize("default_margin").width x: UM.Theme.getSize("default_margin").width
y: UM.Theme.getSize("default_margin").height y: UM.Theme.getSize("default_margin").height
source: UM.ActiveTool.valid ? UM.ActiveTool.activeToolPanel : "" source: UM.Controller.valid ? UM.Controller.activeToolPanel : ""
enabled: UM.Controller.toolsEnabled enabled: UM.Controller.toolsEnabled
} }
} }
@ -222,7 +222,7 @@ Item
UM.Label UM.Label
{ {
id: toolHint id: toolHint
text: UM.ActiveTool.properties.getValue("ToolHint") != undefined ? UM.ActiveTool.properties.getValue("ToolHint") : "" text: UM.Controller.properties.getValue("ToolHint") != undefined ? UM.ActiveTool.properties.getValue("ToolHint") : ""
color: UM.Theme.getColor("tooltip_text") color: UM.Theme.getColor("tooltip_text")
anchors.horizontalCenter: parent.horizontalCenter anchors.horizontalCenter: parent.horizontalCenter
} }