diff --git a/cura/BuildVolume.py b/cura/BuildVolume.py index 1cdcf9971a..b929f0f8f1 100755 --- a/cura/BuildVolume.py +++ b/cura/BuildVolume.py @@ -937,8 +937,8 @@ class BuildVolume(SceneNode): # stack. # # \return A sequence of setting values, one for each extruder. - def _getSettingFromAllExtruders(self, setting_key, property = "value"): - all_values = ExtruderManager.getInstance().getAllExtruderSettings(setting_key, property) + def _getSettingFromAllExtruders(self, setting_key): + all_values = ExtruderManager.getInstance().getAllExtruderSettings(setting_key, "value") all_types = ExtruderManager.getInstance().getAllExtruderSettings(setting_key, "type") for i in range(len(all_values)): if not all_values[i] and (all_types[i] == "int" or all_types[i] == "float"): @@ -951,7 +951,7 @@ class BuildVolume(SceneNode): # not part of the collision radius, such as bed adhesion (skirt/brim/raft) # and travel avoid distance. def _getEdgeDisallowedSize(self): - if not self._global_container_stack: + if not self._global_container_stack or not self._global_container_stack.extruders: return 0 container_stack = self._global_container_stack diff --git a/cura/CuraApplication.py b/cura/CuraApplication.py index 90c7dbb75e..2ca321e4cc 100755 --- a/cura/CuraApplication.py +++ b/cura/CuraApplication.py @@ -2,6 +2,8 @@ # Cura is released under the terms of the LGPLv3 or higher. #Type hinting. from typing import Dict + +from PyQt5.QtCore import QObject from PyQt5.QtNetwork import QLocalServer from PyQt5.QtNetwork import QLocalSocket @@ -52,13 +54,23 @@ from UM.Settings.SettingDefinition import SettingDefinition, DefinitionPropertyT from UM.Settings.ContainerRegistry import ContainerRegistry from UM.Settings.SettingFunction import SettingFunction from cura.Settings.MachineNameValidator import MachineNameValidator -from cura.Settings.ProfilesModel import ProfilesModel -from cura.Settings.MaterialsModel import MaterialsModel -from cura.Settings.QualityAndUserProfilesModel import QualityAndUserProfilesModel + +from cura.Machines.Models.BuildPlateModel import BuildPlateModel +from cura.Machines.Models.NozzleModel import NozzleModel +from cura.Machines.Models.QualityProfilesDropDownMenuModel import QualityProfilesDropDownMenuModel +from cura.Machines.Models.CustomQualityProfilesDropDownMenuModel import CustomQualityProfilesDropDownMenuModel + +from cura.Machines.Models.MultiBuildPlateModel import MultiBuildPlateModel + +from cura.Machines.Models.MaterialManagementModel import MaterialManagementModel +from cura.Machines.Models.GenericMaterialsModel import GenericMaterialsModel +from cura.Machines.Models.BrandMaterialsModel import BrandMaterialsModel + from cura.Settings.SettingInheritanceManager import SettingInheritanceManager -from cura.Settings.UserProfilesModel import UserProfilesModel from cura.Settings.SimpleModeSettingsManager import SimpleModeSettingsManager +from cura.Machines.VariantManager import VariantManager +from cura.Machines.Models.QualityManagementModel import QualityManagementModel from . import PlatformPhysics from . import BuildVolume @@ -71,17 +83,14 @@ from . import CameraImageProvider from . import MachineActionManager from cura.Settings.MachineManager import MachineManager -from cura.Settings.MaterialManager import MaterialManager from cura.Settings.ExtruderManager import ExtruderManager from cura.Settings.UserChangesModel import UserChangesModel from cura.Settings.ExtrudersModel import ExtrudersModel -from cura.Settings.ContainerSettingsModel import ContainerSettingsModel from cura.Settings.MaterialSettingsVisibilityHandler import MaterialSettingsVisibilityHandler -from cura.Settings.QualitySettingsModel import QualitySettingsModel +from cura.Machines.Models.QualitySettingsModel import QualitySettingsModel from cura.Settings.ContainerManager import ContainerManager from cura.ObjectsModel import ObjectsModel -from cura.BuildPlateModel import BuildPlateModel from PyQt5.QtCore import QUrl, pyqtSignal, pyqtProperty, QEvent, Q_ENUMS from UM.FlameProfiler import pyqtSlot @@ -216,6 +225,7 @@ class CuraApplication(QtApplication): self._material_manager = None self._object_manager = None self._build_plate_model = None + self._multi_build_plate_model = None self._setting_inheritance_manager = None self._simple_mode_settings_manager = None self._cura_scene_controller = None @@ -233,6 +243,8 @@ class CuraApplication(QtApplication): if kwargs["parsed_command_line"].get("trigger_early_crash", False): assert not "This crash is triggered by the trigger_early_crash command line argument." + self._variant_manager = None + self.default_theme = "cura-light" self.setWindowIcon(QIcon(Resources.getPath(Resources.Images, "cura-icon.png"))) @@ -287,21 +299,25 @@ class CuraApplication(QtApplication): # Since they are empty, they should never be serialized and instead just programmatically created. # We need them to simplify the switching between materials. empty_container = ContainerRegistry.getInstance().getEmptyInstanceContainer() + self.empty_container = empty_container empty_definition_changes_container = copy.deepcopy(empty_container) empty_definition_changes_container.setMetaDataEntry("id", "empty_definition_changes") empty_definition_changes_container.addMetaDataEntry("type", "definition_changes") ContainerRegistry.getInstance().addContainer(empty_definition_changes_container) + self.empty_definition_changes_container = empty_definition_changes_container empty_variant_container = copy.deepcopy(empty_container) empty_variant_container.setMetaDataEntry("id", "empty_variant") empty_variant_container.addMetaDataEntry("type", "variant") ContainerRegistry.getInstance().addContainer(empty_variant_container) + self.empty_variant_container = empty_variant_container empty_material_container = copy.deepcopy(empty_container) empty_material_container.setMetaDataEntry("id", "empty_material") empty_material_container.addMetaDataEntry("type", "material") ContainerRegistry.getInstance().addContainer(empty_material_container) + self.empty_material_container = empty_material_container empty_quality_container = copy.deepcopy(empty_container) empty_quality_container.setMetaDataEntry("id", "empty_quality") @@ -310,12 +326,14 @@ class CuraApplication(QtApplication): empty_quality_container.addMetaDataEntry("type", "quality") empty_quality_container.addMetaDataEntry("supported", False) ContainerRegistry.getInstance().addContainer(empty_quality_container) + self.empty_quality_container = empty_quality_container empty_quality_changes_container = copy.deepcopy(empty_container) empty_quality_changes_container.setMetaDataEntry("id", "empty_quality_changes") empty_quality_changes_container.addMetaDataEntry("type", "quality_changes") empty_quality_changes_container.addMetaDataEntry("quality_type", "not_supported") ContainerRegistry.getInstance().addContainer(empty_quality_changes_container) + self.empty_quality_changes_container = empty_quality_changes_container with ContainerRegistry.getInstance().lockFile(): ContainerRegistry.getInstance().loadAllMetadata() @@ -381,6 +399,9 @@ class CuraApplication(QtApplication): self.getCuraSceneController().setActiveBuildPlate(0) # Initialize + self._quality_profile_drop_down_menu_model = None + self._custom_quality_profile_drop_down_menu_model = None + CuraApplication.Created = True @pyqtSlot(str, result = str) @@ -523,8 +544,6 @@ class CuraApplication(QtApplication): has_user_interaction = True return has_user_interaction - onDiscardOrKeepProfileChangesClosed = pyqtSignal() # Used to notify other managers that the dialog was closed - @pyqtSlot(str) def discardOrKeepProfileChangesClosed(self, option): if option == "discard": @@ -547,7 +566,6 @@ class CuraApplication(QtApplication): user_global_container.update() # notify listeners that quality has changed (after user selected discard or keep) - self.onDiscardOrKeepProfileChangesClosed.emit() self.getMachineManager().activeQualityChanged.emit() @pyqtSlot(int) @@ -723,6 +741,20 @@ class CuraApplication(QtApplication): def run(self): self.preRun() + container_registry = ContainerRegistry.getInstance() + self._variant_manager = VariantManager(container_registry) + self._variant_manager.initialize() + + from cura.Machines.MaterialManager import MaterialManager + self._material_manager = MaterialManager(container_registry, parent = self) + self._material_manager.initialize() + + from cura.Machines.QualityManager import QualityManager + self._quality_manager = QualityManager(container_registry, parent = self) + self._quality_manager.initialize() + + self._machine_manager = MachineManager(self) + # Check if we should run as single instance or not self._setUpSingleInstanceServer() @@ -816,7 +848,7 @@ class CuraApplication(QtApplication): def getMachineManager(self, *args) -> MachineManager: if self._machine_manager is None: - self._machine_manager = MachineManager.createMachineManager() + self._machine_manager = MachineManager(self) return self._machine_manager def getExtruderManager(self, *args): @@ -824,20 +856,32 @@ class CuraApplication(QtApplication): self._extruder_manager = ExtruderManager.createExtruderManager() return self._extruder_manager + def getVariantManager(self, *args): + return self._variant_manager + + @pyqtSlot(result = QObject) def getMaterialManager(self, *args): - if self._material_manager is None: - self._material_manager = MaterialManager.createMaterialManager() return self._material_manager + @pyqtSlot(result = QObject) + def getQualityManager(self, *args): + return self._quality_manager + def getObjectsModel(self, *args): if self._object_manager is None: self._object_manager = ObjectsModel.createObjectsModel() return self._object_manager + @pyqtSlot(result = QObject) + def getMultiBuildPlateModel(self, *args): + if self._multi_build_plate_model is None: + self._multi_build_plate_model = MultiBuildPlateModel(self) + return self._multi_build_plate_model + + @pyqtSlot(result = QObject) def getBuildPlateModel(self, *args): if self._build_plate_model is None: - self._build_plate_model = BuildPlateModel.createBuildPlateModel() - + self._build_plate_model = BuildPlateModel(self) return self._build_plate_model def getCuraSceneController(self, *args): @@ -875,6 +919,16 @@ class CuraApplication(QtApplication): def getPrintInformation(self): return self._print_information + def getQualityProfilesDropDownMenuModel(self, *args, **kwargs): + if self._quality_profile_drop_down_menu_model is None: + self._quality_profile_drop_down_menu_model = QualityProfilesDropDownMenuModel(self) + return self._quality_profile_drop_down_menu_model + + def getCustomQualityProfilesDropDownMenuModel(self, *args, **kwargs): + if self._custom_quality_profile_drop_down_menu_model is None: + self._custom_quality_profile_drop_down_menu_model = CustomQualityProfilesDropDownMenuModel(self) + return self._custom_quality_profile_drop_down_menu_model + ## Registers objects for the QML engine to use. # # \param engine The QML engine. @@ -889,27 +943,34 @@ class CuraApplication(QtApplication): qmlRegisterUncreatableType(CuraApplication, "Cura", 1, 0, "ResourceTypes", "Just an Enum type") - qmlRegisterSingletonType(CuraSceneController, "Cura", 1, 2, "SceneController", self.getCuraSceneController) + qmlRegisterSingletonType(CuraSceneController, "Cura", 1, 0, "SceneController", self.getCuraSceneController) qmlRegisterSingletonType(ExtruderManager, "Cura", 1, 0, "ExtruderManager", self.getExtruderManager) qmlRegisterSingletonType(MachineManager, "Cura", 1, 0, "MachineManager", self.getMachineManager) - qmlRegisterSingletonType(MaterialManager, "Cura", 1, 0, "MaterialManager", self.getMaterialManager) qmlRegisterSingletonType(SettingInheritanceManager, "Cura", 1, 0, "SettingInheritanceManager", self.getSettingInheritanceManager) - qmlRegisterSingletonType(SimpleModeSettingsManager, "Cura", 1, 2, "SimpleModeSettingsManager", self.getSimpleModeSettingsManager) + qmlRegisterSingletonType(SimpleModeSettingsManager, "Cura", 1, 0, "SimpleModeSettingsManager", self.getSimpleModeSettingsManager) qmlRegisterSingletonType(MachineActionManager.MachineActionManager, "Cura", 1, 0, "MachineActionManager", self.getMachineActionManager) - qmlRegisterSingletonType(ObjectsModel, "Cura", 1, 2, "ObjectsModel", self.getObjectsModel) - qmlRegisterSingletonType(BuildPlateModel, "Cura", 1, 2, "BuildPlateModel", self.getBuildPlateModel) + qmlRegisterSingletonType(ObjectsModel, "Cura", 1, 0, "ObjectsModel", self.getObjectsModel) + qmlRegisterType(BuildPlateModel, "Cura", 1, 0, "BuildPlateModel") + qmlRegisterType(MultiBuildPlateModel, "Cura", 1, 0, "MultiBuildPlateModel") qmlRegisterType(InstanceContainer, "Cura", 1, 0, "InstanceContainer") qmlRegisterType(ExtrudersModel, "Cura", 1, 0, "ExtrudersModel") - qmlRegisterType(ContainerSettingsModel, "Cura", 1, 0, "ContainerSettingsModel") - qmlRegisterSingletonType(ProfilesModel, "Cura", 1, 0, "ProfilesModel", ProfilesModel.createProfilesModel) - qmlRegisterType(MaterialsModel, "Cura", 1, 0, "MaterialsModel") - qmlRegisterType(QualityAndUserProfilesModel, "Cura", 1, 0, "QualityAndUserProfilesModel") - qmlRegisterType(UserProfilesModel, "Cura", 1, 0, "UserProfilesModel") + + qmlRegisterType(GenericMaterialsModel, "Cura", 1, 0, "GenericMaterialsModel") + qmlRegisterType(BrandMaterialsModel, "Cura", 1, 0, "BrandMaterialsModel") + qmlRegisterType(MaterialManagementModel, "Cura", 1, 0, "MaterialManagementModel") + qmlRegisterType(QualityManagementModel, "Cura", 1, 0, "QualityManagementModel") + + qmlRegisterSingletonType(QualityProfilesDropDownMenuModel, "Cura", 1, 0, + "QualityProfilesDropDownMenuModel", self.getQualityProfilesDropDownMenuModel) + qmlRegisterSingletonType(CustomQualityProfilesDropDownMenuModel, "Cura", 1, 0, + "CustomQualityProfilesDropDownMenuModel", self.getCustomQualityProfilesDropDownMenuModel) + qmlRegisterType(NozzleModel, "Cura", 1, 0, "NozzleModel") + qmlRegisterType(MaterialSettingsVisibilityHandler, "Cura", 1, 0, "MaterialSettingsVisibilityHandler") qmlRegisterType(QualitySettingsModel, "Cura", 1, 0, "QualitySettingsModel") qmlRegisterType(MachineNameValidator, "Cura", 1, 0, "MachineNameValidator") - qmlRegisterType(UserChangesModel, "Cura", 1, 1, "UserChangesModel") + qmlRegisterType(UserChangesModel, "Cura", 1, 0, "UserChangesModel") qmlRegisterSingletonType(ContainerManager, "Cura", 1, 0, "ContainerManager", ContainerManager.createContainerManager) # As of Qt5.7, it is necessary to get rid of any ".." in the path for the singleton to work. @@ -991,7 +1052,7 @@ class CuraApplication(QtApplication): count = 0 scene_bounding_box = None is_block_slicing_node = False - active_build_plate = self.getBuildPlateModel().activeBuildPlate + active_build_plate = self.getMultiBuildPlateModel().activeBuildPlate for node in DepthFirstIterator(self.getController().getScene().getRoot()): if ( not issubclass(type(node), CuraSceneNode) or @@ -1240,7 +1301,7 @@ class CuraApplication(QtApplication): @pyqtSlot() def arrangeAll(self): nodes = [] - active_build_plate = self.getBuildPlateModel().activeBuildPlate + active_build_plate = self.getMultiBuildPlateModel().activeBuildPlate for node in DepthFirstIterator(self.getController().getScene().getRoot()): if not isinstance(node, SceneNode): continue @@ -1389,7 +1450,7 @@ class CuraApplication(QtApplication): group_decorator = GroupDecorator() group_node.addDecorator(group_decorator) group_node.addDecorator(ConvexHullDecorator()) - group_node.addDecorator(BuildPlateDecorator(self.getBuildPlateModel().activeBuildPlate)) + group_node.addDecorator(BuildPlateDecorator(self.getMultiBuildPlateModel().activeBuildPlate)) group_node.setParent(self.getController().getScene().getRoot()) group_node.setSelectable(True) center = Selection.getSelectionCenter() @@ -1534,7 +1595,7 @@ class CuraApplication(QtApplication): arrange_objects_on_load = ( not Preferences.getInstance().getValue("cura/use_multi_build_plate") or not Preferences.getInstance().getValue("cura/not_arrange_objects_on_load")) - target_build_plate = self.getBuildPlateModel().activeBuildPlate if arrange_objects_on_load else -1 + target_build_plate = self.getMultiBuildPlateModel().activeBuildPlate if arrange_objects_on_load else -1 root = self.getController().getScene().getRoot() fixed_nodes = [] diff --git a/cura/Machines/ContainerNode.py b/cura/Machines/ContainerNode.py new file mode 100644 index 0000000000..6a839fb921 --- /dev/null +++ b/cura/Machines/ContainerNode.py @@ -0,0 +1,49 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from typing import Optional + +from collections import OrderedDict + +from UM.Logger import Logger +from UM.Settings.InstanceContainer import InstanceContainer + + +## +# A metadata / container combination. Use getContainer() to get the container corresponding to the metadata. +# +# ContainerNode is a multi-purpose class. It has two main purposes: +# 1. It encapsulates an InstanceContainer. It contains that InstanceContainer's +# - metadata (Always) +# - container (lazy-loaded when needed) +# 2. It also serves as a node in a hierarchical InstanceContainer lookup table/tree. +# This is used in Variant, Material, and Quality Managers. +# +class ContainerNode: + __slots__ = ("metadata", "container", "children_map") + + def __init__(self, metadata: Optional[dict] = None): + self.metadata = metadata + self.container = None + self.children_map = OrderedDict() + + def getChildNode(self, child_key: str) -> Optional["ContainerNode"]: + return self.children_map.get(child_key) + + def getContainer(self) -> "InstanceContainer": + if self.metadata is None: + raise RuntimeError("Cannot get container for a ContainerNode without metadata") + + if self.container is None: + container_id = self.metadata["id"] + Logger.log("i", "Lazy-loading container [%s]", container_id) + from UM.Settings.ContainerRegistry import ContainerRegistry + container_list = ContainerRegistry.getInstance().findInstanceContainers(id = container_id) + if not container_list: + raise RuntimeError("Failed to lazy-load container [%s], cannot find it" % container_id) + self.container = container_list[0] + + return self.container + + def __str__(self) -> str: + return "%s[%s]" % (self.__class__.__name__, self.metadata.get("id")) diff --git a/cura/Machines/MaterialGroup.py b/cura/Machines/MaterialGroup.py new file mode 100644 index 0000000000..009778943a --- /dev/null +++ b/cura/Machines/MaterialGroup.py @@ -0,0 +1,26 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + + +# +# A MaterialGroup represents a group of material InstanceContainers that are derived from a single material profile. +# The main InstanceContainer which has the ID of the material profile file name is called the "root_material". For +# example: "generic_abs" is the root material (ID) of "generic_abs_ultimaker3" and "generic_abs_ultimaker3_AA_0.4", +# and "generic_abs_ultimaker3" and "generic_abs_ultimaker3_AA_0.4" are derived materials of "generic_abs". +# +# Using "generic_abs" as an example, the MaterialGroup for "generic_abs" will contain the following information: +# - name: "generic_abs", root_material_id +# - root_material_node: MaterialNode of "generic_abs" +# - derived_material_node_list: A list of MaterialNodes that are derived from "generic_abs", +# so "generic_abs_ultimaker3", "generic_abs_ultimaker3_AA_0.4", etc. +# +class MaterialGroup: + __slots__ = ("name", "root_material_node", "derived_material_node_list") + + def __init__(self, name: str): + self.name = name + self.root_material_node = None + self.derived_material_node_list = [] + + def __str__(self) -> str: + return "%s[%s]" % (self.__class__.__name__, self.name) diff --git a/cura/Machines/MaterialManager.py b/cura/Machines/MaterialManager.py new file mode 100644 index 0000000000..98e4f67f82 --- /dev/null +++ b/cura/Machines/MaterialManager.py @@ -0,0 +1,479 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from collections import defaultdict, OrderedDict +import copy +import uuid +from typing import Optional, TYPE_CHECKING + +from PyQt5.Qt import QTimer, QObject, pyqtSignal, pyqtSlot + +from UM.Application import Application +from UM.Logger import Logger +from UM.Settings.ContainerRegistry import ContainerRegistry +from UM.Settings.SettingFunction import SettingFunction +from UM.Util import parseBool + +from .MaterialNode import MaterialNode +from .MaterialGroup import MaterialGroup + +if TYPE_CHECKING: + from cura.Settings.GlobalStack import GlobalStack + + +# +# MaterialManager maintains a number of maps and trees for material lookup. +# The models GUI and QML use are now only dependent on the MaterialManager. That means as long as the data in +# MaterialManager gets updated correctly, the GUI models should be updated correctly too, and the same goes for GUI. +# +# For now, updating the lookup maps and trees here is very simple: we discard the old data completely and recreate them +# again. This means the update is exactly the same as initialization. There are performance concerns about this approach +# but so far the creation of the tables and maps is very fast and there is no noticeable slowness, we keep it like this +# because it's simple. +# +class MaterialManager(QObject): + + materialsUpdated = pyqtSignal() # Emitted whenever the material lookup tables are updated. + + def __init__(self, container_registry, parent = None): + super().__init__(parent) + self._application = Application.getInstance() + self._container_registry = container_registry # type: ContainerRegistry + + self._fallback_materials_map = dict() # material_type -> generic material metadata + self._material_group_map = dict() # root_material_id -> MaterialGroup + self._diameter_machine_variant_material_map = dict() # approximate diameter str -> dict(machine_definition_id -> MaterialNode) + + # We're using these two maps to convert between the specific diameter material id and the generic material id + # because the generic material ids are used in qualities and definitions, while the specific diameter material is meant + # i.e. generic_pla -> generic_pla_175 + self._material_diameter_map = defaultdict(dict) # root_material_id -> approximate diameter str -> root_material_id for that diameter + self._diameter_material_map = dict() # material id including diameter (generic_pla_175) -> material root id (generic_pla) + + # This is used in Legacy UM3 send material function and the material management page. + self._guid_material_groups_map = defaultdict(list) # GUID -> a list of material_groups + + # The machine definition ID for the non-machine-specific materials. + # This is used as the last fallback option if the given machine-specific material(s) cannot be found. + self._default_machine_definition_id = "fdmprinter" + self._default_approximate_diameter_for_quality_search = "3" + + # When a material gets added/imported, there can be more than one InstanceContainers. In those cases, we don't + # want to react on every container/metadata changed signal. The timer here is to buffer it a bit so we don't + # react too many time. + self._update_timer = QTimer(self) + self._update_timer.setInterval(300) + self._update_timer.setSingleShot(True) + self._update_timer.timeout.connect(self._updateMaps) + + self._container_registry.containerMetaDataChanged.connect(self._onContainerMetadataChanged) + self._container_registry.containerAdded.connect(self._onContainerMetadataChanged) + self._container_registry.containerRemoved.connect(self._onContainerMetadataChanged) + + def initialize(self): + # Find all materials and put them in a matrix for quick search. + material_metadata_list = self._container_registry.findContainersMetadata(type = "material") + + self._material_group_map = dict() + + # Map #1 + # root_material_id -> MaterialGroup + for material_metadata in material_metadata_list: + material_id = material_metadata["id"] + # We don't store empty material in the lookup tables + if material_id == "empty_material": + continue + + root_material_id = material_metadata.get("base_file") + if root_material_id not in self._material_group_map: + self._material_group_map[root_material_id] = MaterialGroup(root_material_id) + group = self._material_group_map[root_material_id] + + # We only add root materials here + if material_id == root_material_id: + group.root_material_node = MaterialNode(material_metadata) + else: + new_node = MaterialNode(material_metadata) + group.derived_material_node_list.append(new_node) + # Order this map alphabetically so it's easier to navigate in a debugger + self._material_group_map = OrderedDict(sorted(self._material_group_map.items(), key = lambda x: x[0])) + + # Map #1.5 + # GUID -> material group list + self._guid_material_groups_map = defaultdict(list) + for root_material_id, material_group in self._material_group_map.items(): + guid = material_group.root_material_node.metadata["GUID"] + self._guid_material_groups_map[guid].append(material_group) + + # Map #2 + # Lookup table for material type -> fallback material metadata, only for read-only materials + grouped_by_type_dict = dict() + for root_material_id, material_node in self._material_group_map.items(): + if not self._container_registry.isReadOnly(root_material_id): + continue + material_type = material_node.root_material_node.metadata["material"] + if material_type not in grouped_by_type_dict: + grouped_by_type_dict[material_type] = {"generic": None, + "others": []} + brand = material_node.root_material_node.metadata["brand"] + if brand.lower() == "generic": + to_add = True + if material_type in grouped_by_type_dict: + diameter = material_node.root_material_node.metadata.get("approximate_diameter") + if diameter != self._default_approximate_diameter_for_quality_search: + to_add = False # don't add if it's not the default diameter + if to_add: + grouped_by_type_dict[material_type] = material_node.root_material_node.metadata + self._fallback_materials_map = grouped_by_type_dict + + # Map #3 + # There can be multiple material profiles for the same material with different diameters, such as "generic_pla" + # and "generic_pla_175". This is inconvenient when we do material-specific quality lookup because a quality can + # be for either "generic_pla" or "generic_pla_175", but not both. This map helps to get the correct material ID + # for quality search. + self._material_diameter_map = defaultdict(dict) + self._diameter_material_map = dict() + + # Group the material IDs by the same name, material, brand, and color but with different diameters. + material_group_dict = dict() + keys_to_fetch = ("name", "material", "brand", "color") + for root_material_id, machine_node in self._material_group_map.items(): + if not self._container_registry.isReadOnly(root_material_id): + continue + + root_material_metadata = machine_node.root_material_node.metadata + + key_data = [] + for key in keys_to_fetch: + key_data.append(root_material_metadata.get(key)) + key_data = tuple(key_data) + + if key_data not in material_group_dict: + material_group_dict[key_data] = dict() + approximate_diameter = root_material_metadata.get("approximate_diameter") + material_group_dict[key_data][approximate_diameter] = root_material_metadata["id"] + + # Map [root_material_id][diameter] -> root_material_id for this diameter + for data_dict in material_group_dict.values(): + for root_material_id1 in data_dict.values(): + if root_material_id1 in self._material_diameter_map: + continue + diameter_map = data_dict + for root_material_id2 in data_dict.values(): + self._material_diameter_map[root_material_id2] = diameter_map + + default_root_material_id = data_dict.get(self._default_approximate_diameter_for_quality_search) + if default_root_material_id is None: + default_root_material_id = list(data_dict.values())[0] # no default diameter present, just take "the" only one + for root_material_id in data_dict.values(): + self._diameter_material_map[root_material_id] = default_root_material_id + + # Map #4 + # "machine" -> "variant_name" -> "root material ID" -> specific material InstanceContainer + # Construct the "machine" -> "variant" -> "root material ID" -> specific material InstanceContainer + self._diameter_machine_variant_material_map = dict() + for material_metadata in material_metadata_list: + # We don't store empty material in the lookup tables + if material_metadata["id"] == "empty_material": + continue + + root_material_id = material_metadata["base_file"] + definition = material_metadata["definition"] + approximate_diameter = material_metadata["approximate_diameter"] + + if approximate_diameter not in self._diameter_machine_variant_material_map: + self._diameter_machine_variant_material_map[approximate_diameter] = {} + + machine_variant_material_map = self._diameter_machine_variant_material_map[approximate_diameter] + if definition not in machine_variant_material_map: + machine_variant_material_map[definition] = MaterialNode() + + machine_node = machine_variant_material_map[definition] + variant_name = material_metadata.get("variant_name") + if not variant_name: + # if there is no variant, this material is for the machine, so put its metadata in the machine node. + machine_node.material_map[root_material_id] = MaterialNode(material_metadata) + else: + # this material is variant-specific, so we save it in a variant-specific node under the + # machine-specific node + if variant_name not in machine_node.children_map: + machine_node.children_map[variant_name] = MaterialNode() + + variant_node = machine_node.children_map[variant_name] + if root_material_id not in variant_node.material_map: + variant_node.material_map[root_material_id] = MaterialNode(material_metadata) + else: + # Sanity check: make sure we don't have duplicated variant-specific materials for the same machine + raise RuntimeError("Found duplicate variant name [%s] for machine [%s] in material [%s]" % + (variant_name, definition, material_metadata["id"])) + + self.materialsUpdated.emit() + + def _updateMaps(self): + self.initialize() + + def _onContainerMetadataChanged(self, container): + self._onContainerChanged(container) + + def _onContainerChanged(self, container): + container_type = container.getMetaDataEntry("type") + if container_type != "material": + return + + # update the maps + self._update_timer.start() + + def getMaterialGroup(self, root_material_id: str) -> Optional[MaterialGroup]: + return self._material_group_map.get(root_material_id) + + def getRootMaterialIDForDiameter(self, root_material_id: str, approximate_diameter: str) -> str: + return self._material_diameter_map.get(root_material_id).get(approximate_diameter, root_material_id) + + def getRootMaterialIDWithoutDiameter(self, root_material_id: str) -> str: + return self._diameter_material_map.get(root_material_id) + + def getMaterialGroupListByGUID(self, guid: str) -> Optional[list]: + return self._guid_material_groups_map.get(guid) + + # + # Return a dict with all root material IDs (k) and ContainerNodes (v) that's suitable for the given setup. + # + def getAvailableMaterials(self, machine_definition_id: str, extruder_variant_name: Optional[str], + diameter: float) -> dict: + # round the diameter to get the approximate diameter + rounded_diameter = str(round(diameter)) + if rounded_diameter not in self._diameter_machine_variant_material_map: + Logger.log("i", "Cannot find materials with diameter [%s] (rounded to [%s])", diameter, rounded_diameter) + return dict() + + # If there are variant materials, get the variant material + machine_variant_material_map = self._diameter_machine_variant_material_map[rounded_diameter] + machine_node = machine_variant_material_map.get(machine_definition_id) + default_machine_node = machine_variant_material_map.get(self._default_machine_definition_id) + variant_node = None + if extruder_variant_name is not None and machine_node is not None: + variant_node = machine_node.getChildNode(extruder_variant_name) + + nodes_to_check = [variant_node, machine_node, default_machine_node] + + # Fallback mechanism of finding materials: + # 1. variant-specific material + # 2. machine-specific material + # 3. generic material (for fdmprinter) + material_id_metadata_dict = dict() + for node in nodes_to_check: + if node is not None: + for material_id, node in node.material_map.items(): + if material_id not in material_id_metadata_dict: + material_id_metadata_dict[material_id] = node + + return material_id_metadata_dict + + # + # A convenience function to get available materials for the given machine with the extruder position. + # + def getAvailableMaterialsForMachineExtruder(self, machine: "GlobalStack", + extruder_stack: "ExtruderStack") -> Optional[dict]: + machine_definition_id = machine.definition.getId() + variant_name = None + if extruder_stack.variant.getId() != "empty_variant": + variant_name = extruder_stack.variant.getName() + diameter = extruder_stack.approximateMaterialDiameter + + # Fetch the available materials (ContainerNode) for the current active machine and extruder setup. + return self.getAvailableMaterials(machine_definition_id, variant_name, diameter) + + # + # Gets MaterialNode for the given extruder and machine with the given material name. + # Returns None if: + # 1. the given machine doesn't have materials; + # 2. cannot find any material InstanceContainers with the given settings. + # + def getMaterialNode(self, machine_definition_id: str, extruder_variant_name: Optional[str], + diameter: float, root_material_id: str) -> Optional["InstanceContainer"]: + # round the diameter to get the approximate diameter + rounded_diameter = str(round(diameter)) + if rounded_diameter not in self._diameter_machine_variant_material_map: + Logger.log("i", "Cannot find materials with diameter [%s] (rounded to [%s]) for root material id [%s]", + diameter, rounded_diameter, root_material_id) + return None + + # If there are variant materials, get the variant material + machine_variant_material_map = self._diameter_machine_variant_material_map[rounded_diameter] + machine_node = machine_variant_material_map.get(machine_definition_id) + variant_node = None + + # Fallback for "fdmprinter" if the machine-specific materials cannot be found + if machine_node is None: + machine_node = machine_variant_material_map.get(self._default_machine_definition_id) + if machine_node is not None and extruder_variant_name is not None: + variant_node = machine_node.getChildNode(extruder_variant_name) + + # Fallback mechanism of finding materials: + # 1. variant-specific material + # 2. machine-specific material + # 3. generic material (for fdmprinter) + nodes_to_check = [variant_node, machine_node, + machine_variant_material_map.get(self._default_machine_definition_id)] + + material_node = None + for node in nodes_to_check: + if node is not None: + material_node = node.material_map.get(root_material_id) + if material_node: + break + + return material_node + + # + # Used by QualityManager. Built-in quality profiles may be based on generic material IDs such as "generic_pla". + # For materials such as ultimaker_pla_orange, no quality profiles may be found, so we should fall back to use + # the generic material IDs to search for qualities. + # + # An example would be, suppose we have machine with preferred material set to "filo3d_pla" (1.75mm), but its + # extruders only use 2.85mm materials, then we won't be able to find the preferred material for this machine. + # A fallback would be to fetch a generic material of the same type "PLA" as "filo3d_pla", and in this case it will + # be "generic_pla". This function is intended to get a generic fallback material for the given material type. + # + # This function returns the generic root material ID for the given material type, where material types are "PLA", + # "ABS", etc. + # + def getFallbackMaterialIdByMaterialType(self, material_type: str) -> Optional[str]: + # For safety + if material_type not in self._fallback_materials_map: + Logger.log("w", "The material type [%s] does not have a fallback material" % material_type) + return None + fallback_material = self._fallback_materials_map[material_type] + if fallback_material: + return self.getRootMaterialIDWithoutDiameter(fallback_material["id"]) + else: + return None + + def getDefaultMaterial(self, global_stack: "GlobalStack", extruder_variant_name: str) -> Optional["MaterialNode"]: + node = None + machine_definition = global_stack.definition + if parseBool(machine_definition.getMetaDataEntry("has_materials", False)): + material_diameter = machine_definition.getProperty("material_diameter", "value") + if isinstance(material_diameter, SettingFunction): + material_diameter = material_diameter(global_stack) + approximate_material_diameter = str(round(material_diameter)) + root_material_id = machine_definition.getMetaDataEntry("preferred_material") + root_material_id = self.getRootMaterialIDForDiameter(root_material_id, approximate_material_diameter) + node = self.getMaterialNode(machine_definition.getId(), extruder_variant_name, + material_diameter, root_material_id) + return node + + # + # Methods for GUI + # + + # + # Sets the new name for the given material. + # + @pyqtSlot("QVariant", str) + def setMaterialName(self, material_node: "MaterialNode", name: str): + root_material_id = material_node.metadata["base_file"] + if self._container_registry.isReadOnly(root_material_id): + Logger.log("w", "Cannot set name of read-only container %s.", root_material_id) + return + + material_group = self.getMaterialGroup(root_material_id) + material_group.root_material_node.getContainer().setName(name) + + # + # Removes the given material. + # + @pyqtSlot("QVariant") + def removeMaterial(self, material_node: "MaterialNode"): + root_material_id = material_node.metadata["base_file"] + material_group = self.getMaterialGroup(root_material_id) + if not material_group: + Logger.log("d", "Unable to remove the material with id %s, because it doesn't exist.", root_material_id) + return + + nodes_to_remove = [material_group.root_material_node] + material_group.derived_material_node_list + for node in nodes_to_remove: + self._container_registry.removeContainer(node.metadata["id"]) + + # + # Creates a duplicate of a material, which has the same GUID and base_file metadata. + # Returns the root material ID of the duplicated material if successful. + # + @pyqtSlot("QVariant", result = str) + def duplicateMaterial(self, material_node, new_base_id = None, new_metadata = None) -> Optional[str]: + root_material_id = material_node.metadata["base_file"] + + material_group = self.getMaterialGroup(root_material_id) + if not material_group: + Logger.log("i", "Unable to duplicate the material with id %s, because it doesn't exist.", root_material_id) + return None + + base_container = material_group.root_material_node.getContainer() + + # Ensure all settings are saved. + self._application.saveSettings() + + # Create a new ID & container to hold the data. + new_containers = [] + if new_base_id is None: + new_base_id = self._container_registry.uniqueName(base_container.getId()) + new_base_container = copy.deepcopy(base_container) + new_base_container.getMetaData()["id"] = new_base_id + new_base_container.getMetaData()["base_file"] = new_base_id + if new_metadata is not None: + for key, value in new_metadata.items(): + new_base_container.getMetaData()[key] = value + new_containers.append(new_base_container) + + # Clone all of them. + for node in material_group.derived_material_node_list: + container_to_copy = node.getContainer() + # Create unique IDs for every clone. + new_id = new_base_id + if container_to_copy.getMetaDataEntry("definition") != "fdmprinter": + new_id += "_" + container_to_copy.getMetaDataEntry("definition") + if container_to_copy.getMetaDataEntry("variant_name"): + variant_name = container_to_copy.getMetaDataEntry("variant_name") + new_id += "_" + variant_name.replace(" ", "_") + + new_container = copy.deepcopy(container_to_copy) + new_container.getMetaData()["id"] = new_id + new_container.getMetaData()["base_file"] = new_base_id + if new_metadata is not None: + for key, value in new_metadata.items(): + new_container.getMetaData()[key] = value + + new_containers.append(new_container) + + for container_to_add in new_containers: + container_to_add.setDirty(True) + self._container_registry.addContainer(container_to_add) + return new_base_id + + # + # Create a new material by cloning Generic PLA for the current material diameter and generate a new GUID. + # + @pyqtSlot(result = str) + def createMaterial(self) -> str: + from UM.i18n import i18nCatalog + catalog = i18nCatalog("cura") + # Ensure all settings are saved. + self._application.saveSettings() + + global_stack = self._application.getGlobalContainerStack() + approximate_diameter = str(round(global_stack.getProperty("material_diameter", "value"))) + root_material_id = "generic_pla" + root_material_id = self.getRootMaterialIDForDiameter(root_material_id, approximate_diameter) + material_group = self.getMaterialGroup(root_material_id) + + # Create a new ID & container to hold the data. + new_id = self._container_registry.uniqueName("custom_material") + new_metadata = {"name": catalog.i18nc("@label", "Custom Material"), + "brand": catalog.i18nc("@label", "Custom"), + "GUID": str(uuid.uuid4()), + } + + self.duplicateMaterial(material_group.root_material_node, + new_base_id = new_id, + new_metadata = new_metadata) + return new_id diff --git a/cura/Machines/MaterialNode.py b/cura/Machines/MaterialNode.py new file mode 100644 index 0000000000..fde11186c2 --- /dev/null +++ b/cura/Machines/MaterialNode.py @@ -0,0 +1,21 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from typing import Optional + +from .ContainerNode import ContainerNode + + +# +# A MaterialNode is a node in the material lookup tree/map/table. It contains 2 (extra) fields: +# - material_map: a one-to-one map of "material_root_id" to material_node. +# - children_map: the key-value map for child nodes of this node. This is used in a lookup tree. +# +# +class MaterialNode(ContainerNode): + __slots__ = ("material_map", "children_map") + + def __init__(self, metadata: Optional[dict] = None): + super().__init__(metadata = metadata) + self.material_map = {} # material_root_id -> material_node + self.children_map = {} # mapping for the child nodes diff --git a/cura/Machines/Models/BaseMaterialsModel.py b/cura/Machines/Models/BaseMaterialsModel.py new file mode 100644 index 0000000000..de0c68d60a --- /dev/null +++ b/cura/Machines/Models/BaseMaterialsModel.py @@ -0,0 +1,46 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from PyQt5.QtCore import Qt, pyqtSignal, pyqtProperty + +from UM.Qt.ListModel import ListModel + + +# +# This is the base model class for GenericMaterialsModel and BrandMaterialsModel +# Those 2 models are used by the material drop down menu to show generic materials and branded materials separately. +# The extruder position defined here is being used to bound a menu to the correct extruder. This is used in the top +# bar menu "Settings" -> "Extruder nr" -> "Material" -> this menu +# +class BaseMaterialsModel(ListModel): + RootMaterialIdRole = Qt.UserRole + 1 + IdRole = Qt.UserRole + 2 + NameRole = Qt.UserRole + 3 + BrandRole = Qt.UserRole + 4 + MaterialRole = Qt.UserRole + 5 + ColorRole = Qt.UserRole + 6 + ContainerNodeRole = Qt.UserRole + 7 + + extruderPositionChanged = pyqtSignal() + + def __init__(self, parent = None): + super().__init__(parent) + + self.addRoleName(self.RootMaterialIdRole, "root_material_id") + self.addRoleName(self.IdRole, "id") + self.addRoleName(self.NameRole, "name") + self.addRoleName(self.BrandRole, "brand") + self.addRoleName(self.MaterialRole, "material") + self.addRoleName(self.ColorRole, "color_name") + self.addRoleName(self.ContainerNodeRole, "container_node") + + self._extruder_position = 0 + + def setExtruderPosition(self, position: int): + if self._extruder_position != position: + self._extruder_position = position + self.extruderPositionChanged.emit() + + @pyqtProperty(int, fset = setExtruderPosition, notify = extruderPositionChanged) + def extruderPosition(self) -> int: + return self._extruder_positoin diff --git a/cura/Machines/Models/BrandMaterialsModel.py b/cura/Machines/Models/BrandMaterialsModel.py new file mode 100644 index 0000000000..6628d924f1 --- /dev/null +++ b/cura/Machines/Models/BrandMaterialsModel.py @@ -0,0 +1,131 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from PyQt5.QtCore import Qt, pyqtSignal, pyqtProperty + +from UM.Qt.ListModel import ListModel + +from .BaseMaterialsModel import BaseMaterialsModel + + +# +# This is an intermediate model to group materials with different colours for a same brand and type. +# +class MaterialsModelGroupedByType(ListModel): + NameRole = Qt.UserRole + 1 + ColorsRole = Qt.UserRole + 2 + + def __init__(self, parent = None): + super().__init__(parent) + + self.addRoleName(self.NameRole, "name") + self.addRoleName(self.ColorsRole, "colors") + + +# +# This model is used to show branded materials in the material drop down menu. +# The structure of the menu looks like this: +# Brand -> Material Type -> list of materials +# +# To illustrate, a branded material menu may look like this: +# Ultimaker -> PLA -> Yellow PLA +# -> Black PLA +# -> ... +# -> ABS -> White ABS +# ... +# +class BrandMaterialsModel(ListModel): + NameRole = Qt.UserRole + 1 + MaterialsRole = Qt.UserRole + 2 + + extruderPositionChanged = pyqtSignal() + + def __init__(self, parent = None): + super().__init__(parent) + + self.addRoleName(self.NameRole, "name") + self.addRoleName(self.MaterialsRole, "materials") + + self._extruder_position = 0 + + from cura.CuraApplication import CuraApplication + self._machine_manager = CuraApplication.getInstance().getMachineManager() + self._extruder_manager = CuraApplication.getInstance().getExtruderManager() + self._material_manager = CuraApplication.getInstance().getMaterialManager() + + self._machine_manager.globalContainerChanged.connect(self._update) + self._extruder_manager.activeExtruderChanged.connect(self._update) + self._material_manager.materialsUpdated.connect(self._update) + + self._update() + + def setExtruderPosition(self, position: int): + if self._extruder_position != position: + self._extruder_position = position + self.extruderPositionChanged.emit() + + @pyqtProperty(int, fset = setExtruderPosition, notify = extruderPositionChanged) + def extruderPosition(self) -> int: + return self._extruder_position + + def _update(self): + global_stack = self._machine_manager.activeMachine + if global_stack is None: + self.setItems([]) + return + extruder_position = str(self._extruder_position) + if extruder_position not in global_stack.extruders: + self.setItems([]) + return + extruder_stack = global_stack.extruders[str(self._extruder_position)] + + available_material_dict = self._material_manager.getAvailableMaterialsForMachineExtruder(global_stack, + extruder_stack) + if available_material_dict is None: + self.setItems([]) + return + + brand_item_list = [] + brand_group_dict = {} + for root_material_id, container_node in available_material_dict.items(): + metadata = container_node.metadata + brand = metadata["brand"] + # Only add results for generic materials + if brand.lower() == "generic": + continue + + if brand not in brand_group_dict: + brand_group_dict[brand] = {} + + material_type = metadata["material"] + if material_type not in brand_group_dict[brand]: + brand_group_dict[brand][material_type] = [] + + item = {"root_material_id": root_material_id, + "id": metadata["id"], + "name": metadata["name"], + "brand": metadata["brand"], + "material": metadata["material"], + "color_name": metadata["color_name"], + "container_node": container_node + } + brand_group_dict[brand][material_type].append(item) + + for brand, material_dict in brand_group_dict.items(): + brand_item = {"name": brand, + "materials": MaterialsModelGroupedByType(self)} + + material_type_item_list = [] + for material_type, material_list in material_dict.items(): + material_type_item = {"name": material_type, + "colors": BaseMaterialsModel(self)} + material_type_item["colors"].clear() + material_type_item["colors"].setItems(material_list) + + material_type_item_list.append(material_type_item) + + brand_item["materials"].setItems(material_type_item_list) + + brand_item_list.append(brand_item) + + self.setItems(brand_item_list) diff --git a/cura/Machines/Models/BuildPlateModel.py b/cura/Machines/Models/BuildPlateModel.py new file mode 100644 index 0000000000..1cb94216a6 --- /dev/null +++ b/cura/Machines/Models/BuildPlateModel.py @@ -0,0 +1,49 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from PyQt5.QtCore import Qt + +from UM.Application import Application +from UM.Qt.ListModel import ListModel +from UM.Util import parseBool + +from cura.Machines.VariantManager import VariantType + + +class BuildPlateModel(ListModel): + NameRole = Qt.UserRole + 1 + ContainerNodeRole = Qt.UserRole + 2 + + def __init__(self, parent = None): + super().__init__(parent) + + self.addRoleName(self.NameRole, "name") + self.addRoleName(self.ContainerNodeRole, "container_node") + + self._application = Application.getInstance() + self._variant_manager = self._application._variant_manager + self._machine_manager = self._application.getMachineManager() + + self._machine_manager.globalContainerChanged.connect(self._update) + + self._update() + + def _update(self): + global_stack = self._machine_manager._global_container_stack + if not global_stack: + self.setItems([]) + return + + has_variants = parseBool(global_stack.getMetaDataEntry("has_variant_buildplates", False)) + if not has_variants: + self.setItems([]) + return + + variant_dict = self._variant_manager.getVariantNodes(global_stack, variant_type = VariantType.BUILD_PLATE) + + item_list = [] + for name, variant_node in variant_dict.items(): + item = {"name": name, + "container_node": variant_node} + item_list.append(item) + self.setItems(item_list) diff --git a/cura/Machines/Models/CustomQualityProfilesDropDownMenuModel.py b/cura/Machines/Models/CustomQualityProfilesDropDownMenuModel.py new file mode 100644 index 0000000000..0d297379cd --- /dev/null +++ b/cura/Machines/Models/CustomQualityProfilesDropDownMenuModel.py @@ -0,0 +1,37 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from UM.Logger import Logger + +from cura.Machines.Models.QualityProfilesDropDownMenuModel import QualityProfilesDropDownMenuModel + + +# +# This model is used for the custom profile items in the profile drop down menu. +# +class CustomQualityProfilesDropDownMenuModel(QualityProfilesDropDownMenuModel): + + def _update(self): + Logger.log("d", "Updating %s ...", self.__class__.__name__) + + active_global_stack = self._machine_manager.activeMachine + if active_global_stack is None: + self.setItems([]) + Logger.log("d", "No active GlobalStack, set %s as empty.", self.__class__.__name__) + return + + quality_changes_group_dict = self._quality_manager.getQualityChangesGroups(active_global_stack) + + item_list = [] + for key in sorted(quality_changes_group_dict): + quality_changes_group = quality_changes_group_dict[key] + + item = {"name": quality_changes_group.name, + "layer_height": "", + "layer_height_without_unit": "", + "available": quality_changes_group.is_available, + "quality_changes_group": quality_changes_group} + + item_list.append(item) + + self.setItems(item_list) diff --git a/cura/Machines/Models/GenericMaterialsModel.py b/cura/Machines/Models/GenericMaterialsModel.py new file mode 100644 index 0000000000..d20fc05b6e --- /dev/null +++ b/cura/Machines/Models/GenericMaterialsModel.py @@ -0,0 +1,60 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from .BaseMaterialsModel import BaseMaterialsModel + + +class GenericMaterialsModel(BaseMaterialsModel): + + def __init__(self, parent = None): + super().__init__(parent) + + from cura.CuraApplication import CuraApplication + self._machine_manager = CuraApplication.getInstance().getMachineManager() + self._extruder_manager = CuraApplication.getInstance().getExtruderManager() + self._material_manager = CuraApplication.getInstance().getMaterialManager() + + self._machine_manager.globalContainerChanged.connect(self._update) + self._extruder_manager.activeExtruderChanged.connect(self._update) + self._material_manager.materialsUpdated.connect(self._update) + + self._update() + + def _update(self): + global_stack = self._machine_manager.activeMachine + if global_stack is None: + self.setItems([]) + return + extruder_position = str(self._extruder_position) + if extruder_position not in global_stack.extruders: + self.setItems([]) + return + extruder_stack = global_stack.extruders[extruder_position] + + available_material_dict = self._material_manager.getAvailableMaterialsForMachineExtruder(global_stack, + extruder_stack) + if available_material_dict is None: + self.setItems([]) + return + + item_list = [] + for root_material_id, container_node in available_material_dict.items(): + metadata = container_node.metadata + # Only add results for generic materials + if metadata["brand"].lower() != "generic": + continue + + item = {"root_material_id": root_material_id, + "id": metadata["id"], + "name": metadata["name"], + "brand": metadata["brand"], + "material": metadata["material"], + "color_name": metadata["color_name"], + "container_node": container_node + } + item_list.append(item) + + # Sort the item list by material name alphabetically + item_list = sorted(item_list, key = lambda d: d["name"]) + + self.setItems(item_list) diff --git a/cura/Machines/Models/MaterialManagementModel.py b/cura/Machines/Models/MaterialManagementModel.py new file mode 100644 index 0000000000..b250232282 --- /dev/null +++ b/cura/Machines/Models/MaterialManagementModel.py @@ -0,0 +1,101 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from PyQt5.QtCore import Qt, pyqtProperty + +from UM.Qt.ListModel import ListModel + + +# +# This model is for the Material management page. +# +class MaterialManagementModel(ListModel): + RootMaterialIdRole = Qt.UserRole + 1 + DisplayNameRole = Qt.UserRole + 2 + BrandRole = Qt.UserRole + 3 + MaterialTypeRole = Qt.UserRole + 4 + ColorNameRole = Qt.UserRole + 5 + ColorCodeRole = Qt.UserRole + 6 + ContainerNodeRole = Qt.UserRole + 7 + ContainerIdRole = Qt.UserRole + 8 + + DescriptionRole = Qt.UserRole + 9 + AdhesionInfoRole = Qt.UserRole + 10 + ApproximateDiameterRole = Qt.UserRole + 11 + GuidRole = Qt.UserRole + 12 + DensityRole = Qt.UserRole + 13 + DiameterRole = Qt.UserRole + 14 + IsReadOnlyRole = Qt.UserRole + 15 + + def __init__(self, parent = None): + super().__init__(parent) + + self.addRoleName(self.RootMaterialIdRole, "root_material_id") + self.addRoleName(self.DisplayNameRole, "name") + self.addRoleName(self.BrandRole, "brand") + self.addRoleName(self.MaterialTypeRole, "material") + self.addRoleName(self.ColorNameRole, "color_name") + self.addRoleName(self.ColorCodeRole, "color_code") + self.addRoleName(self.ContainerNodeRole, "container_node") + self.addRoleName(self.ContainerIdRole, "container_id") + + self.addRoleName(self.DescriptionRole, "description") + self.addRoleName(self.AdhesionInfoRole, "adhesion_info") + self.addRoleName(self.ApproximateDiameterRole, "approximate_diameter") + self.addRoleName(self.GuidRole, "guid") + self.addRoleName(self.DensityRole, "density") + self.addRoleName(self.DiameterRole, "diameter") + self.addRoleName(self.IsReadOnlyRole, "is_read_only") + + from cura.CuraApplication import CuraApplication + self._container_registry = CuraApplication.getInstance().getContainerRegistry() + self._machine_manager = CuraApplication.getInstance().getMachineManager() + self._extruder_manager = CuraApplication.getInstance().getExtruderManager() + self._material_manager = CuraApplication.getInstance().getMaterialManager() + + self._machine_manager.globalContainerChanged.connect(self._update) + self._extruder_manager.activeExtruderChanged.connect(self._update) + self._material_manager.materialsUpdated.connect(self._update) + + self._update() + + def _update(self): + global_stack = self._machine_manager.activeMachine + if global_stack is None: + self.setItems([]) + return + active_extruder_stack = self._machine_manager.activeStack + + available_material_dict = self._material_manager.getAvailableMaterialsForMachineExtruder(global_stack, + active_extruder_stack) + if available_material_dict is None: + self.setItems([]) + return + + material_list = [] + for root_material_id, container_node in available_material_dict.items(): + keys_to_fetch = ("name", + "brand", + "material", + "color_name", + "color_code", + "description", + "adhesion_info", + "approximate_diameter",) + + item = {"root_material_id": container_node.metadata["base_file"], + "container_node": container_node, + "guid": container_node.metadata["GUID"], + "container_id": container_node.metadata["id"], + "density": container_node.metadata.get("properties", {}).get("density", ""), + "diameter": container_node.metadata.get("properties", {}).get("diameter", ""), + "is_read_only": self._container_registry.isReadOnly(container_node.metadata["id"]), + } + + for key in keys_to_fetch: + item[key] = container_node.metadata.get(key, "") + + material_list.append(item) + + material_list = sorted(material_list, key = lambda k: (k["brand"].lower(), k["name"])) + self.setItems(material_list) diff --git a/cura/BuildPlateModel.py b/cura/Machines/Models/MultiBuildPlateModel.py similarity index 70% rename from cura/BuildPlateModel.py rename to cura/Machines/Models/MultiBuildPlateModel.py index 73f61202c6..f0f4997014 100644 --- a/cura/BuildPlateModel.py +++ b/cura/Machines/Models/MultiBuildPlateModel.py @@ -1,24 +1,32 @@ -from PyQt5.QtCore import pyqtSignal, pyqtProperty, pyqtSlot +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from PyQt5.QtCore import pyqtSignal, pyqtProperty -from UM.Qt.ListModel import ListModel -from UM.Scene.Selection import Selection -from UM.Logger import Logger from UM.Application import Application +from UM.Scene.Selection import Selection +from UM.Qt.ListModel import ListModel -class BuildPlateModel(ListModel): +# +# This is the model for multi build plate feature. +# This has nothing to do with the build plate types you can choose on the sidebar for a machine. +# +class MultiBuildPlateModel(ListModel): + maxBuildPlateChanged = pyqtSignal() activeBuildPlateChanged = pyqtSignal() selectionChanged = pyqtSignal() - def __init__(self): - super().__init__() - Application.getInstance().getController().getScene().sceneChanged.connect(self._updateSelectedObjectBuildPlateNumbers) + def __init__(self, parent = None): + super().__init__(parent) + + self._application = Application.getInstance() + self._application.getController().getScene().sceneChanged.connect(self._updateSelectedObjectBuildPlateNumbers) Selection.selectionChanged.connect(self._updateSelectedObjectBuildPlateNumbers) self._max_build_plate = 1 # default self._active_build_plate = -1 - self._selection_build_plates = [] def setMaxBuildPlate(self, max_build_plate): self._max_build_plate = max_build_plate @@ -37,10 +45,6 @@ class BuildPlateModel(ListModel): def activeBuildPlate(self): return self._active_build_plate - @staticmethod - def createBuildPlateModel(): - return BuildPlateModel() - def _updateSelectedObjectBuildPlateNumbers(self, *args): result = set() for node in Selection.getAllSelectedObjects(): diff --git a/cura/Machines/Models/NozzleModel.py b/cura/Machines/Models/NozzleModel.py new file mode 100644 index 0000000000..19d4a800c8 --- /dev/null +++ b/cura/Machines/Models/NozzleModel.py @@ -0,0 +1,56 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from PyQt5.QtCore import Qt + +from UM.Application import Application +from UM.Qt.ListModel import ListModel +from UM.Util import parseBool + + +class NozzleModel(ListModel): + IdRole = Qt.UserRole + 1 + HotendNameRole = Qt.UserRole + 2 + ContainerNodeRole = Qt.UserRole + 3 + + def __init__(self, parent = None): + super().__init__(parent) + + self.addRoleName(self.IdRole, "id") + self.addRoleName(self.HotendNameRole, "hotend_name") + self.addRoleName(self.ContainerNodeRole, "container_node") + + Application.getInstance().globalContainerStackChanged.connect(self._update) + Application.getInstance().getMachineManager().activeVariantChanged.connect(self._update) + Application.getInstance().getMachineManager().activeStackChanged.connect(self._update) + Application.getInstance().getMachineManager().activeMaterialChanged.connect(self._update) + + def _update(self): + self.items.clear() + + variant_manager = Application.getInstance()._variant_manager + active_global_stack = Application.getInstance().getMachineManager()._global_container_stack + if active_global_stack is None: + self.setItems([]) + return + + has_variants = parseBool(active_global_stack.getMetaDataEntry("has_variants", False)) + if not has_variants: + self.setItems([]) + return + + variant_node_dict = variant_manager.getVariantNodes(active_global_stack) + if not variant_node_dict: + self.setItems([]) + return + + item_list = [] + for hotend_name, container_node in sorted(variant_node_dict.items(), key = lambda i: i[0]): + item = {"id": hotend_name, + "hotend_name": hotend_name, + "container_node": container_node + } + + item_list.append(item) + + self.setItems(item_list) diff --git a/cura/Machines/Models/QualityManagementModel.py b/cura/Machines/Models/QualityManagementModel.py new file mode 100644 index 0000000000..e089f92329 --- /dev/null +++ b/cura/Machines/Models/QualityManagementModel.py @@ -0,0 +1,122 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from PyQt5.QtCore import Qt, pyqtSlot + +from UM.Qt.ListModel import ListModel + + +# +# This the QML model for the quality management page. +# +class QualityManagementModel(ListModel): + NameRole = Qt.UserRole + 1 + IsReadOnlyRole = Qt.UserRole + 2 + QualityGroupRole = Qt.UserRole + 3 + QualityChangesGroupRole = Qt.UserRole + 4 + + def __init__(self, parent = None): + super().__init__(parent) + + self.addRoleName(self.NameRole, "name") + self.addRoleName(self.IsReadOnlyRole, "is_read_only") + self.addRoleName(self.QualityGroupRole, "quality_group") + self.addRoleName(self.QualityChangesGroupRole, "quality_changes_group") + + from cura.CuraApplication import CuraApplication + self._container_registry = CuraApplication.getInstance().getContainerRegistry() + self._machine_manager = CuraApplication.getInstance().getMachineManager() + self._extruder_manager = CuraApplication.getInstance().getExtruderManager() + self._quality_manager = CuraApplication.getInstance().getQualityManager() + + self._machine_manager.globalContainerChanged.connect(self._update) + self._quality_manager.qualitiesUpdated.connect(self._update) + + self._update() + + def _update(self): + global_stack = self._machine_manager.activeMachine + + quality_group_dict = self._quality_manager.getQualityGroups(global_stack) + quality_changes_group_dict = self._quality_manager.getQualityChangesGroups(global_stack) + + available_quality_types = set(quality_type for quality_type, quality_group in quality_group_dict.items() + if quality_group.is_available) + if not available_quality_types and not quality_changes_group_dict: + # Nothing to show + self.setItems([]) + return + + item_list = [] + # Create quality group items + for quality_group in quality_group_dict.values(): + if not quality_group.is_available: + continue + + item = {"name": quality_group.name, + "is_read_only": True, + "quality_group": quality_group, + "quality_changes_group": None} + item_list.append(item) + # Sort by quality names + item_list = sorted(item_list, key = lambda x: x["name"]) + + # Create quality_changes group items + quality_changes_item_list = [] + for quality_changes_group in quality_changes_group_dict.values(): + if quality_changes_group.quality_type not in available_quality_types: + continue + quality_group = quality_group_dict[quality_changes_group.quality_type] + item = {"name": quality_changes_group.name, + "is_read_only": False, + "quality_group": quality_group, + "quality_changes_group": quality_changes_group} + quality_changes_item_list.append(item) + + # Sort quality_changes items by names and append to the item list + quality_changes_item_list = sorted(quality_changes_item_list, key = lambda x: x["name"]) + item_list += quality_changes_item_list + + self.setItems(item_list) + + # TODO: Duplicated code here from InstanceContainersModel. Refactor and remove this later. + # + ## Gets a list of the possible file filters that the plugins have + # registered they can read or write. The convenience meta-filters + # "All Supported Types" and "All Files" are added when listing + # readers, but not when listing writers. + # + # \param io_type \type{str} name of the needed IO type + # \return A list of strings indicating file name filters for a file + # dialog. + @pyqtSlot(str, result = "QVariantList") + def getFileNameFilters(self, io_type): + from UM.i18n import i18nCatalog + catalog = i18nCatalog("uranium") + #TODO: This function should be in UM.Resources! + filters = [] + all_types = [] + for plugin_id, meta_data in self._getIOPlugins(io_type): + for io_plugin in meta_data[io_type]: + filters.append(io_plugin["description"] + " (*." + io_plugin["extension"] + ")") + all_types.append("*.{0}".format(io_plugin["extension"])) + + if "_reader" in io_type: + # if we're listing readers, add the option to show all supported files as the default option + filters.insert(0, catalog.i18nc("@item:inlistbox", "All Supported Types ({0})", " ".join(all_types))) + filters.append(catalog.i18nc("@item:inlistbox", "All Files (*)")) # Also allow arbitrary files, if the user so prefers. + return filters + + ## Gets a list of profile reader or writer plugins + # \return List of tuples of (plugin_id, meta_data). + def _getIOPlugins(self, io_type): + from UM.PluginRegistry import PluginRegistry + pr = PluginRegistry.getInstance() + active_plugin_ids = pr.getActivePlugins() + + result = [] + for plugin_id in active_plugin_ids: + meta_data = pr.getMetaData(plugin_id) + if io_type in meta_data: + result.append( (plugin_id, meta_data) ) + return result diff --git a/cura/Machines/Models/QualityProfilesDropDownMenuModel.py b/cura/Machines/Models/QualityProfilesDropDownMenuModel.py new file mode 100644 index 0000000000..fd919639c3 --- /dev/null +++ b/cura/Machines/Models/QualityProfilesDropDownMenuModel.py @@ -0,0 +1,106 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from PyQt5.QtCore import Qt + +from UM.Application import Application +from UM.Logger import Logger +from UM.Qt.ListModel import ListModel + +from cura.Machines.QualityManager import QualityGroup + + +# +# QML Model for all built-in quality profiles. This model is used for the drop-down quality menu. +# +class QualityProfilesDropDownMenuModel(ListModel): + NameRole = Qt.UserRole + 1 + QualityTypeRole = Qt.UserRole + 2 + LayerHeightRole = Qt.UserRole + 3 + LayerHeightUnitRole = Qt.UserRole + 4 + AvailableRole = Qt.UserRole + 5 + QualityGroupRole = Qt.UserRole + 6 + QualityChangesGroupRole = Qt.UserRole + 7 + + def __init__(self, parent = None): + super().__init__(parent) + + self.addRoleName(self.NameRole, "name") + self.addRoleName(self.QualityTypeRole, "quality_type") + self.addRoleName(self.LayerHeightRole, "layer_height") + self.addRoleName(self.LayerHeightUnitRole, "layer_height_unit") + self.addRoleName(self.AvailableRole, "available") + self.addRoleName(self.QualityGroupRole, "quality_group") + self.addRoleName(self.QualityChangesGroupRole, "quality_changes_group") + + self._application = Application.getInstance() + self._machine_manager = self._application.getMachineManager() + self._quality_manager = Application.getInstance().getQualityManager() + + self._application.globalContainerStackChanged.connect(self._update) + self._machine_manager.activeQualityGroupChanged.connect(self._update) + self._quality_manager.qualitiesUpdated.connect(self._update) + + self._layer_height_unit = "" # This is cached + + self._update() + + def _update(self): + Logger.log("d", "Updating quality profile model ...") + + global_stack = self._machine_manager.activeMachine + if global_stack is None: + self.setItems([]) + Logger.log("d", "No active GlobalStack, set quality profile model as empty.") + return + + # Check for material compatibility + if not self._machine_manager.activeMaterialsCompatible(): + Logger.log("d", "No active material compatibility, set quality profile model as empty.") + self.setItems([]) + return + + quality_group_dict = self._quality_manager.getQualityGroups(global_stack) + + item_list = [] + for key in sorted(quality_group_dict): + quality_group = quality_group_dict[key] + + layer_height = self._fetchLayerHeight(quality_group) + + item = {"name": quality_group.name, + "quality_type": quality_group.quality_type, + "layer_height": layer_height, + "layer_height_unit": self._layer_height_unit, + "available": quality_group.is_available, + "quality_group": quality_group} + + item_list.append(item) + + # Sort items based on layer_height + item_list = sorted(item_list, key = lambda x: x["layer_height"]) + + self.setItems(item_list) + + def _fetchLayerHeight(self, quality_group: "QualityGroup"): + global_stack = self._machine_manager.activeMachine + if not self._layer_height_unit: + unit = global_stack.definition.getProperty("layer_height", "unit") + if not unit: + unit = "" + self._layer_height_unit = unit + + default_layer_height = global_stack.definition.getProperty("layer_height", "value") + + # Get layer_height from the quality profile for the GlobalStack + container = quality_group.node_for_global.getContainer() + + layer_height = default_layer_height + if container.hasProperty("layer_height", "value"): + layer_height = container.getProperty("layer_height", "value") + else: + # Look for layer_height in the GlobalStack from material -> definition + container = global_stack.definition + if container.hasProperty("layer_height", "value"): + layer_height = container.getProperty("layer_height", "value") + return float(layer_height) diff --git a/cura/Machines/Models/QualitySettingsModel.py b/cura/Machines/Models/QualitySettingsModel.py new file mode 100644 index 0000000000..38b7ec28e4 --- /dev/null +++ b/cura/Machines/Models/QualitySettingsModel.py @@ -0,0 +1,159 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from PyQt5.QtCore import pyqtProperty, pyqtSignal, Qt + +from UM.Application import Application +from UM.Logger import Logger +from UM.Qt.ListModel import ListModel +from UM.Settings.ContainerRegistry import ContainerRegistry + + +# +# This model is used to show details settings of the selected quality in the quality management page. +# +class QualitySettingsModel(ListModel): + KeyRole = Qt.UserRole + 1 + LabelRole = Qt.UserRole + 2 + UnitRole = Qt.UserRole + 3 + ProfileValueRole = Qt.UserRole + 4 + ProfileValueSourceRole = Qt.UserRole + 5 + UserValueRole = Qt.UserRole + 6 + CategoryRole = Qt.UserRole + 7 + + def __init__(self, parent = None): + super().__init__(parent = parent) + + self.addRoleName(self.KeyRole, "key") + self.addRoleName(self.LabelRole, "label") + self.addRoleName(self.UnitRole, "unit") + self.addRoleName(self.ProfileValueRole, "profile_value") + self.addRoleName(self.ProfileValueSourceRole, "profile_value_source") + self.addRoleName(self.UserValueRole, "user_value") + self.addRoleName(self.CategoryRole, "category") + + self._container_registry = ContainerRegistry.getInstance() + self._application = Application.getInstance() + self._quality_manager = self._application.getQualityManager() + + self._selected_position = "" # empty string means GlobalStack + # strings such as "0", "1", etc. mean extruder positions + self._selected_quality_item = None # The selected quality in the quality management page + self._i18n_catalog = None + + self._quality_manager.qualitiesUpdated.connect(self._update) + + self._update() + + selectedPositionChanged = pyqtSignal() + selectedQualityItemChanged = pyqtSignal() + + def setSelectedPosition(self, selected_position): + if selected_position != self._selected_position: + self._selected_position = selected_position + self.selectedPositionChanged.emit() + self._update() + + @pyqtProperty(str, fset = setSelectedPosition, notify = selectedPositionChanged) + def selectedPosition(self): + return self._selected_position + + def setSelectedQualityItem(self, selected_quality_item): + if selected_quality_item != self._selected_quality_item: + self._selected_quality_item = selected_quality_item + self.selectedQualityItemChanged.emit() + self._update() + + @pyqtProperty("QVariantMap", fset = setSelectedQualityItem, notify = selectedQualityItemChanged) + def selectedQualityItem(self): + return self._selected_quality_item + + def _update(self): + if self._selected_quality_item is None: + self.setItems([]) + return + + items = [] + + global_container_stack = self._application.getGlobalContainerStack() + definition_container = global_container_stack.definition + + quality_group = self._selected_quality_item["quality_group"] + quality_changes_group = self._selected_quality_item["quality_changes_group"] + + if self._selected_position == "": + quality_node = quality_group.node_for_global + else: + quality_node = quality_group.nodes_for_extruders.get(self._selected_position) + settings_keys = quality_group.getAllKeys() + quality_containers = [quality_node.getContainer()] + + # Here, if the user has selected a quality changes, then "quality_changes_group" will not be None, and we fetch + # the settings in that quality_changes_group. + if quality_changes_group is not None: + if self._selected_position == "": + quality_changes_node = quality_changes_group.node_for_global + else: + quality_changes_node = quality_changes_group.nodes_for_extruders.get(self._selected_position) + if quality_changes_node is not None: # it can be None if number of extruders are changed during runtime + try: + quality_containers.insert(0, quality_changes_node.getContainer()) + except: + # FIXME: This is to prevent incomplete update of QualityManager + Logger.logException("d", "Failed to get container for quality changes node %s", quality_changes_node) + return + settings_keys.update(quality_changes_group.getAllKeys()) + + # We iterate over all definitions instead of settings in a quality/qualtiy_changes group is because in the GUI, + # the settings are grouped together by categories, and we had to go over all the definitions to figure out + # which setting belongs in which category. + current_category = "" + for definition in definition_container.findDefinitions(): + if definition.type == "category": + current_category = definition.label + if self._i18n_catalog: + current_category = self._i18n_catalog.i18nc(definition.key + " label", definition.label) + continue + + profile_value = None + profile_value_source = "" + for quality_container in quality_containers: + new_value = quality_container.getProperty(definition.key, "value") + + if new_value is not None: + profile_value_source = quality_container.getMetaDataEntry("type") + profile_value = new_value + + # Global tab should use resolve (if there is one) + if self._selected_position == "": + resolve_value = global_container_stack.getProperty(definition.key, "resolve") + if resolve_value is not None and definition.key in settings_keys: + profile_value = resolve_value + + if profile_value is not None: + break + + if not self._selected_position: + user_value = global_container_stack.userChanges.getProperty(definition.key, "value") + else: + extruder_stack = global_container_stack.extruders[self._selected_position] + user_value = extruder_stack.userChanges.getProperty(definition.key, "value") + + if profile_value is None and user_value is None: + continue + + label = definition.label + if self._i18n_catalog: + label = self._i18n_catalog.i18nc(definition.key + " label", label) + + items.append({ + "key": definition.key, + "label": label, + "unit": definition.unit, + "profile_value": "" if profile_value is None else str(profile_value), # it is for display only + "profile_value_source": profile_value_source, + "user_value": "" if user_value is None else str(user_value), + "category": current_category + }) + + self.setItems(items) diff --git a/cura/Machines/Models/__init__.py b/cura/Machines/Models/__init__.py new file mode 100644 index 0000000000..e69de29bb2 diff --git a/cura/Machines/QualityChangesGroup.py b/cura/Machines/QualityChangesGroup.py new file mode 100644 index 0000000000..f8de3d2011 --- /dev/null +++ b/cura/Machines/QualityChangesGroup.py @@ -0,0 +1,53 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from UM.Application import Application + +from .QualityGroup import QualityGroup + + +class QualityChangesGroup(QualityGroup): + + def __init__(self, name: str, quality_type: str, parent = None): + super().__init__(name, quality_type, parent) + self._container_registry = Application.getInstance().getContainerRegistry() + + def addNode(self, node: "QualityNode"): + # TODO: in 3.2 and earlier, a quality_changes container may have a field called "extruder" which contains the + # extruder definition ID it belongs to. But, in fact, we only need to know the following things: + # 1. which machine a custom profile is suitable for, + # 2. if this profile is for the GlobalStack, + # 3. if this profile is for an ExtruderStack and which one (the position). + # + # So, it is preferred to have a field like this: + # extruder_position = 1 + # instead of this: + # extruder = custom_extruder_1 + # + # An upgrade needs to be done if we want to do it this way. Before that, we use the extruder's definition + # to figure out its position. + # + extruder_definition_id = node.metadata.get("extruder") + if extruder_definition_id: + metadata_list = self._container_registry.findDefinitionContainersMetadata(id = extruder_definition_id) + if not metadata_list: + raise RuntimeError("%s cannot get metadata for extruder definition [%s]" % + (self, extruder_definition_id)) + extruder_definition_metadata = metadata_list[0] + extruder_position = str(extruder_definition_metadata["position"]) + + if extruder_position in self.nodes_for_extruders: + raise RuntimeError("%s tries to overwrite the existing nodes_for_extruders position [%s] %s with %s" % + (self, extruder_position, self.node_for_global, node)) + + self.nodes_for_extruders[extruder_position] = node + + else: + # This is a quality_changes for the GlobalStack + if self.node_for_global is not None: + raise RuntimeError("%s tries to overwrite the existing node_for_global %s with %s" % + (self, self.node_for_global, node)) + self.node_for_global = node + + def __str__(self) -> str: + return "%s[<%s>, available = %s]" % (self.__class__.__name__, self.name, self.is_available) diff --git a/cura/Machines/QualityGroup.py b/cura/Machines/QualityGroup.py new file mode 100644 index 0000000000..6945162401 --- /dev/null +++ b/cura/Machines/QualityGroup.py @@ -0,0 +1,50 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from typing import Optional, List + +from PyQt5.QtCore import QObject, pyqtSlot + + +# +# A QualityGroup represents a group of containers that must be applied to each ContainerStack when it's used. +# Some concrete examples are Quality and QualityChanges: when we select quality type "normal", this quality type +# must be applied to all stacks in a machine, although each stack can have different containers. Use an Ultimaker 3 +# as an example, suppose we choose quality type "normal", the actual InstanceContainers on each stack may look +# as below: +# GlobalStack ExtruderStack 1 ExtruderStack 2 +# quality container: um3_global_normal um3_aa04_pla_normal um3_aa04_abs_normal +# +# This QualityGroup is mainly used in quality and quality_changes to group the containers that can be applied to +# a machine, so when a quality/custom quality is selected, the container can be directly applied to each stack instead +# of looking them up again. +# +class QualityGroup(QObject): + + def __init__(self, name: str, quality_type: str, parent = None): + super().__init__(parent) + self.name = name + self.node_for_global = None # type: Optional["QualityGroup"] + self.nodes_for_extruders = dict() # position str -> QualityGroup + self.quality_type = quality_type + self.is_available = False + + @pyqtSlot(result = str) + def getName(self) -> str: + return self.name + + def getAllKeys(self) -> set: + result = set() + for node in [self.node_for_global] + list(self.nodes_for_extruders.values()): + if node is None: + continue + result.update(node.getContainer().getAllKeys()) + return result + + def getAllNodes(self) -> List["QualityGroup"]: + result = [] + if self.node_for_global is not None: + result.append(self.node_for_global) + for extruder_node in self.nodes_for_extruders.values(): + result.append(extruder_node) + return result diff --git a/cura/Machines/QualityManager.py b/cura/Machines/QualityManager.py new file mode 100644 index 0000000000..dc9dba8c4b --- /dev/null +++ b/cura/Machines/QualityManager.py @@ -0,0 +1,445 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from typing import TYPE_CHECKING, Optional + +from PyQt5.QtCore import QObject, QTimer, pyqtSignal, pyqtSlot + +from UM.Application import Application +from UM.Logger import Logger +from UM.Util import parseBool +from UM.Settings.InstanceContainer import InstanceContainer + +from .QualityGroup import QualityGroup +from .QualityNode import QualityNode + +if TYPE_CHECKING: + from cura.Settings.GlobalStack import GlobalStack + from .QualityChangesGroup import QualityChangesGroup + + +# +# Similar to MaterialManager, QualityManager maintains a number of maps and trees for quality profile lookup. +# The models GUI and QML use are now only dependent on the QualityManager. That means as long as the data in +# QualityManager gets updated correctly, the GUI models should be updated correctly too, and the same goes for GUI. +# +# For now, updating the lookup maps and trees here is very simple: we discard the old data completely and recreate them +# again. This means the update is exactly the same as initialization. There are performance concerns about this approach +# but so far the creation of the tables and maps is very fast and there is no noticeable slowness, we keep it like this +# because it's simple. +# +class QualityManager(QObject): + + qualitiesUpdated = pyqtSignal() + + def __init__(self, container_registry, parent = None): + super().__init__(parent) + self._application = Application.getInstance() + self._material_manager = self._application.getMaterialManager() + self._container_registry = container_registry + + self._empty_quality_container = self._application.empty_quality_container + self._empty_quality_changes_container = self._application.empty_quality_changes_container + + self._machine_variant_material_quality_type_to_quality_dict = {} # for quality lookup + self._machine_quality_type_to_quality_changes_dict = {} # for quality_changes lookup + + self._default_machine_definition_id = "fdmprinter" + + self._container_registry.containerMetaDataChanged.connect(self._onContainerMetadataChanged) + self._container_registry.containerAdded.connect(self._onContainerMetadataChanged) + self._container_registry.containerRemoved.connect(self._onContainerMetadataChanged) + + # When a custom quality gets added/imported, there can be more than one InstanceContainers. In those cases, + # we don't want to react on every container/metadata changed signal. The timer here is to buffer it a bit so + # we don't react too many time. + self._update_timer = QTimer(self) + self._update_timer.setInterval(300) + self._update_timer.setSingleShot(True) + self._update_timer.timeout.connect(self._updateMaps) + + def initialize(self): + # Initialize the lookup tree for quality profiles with following structure: + # -> -> + # -> + + self._machine_variant_material_quality_type_to_quality_dict = {} # for quality lookup + self._machine_quality_type_to_quality_changes_dict = {} # for quality_changes lookup + + quality_metadata_list = self._container_registry.findContainersMetadata(type = "quality") + for metadata in quality_metadata_list: + if metadata["id"] == "empty_quality": + continue + + definition_id = metadata["definition"] + quality_type = metadata["quality_type"] + + root_material_id = metadata.get("material") + variant_name = metadata.get("variant") + is_global_quality = metadata.get("global_quality", False) + is_global_quality = is_global_quality or (root_material_id is None and variant_name is None) + + # Sanity check: material+variant and is_global_quality cannot be present at the same time + if is_global_quality and (root_material_id or variant_name): + raise RuntimeError("Quality profile [%s] contains invalid data: it is a global quality but contains 'material' and 'nozzle' info." % metadata["id"]) + + if definition_id not in self._machine_variant_material_quality_type_to_quality_dict: + self._machine_variant_material_quality_type_to_quality_dict[definition_id] = QualityNode() + machine_node = self._machine_variant_material_quality_type_to_quality_dict[definition_id] + + if is_global_quality: + # For global qualities, save data in the machine node + machine_node.addQualityMetadata(quality_type, metadata) + continue + + if variant_name is not None: + # If variant_name is specified in the quality/quality_changes profile, check if material is specified, + # too. + if variant_name not in machine_node.children_map: + machine_node.children_map[variant_name] = QualityNode() + variant_node = machine_node.children_map[variant_name] + + if root_material_id is None: + # If only variant_name is specified but material is not, add the quality/quality_changes metadata + # into the current variant node. + variant_node.addQualityMetadata(quality_type, metadata) + else: + # If only variant_name and material are both specified, go one level deeper: create a material node + # under the current variant node, and then add the quality/quality_changes metadata into the + # material node. + if root_material_id not in variant_node.children_map: + variant_node.children_map[root_material_id] = QualityNode() + material_node = variant_node.children_map[root_material_id] + + material_node.addQualityMetadata(quality_type, metadata) + + else: + # If variant_name is not specified, check if material is specified. + if root_material_id is not None: + if root_material_id not in machine_node.children_map: + machine_node.children_map[root_material_id] = QualityNode() + material_node = machine_node.children_map[root_material_id] + + material_node.addQualityMetadata(quality_type, metadata) + + # Initialize the lookup tree for quality_changes profiles with following structure: + # -> -> + quality_changes_metadata_list = self._container_registry.findContainersMetadata(type = "quality_changes") + for metadata in quality_changes_metadata_list: + if metadata["id"] == "empty_quality_changes": + continue + + machine_definition_id = metadata["definition"] + quality_type = metadata["quality_type"] + + if machine_definition_id not in self._machine_quality_type_to_quality_changes_dict: + self._machine_quality_type_to_quality_changes_dict[machine_definition_id] = QualityNode() + machine_node = self._machine_quality_type_to_quality_changes_dict[machine_definition_id] + machine_node.addQualityChangesMetadata(quality_type, metadata) + + Logger.log("d", "Lookup tables updated.") + self.qualitiesUpdated.emit() + + def _updateMaps(self): + self.initialize() + + def _onContainerMetadataChanged(self, container): + self._onContainerChanged(container) + + def _onContainerChanged(self, container): + container_type = container.getMetaDataEntry("type") + if container_type not in ("quality", "quality_changes"): + return + + # update the cache table + self._update_timer.start() + + # Updates the given quality groups' availabilities according to which extruders are being used/ enabled. + def _updateQualityGroupsAvailability(self, machine: "GlobalStack", quality_group_list): + used_extruders = set() + # TODO: This will change after the Machine refactoring + for i in range(machine.getProperty("machine_extruder_count", "value")): + used_extruders.add(str(i)) + + # Update the "is_available" flag for each quality group. + for quality_group in quality_group_list: + is_available = True + if quality_group.node_for_global is None: + is_available = False + if is_available: + for position in used_extruders: + if position not in quality_group.nodes_for_extruders: + is_available = False + break + + quality_group.is_available = is_available + + # Returns a dict of "custom profile name" -> QualityChangesGroup + def getQualityChangesGroups(self, machine: "GlobalStack") -> dict: + machine_definition_id = getMachineDefinitionIDForQualitySearch(machine) + + machine_node = self._machine_quality_type_to_quality_changes_dict.get(machine_definition_id) + if not machine_node: + Logger.log("i", "Cannot find node for machine def [%s] in QualityChanges lookup table", machine_definition_id) + return dict() + + # Update availability for each QualityChangesGroup: + # A custom profile is always available as long as the quality_type it's based on is available + quality_group_dict = self.getQualityGroups(machine) + available_quality_type_list = [qt for qt, qg in quality_group_dict.items() if qg.is_available] + + # Iterate over all quality_types in the machine node + quality_changes_group_dict = dict() + for quality_type, quality_changes_node in machine_node.quality_type_map.items(): + for quality_changes_name, quality_changes_group in quality_changes_node.children_map.items(): + quality_changes_group_dict[quality_changes_name] = quality_changes_group + quality_changes_group.is_available = quality_type in available_quality_type_list + + return quality_changes_group_dict + + # + # Gets all quality groups for the given machine. Both available and none available ones will be included. + # It returns a dictionary with "quality_type"s as keys and "QualityGroup"s as values. + # Whether a QualityGroup is available can be unknown via the field QualityGroup.is_available. + # For more details, see QualityGroup. + # + def getQualityGroups(self, machine: "GlobalStack") -> dict: + machine_definition_id = getMachineDefinitionIDForQualitySearch(machine) + + # This determines if we should only get the global qualities for the global stack and skip the global qualities for the extruder stacks + has_variant_materials = parseBool(machine.getMetaDataEntry("has_variant_materials", False)) + + # To find the quality container for the GlobalStack, check in the following fall-back manner: + # (1) the machine-specific node + # (2) the generic node + machine_node = self._machine_variant_material_quality_type_to_quality_dict.get(machine_definition_id) + default_machine_node = self._machine_variant_material_quality_type_to_quality_dict.get(self._default_machine_definition_id) + nodes_to_check = [machine_node, default_machine_node] + + # Iterate over all quality_types in the machine node + quality_group_dict = {} + for node in nodes_to_check: + if node and node.quality_type_map: + # Only include global qualities + if has_variant_materials: + quality_node = list(node.quality_type_map.values())[0] + is_global_quality = parseBool(quality_node.metadata.get("global_quality", False)) + if not is_global_quality: + continue + + for quality_type, quality_node in node.quality_type_map.items(): + quality_group = QualityGroup(quality_node.metadata["name"], quality_type) + quality_group.node_for_global = quality_node + quality_group_dict[quality_type] = quality_group + break + + # Iterate over all extruders to find quality containers for each extruder + for position, extruder in machine.extruders.items(): + variant_name = None + if extruder.variant.getId() != "empty_variant": + variant_name = extruder.variant.getName() + + # This is a list of root material IDs to use for searching for suitable quality profiles. + # The root material IDs in this list are in prioritized order. + root_material_id_list = [] + has_material = False # flag indicating whether this extruder has a material assigned + if extruder.material.getId() != "empty_material": + has_material = True + root_material_id = extruder.material.getMetaDataEntry("base_file") + # Convert possible generic_pla_175 -> generic_pla + root_material_id = self._material_manager.getRootMaterialIDWithoutDiameter(root_material_id) + root_material_id_list.append(root_material_id) + + # Also try to get the fallback material + material_type = extruder.material.getMetaDataEntry("material") + fallback_root_material_id = self._material_manager.getFallbackMaterialIdByMaterialType(material_type) + if fallback_root_material_id: + root_material_id_list.append(fallback_root_material_id) + + # Here we construct a list of nodes we want to look for qualities with the highest priority first. + # The use case is that, when we look for qualities for a machine, we first want to search in the following + # order: + # 1. machine-variant-and-material-specific qualities if exist + # 2. machine-variant-specific qualities if exist + # 3. machine-material-specific qualities if exist + # 4. machine-specific qualities if exist + # 5. generic qualities if exist + # Each points above can be represented as a node in the lookup tree, so here we simply put those nodes into + # the list with priorities as the order. Later, we just need to loop over each node in this list and fetch + # qualities from there. + nodes_to_check = [] + + if variant_name: + # In this case, we have both a specific variant and a specific material + variant_node = machine_node.getChildNode(variant_name) + if variant_node and has_material: + for root_material_id in root_material_id_list: + material_node = variant_node.getChildNode(root_material_id) + if material_node: + nodes_to_check.append(material_node) + break + nodes_to_check.append(variant_node) + + # In this case, we only have a specific material but NOT a variant + if has_material: + for root_material_id in root_material_id_list: + material_node = machine_node.getChildNode(root_material_id) + if material_node: + nodes_to_check.append(material_node) + break + + nodes_to_check += [machine_node, default_machine_node] + for node in nodes_to_check: + if node and node.quality_type_map: + if has_variant_materials: + # Only include variant qualities; skip non global qualities + quality_node = list(node.quality_type_map.values())[0] + is_global_quality = parseBool(quality_node.metadata.get("global_quality", False)) + if is_global_quality: + continue + + for quality_type, quality_node in node.quality_type_map.items(): + if quality_type not in quality_group_dict: + quality_group = QualityGroup(quality_node.metadata["name"], quality_type) + quality_group_dict[quality_type] = quality_group + + quality_group = quality_group_dict[quality_type] + quality_group.nodes_for_extruders[position] = quality_node + break + + # Update availabilities for each quality group + self._updateQualityGroupsAvailability(machine, quality_group_dict.values()) + + return quality_group_dict + + def getQualityGroupsForMachineDefinition(self, machine: "GlobalStack") -> dict: + machine_definition_id = getMachineDefinitionIDForQualitySearch(machine) + + # To find the quality container for the GlobalStack, check in the following fall-back manner: + # (1) the machine-specific node + # (2) the generic node + machine_node = self._machine_variant_material_quality_type_to_quality_dict.get(machine_definition_id) + default_machine_node = self._machine_variant_material_quality_type_to_quality_dict.get( + self._default_machine_definition_id) + nodes_to_check = [machine_node, default_machine_node] + + # Iterate over all quality_types in the machine node + quality_group_dict = dict() + for node in nodes_to_check: + if node and node.quality_type_map: + for quality_type, quality_node in node.quality_type_map.items(): + quality_group = QualityGroup(quality_node.metadata["name"], quality_type) + quality_group.node_for_global = quality_node + quality_group_dict[quality_type] = quality_group + break + + return quality_group_dict + + # + # Methods for GUI + # + + # + # Remove the given quality changes group. + # + @pyqtSlot(QObject) + def removeQualityChangesGroup(self, quality_changes_group: "QualityChangesGroup"): + Logger.log("i", "Removing quality changes group [%s]", quality_changes_group.name) + for node in quality_changes_group.getAllNodes(): + self._container_registry.removeContainer(node.metadata["id"]) + + # + # Rename a set of quality changes containers. Returns the new name. + # + @pyqtSlot(QObject, str, result = str) + def renameQualityChangesGroup(self, quality_changes_group: "QualityChangesGroup", new_name: str) -> str: + Logger.log("i", "Renaming QualityChangesGroup[%s] to [%s]", quality_changes_group.name, new_name) + if new_name == quality_changes_group.name: + Logger.log("i", "QualityChangesGroup name [%s] unchanged.", quality_changes_group.name) + return new_name + + new_name = self._container_registry.uniqueName(new_name) + for node in quality_changes_group.getAllNodes(): + node.getContainer().setName(new_name) + + quality_changes_group.name = new_name + + self._application.getMachineManager().activeQualityChanged.emit() + self._application.getMachineManager().activeQualityGroupChanged.emit() + + return new_name + + # + # Duplicates the given quality. + # + @pyqtSlot(str, "QVariantMap") + def duplicateQualityChanges(self, quality_changes_name, quality_model_item): + global_stack = self._application.getGlobalContainerStack() + if not global_stack: + Logger.log("i", "No active global stack, cannot duplicate quality changes.") + return + + quality_group = quality_model_item["quality_group"] + quality_changes_group = quality_model_item["quality_changes_group"] + if quality_changes_group is None: + # create global quality changes only + new_quality_changes = self._createQualityChanges(quality_group.quality_type, quality_changes_name, + global_stack, extruder_id = None) + self._container_registry.addContainer(new_quality_changes) + else: + new_name = self._container_registry.uniqueName(quality_changes_name) + for node in quality_changes_group.getAllNodes(): + container = node.getContainer() + new_id = self._container_registry.uniqueName(container.getId()) + self._container_registry.addContainer(container.duplicate(new_id, new_name)) + + # + # Create a quality changes container with the given setup. + # + def _createQualityChanges(self, quality_type: str, new_name: str, machine: "GlobalStack", + extruder_id: Optional[str]) -> "InstanceContainer": + base_id = machine.definition.getId() if extruder_id is None else extruder_id + new_id = base_id + "_" + new_name + new_id = new_id.lower().replace(" ", "_") + new_id = self._container_registry.uniqueName(new_id) + + # Create a new quality_changes container for the quality. + quality_changes = InstanceContainer(new_id) + quality_changes.setName(new_name) + quality_changes.addMetaDataEntry("type", "quality_changes") + quality_changes.addMetaDataEntry("quality_type", quality_type) + + # If we are creating a container for an extruder, ensure we add that to the container + if extruder_id is not None: + quality_changes.addMetaDataEntry("extruder", extruder_id) + + # If the machine specifies qualities should be filtered, ensure we match the current criteria. + machine_definition_id = getMachineDefinitionIDForQualitySearch(machine) + quality_changes.setDefinition(machine_definition_id) + + quality_changes.addMetaDataEntry("setting_version", self._application.SettingVersion) + return quality_changes + + +# +# Gets the machine definition ID that can be used to search for Quality containers that are suitable for the given +# machine. The rule is as follows: +# 1. By default, the machine definition ID for quality container search will be "fdmprinter", which is the generic +# machine. +# 2. If a machine has its own machine quality (with "has_machine_quality = True"), we should use the given machine's +# own machine definition ID for quality search. +# Example: for an Ultimaker 3, the definition ID should be "ultimaker3". +# 3. When condition (2) is met, AND the machine has "quality_definition" defined in its definition file, then the +# definition ID specified in "quality_definition" should be used. +# Example: for an Ultimaker 3 Extended, it has "quality_definition = ultimaker3". This means Ultimaker 3 Extended +# shares the same set of qualities profiles as Ultimaker 3. +# +def getMachineDefinitionIDForQualitySearch(machine: "GlobalStack", default_definition_id: str = "fdmprinter") -> str: + machine_definition_id = default_definition_id + if parseBool(machine.getMetaDataEntry("has_machine_quality", False)): + # Only use the machine's own quality definition ID if this machine has machine quality. + machine_definition_id = machine.getMetaDataEntry("quality_definition") + if machine_definition_id is None: + machine_definition_id = machine.definition.getId() + + return machine_definition_id diff --git a/cura/Machines/QualityNode.py b/cura/Machines/QualityNode.py new file mode 100644 index 0000000000..a30e219da3 --- /dev/null +++ b/cura/Machines/QualityNode.py @@ -0,0 +1,35 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from typing import Optional + +from .ContainerNode import ContainerNode +from .QualityChangesGroup import QualityChangesGroup + + +# +# QualityNode is used for BOTH quality and quality_changes containers. +# +class QualityNode(ContainerNode): + + def __init__(self, metadata: Optional[dict] = None): + super().__init__(metadata = metadata) + self.quality_type_map = {} # quality_type -> QualityNode for InstanceContainer + + def addQualityMetadata(self, quality_type: str, metadata: dict): + if quality_type not in self.quality_type_map: + self.quality_type_map[quality_type] = QualityNode(metadata) + + def getQualityNode(self, quality_type: str) -> Optional["QualityNode"]: + return self.quality_type_map.get(quality_type) + + def addQualityChangesMetadata(self, quality_type: str, metadata: dict): + if quality_type not in self.quality_type_map: + self.quality_type_map[quality_type] = QualityNode() + quality_type_node = self.quality_type_map[quality_type] + + name = metadata["name"] + if name not in quality_type_node.children_map: + quality_type_node.children_map[name] = QualityChangesGroup(name, quality_type) + quality_changes_group = quality_type_node.children_map[name] + quality_changes_group.addNode(QualityNode(metadata)) diff --git a/cura/Machines/VariantManager.py b/cura/Machines/VariantManager.py new file mode 100644 index 0000000000..6cb0a3d7b2 --- /dev/null +++ b/cura/Machines/VariantManager.py @@ -0,0 +1,111 @@ +# Copyright (c) 2018 Ultimaker B.V. +# Cura is released under the terms of the LGPLv3 or higher. + +from enum import Enum +from collections import OrderedDict +from typing import Optional, TYPE_CHECKING + +from UM.Logger import Logger +from UM.Settings.ContainerRegistry import ContainerRegistry +from UM.Util import parseBool + +from cura.Machines.ContainerNode import ContainerNode +from cura.Settings.GlobalStack import GlobalStack + +if TYPE_CHECKING: + from UM.Settings.DefinitionContainer import DefinitionContainer + + +class VariantType(Enum): + BUILD_PLATE = "buildplate" + NOZZLE = "nozzle" + + +ALL_VARIANT_TYPES = (VariantType.BUILD_PLATE, VariantType.NOZZLE) + + +# +# VariantManager is THE place to look for a specific variant. It maintains a variant lookup table with the following +# structure: +# +# [machine_definition_id] -> [variant_type] -> [variant_name] -> ContainerNode(metadata / container) +# Example: "ultimaker3" -> "buildplate" -> "Glass" (if present) -> ContainerNode +# -> ... +# -> "nozzle" -> "AA 0.4" +# -> "BB 0.8" +# -> ... +# +# Note that the "container" field is not loaded in the beginning because it would defeat the purpose of lazy-loading. +# A container is loaded when getVariant() is called to load a variant InstanceContainer. +# +class VariantManager: + + def __init__(self, container_registry): + self._container_registry = container_registry # type: ContainerRegistry + + self._machine_to_variant_dict_map = dict() # -> + + self._exclude_variant_id_list = ["empty_variant"] + + # + # Initializes the VariantManager including: + # - initializing the variant lookup table based on the metadata in ContainerRegistry. + # + def initialize(self): + self._machine_to_variant_dict_map = OrderedDict() + + # Cache all variants from the container registry to a variant map for better searching and organization. + variant_metadata_list = self._container_registry.findContainersMetadata(type = "variant") + for variant_metadata in variant_metadata_list: + if variant_metadata["id"] in self._exclude_variant_id_list: + Logger.log("d", "Exclude variant [%s]", variant_metadata["id"]) + continue + + variant_name = variant_metadata["name"] + variant_definition = variant_metadata["definition"] + if variant_definition not in self._machine_to_variant_dict_map: + self._machine_to_variant_dict_map[variant_definition] = OrderedDict() + for variant_type in ALL_VARIANT_TYPES: + self._machine_to_variant_dict_map[variant_definition][variant_type] = dict() + + variant_type = variant_metadata["hardware_type"] + variant_type = VariantType(variant_type) + variant_dict = self._machine_to_variant_dict_map[variant_definition][variant_type] + if variant_name in variant_dict: + # ERROR: duplicated variant name. + raise RuntimeError("Found duplicated variant name [%s], type [%s] for machine [%s]" % + (variant_name, variant_type, variant_definition)) + + variant_dict[variant_name] = ContainerNode(metadata = variant_metadata) + + # + # Gets the variant InstanceContainer with the given information. + # Almost the same as getVariantMetadata() except that this returns an InstanceContainer if present. + # + def getVariantNode(self, machine_definition_id: str, variant_name: str, + variant_type: Optional["VariantType"] = VariantType.NOZZLE) -> Optional["ContainerNode"]: + return self._machine_to_variant_dict_map[machine_definition_id].get(variant_type, {}).get(variant_name) + + def getVariantNodes(self, machine: "GlobalStack", + variant_type: Optional["VariantType"] = VariantType.NOZZLE) -> dict: + machine_definition_id = machine.definition.getId() + return self._machine_to_variant_dict_map.get(machine_definition_id, {}).get(variant_type, {}) + + # + # Gets the default variant for the given machine definition. + # + def getDefaultVariantNode(self, machine_definition: "DefinitionContainer", + variant_type: VariantType) -> Optional["ContainerNode"]: + machine_definition_id = machine_definition.getId() + preferred_variant_name = None + if variant_type == VariantType.BUILD_PLATE: + if parseBool(machine_definition.getMetaDataEntry("has_variant_buildplates", False)): + preferred_variant_name = machine_definition.getMetaDataEntry("preferred_variant_buildplate_name") + else: + if parseBool(machine_definition.getMetaDataEntry("has_variants", False)): + preferred_variant_name = machine_definition.getMetaDataEntry("preferred_variant_name") + + node = None + if preferred_variant_name: + node = self.getVariantNode(machine_definition_id, preferred_variant_name, variant_type) + return node diff --git a/cura/Machines/__init__.py b/cura/Machines/__init__.py new file mode 100644 index 0000000000..e69de29bb2 diff --git a/cura/PrintInformation.py b/cura/PrintInformation.py index e71052023c..05b740637d 100644 --- a/cura/PrintInformation.py +++ b/cura/PrintInformation.py @@ -1,27 +1,22 @@ # Copyright (c) 2018 Ultimaker B.V. # Cura is released under the terms of the LGPLv3 or higher. -from PyQt5.QtCore import QObject, pyqtSignal, pyqtProperty -from UM.FlameProfiler import pyqtSlot +from typing import Dict +import math +import os.path +import unicodedata +import json +import re # To create abbreviations for printer names. + +from PyQt5.QtCore import QObject, pyqtSignal, pyqtProperty, pyqtSlot from UM.Application import Application from UM.Logger import Logger from UM.Qt.Duration import Duration from UM.Preferences import Preferences from UM.Scene.SceneNode import SceneNode -from UM.Settings.ContainerRegistry import ContainerRegistry -from cura.Scene.CuraSceneNode import CuraSceneNode - -from cura.Settings.ExtruderManager import ExtruderManager -from typing import Dict - -import math -import os.path -import unicodedata -import json -import re #To create abbreviations for printer names. - from UM.i18n import i18nCatalog + catalog = i18nCatalog("cura") ## A class for processing and calculating minimum, current and maximum print time as well as managing the job name @@ -76,16 +71,19 @@ class PrintInformation(QObject): self._active_build_plate = 0 self._initVariablesWithBuildPlate(self._active_build_plate) - Application.getInstance().globalContainerStackChanged.connect(self._updateJobName) - Application.getInstance().fileLoaded.connect(self.setBaseName) - Application.getInstance().getBuildPlateModel().activeBuildPlateChanged.connect(self._onActiveBuildPlateChanged) - Application.getInstance().workspaceLoaded.connect(self.setProjectName) + self._application = Application.getInstance() + self._multi_build_plate_model = self._application.getMultiBuildPlateModel() + + self._application.globalContainerStackChanged.connect(self._updateJobName) + self._application.globalContainerStackChanged.connect(self.setToZeroPrintInformation) + self._application.fileLoaded.connect(self.setBaseName) + self._application.workspaceLoaded.connect(self.setProjectName) + self._multi_build_plate_model.activeBuildPlateChanged.connect(self._onActiveBuildPlateChanged) Preferences.getInstance().preferenceChanged.connect(self._onPreferencesChanged) - self._active_material_container = None - Application.getInstance().getMachineManager().activeMaterialChanged.connect(self._onActiveMaterialChanged) - self._onActiveMaterialChanged() + self._application.getMachineManager().rootMaterialChanged.connect(self._onActiveMaterialsChanged) + self._onActiveMaterialsChanged() self._material_amounts = [] @@ -200,7 +198,8 @@ class PrintInformation(QObject): self._current_print_time[build_plate_number].setDuration(total_estimated_time) def _calculateInformation(self, build_plate_number): - if Application.getInstance().getGlobalContainerStack() is None: + global_stack = Application.getInstance().getGlobalContainerStack() + if global_stack is None: return self._material_lengths[build_plate_number] = [] @@ -210,19 +209,17 @@ class PrintInformation(QObject): material_preference_values = json.loads(Preferences.getInstance().getValue("cura/material_settings")) - extruder_stacks = list(ExtruderManager.getInstance().getMachineExtruders(Application.getInstance().getGlobalContainerStack().getId())) - for index, amount in enumerate(self._material_amounts): + extruder_stacks = global_stack.extruders + for position, extruder_stack in extruder_stacks.items(): + index = int(position) + if index >= len(self._material_amounts): + continue + amount = self._material_amounts[index] ## Find the right extruder stack. As the list isn't sorted because it's a annoying generator, we do some # list comprehension filtering to solve this for us. - if extruder_stacks: # Multi extrusion machine - extruder_stack = [extruder for extruder in extruder_stacks if extruder.getMetaDataEntry("position") == str(index)][0] - density = extruder_stack.getMetaDataEntry("properties", {}).get("density", 0) - material = extruder_stack.findContainer({"type": "material"}) - radius = extruder_stack.getProperty("material_diameter", "value") / 2 - else: # Machine with no extruder stacks - density = Application.getInstance().getGlobalContainerStack().getMetaDataEntry("properties", {}).get("density", 0) - material = Application.getInstance().getGlobalContainerStack().findContainer({"type": "material"}) - radius = Application.getInstance().getGlobalContainerStack().getProperty("material_diameter", "value") / 2 + density = extruder_stack.getMetaDataEntry("properties", {}).get("density", 0) + material = extruder_stack.findContainer({"type": "material"}) + radius = extruder_stack.getProperty("material_diameter", "value") / 2 weight = float(amount) * float(density) / 1000 cost = 0 @@ -260,25 +257,11 @@ class PrintInformation(QObject): if preference != "cura/material_settings": return - for build_plate_number in range(Application.getInstance().getBuildPlateModel().maxBuildPlate + 1): + for build_plate_number in range(self._multi_build_plate_model.maxBuildPlate + 1): self._calculateInformation(build_plate_number) - def _onActiveMaterialChanged(self): - if self._active_material_container: - try: - self._active_material_container.metaDataChanged.disconnect(self._onMaterialMetaDataChanged) - except TypeError: #pyQtSignal gives a TypeError when disconnecting from something that is already disconnected. - pass - - active_material_id = Application.getInstance().getMachineManager().activeMaterialId - active_material_containers = ContainerRegistry.getInstance().findInstanceContainers(id = active_material_id) - - if active_material_containers: - self._active_material_container = active_material_containers[0] - self._active_material_container.metaDataChanged.connect(self._onMaterialMetaDataChanged) - def _onActiveBuildPlateChanged(self): - new_active_build_plate = Application.getInstance().getBuildPlateModel().activeBuildPlate + new_active_build_plate = self._multi_build_plate_model.activeBuildPlate if new_active_build_plate != self._active_build_plate: self._active_build_plate = new_active_build_plate @@ -290,8 +273,8 @@ class PrintInformation(QObject): self.materialNamesChanged.emit() self.currentPrintTimeChanged.emit() - def _onMaterialMetaDataChanged(self, *args, **kwargs): - for build_plate_number in range(Application.getInstance().getBuildPlateModel().maxBuildPlate + 1): + def _onActiveMaterialsChanged(self, *args, **kwargs): + for build_plate_number in range(self._multi_build_plate_model.maxBuildPlate + 1): self._calculateInformation(build_plate_number) @pyqtSlot(str) @@ -396,7 +379,9 @@ class PrintInformation(QObject): return result # Simulate message with zero time duration - def setToZeroPrintInformation(self, build_plate): + def setToZeroPrintInformation(self, build_plate = None): + if build_plate is None: + build_plate = self._active_build_plate # Construct the 0-time message temp_message = {} diff --git a/cura/QualityManager.py b/cura/QualityManager.py deleted file mode 100644 index 76a0c86a5f..0000000000 --- a/cura/QualityManager.py +++ /dev/null @@ -1,332 +0,0 @@ -# Copyright (c) 2017 Ultimaker B.V. -# Cura is released under the terms of the LGPLv3 or higher. - -# This collects a lot of quality and quality changes related code which was split between ContainerManager -# and the MachineManager and really needs to usable from both. -from typing import Any, Dict, List, Optional, TYPE_CHECKING - -from UM.Application import Application -from UM.Settings.ContainerRegistry import ContainerRegistry -from UM.Settings.InstanceContainer import InstanceContainer -from cura.Settings.ExtruderManager import ExtruderManager - -if TYPE_CHECKING: - from cura.Settings.GlobalStack import GlobalStack - from cura.Settings.ExtruderStack import ExtruderStack - from UM.Settings.DefinitionContainer import DefinitionContainerInterface - -class QualityManager: - - ## Get the singleton instance for this class. - @classmethod - def getInstance(cls) -> "QualityManager": - # Note: Explicit use of class name to prevent issues with inheritance. - if not QualityManager.__instance: - QualityManager.__instance = cls() - return QualityManager.__instance - - __instance = None # type: "QualityManager" - - ## Find a quality by name for a specific machine definition and materials. - # - # \param quality_name - # \param machine_definition (Optional) \type{DefinitionContainerInterface} If nothing is - # specified then the currently selected machine definition is used. - # \param material_containers_metadata If nothing is specified then the - # current set of selected materials is used. - # \return the matching quality container \type{InstanceContainer} - def findQualityByName(self, quality_name: str, machine_definition: Optional["DefinitionContainerInterface"] = None, material_containers_metadata: Optional[List[Dict[str, Any]]] = None) -> Optional[InstanceContainer]: - criteria = {"type": "quality", "name": quality_name} - result = self._getFilteredContainersForStack(machine_definition, material_containers_metadata, **criteria) - - # Fall back to using generic materials and qualities if nothing could be found. - if not result and material_containers_metadata and len(material_containers_metadata) == 1: - basic_materials = self._getBasicMaterialMetadatas(material_containers_metadata[0]) - result = self._getFilteredContainersForStack(machine_definition, basic_materials, **criteria) - - return result[0] if result else None - - ## Find a quality changes container by name. - # - # \param quality_changes_name \type{str} the name of the quality changes container. - # \param machine_definition (Optional) \type{DefinitionContainer} If nothing is - # specified then the currently selected machine definition is used.. - # \return the matching quality changes containers \type{List[InstanceContainer]} - def findQualityChangesByName(self, quality_changes_name: str, machine_definition: Optional["DefinitionContainerInterface"] = None): - if not machine_definition: - global_stack = Application.getGlobalContainerStack() - if not global_stack: - return [] #No stack, so no current definition could be found, so there are no quality changes either. - machine_definition = global_stack.definition - - result = self.findAllQualityChangesForMachine(machine_definition) - result = [quality_change for quality_change in result if quality_change.getName() == quality_changes_name] - return result - - ## Fetch the list of available quality types for this combination of machine definition and materials. - # - # \param machine_definition \type{DefinitionContainer} - # \param material_containers \type{List[InstanceContainer]} - # \return \type{List[str]} - def findAllQualityTypesForMachineAndMaterials(self, machine_definition: "DefinitionContainerInterface", material_containers: List[InstanceContainer]) -> List[str]: - # Determine the common set of quality types which can be - # applied to all of the materials for this machine. - quality_type_dict = self.__fetchQualityTypeDictForMaterial(machine_definition, material_containers[0]) - common_quality_types = set(quality_type_dict.keys()) - for material_container in material_containers[1:]: - next_quality_type_dict = self.__fetchQualityTypeDictForMaterial(machine_definition, material_container) - common_quality_types.intersection_update(set(next_quality_type_dict.keys())) - - return list(common_quality_types) - - def findAllQualitiesForMachineAndMaterials(self, machine_definition: "DefinitionContainerInterface", material_containers: List[InstanceContainer]) -> List[InstanceContainer]: - # Determine the common set of quality types which can be - # applied to all of the materials for this machine. - quality_type_dict = self.__fetchQualityTypeDictForMaterial(machine_definition, material_containers[0]) - qualities = set(quality_type_dict.values()) - for material_container in material_containers[1:]: - next_quality_type_dict = self.__fetchQualityTypeDictForMaterial(machine_definition, material_container) - qualities.intersection_update(set(next_quality_type_dict.values())) - - return list(qualities) - - ## Fetches a dict of quality types names to quality profiles for a combination of machine and material. - # - # \param machine_definition \type{DefinitionContainer} the machine definition. - # \param material \type{InstanceContainer} the material. - # \return \type{Dict[str, InstanceContainer]} the dict of suitable quality type names mapping to qualities. - def __fetchQualityTypeDictForMaterial(self, machine_definition: "DefinitionContainerInterface", material: InstanceContainer) -> Dict[str, InstanceContainer]: - qualities = self.findAllQualitiesForMachineMaterial(machine_definition, material) - quality_type_dict = {} - for quality in qualities: - quality_type_dict[quality.getMetaDataEntry("quality_type")] = quality - return quality_type_dict - - ## Find a quality container by quality type. - # - # \param quality_type \type{str} the name of the quality type to search for. - # \param machine_definition (Optional) \type{InstanceContainer} If nothing is - # specified then the currently selected machine definition is used. - # \param material_containers_metadata If nothing is specified then the - # current set of selected materials is used. - # \return the matching quality container \type{InstanceContainer} - def findQualityByQualityType(self, quality_type: str, machine_definition: Optional["DefinitionContainerInterface"] = None, material_containers_metadata: Optional[List[Dict[str, Any]]] = None, **kwargs) -> InstanceContainer: - criteria = kwargs - criteria["type"] = "quality" - if quality_type: - criteria["quality_type"] = quality_type - result = self._getFilteredContainersForStack(machine_definition, material_containers_metadata, **criteria) - # Fall back to using generic materials and qualities if nothing could be found. - if not result and material_containers_metadata and len(material_containers_metadata) == 1: - basic_materials = self._getBasicMaterialMetadatas(material_containers_metadata[0]) - if basic_materials: - result = self._getFilteredContainersForStack(machine_definition, basic_materials, **criteria) - return result[0] if result else None - - ## Find all suitable qualities for a combination of machine and material. - # - # \param machine_definition \type{DefinitionContainer} the machine definition. - # \param material_container \type{InstanceContainer} the material. - # \return \type{List[InstanceContainer]} the list of suitable qualities. - def findAllQualitiesForMachineMaterial(self, machine_definition: "DefinitionContainerInterface", material_container: InstanceContainer) -> List[InstanceContainer]: - criteria = {"type": "quality"} - result = self._getFilteredContainersForStack(machine_definition, [material_container.getMetaData()], **criteria) - if not result: - basic_materials = self._getBasicMaterialMetadatas(material_container.getMetaData()) - if basic_materials: - result = self._getFilteredContainersForStack(machine_definition, basic_materials, **criteria) - - return result - - ## Find all quality changes for a machine. - # - # \param machine_definition \type{DefinitionContainer} the machine definition. - # \return \type{List[InstanceContainer]} the list of quality changes - def findAllQualityChangesForMachine(self, machine_definition: "DefinitionContainerInterface") -> List[InstanceContainer]: - if machine_definition.getMetaDataEntry("has_machine_quality"): - definition_id = machine_definition.getId() - else: - definition_id = "fdmprinter" - - filter_dict = { "type": "quality_changes", "definition": definition_id } - quality_changes_list = ContainerRegistry.getInstance().findInstanceContainers(**filter_dict) - return quality_changes_list - - def findAllExtruderDefinitionsForMachine(self, machine_definition: "DefinitionContainerInterface") -> List["DefinitionContainerInterface"]: - filter_dict = { "machine": machine_definition.getId() } - return ContainerRegistry.getInstance().findDefinitionContainers(**filter_dict) - - ## Find all quality changes for a given extruder. - # - # \param extruder_definition The extruder to find the quality changes for. - # \return The list of quality changes for the given extruder. - def findAllQualityChangesForExtruder(self, extruder_definition: "DefinitionContainerInterface") -> List[InstanceContainer]: - filter_dict = {"type": "quality_changes", "extruder": extruder_definition.getId()} - return ContainerRegistry.getInstance().findInstanceContainers(**filter_dict) - - ## Find all usable qualities for a machine and extruders. - # - # Finds all of the qualities for this combination of machine and extruders. - # Only one quality per quality type is returned. i.e. if there are 2 qualities with quality_type=normal - # then only one of then is returned (at random). - # - # \param global_container_stack \type{GlobalStack} the global machine definition - # \param extruder_stacks \type{List[ExtruderStack]} the list of extruder stacks - # \return \type{List[InstanceContainer]} the list of the matching qualities. The quality profiles - # return come from the first extruder in the given list of extruders. - def findAllUsableQualitiesForMachineAndExtruders(self, global_container_stack: "GlobalStack", extruder_stacks: List["ExtruderStack"]) -> List[InstanceContainer]: - global_machine_definition = global_container_stack.getBottom() - - machine_manager = Application.getInstance().getMachineManager() - active_stack_id = machine_manager.activeStackId - - materials = [] - - for stack in extruder_stacks: - if stack.getId() == active_stack_id and machine_manager.newMaterial: - materials.append(machine_manager.newMaterial) - else: - materials.append(stack.material) - - quality_types = self.findAllQualityTypesForMachineAndMaterials(global_machine_definition, materials) - - # Map the list of quality_types to InstanceContainers - qualities = self.findAllQualitiesForMachineMaterial(global_machine_definition, materials[0]) - quality_type_dict = {} - for quality in qualities: - quality_type_dict[quality.getMetaDataEntry("quality_type")] = quality - - return [quality_type_dict[quality_type] for quality_type in quality_types] - - ## Fetch more basic versions of a material. - # - # This tries to find a generic or basic version of the given material. - # \param material_container \type{Dict[str, Any]} The metadata of a - # material to find the basic versions of. - # \return \type{List[Dict[str, Any]]} A list of the metadata of basic - # materials, or an empty list if none could be found. - def _getBasicMaterialMetadatas(self, material_container: Dict[str, Any]) -> List[Dict[str, Any]]: - if "definition" not in material_container: - definition_id = "fdmprinter" - else: - material_container_definition = ContainerRegistry.getInstance().findDefinitionContainersMetadata(id = material_container["definition"]) - if not material_container_definition: - definition_id = "fdmprinter" - else: - material_container_definition = material_container_definition[0] - if "has_machine_quality" not in material_container_definition: - definition_id = "fdmprinter" - else: - definition_id = material_container_definition.get("quality_definition", material_container_definition["id"]) - - base_material = material_container.get("material") - if base_material: - # There is a basic material specified - criteria = { - "type": "material", - "name": base_material, - "definition": definition_id, - "variant": material_container.get("variant") - } - containers = ContainerRegistry.getInstance().findInstanceContainersMetadata(**criteria) - return containers - - return [] - - def _getFilteredContainers(self, **kwargs): - return self._getFilteredContainersForStack(None, None, **kwargs) - - def _getFilteredContainersForStack(self, machine_definition: "DefinitionContainerInterface" = None, material_metadata: Optional[List[Dict[str, Any]]] = None, **kwargs): - # Fill in any default values. - if machine_definition is None: - machine_definition = Application.getInstance().getGlobalContainerStack().getBottom() - quality_definition_id = machine_definition.getMetaDataEntry("quality_definition") - if quality_definition_id is not None: - machine_definition = ContainerRegistry.getInstance().findDefinitionContainers(id = quality_definition_id)[0] - - if not material_metadata: - active_stacks = ExtruderManager.getInstance().getActiveGlobalAndExtruderStacks() - if active_stacks: - material_metadata = [stack.material.getMetaData() for stack in active_stacks] - - criteria = kwargs - filter_by_material = False - - machine_definition = self.getParentMachineDefinition(machine_definition) - criteria["definition"] = machine_definition.getId() - found_containers_with_machine_definition = ContainerRegistry.getInstance().findInstanceContainersMetadata(**criteria) - whole_machine_definition = self.getWholeMachineDefinition(machine_definition) - if whole_machine_definition.getMetaDataEntry("has_machine_quality"): - definition_id = machine_definition.getMetaDataEntry("quality_definition", whole_machine_definition.getId()) - criteria["definition"] = definition_id - - filter_by_material = whole_machine_definition.getMetaDataEntry("has_materials") - # only fall back to "fdmprinter" when there is no container for this machine - elif not found_containers_with_machine_definition: - criteria["definition"] = "fdmprinter" - - # Stick the material IDs in a set - material_ids = set() - - for material_instance in material_metadata: - if material_instance is not None: - # Add the parent material too. - for basic_material in self._getBasicMaterialMetadatas(material_instance): - material_ids.add(basic_material["id"]) - material_ids.add(material_instance["id"]) - containers = ContainerRegistry.getInstance().findInstanceContainers(**criteria) - - result = [] - for container in containers: - # If the machine specifies we should filter by material, exclude containers that do not match any active material. - if filter_by_material and container.getMetaDataEntry("material") not in material_ids and "global_quality" not in kwargs: - continue - result.append(container) - - return result - - ## Get the parent machine definition of a machine definition. - # - # \param machine_definition \type{DefinitionContainer} This may be a normal machine definition or - # an extruder definition. - # \return \type{DefinitionContainer} the parent machine definition. If the given machine - # definition doesn't have a parent then it is simply returned. - def getParentMachineDefinition(self, machine_definition: "DefinitionContainerInterface") -> "DefinitionContainerInterface": - container_registry = ContainerRegistry.getInstance() - - machine_entry = machine_definition.getMetaDataEntry("machine") - if machine_entry is None: - # We have a normal (whole) machine defintion - quality_definition = machine_definition.getMetaDataEntry("quality_definition") - if quality_definition is not None: - parent_machine_definition = container_registry.findDefinitionContainers(id = quality_definition)[0] - return self.getParentMachineDefinition(parent_machine_definition) - else: - return machine_definition - else: - # This looks like an extruder. Find the rest of the machine. - whole_machine = container_registry.findDefinitionContainers(id = machine_entry)[0] - parent_machine = self.getParentMachineDefinition(whole_machine) - if whole_machine is parent_machine: - # This extruder already belongs to a 'parent' machine def. - return machine_definition - else: - # Look up the corresponding extruder definition in the parent machine definition. - extruder_position = machine_definition.getMetaDataEntry("position") - parent_extruder_id = parent_machine.getMetaDataEntry("machine_extruder_trains")[extruder_position] - return container_registry.findDefinitionContainers(id = parent_extruder_id)[0] - - ## Get the whole/global machine definition from an extruder definition. - # - # \param machine_definition \type{DefinitionContainer} This may be a normal machine definition or - # an extruder definition. - # \return \type{DefinitionContainerInterface} - def getWholeMachineDefinition(self, machine_definition: "DefinitionContainerInterface") -> "DefinitionContainerInterface": - machine_entry = machine_definition.getMetaDataEntry("machine") - if machine_entry is None: - # This already is a 'global' machine definition. - return machine_definition - else: - container_registry = ContainerRegistry.getInstance() - whole_machine = container_registry.findDefinitionContainers(id = machine_entry)[0] - return whole_machine diff --git a/cura/Scene/ConvexHullNode.py b/cura/Scene/ConvexHullNode.py index 6c8c201498..1131958627 100644 --- a/cura/Scene/ConvexHullNode.py +++ b/cura/Scene/ConvexHullNode.py @@ -68,7 +68,7 @@ class ConvexHullNode(SceneNode): ConvexHullNode.shader.setUniformValue("u_opacity", 0.6) if self.getParent(): - if self.getMeshData() and isinstance(self._node, SceneNode) and self._node.callDecoration("getBuildPlateNumber") == Application.getInstance().getBuildPlateModel().activeBuildPlate: + if self.getMeshData() and isinstance(self._node, SceneNode) and self._node.callDecoration("getBuildPlateNumber") == Application.getInstance().getMultiBuildPlateModel().activeBuildPlate: renderer.queueNode(self, transparent = True, shader = ConvexHullNode.shader, backface_cull = True, sort = -8) if self._convex_hull_head_mesh: renderer.queueNode(self, shader = ConvexHullNode.shader, transparent = True, mesh = self._convex_hull_head_mesh, backface_cull = True, sort = -8) diff --git a/cura/Scene/CuraSceneController.py b/cura/Scene/CuraSceneController.py index 1c008d1893..749c5257a2 100644 --- a/cura/Scene/CuraSceneController.py +++ b/cura/Scene/CuraSceneController.py @@ -4,7 +4,7 @@ from PyQt5.QtCore import Qt, pyqtSlot, QObject from PyQt5.QtWidgets import QApplication from cura.ObjectsModel import ObjectsModel -from cura.BuildPlateModel import BuildPlateModel +from cura.Machines.Models.MultiBuildPlateModel import MultiBuildPlateModel from UM.Application import Application from UM.Scene.Iterator.DepthFirstIterator import DepthFirstIterator @@ -16,11 +16,11 @@ from UM.Signal import Signal class CuraSceneController(QObject): activeBuildPlateChanged = Signal() - def __init__(self, objects_model: ObjectsModel, build_plate_model: BuildPlateModel): + def __init__(self, objects_model: ObjectsModel, multi_build_plate_model: MultiBuildPlateModel): super().__init__() self._objects_model = objects_model - self._build_plate_model = build_plate_model + self._multi_build_plate_model = multi_build_plate_model self._active_build_plate = -1 self._last_selected_index = 0 @@ -41,9 +41,9 @@ class CuraSceneController(QObject): self._max_build_plate = max_build_plate changed = True if changed: - self._build_plate_model.setMaxBuildPlate(self._max_build_plate) + self._multi_build_plate_model.setMaxBuildPlate(self._max_build_plate) build_plates = [{"name": "Build Plate %d" % (i + 1), "buildPlateNumber": i} for i in range(self._max_build_plate + 1)] - self._build_plate_model.setItems(build_plates) + self._multi_build_plate_model.setItems(build_plates) if self._active_build_plate > self._max_build_plate: build_plate_number = 0 if self._last_selected_index >= 0: # go to the buildplate of the item you last selected @@ -104,12 +104,12 @@ class CuraSceneController(QObject): self._active_build_plate = nr Selection.clear() - self._build_plate_model.setActiveBuildPlate(nr) + self._multi_build_plate_model.setActiveBuildPlate(nr) self._objects_model.setActiveBuildPlate(nr) self.activeBuildPlateChanged.emit() @staticmethod def createCuraSceneController(): objects_model = Application.getInstance().getObjectsModel() - build_plate_model = Application.getInstance().getBuildPlateModel() - return CuraSceneController(objects_model = objects_model, build_plate_model = build_plate_model) + multi_build_plate_model = Application.getInstance().getMultiBuildPlateModel() + return CuraSceneController(objects_model = objects_model, multi_build_plate_model = multi_build_plate_model) diff --git a/cura/Scene/CuraSceneNode.py b/cura/Scene/CuraSceneNode.py index 969d491f49..df346baaad 100644 --- a/cura/Scene/CuraSceneNode.py +++ b/cura/Scene/CuraSceneNode.py @@ -20,10 +20,10 @@ class CuraSceneNode(SceneNode): return self._outside_buildarea or self.callDecoration("getBuildPlateNumber") < 0 def isVisible(self): - return super().isVisible() and self.callDecoration("getBuildPlateNumber") == Application.getInstance().getBuildPlateModel().activeBuildPlate + return super().isVisible() and self.callDecoration("getBuildPlateNumber") == Application.getInstance().getMultiBuildPlateModel().activeBuildPlate def isSelectable(self) -> bool: - return super().isSelectable() and self.callDecoration("getBuildPlateNumber") == Application.getInstance().getBuildPlateModel().activeBuildPlate + return super().isSelectable() and self.callDecoration("getBuildPlateNumber") == Application.getInstance().getMultiBuildPlateModel().activeBuildPlate ## Get the extruder used to print this node. If there is no active node, then the extruder in position zero is returned # TODO The best way to do it is by adding the setActiveExtruder decorator to every node when is loaded diff --git a/cura/Settings/ContainerManager.py b/cura/Settings/ContainerManager.py index d2e8410dde..b833e1f1e9 100644 --- a/cura/Settings/ContainerManager.py +++ b/cura/Settings/ContainerManager.py @@ -1,16 +1,14 @@ # Copyright (c) 2017 Ultimaker B.V. # Cura is released under the terms of the LGPLv3 or higher. -import copy import os.path import urllib.parse import uuid -from typing import Any, Dict, List, Union +from typing import Dict, Union from PyQt5.QtCore import QObject, QUrl, QVariant from UM.FlameProfiler import pyqtSlot from PyQt5.QtWidgets import QMessageBox -from UM.Util import parseBool from UM.PluginRegistry import PluginRegistry from UM.SaveFile import SaveFile @@ -22,7 +20,6 @@ from UM.Application import Application from UM.Settings.ContainerStack import ContainerStack from UM.Settings.DefinitionContainer import DefinitionContainer from UM.Settings.InstanceContainer import InstanceContainer -from cura.QualityManager import QualityManager from UM.MimeTypeDatabase import MimeTypeNotFoundError from UM.Settings.ContainerRegistry import ContainerRegistry @@ -30,9 +27,11 @@ from UM.Settings.ContainerRegistry import ContainerRegistry from UM.i18n import i18nCatalog from cura.Settings.ExtruderManager import ExtruderManager +from cura.Settings.ExtruderStack import ExtruderStack catalog = i18nCatalog("cura") + ## Manager class that contains common actions to deal with containers in Cura. # # This is primarily intended as a class to be able to perform certain actions @@ -42,154 +41,12 @@ class ContainerManager(QObject): def __init__(self, parent = None): super().__init__(parent) + self._application = Application.getInstance() self._container_registry = ContainerRegistry.getInstance() - self._machine_manager = Application.getInstance().getMachineManager() + self._machine_manager = self._application.getMachineManager() + self._material_manager = self._application.getMaterialManager() self._container_name_filters = {} - ## Create a duplicate of the specified container - # - # This will create and add a duplicate of the container corresponding - # to the container ID. - # - # \param container_id \type{str} The ID of the container to duplicate. - # - # \return The ID of the new container, or an empty string if duplication failed. - @pyqtSlot(str, result = str) - def duplicateContainer(self, container_id): - #TODO: It should be able to duplicate a container of which only the metadata is known. - containers = self._container_registry.findContainers(id = container_id) - if not containers: - Logger.log("w", "Could duplicate container %s because it was not found.", container_id) - return "" - - container = containers[0] - new_container = self.duplicateContainerInstance(container) - return new_container.getId() - - ## Create a duplicate of the given container instance - # - # This will create and add a duplicate of the container that was passed. - # - # \param container \type{ContainerInterface} The container to duplicate. - # - # \return The duplicated container, or None if duplication failed. - def duplicateContainerInstance(self, container): - new_container = None - new_name = self._container_registry.uniqueName(container.getName()) - # Only InstanceContainer has a duplicate method at the moment. - # So fall back to serialize/deserialize when no duplicate method exists. - if hasattr(container, "duplicate"): - new_container = container.duplicate(new_name) - else: - new_container = container.__class__(new_name) - new_container.deserialize(container.serialize()) - new_container.setName(new_name) - - # TODO: we probably don't want to add it to the registry here! - if new_container: - self._container_registry.addContainer(new_container) - - return new_container - - ## Change the name of a specified container to a new name. - # - # \param container_id \type{str} The ID of the container to change the name of. - # \param new_id \type{str} The new ID of the container. - # \param new_name \type{str} The new name of the specified container. - # - # \return True if successful, False if not. - @pyqtSlot(str, str, str, result = bool) - def renameContainer(self, container_id, new_id, new_name): - containers = self._container_registry.findContainers(id = container_id) - if not containers: - Logger.log("w", "Could rename container %s because it was not found.", container_id) - return False - - container = containers[0] - # First, remove the container from the registry. This will clean up any files related to the container. - self._container_registry.removeContainer(container_id) - - # Ensure we have a unique name for the container - new_name = self._container_registry.uniqueName(new_name) - - # Then, update the name and ID of the container - container.setName(new_name) - container._id = new_id # TODO: Find a nicer way to set a new, unique ID - - # Finally, re-add the container so it will be properly serialized again. - self._container_registry.addContainer(container) - - return True - - ## Remove the specified container. - # - # \param container_id \type{str} The ID of the container to remove. - # - # \return True if the container was successfully removed, False if not. - @pyqtSlot(str, result = bool) - def removeContainer(self, container_id): - containers = self._container_registry.findContainers(id = container_id) - if not containers: - Logger.log("w", "Could not remove container %s because it was not found.", container_id) - return False - - self._container_registry.removeContainer(containers[0].getId()) - - return True - - ## Merge a container with another. - # - # This will try to merge one container into the other, by going through the container - # and setting the right properties on the other container. - # - # \param merge_into_id \type{str} The ID of the container to merge into. - # \param merge_id \type{str} The ID of the container to merge. - # - # \return True if successfully merged, False if not. - @pyqtSlot(str, result = bool) - def mergeContainers(self, merge_into_id, merge_id): - containers = self._container_registry.findContainers(id = merge_into_id) - if not containers: - Logger.log("w", "Could merge into container %s because it was not found.", merge_into_id) - return False - - merge_into = containers[0] - - containers = self._container_registry.findContainers(id = merge_id) - if not containers: - Logger.log("w", "Could not merge container %s because it was not found", merge_id) - return False - - merge = containers[0] - - if not isinstance(merge, type(merge_into)): - Logger.log("w", "Cannot merge two containers of different types") - return False - - self._performMerge(merge_into, merge) - - return True - - ## Clear the contents of a container. - # - # \param container_id \type{str} The ID of the container to clear. - # - # \return True if successful, False if not. - @pyqtSlot(str, result = bool) - def clearContainer(self, container_id): - if self._container_registry.isReadOnly(container_id): - Logger.log("w", "Cannot clear read-only container %s", container_id) - return False - - containers = self._container_registry.findContainers(id = container_id) - if not containers: - Logger.log("w", "Could clear container %s because it was not found.", container_id) - return False - - containers[0].clear() - - return True - @pyqtSlot(str, str, result=str) def getContainerMetaDataEntry(self, container_id, entry_name): metadatas = self._container_registry.findContainersMetadata(id = container_id) @@ -211,18 +68,15 @@ class ContainerManager(QObject): # \param entry_value The new value of the entry. # # \return True if successful, False if not. - @pyqtSlot(str, str, str, result = bool) - def setContainerMetaDataEntry(self, container_id, entry_name, entry_value): - if self._container_registry.isReadOnly(container_id): - Logger.log("w", "Cannot set metadata of read-only container %s.", container_id) + # TODO: This is ONLY used by MaterialView for material containers. Maybe refactor this. + @pyqtSlot("QVariant", str, str) + def setContainerMetaDataEntry(self, container_node, entry_name, entry_value): + root_material_id = container_node.metadata["base_file"] + if self._container_registry.isReadOnly(root_material_id): + Logger.log("w", "Cannot set metadata of read-only container %s.", root_material_id) return False - containers = self._container_registry.findContainers(id = container_id) #We need the complete container, since we need to know whether the container is read-only or not. - if not containers: - Logger.log("w", "Could not set metadata of container %s because it was not found.", container_id) - return False - - container = containers[0] + material_group = self._material_manager.getMaterialGroup(root_material_id) entries = entry_name.split("/") entry_name = entries.pop() @@ -230,7 +84,7 @@ class ContainerManager(QObject): sub_item_changed = False if entries: root_name = entries.pop(0) - root = container.getMetaDataEntry(root_name) + root = material_group.root_material_node.metadata.get(root_name) item = root for _ in range(len(entries)): @@ -243,12 +97,11 @@ class ContainerManager(QObject): entry_name = root_name entry_value = root + container = material_group.root_material_node.getContainer() container.setMetaDataEntry(entry_name, entry_value) if sub_item_changed: #If it was only a sub-item that has changed then the setMetaDataEntry won't correctly notice that something changed, and we must manually signal that the metadata changed. container.metaDataChanged.emit(container) - return True - ## Set a setting property of the specified container. # # This will set the specified property of the specified setting of the container @@ -306,60 +159,6 @@ class ContainerManager(QObject): return container.getProperty(setting_key, property_name) - ## Set the name of the specified container. - @pyqtSlot(str, str, result = bool) - def setContainerName(self, container_id, new_name): - if self._container_registry.isReadOnly(container_id): - Logger.log("w", "Cannot set name of read-only container %s.", container_id) - return False - - containers = self._container_registry.findContainers(id = container_id) #We need to get the full container, not just metadata, since we need to know whether it's read-only. - if not containers: - Logger.log("w", "Could not set name of container %s because it was not found.", container_id) - return False - - containers[0].setName(new_name) - - return True - - ## Find instance containers matching certain criteria. - # - # This effectively forwards to - # ContainerRegistry::findInstanceContainersMetadata. - # - # \param criteria A dict of key - value pairs to search for. - # - # \return A list of container IDs that match the given criteria. - @pyqtSlot("QVariantMap", result = "QVariantList") - def findInstanceContainers(self, criteria): - return [entry["id"] for entry in self._container_registry.findInstanceContainersMetadata(**criteria)] - - @pyqtSlot(str, result = bool) - def isContainerUsed(self, container_id): - Logger.log("d", "Checking if container %s is currently used", container_id) - # check if this is a material container. If so, check if any material with the same base is being used by any - # stacks. - container_ids_to_check = [container_id] - container_results = self._container_registry.findInstanceContainersMetadata(id = container_id, type = "material") - if container_results: - this_container = container_results[0] - material_base_file = this_container["id"] - if "base_file" in this_container: - material_base_file = this_container["base_file"] - # check all material container IDs with the same base - material_containers = self._container_registry.findInstanceContainersMetadata(base_file = material_base_file, - type = "material") - if material_containers: - container_ids_to_check = [container["id"] for container in material_containers] - - all_stacks = self._container_registry.findContainerStacks() - for stack in all_stacks: - for used_container_id in container_ids_to_check: - if used_container_id in [child.getId() for child in stack.getContainers()]: - Logger.log("d", "The container is in use by %s", stack.getId()) - return True - return False - @pyqtSlot(str, result = str) def makeUniqueName(self, original_name): return self._container_registry.uniqueName(original_name) @@ -399,7 +198,7 @@ class ContainerManager(QObject): @pyqtSlot(str, str, QUrl, result = "QVariantMap") def exportContainer(self, container_id: str, file_type: str, file_url_or_string: Union[QUrl, str]) -> Dict[str, str]: if not container_id or not file_type or not file_url_or_string: - return { "status": "error", "message": "Invalid arguments"} + return {"status": "error", "message": "Invalid arguments"} if isinstance(file_url_or_string, QUrl): file_url = file_url_or_string.toLocalFile() @@ -407,20 +206,20 @@ class ContainerManager(QObject): file_url = file_url_or_string if not file_url: - return { "status": "error", "message": "Invalid path"} + return {"status": "error", "message": "Invalid path"} mime_type = None - if not file_type in self._container_name_filters: + if file_type not in self._container_name_filters: try: mime_type = MimeTypeDatabase.getMimeTypeForFile(file_url) except MimeTypeNotFoundError: - return { "status": "error", "message": "Unknown File Type" } + return {"status": "error", "message": "Unknown File Type"} else: mime_type = self._container_name_filters[file_type]["mime"] containers = self._container_registry.findContainers(id = container_id) if not containers: - return { "status": "error", "message": "Container not found"} + return {"status": "error", "message": "Container not found"} container = containers[0] if Platform.isOSX() and "." in file_url: @@ -437,12 +236,12 @@ class ContainerManager(QObject): result = QMessageBox.question(None, catalog.i18nc("@title:window", "File Already Exists"), catalog.i18nc("@label Don't translate the XML tag !", "The file {0} already exists. Are you sure you want to overwrite it?").format(file_url)) if result == QMessageBox.No: - return { "status": "cancelled", "message": "User cancelled"} + return {"status": "cancelled", "message": "User cancelled"} try: contents = container.serialize() except NotImplementedError: - return { "status": "error", "message": "Unable to serialize container"} + return {"status": "error", "message": "Unable to serialize container"} if contents is None: return {"status": "error", "message": "Serialization returned None. Unable to write to file"} @@ -450,7 +249,7 @@ class ContainerManager(QObject): with SaveFile(file_url, "w") as f: f.write(contents) - return { "status": "success", "message": "Succesfully exported container", "path": file_url} + return {"status": "success", "message": "Successfully exported container", "path": file_url} ## Imports a profile from a file # @@ -461,7 +260,7 @@ class ContainerManager(QObject): @pyqtSlot(QUrl, result = "QVariantMap") def importMaterialContainer(self, file_url_or_string: Union[QUrl, str]) -> Dict[str, str]: if not file_url_or_string: - return { "status": "error", "message": "Invalid path"} + return {"status": "error", "message": "Invalid path"} if isinstance(file_url_or_string, QUrl): file_url = file_url_or_string.toLocalFile() @@ -469,16 +268,16 @@ class ContainerManager(QObject): file_url = file_url_or_string if not file_url or not os.path.exists(file_url): - return { "status": "error", "message": "Invalid path" } + return {"status": "error", "message": "Invalid path"} try: mime_type = MimeTypeDatabase.getMimeTypeForFile(file_url) except MimeTypeNotFoundError: - return { "status": "error", "message": "Could not determine mime type of file" } + return {"status": "error", "message": "Could not determine mime type of file"} container_type = self._container_registry.getContainerForMimeType(mime_type) if not container_type: - return { "status": "error", "message": "Could not find a container to handle the specified file."} + return {"status": "error", "message": "Could not find a container to handle the specified file."} container_id = urllib.parse.unquote_plus(mime_type.stripExtension(os.path.basename(file_url))) container_id = self._container_registry.uniqueName(container_id) @@ -489,7 +288,7 @@ class ContainerManager(QObject): with open(file_url, "rt", encoding = "utf-8") as f: container.deserialize(f.read()) except PermissionError: - return { "status": "error", "message": "Permission denied when trying to read the file"} + return {"status": "error", "message": "Permission denied when trying to read the file"} except Exception as ex: return {"status": "error", "message": str(ex)} @@ -497,7 +296,7 @@ class ContainerManager(QObject): self._container_registry.addContainer(container) - return { "status": "success", "message": "Successfully imported container {0}".format(container.getName()) } + return {"status": "success", "message": "Successfully imported container {0}".format(container.getName())} ## Update the current active quality changes container with the settings from the user container. # @@ -522,7 +321,7 @@ class ContainerManager(QObject): self._performMerge(quality_changes, stack.getTop()) - self._machine_manager.activeQualityChanged.emit() + self._machine_manager.activeQualityChangesGroupChanged.emit() return True @@ -547,18 +346,16 @@ class ContainerManager(QObject): # This will go through the global and extruder stacks and create quality_changes containers from # the user containers in each stack. These then replace the quality_changes containers in the # stack and clear the user settings. - # - # \return \type{bool} True if the operation was successfully, False if not. - @pyqtSlot(str, result = bool) + @pyqtSlot(str) def createQualityChanges(self, base_name): global_stack = Application.getInstance().getGlobalContainerStack() if not global_stack: - return False + return - active_quality_name = self._machine_manager.activeQualityName + active_quality_name = self._machine_manager.activeQualityOrQualityChangesName if active_quality_name == "": Logger.log("w", "No quality container found in stack %s, cannot create profile", global_stack.getId()) - return False + return self._machine_manager.blurSettings.emit() if base_name is None or base_name == "": @@ -567,382 +364,54 @@ class ContainerManager(QObject): # Go through the active stacks and create quality_changes containers from the user containers. for stack in ExtruderManager.getInstance().getActiveGlobalAndExtruderStacks(): - user_container = stack.getTop() + user_container = stack.userChanges quality_container = stack.quality quality_changes_container = stack.qualityChanges if not quality_container or not quality_changes_container: Logger.log("w", "No quality or quality changes container found in stack %s, ignoring it", stack.getId()) continue - extruder_id = None if stack is global_stack else QualityManager.getInstance().getParentMachineDefinition(stack.getBottom()).getId() - new_changes = self._createQualityChanges(quality_container, unique_name, - Application.getInstance().getGlobalContainerStack().getBottom(), - extruder_id) + extruder_definition_id = None + if isinstance(stack, ExtruderStack): + extruder_definition_id = stack.definition.getId() + quality_type = quality_container.getMetaDataEntry("quality_type") + new_changes = self._createQualityChanges(quality_type, unique_name, global_stack, extruder_definition_id) self._performMerge(new_changes, quality_changes_container, clear_settings = False) self._performMerge(new_changes, user_container) self._container_registry.addContainer(new_changes) - stack.replaceContainer(stack.getContainerIndex(quality_changes_container), new_changes) - - self._machine_manager.activeQualityChanged.emit() - return True - - ## Remove all quality changes containers matching a specified name. - # - # This will search for quality_changes containers matching the supplied name and remove them. - # Note that if the machine specifies that qualities should be filtered by machine and/or material - # only the containers related to the active machine/material are removed. - # - # \param quality_name The name of the quality changes to remove. - # - # \return \type{bool} True if successful, False if not. - @pyqtSlot(str, result = bool) - def removeQualityChanges(self, quality_name): - Logger.log("d", "Attempting to remove the quality change containers with name %s", quality_name) - containers_found = False - - if not quality_name: - return containers_found # Without a name we will never find a container to remove. - - # If the container that is being removed is the currently active quality, set another quality as the active quality - activate_quality = quality_name == self._machine_manager.activeQualityName - activate_quality_type = None - - global_stack = Application.getInstance().getGlobalContainerStack() - if not global_stack or not quality_name: - return "" - machine_definition = QualityManager.getInstance().getParentMachineDefinition(global_stack.getBottom()) - - for container in QualityManager.getInstance().findQualityChangesByName(quality_name, machine_definition): - containers_found = True - if activate_quality and not activate_quality_type: - activate_quality_type = container.getMetaDataEntry("quality") - self._container_registry.removeContainer(container.getId()) - - if not containers_found: - Logger.log("d", "Unable to remove quality containers, as we did not find any by the name of %s", quality_name) - - elif activate_quality: - definition_id = "fdmprinter" if not self._machine_manager.filterQualityByMachine else self._machine_manager.activeDefinitionId - containers = self._container_registry.findInstanceContainersMetadata(type = "quality", definition = definition_id, quality_type = activate_quality_type) - if containers: - self._machine_manager.setActiveQuality(containers[0]["id"]) - self._machine_manager.activeQualityChanged.emit() - - return containers_found - - ## Rename a set of quality changes containers. - # - # This will search for quality_changes containers matching the supplied name and rename them. - # Note that if the machine specifies that qualities should be filtered by machine and/or material - # only the containers related to the active machine/material are renamed. - # - # \param quality_name The name of the quality changes containers to rename. - # \param new_name The new name of the quality changes. - # - # \return True if successful, False if not. - @pyqtSlot(str, str, result = bool) - def renameQualityChanges(self, quality_name, new_name): - Logger.log("d", "User requested QualityChanges container rename of %s to %s", quality_name, new_name) - if not quality_name or not new_name: - return False - - if quality_name == new_name: - Logger.log("w", "Unable to rename %s to %s, because they are the same.", quality_name, new_name) - return True - - global_stack = Application.getInstance().getGlobalContainerStack() - if not global_stack: - return False - - self._machine_manager.blurSettings.emit() - - new_name = self._container_registry.uniqueName(new_name) - - container_registry = self._container_registry - - containers_to_rename = self._container_registry.findInstanceContainersMetadata(type = "quality_changes", name = quality_name) - - for container in containers_to_rename: - stack_id = global_stack.getId() - if "extruder" in container: - stack_id = container["extruder"] - container_registry.renameContainer(container["id"], new_name, self._createUniqueId(stack_id, new_name)) - - if not containers_to_rename: - Logger.log("e", "Unable to rename %s, because we could not find the profile", quality_name) - - self._machine_manager.activeQualityChanged.emit() - return True - - ## Duplicate a specified set of quality or quality_changes containers. - # - # This will search for containers matching the specified name. If the container is a "quality" type container, a new - # quality_changes container will be created with the specified quality as base. If the container is a "quality_changes" - # container, it is simply duplicated and renamed. - # - # \param quality_name The name of the quality to duplicate. - # - # \return A string containing the name of the duplicated containers, or an empty string if it failed. - @pyqtSlot(str, str, result = str) - def duplicateQualityOrQualityChanges(self, quality_name, base_name): - global_stack = Application.getInstance().getGlobalContainerStack() - if not global_stack or not quality_name: - return "" - machine_definition = global_stack.definition - - active_stacks = ExtruderManager.getInstance().getActiveGlobalAndExtruderStacks() - if active_stacks is None: - return "" - material_metadatas = [stack.material.getMetaData() for stack in active_stacks] - - result = self._duplicateQualityOrQualityChangesForMachineType(quality_name, base_name, - QualityManager.getInstance().getParentMachineDefinition(machine_definition), - material_metadatas) - return result[0].getName() if result else "" - - ## Duplicate a quality or quality changes profile specific to a machine type - # - # \param quality_name The name of the quality or quality changes container to duplicate. - # \param base_name The desired name for the new container. - # \param machine_definition The machine with the specific machine type. - # \param material_metadatas Metadata of materials - # \return List of duplicated quality profiles. - def _duplicateQualityOrQualityChangesForMachineType(self, quality_name: str, base_name: str, machine_definition: DefinitionContainer, material_metadatas: List[Dict[str, Any]]) -> List[InstanceContainer]: - Logger.log("d", "Attempting to duplicate the quality %s", quality_name) - - if base_name is None: - base_name = quality_name - # Try to find a Quality with the name. - container = QualityManager.getInstance().findQualityByName(quality_name, machine_definition, material_metadatas) - if container: - Logger.log("d", "We found a quality to duplicate.") - return self._duplicateQualityForMachineType(container, base_name, machine_definition) - Logger.log("d", "We found a quality_changes to duplicate.") - # Assume it is a quality changes. - return self._duplicateQualityChangesForMachineType(quality_name, base_name, machine_definition) - - # Duplicate a quality profile - def _duplicateQualityForMachineType(self, quality_container, base_name, machine_definition) -> List[InstanceContainer]: - if base_name is None: - base_name = quality_container.getName() - new_name = self._container_registry.uniqueName(base_name) - - new_change_instances = [] - - # Handle the global stack first. - global_changes = self._createQualityChanges(quality_container, new_name, machine_definition, None) - new_change_instances.append(global_changes) - self._container_registry.addContainer(global_changes) - - # Handle the extruders if present. - extruders = machine_definition.getMetaDataEntry("machine_extruder_trains") - if extruders: - for extruder_id in extruders: - extruder = extruders[extruder_id] - new_changes = self._createQualityChanges(quality_container, new_name, machine_definition, extruder) - new_change_instances.append(new_changes) - self._container_registry.addContainer(new_changes) - - return new_change_instances - - # Duplicate a quality changes container - def _duplicateQualityChangesForMachineType(self, quality_changes_name, base_name, machine_definition) -> List[InstanceContainer]: - new_change_instances = [] - for container in QualityManager.getInstance().findQualityChangesByName(quality_changes_name, - machine_definition): - base_id = container.getMetaDataEntry("extruder") - if not base_id: - base_id = container.getDefinition().getId() - new_unique_id = self._createUniqueId(base_id, base_name) - new_container = container.duplicate(new_unique_id, base_name) - new_change_instances.append(new_container) - self._container_registry.addContainer(new_container) - - return new_change_instances - - ## Create a duplicate of a material, which has the same GUID and base_file metadata - # - # \return \type{str} the id of the newly created container. - @pyqtSlot(str, result = str) - def duplicateMaterial(self, material_id: str) -> str: - original = self._container_registry.findContainersMetadata(id = material_id) - if not original: - Logger.log("d", "Unable to duplicate the material with id %s, because it doesn't exist.", material_id) - return "" - original = original[0] - - base_container_id = original.get("base_file") - base_container = self._container_registry.findContainers(id = base_container_id) - if not base_container: - Logger.log("d", "Unable to duplicate the material with id {material_id}, because base_file {base_container_id} doesn't exist.".format(material_id = material_id, base_container_id = base_container_id)) - return "" - base_container = base_container[0] - - #We'll copy all containers with the same base. - #This way the correct variant and machine still gets assigned when loading the copy of the material. - containers_to_copy = self._container_registry.findInstanceContainers(base_file = base_container_id) - - # Ensure all settings are saved. - Application.getInstance().saveSettings() - - # Create a new ID & container to hold the data. - new_containers = [] - new_base_id = self._container_registry.uniqueName(base_container.getId()) - new_base_container = copy.deepcopy(base_container) - new_base_container.getMetaData()["id"] = new_base_id - new_base_container.getMetaData()["base_file"] = new_base_id - new_containers.append(new_base_container) - - #Clone all of them. - clone_of_original = None #Keeping track of which one is the clone of the original material, since we need to return that. - for container_to_copy in containers_to_copy: - #Create unique IDs for every clone. - current_id = container_to_copy.getId() - new_id = new_base_id - if container_to_copy.getMetaDataEntry("definition") != "fdmprinter": - new_id += "_" + container_to_copy.getMetaDataEntry("definition") - if container_to_copy.getMetaDataEntry("variant"): - variant = self._container_registry.findContainers(id = container_to_copy.getMetaDataEntry("variant"))[0] - new_id += "_" + variant.getName().replace(" ", "_") - if current_id == material_id: - clone_of_original = new_id - - new_container = copy.deepcopy(container_to_copy) - new_container.getMetaData()["id"] = new_id - new_container.getMetaData()["base_file"] = new_base_id - new_containers.append(new_container) - - for container_to_add in new_containers: - container_to_add.setDirty(True) - ContainerRegistry.getInstance().addContainer(container_to_add) - return self._getMaterialContainerIdForActiveMachine(clone_of_original) - - ## Create a duplicate of a material or it's original entry - # - # \return \type{str} the id of the newly created container. - @pyqtSlot(str, result = str) - def duplicateOriginalMaterial(self, material_id): - - # check if the given material has a base file (i.e. was shipped by default) - base_file = self.getContainerMetaDataEntry(material_id, "base_file") - - if base_file == "": - # there is no base file, so duplicate by ID - return self.duplicateMaterial(material_id) - else: - # there is a base file, so duplicate the original material - return self.duplicateMaterial(base_file) - - ## Create a new material by cloning Generic PLA for the current material diameter and setting the GUID to something unqiue - # - # \return \type{str} the id of the newly created container. - @pyqtSlot(result = str) - def createMaterial(self) -> str: - # Ensure all settings are saved. - Application.getInstance().saveSettings() - - global_stack = Application.getInstance().getGlobalContainerStack() - if not global_stack: - return "" - - approximate_diameter = str(round(global_stack.getProperty("material_diameter", "value"))) - containers = self._container_registry.findInstanceContainersMetadata(id = "generic_pla*", approximate_diameter = approximate_diameter) - if not containers: - Logger.log("d", "Unable to create a new material by cloning Generic PLA, because it cannot be found for the material diameter for this machine.") - return "" - - base_file = containers[0].get("base_file") - containers = self._container_registry.findInstanceContainers(id = base_file) - if not containers: - Logger.log("d", "Unable to create a new material by cloning Generic PLA, because the base file for Generic PLA for this machine can not be found.") - return "" - - # Create a new ID & container to hold the data. - new_id = self._container_registry.uniqueName("custom_material") - container_type = type(containers[0]) # Always XMLMaterialProfile, since we specifically clone the base_file - duplicated_container = container_type(new_id) - - # Instead of duplicating we load the data from the basefile again. - # This ensures that the inheritance goes well and all "cut up" subclasses of the xmlMaterial profile - # are also correctly created. - with open(containers[0].getPath(), encoding="utf-8") as f: - duplicated_container.deserialize(f.read()) - - duplicated_container.setMetaDataEntry("GUID", str(uuid.uuid4())) - duplicated_container.setMetaDataEntry("brand", catalog.i18nc("@label", "Custom")) - # We're defaulting to PLA, as machines with material profiles don't like material types they don't know. - # TODO: This is a hack, the only reason this is in now is to bandaid the problem as we're close to a release! - duplicated_container.setMetaDataEntry("material", "PLA") - duplicated_container.setName(catalog.i18nc("@label", "Custom Material")) - - self._container_registry.addContainer(duplicated_container) - return self._getMaterialContainerIdForActiveMachine(new_id) - - ## Find the id of a material container based on the new material - # Utilty function that is shared between duplicateMaterial and createMaterial - # - # \param base_file \type{str} the id of the created container. - def _getMaterialContainerIdForActiveMachine(self, base_file): - global_stack = Application.getInstance().getGlobalContainerStack() - if not global_stack: - return base_file - - has_machine_materials = parseBool(global_stack.getMetaDataEntry("has_machine_materials", default = False)) - has_variant_materials = parseBool(global_stack.getMetaDataEntry("has_variant_materials", default = False)) - has_variants = parseBool(global_stack.getMetaDataEntry("has_variants", default = False)) - if has_machine_materials or has_variant_materials: - if has_variants: - materials = self._container_registry.findInstanceContainersMetadata(type = "material", base_file = base_file, definition = global_stack.getBottom().getId(), variant = self._machine_manager.activeVariantId) - else: - materials = self._container_registry.findInstanceContainersMetadata(type = "material", base_file = base_file, definition = global_stack.getBottom().getId()) - - if materials: - return materials[0]["id"] - - Logger.log("w", "Unable to find a suitable container based on %s for the current machine.", base_file) - return "" # do not activate a new material if a container can not be found - - return base_file ## Get a list of materials that have the same GUID as the reference material # # \param material_id \type{str} the id of the material for which to get the linked materials. # \return \type{list} a list of names of materials with the same GUID - @pyqtSlot(str, result = "QStringList") - def getLinkedMaterials(self, material_id: str): - containers = self._container_registry.findInstanceContainersMetadata(id = material_id) - if not containers: - Logger.log("d", "Unable to find materials linked to material with id %s, because it doesn't exist.", material_id) - return [] + @pyqtSlot("QVariant", result = "QStringList") + def getLinkedMaterials(self, material_node): + guid = material_node.metadata["GUID"] - material_container = containers[0] - material_base_file = material_container.get("base_file", "") - material_guid = material_container.get("GUID", "") - if not material_guid: - Logger.log("d", "Unable to find materials linked to material with id %s, because it doesn't have a GUID.", material_id) - return [] + material_group_list = self._material_manager.getMaterialGroupListByGUID(guid) - containers = self._container_registry.findInstanceContainersMetadata(type = "material", GUID = material_guid) linked_material_names = [] - for container in containers: - if container["id"] in [material_id, material_base_file] or container.get("base_file") != container["id"]: - continue - - linked_material_names.append(container["name"]) + if material_group_list: + for material_group in material_group_list: + linked_material_names.append(material_group.root_material_node.metadata["name"]) return linked_material_names ## Unlink a material from all other materials by creating a new GUID # \param material_id \type{str} the id of the material to create a new GUID for. - @pyqtSlot(str) - def unlinkMaterial(self, material_id: str): - containers = self._container_registry.findInstanceContainers(id=material_id) - if not containers: - Logger.log("d", "Unable to make the material with id %s unique, because it doesn't exist.", material_id) - return "" + @pyqtSlot("QVariant") + def unlinkMaterial(self, material_node): + # Get the material group + material_group = self._material_manager.getMaterialGroup(material_node.metadata["base_file"]) - containers[0].setMetaDataEntry("GUID", str(uuid.uuid4())) + # Generate a new GUID + new_guid = str(uuid.uuid4()) + # Update the GUID + # NOTE: We only need to set the root material container because XmlMaterialProfile.setMetaDataEntry() will + # take care of the derived containers too + container = material_group.root_material_node.getContainer() + container.setMetaDataEntry("GUID", new_guid) ## Get the singleton instance for this class. @classmethod @@ -1015,81 +484,6 @@ class ContainerManager(QObject): name_filter = "{0} ({1})".format(mime_type.comment, suffix_list) self._container_name_filters[name_filter] = entry - ## Creates a unique ID for a container by prefixing the name with the stack ID. - # - # This method creates a unique ID for a container by prefixing it with a specified stack ID. - # This is done to ensure we have an easily identified ID for quality changes, which have the - # same name across several stacks. - # - # \param stack_id The ID of the stack to prepend. - # \param container_name The name of the container that we are creating a unique ID for. - # - # \return Container name prefixed with stack ID, in lower case with spaces replaced by underscores. - def _createUniqueId(self, stack_id, container_name): - result = stack_id + "_" + container_name - result = result.lower() - result.replace(" ", "_") - return result - - ## Create a quality changes container for a specified quality container. - # - # \param quality_container The quality container to create a changes container for. - # \param new_name The name of the new quality_changes container. - # \param machine_definition The machine definition this quality changes container is specific to. - # \param extruder_id - # - # \return A new quality_changes container with the specified container as base. - def _createQualityChanges(self, quality_container, new_name, machine_definition, extruder_id): - base_id = machine_definition.getId() if extruder_id is None else extruder_id - - # Create a new quality_changes container for the quality. - quality_changes = InstanceContainer(self._createUniqueId(base_id, new_name)) - quality_changes.setName(new_name) - quality_changes.addMetaDataEntry("type", "quality_changes") - quality_changes.addMetaDataEntry("quality_type", quality_container.getMetaDataEntry("quality_type")) - - # If we are creating a container for an extruder, ensure we add that to the container - if extruder_id is not None: - quality_changes.addMetaDataEntry("extruder", extruder_id) - - # If the machine specifies qualities should be filtered, ensure we match the current criteria. - if not machine_definition.getMetaDataEntry("has_machine_quality"): - quality_changes.setDefinition("fdmprinter") - else: - quality_changes.setDefinition(QualityManager.getInstance().getParentMachineDefinition(machine_definition).getId()) - - from cura.CuraApplication import CuraApplication - quality_changes.addMetaDataEntry("setting_version", CuraApplication.SettingVersion) - return quality_changes - - - ## Import profiles from a list of file_urls. - # Each QUrl item must end with .curaprofile, or it will not be imported. - # - # \param QVariant, essentially a list with QUrl objects. - # \return Dict with keys status, text - @pyqtSlot("QVariantList", result="QVariantMap") - def importProfiles(self, file_urls): - status = "ok" - results = {"ok": [], "error": []} - for file_url in file_urls: - if not file_url.isValid(): - continue - path = file_url.toLocalFile() - if not path: - continue - if not path.endswith(".curaprofile"): - continue - - single_result = self._container_registry.importProfile(path) - if single_result["status"] == "error": - status = "error" - results[single_result["status"]].append(single_result["message"]) - - return { - "status": status, - "message": "\n".join(results["ok"] + results["error"])} - ## Import single profile, file_url does not have to end with curaprofile @pyqtSlot(QUrl, result="QVariantMap") def importProfile(self, file_url): @@ -1100,11 +494,13 @@ class ContainerManager(QObject): return return self._container_registry.importProfile(path) - @pyqtSlot("QVariantList", QUrl, str) - def exportProfile(self, instance_id: str, file_url: QUrl, file_type: str) -> None: + @pyqtSlot(QObject, QUrl, str) + def exportQualityChangesGroup(self, quality_changes_group, file_url: QUrl, file_type: str): if not file_url.isValid(): return path = file_url.toLocalFile() if not path: return - self._container_registry.exportProfile(instance_id, path, file_type) + + container_list = [n.getContainer() for n in quality_changes_group.getAllNodes()] + self._container_registry.exportQualityProfile(container_list, path, file_type) diff --git a/cura/Settings/ContainerSettingsModel.py b/cura/Settings/ContainerSettingsModel.py deleted file mode 100644 index 2c4bef6464..0000000000 --- a/cura/Settings/ContainerSettingsModel.py +++ /dev/null @@ -1,97 +0,0 @@ -# Copyright (c) 2016 Ultimaker B.V. -# Cura is released under the terms of the LGPLv3 or higher. - -from UM.Application import Application -from UM.Qt.ListModel import ListModel - -from PyQt5.QtCore import pyqtProperty, Qt, pyqtSignal, pyqtSlot, QUrl - -from UM.Settings.ContainerRegistry import ContainerRegistry -from UM.Settings.InstanceContainer import InstanceContainer -from UM.Settings.SettingFunction import SettingFunction - -class ContainerSettingsModel(ListModel): - LabelRole = Qt.UserRole + 1 - CategoryRole = Qt.UserRole + 2 - UnitRole = Qt.UserRole + 3 - ValuesRole = Qt.UserRole + 4 - - def __init__(self, parent = None): - super().__init__(parent) - self.addRoleName(self.LabelRole, "label") - self.addRoleName(self.CategoryRole, "category") - self.addRoleName(self.UnitRole, "unit") - self.addRoleName(self.ValuesRole, "values") - - self._container_ids = [] - self._containers = [] - - def _onPropertyChanged(self, key, property_name): - if property_name == "value": - self._update() - - def _update(self): - items = [] - - if len(self._container_ids) == 0: - return - - keys = [] - for container in self._containers: - keys = keys + list(container.getAllKeys()) - - keys = list(set(keys)) # remove duplicate keys - - for key in keys: - definition = None - category = None - values = [] - for container in self._containers: - instance = container.getInstance(key) - if instance: - definition = instance.definition - - # Traverse up to find the category - category = definition - while category.type != "category": - category = category.parent - - value = container.getProperty(key, "value") - if type(value) == SettingFunction: - values.append("=\u0192") - else: - values.append(container.getProperty(key, "value")) - else: - values.append("") - - items.append({ - "key": key, - "values": values, - "label": definition.label, - "unit": definition.unit, - "category": category.label - }) - items.sort(key = lambda k: (k["category"], k["key"])) - self.setItems(items) - - ## Set the ids of the containers which have the settings this model should list. - # Also makes sure the model updates when the containers have property changes - def setContainers(self, container_ids): - for container in self._containers: - container.propertyChanged.disconnect(self._onPropertyChanged) - - self._container_ids = container_ids - self._containers = [] - - for container_id in self._container_ids: - containers = ContainerRegistry.getInstance().findContainers(id = container_id) - if containers: - containers[0].propertyChanged.connect(self._onPropertyChanged) - self._containers.append(containers[0]) - - self._update() - - containersChanged = pyqtSignal() - @pyqtProperty("QVariantList", fset = setContainers, notify = containersChanged) - def containers(self): - return self.container_ids diff --git a/cura/Settings/CuraContainerRegistry.py b/cura/Settings/CuraContainerRegistry.py index 540f0b3475..e79cfa5335 100644 --- a/cura/Settings/CuraContainerRegistry.py +++ b/cura/Settings/CuraContainerRegistry.py @@ -25,14 +25,15 @@ from UM.Resources import Resources from . import ExtruderStack from . import GlobalStack -from .ContainerManager import ContainerManager from .ExtruderManager import ExtruderManager from cura.CuraApplication import CuraApplication +from cura.Machines.QualityManager import getMachineDefinitionIDForQualitySearch from UM.i18n import i18nCatalog catalog = i18nCatalog("cura") + class CuraContainerRegistry(ContainerRegistry): def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) @@ -102,7 +103,7 @@ class CuraContainerRegistry(ContainerRegistry): # \param instance_ids \type{list} the IDs of the profiles to export. # \param file_name \type{str} the full path and filename to export to. # \param file_type \type{str} the file type with the format " (*.)" - def exportProfile(self, instance_ids, file_name, file_type): + def exportQualityProfile(self, container_list, file_name, file_type): # Parse the fileType to deduce what plugin can save the file format. # fileType has the format " (*.)" split = file_type.rfind(" (*.") # Find where the description ends and the extension starts. @@ -121,31 +122,10 @@ class CuraContainerRegistry(ContainerRegistry): catalog.i18nc("@label Don't translate the XML tag !", "The file {0} already exists. Are you sure you want to overwrite it?").format(file_name)) if result == QMessageBox.No: return - found_containers = [] - extruder_positions = [] - for instance_id in instance_ids: - containers = ContainerRegistry.getInstance().findInstanceContainers(id = instance_id) - if containers: - found_containers.append(containers[0]) - - # Determine the position of the extruder of this container - extruder_id = containers[0].getMetaDataEntry("extruder", "") - if extruder_id == "": - # Global stack - extruder_positions.append(-1) - else: - extruder_containers = ContainerRegistry.getInstance().findDefinitionContainersMetadata(id = extruder_id) - if extruder_containers: - extruder_positions.append(int(extruder_containers[0].get("position", 0))) - else: - extruder_positions.append(0) - # Ensure the profiles are always exported in order (global, extruder 0, extruder 1, ...) - found_containers = [containers for (positions, containers) in sorted(zip(extruder_positions, found_containers))] profile_writer = self._findProfileWriter(extension, description) - try: - success = profile_writer.write(file_name, found_containers) + success = profile_writer.write(file_name, container_list) except Exception as e: Logger.log("e", "Failed to export profile to %s: %s", file_name, str(e)) m = Message(catalog.i18nc("@info:status Don't translate the XML tags or !", "Failed to export profile to {0}: {1}", file_name, str(e)), @@ -289,7 +269,7 @@ class CuraContainerRegistry(ContainerRegistry): elif profile_index < len(machine_extruders) + 1: # This is assumed to be an extruder profile - extruder_id = Application.getInstance().getMachineManager().getQualityDefinitionId(machine_extruders[profile_index - 1].getBottom()) + extruder_id = machine_extruders[profile_index - 1].definition.getId() if not profile.getMetaDataEntry("extruder"): profile.addMetaDataEntry("extruder", extruder_id) else: @@ -348,39 +328,16 @@ class CuraContainerRegistry(ContainerRegistry): return catalog.i18nc("@info:status", "Profile is missing a quality type.") quality_type_criteria = {"quality_type": quality_type} - if self._machineHasOwnQualities(): - profile.setDefinition(self._activeQualityDefinition().getId()) - if self._machineHasOwnMaterials(): - active_material_id = self._activeMaterialId() - if active_material_id and active_material_id != "empty": # only update if there is an active material - profile.addMetaDataEntry("material", active_material_id) - quality_type_criteria["material"] = active_material_id - - quality_type_criteria["definition"] = profile.getDefinition().getId() - - else: - profile.setDefinition("fdmprinter") - quality_type_criteria["definition"] = "fdmprinter" - - machine_definition = Application.getInstance().getGlobalContainerStack().getBottom() - del quality_type_criteria["definition"] - - # materials = None - - if "material" in quality_type_criteria: - # materials = ContainerRegistry.getInstance().findInstanceContainers(id = quality_type_criteria["material"]) - del quality_type_criteria["material"] - - # Do not filter quality containers here with materials because we are trying to import a profile, so it should - # NOT be restricted by the active materials on the current machine. - materials = None + global_stack = Application.getInstance().getGlobalContainerStack() + definition_id = getMachineDefinitionIDForQualitySearch(global_stack) + profile.setDefinition(definition_id) # Check to make sure the imported profile actually makes sense in context of the current configuration. # This prevents issues where importing a "draft" profile for a machine without "draft" qualities would report as # successfully imported but then fail to show up. - from cura.QualityManager import QualityManager - qualities = QualityManager.getInstance()._getFilteredContainersForStack(machine_definition, materials, **quality_type_criteria) - if not qualities: + quality_manager = CuraApplication.getInstance()._quality_manager + quality_group_dict = quality_manager.getQualityGroupsForMachineDefinition(global_stack) + if quality_type not in quality_group_dict: return catalog.i18nc("@info:status", "Could not find a quality type {0} for the current configuration.", quality_type) ContainerRegistry.getInstance().addContainer(profile) @@ -400,18 +357,6 @@ class CuraContainerRegistry(ContainerRegistry): result.append( (plugin_id, meta_data) ) return result - ## Get the definition to use to select quality profiles for the active machine - # \return the active quality definition object or None if there is no quality definition - def _activeQualityDefinition(self): - global_container_stack = Application.getInstance().getGlobalContainerStack() - if global_container_stack: - definition_id = Application.getInstance().getMachineManager().getQualityDefinitionId(global_container_stack.getBottom()) - definition = self.findDefinitionContainers(id = definition_id)[0] - - if definition: - return definition - return None - ## Returns true if the current machine requires its own materials # \return True if the current machine requires its own materials def _machineHasOwnMaterials(self): @@ -507,8 +452,6 @@ class CuraContainerRegistry(ContainerRegistry): extruder_stack.setDefinition(extruder_definition) extruder_stack.addMetaDataEntry("position", extruder_definition.getMetaDataEntry("position")) - from cura.CuraApplication import CuraApplication - # create a new definition_changes container for the extruder stack definition_changes_id = self.uniqueName(extruder_stack.getId() + "_settings") if create_new_ids else extruder_stack.getId() + "_settings" definition_changes_name = definition_changes_id @@ -567,26 +510,28 @@ class CuraContainerRegistry(ContainerRegistry): self.addContainer(user_container) extruder_stack.setUserChanges(user_container) - variant_id = "default" + application = CuraApplication.getInstance() + empty_variant = application.empty_variant_container + empty_material = application.empty_material_container + empty_quality = application.empty_quality_container + if machine.variant.getId() not in ("empty", "empty_variant"): - variant_id = machine.variant.getId() + variant = machine.variant else: - variant_id = "empty_variant" - extruder_stack.setVariantById(variant_id) + variant = empty_variant + extruder_stack.variant = variant - material_id = "default" if machine.material.getId() not in ("empty", "empty_material"): - material_id = machine.material.getId() + material = machine.material else: - material_id = "empty_material" - extruder_stack.setMaterialById(material_id) + material = empty_material + extruder_stack.material = material - quality_id = "default" if machine.quality.getId() not in ("empty", "empty_quality"): - quality_id = machine.quality.getId() + quality = machine.quality else: - quality_id = "empty_quality" - extruder_stack.setQualityById(quality_id) + quality = empty_quality + extruder_stack.quality = quality machine_quality_changes = machine.qualityChanges if new_global_quality_changes is not None: @@ -598,7 +543,7 @@ class CuraContainerRegistry(ContainerRegistry): extruder_quality_changes_container = extruder_quality_changes_container[0] quality_changes_id = extruder_quality_changes_container.getId() - extruder_stack.setQualityChangesById(quality_changes_id) + extruder_stack.qualityChanges = self.findInstanceContainers(id = quality_changes_id)[0] else: # Some extruder quality_changes containers can be created at runtime as files in the qualities # folder. Those files won't be loaded in the registry immediately. So we also need to search @@ -607,7 +552,7 @@ class CuraContainerRegistry(ContainerRegistry): if extruder_quality_changes_container: quality_changes_id = extruder_quality_changes_container.getId() extruder_quality_changes_container.addMetaDataEntry("extruder", extruder_stack.definition.getId()) - extruder_stack.setQualityChangesById(quality_changes_id) + extruder_stack.qualityChanges = self.findInstanceContainers(id = quality_changes_id)[0] else: # if we still cannot find a quality changes container for the extruder, create a new one container_name = machine_quality_changes.getName() @@ -642,7 +587,7 @@ class CuraContainerRegistry(ContainerRegistry): machine_quality_changes.removeInstance(qc_setting_key, postpone_emit=True) else: - extruder_stack.setQualityChangesById("empty_quality_changes") + extruder_stack.qualityChanges = self.findInstanceContainers(id = "empty_quality_changes")[0] self.addContainer(extruder_stack) diff --git a/cura/Settings/CuraContainerStack.py b/cura/Settings/CuraContainerStack.py index b97bb3314e..00db4f57c7 100755 --- a/cura/Settings/CuraContainerStack.py +++ b/cura/Settings/CuraContainerStack.py @@ -83,20 +83,6 @@ class CuraContainerStack(ContainerStack): def setQualityChanges(self, new_quality_changes: InstanceContainer, postpone_emit = False) -> None: self.replaceContainer(_ContainerIndexes.QualityChanges, new_quality_changes, postpone_emit = postpone_emit) - ## Set the quality changes container by an ID. - # - # This will search for the specified container and set it. If no container was found, an error will be raised. - # - # \param new_quality_changes_id The ID of the new quality changes container. - # - # \throws Exceptions.InvalidContainerError Raised when no container could be found with the specified ID. - def setQualityChangesById(self, new_quality_changes_id: str) -> None: - quality_changes = ContainerRegistry.getInstance().findInstanceContainers(id = new_quality_changes_id) - if quality_changes: - self.setQualityChanges(quality_changes[0]) - else: - raise Exceptions.InvalidContainerError("Could not find container with id {id}".format(id = new_quality_changes_id)) - ## Get the quality changes container. # # \return The quality changes container. Should always be a valid container, but can be equal to the empty InstanceContainer. @@ -110,31 +96,6 @@ class CuraContainerStack(ContainerStack): def setQuality(self, new_quality: InstanceContainer, postpone_emit = False) -> None: self.replaceContainer(_ContainerIndexes.Quality, new_quality, postpone_emit = postpone_emit) - ## Set the quality container by an ID. - # - # This will search for the specified container and set it. If no container was found, an error will be raised. - # There is a special value for ID, which is "default". The "default" value indicates the quality should be set - # to whatever the machine definition specifies as "preferred" container, or a fallback value. See findDefaultQuality - # for details. - # - # \param new_quality_id The ID of the new quality container. - # - # \throws Exceptions.InvalidContainerError Raised when no container could be found with the specified ID. - def setQualityById(self, new_quality_id: str) -> None: - quality = self._empty_quality - if new_quality_id == "default": - new_quality = self.findDefaultQuality() - if new_quality: - quality = new_quality - else: - qualities = ContainerRegistry.getInstance().findInstanceContainers(id = new_quality_id) - if qualities: - quality = qualities[0] - else: - raise Exceptions.InvalidContainerError("Could not find container with id {id}".format(id = new_quality_id)) - - self.setQuality(quality) - ## Get the quality container. # # \return The quality container. Should always be a valid container, but can be equal to the empty InstanceContainer. @@ -148,31 +109,6 @@ class CuraContainerStack(ContainerStack): def setMaterial(self, new_material: InstanceContainer, postpone_emit = False) -> None: self.replaceContainer(_ContainerIndexes.Material, new_material, postpone_emit = postpone_emit) - ## Set the material container by an ID. - # - # This will search for the specified container and set it. If no container was found, an error will be raised. - # There is a special value for ID, which is "default". The "default" value indicates the quality should be set - # to whatever the machine definition specifies as "preferred" container, or a fallback value. See findDefaultMaterial - # for details. - # - # \param new_material_id The ID of the new material container. - # - # \throws Exceptions.InvalidContainerError Raised when no container could be found with the specified ID. - def setMaterialById(self, new_material_id: str) -> None: - material = self._empty_material - if new_material_id == "default": - new_material = self.findDefaultMaterial() - if new_material: - material = new_material - else: - materials = ContainerRegistry.getInstance().findInstanceContainers(id = new_material_id) - if materials: - material = materials[0] - else: - raise Exceptions.InvalidContainerError("Could not find container with id {id}".format(id = new_material_id)) - - self.setMaterial(material) - ## Get the material container. # # \return The material container. Should always be a valid container, but can be equal to the empty InstanceContainer. @@ -186,31 +122,6 @@ class CuraContainerStack(ContainerStack): def setVariant(self, new_variant: InstanceContainer) -> None: self.replaceContainer(_ContainerIndexes.Variant, new_variant) - ## Set the variant container by an ID. - # - # This will search for the specified container and set it. If no container was found, an error will be raised. - # There is a special value for ID, which is "default". The "default" value indicates the quality should be set - # to whatever the machine definition specifies as "preferred" container, or a fallback value. See findDefaultVariant - # for details. - # - # \param new_variant_id The ID of the new variant container. - # - # \throws Exceptions.InvalidContainerError Raised when no container could be found with the specified ID. - def setVariantById(self, new_variant_id: str) -> None: - variant = self._empty_variant - if new_variant_id == "default": - new_variant = self.findDefaultVariantBuildplate() if self.getMetaDataEntry("type") == "machine" else self.findDefaultVariant() - if new_variant: - variant = new_variant - else: - variants = ContainerRegistry.getInstance().findInstanceContainers(id = new_variant_id) - if variants: - variant = variants[0] - else: - raise Exceptions.InvalidContainerError("Could not find container with id {id}".format(id = new_variant_id)) - - self.setVariant(variant) - ## Get the variant container. # # \return The variant container. Should always be a valid container, but can be equal to the empty InstanceContainer. @@ -224,18 +135,6 @@ class CuraContainerStack(ContainerStack): def setDefinitionChanges(self, new_definition_changes: InstanceContainer) -> None: self.replaceContainer(_ContainerIndexes.DefinitionChanges, new_definition_changes) - ## Set the definition changes container by an ID. - # - # \param new_definition_changes_id The ID of the new definition changes container. - # - # \throws Exceptions.InvalidContainerError Raised when no container could be found with the specified ID. - def setDefinitionChangesById(self, new_definition_changes_id: str) -> None: - new_definition_changes = ContainerRegistry.getInstance().findInstanceContainers(id = new_definition_changes_id) - if new_definition_changes: - self.setDefinitionChanges(new_definition_changes[0]) - else: - raise Exceptions.InvalidContainerError("Could not find container with id {id}".format(id = new_definition_changes_id)) - ## Get the definition changes container. # # \return The definition changes container. Should always be a valid container, but can be equal to the empty InstanceContainer. @@ -249,18 +148,6 @@ class CuraContainerStack(ContainerStack): def setDefinition(self, new_definition: DefinitionContainerInterface) -> None: self.replaceContainer(_ContainerIndexes.Definition, new_definition) - ## Set the definition container by an ID. - # - # \param new_definition_id The ID of the new definition container. - # - # \throws Exceptions.InvalidContainerError Raised when no container could be found with the specified ID. - def setDefinitionById(self, new_definition_id: str) -> None: - new_definition = ContainerRegistry.getInstance().findDefinitionContainers(id = new_definition_id) - if new_definition: - self.setDefinition(new_definition[0]) - else: - raise Exceptions.InvalidContainerError("Could not find container with id {id}".format(id = new_definition_id)) - ## Get the definition container. # # \return The definition container. Should always be a valid container, but can be equal to the empty InstanceContainer. @@ -348,6 +235,10 @@ class CuraContainerStack(ContainerStack): elif container != self._empty_instance_container and container.getMetaDataEntry("type") != expected_type: raise Exceptions.InvalidContainerError("Cannot replace container at index {index} with a container that is not of {type} type, but {actual_type} type.".format(index = index, type = expected_type, actual_type = container.getMetaDataEntry("type"))) + current_container = self._containers[index] + if current_container.getId() == container.getId(): + return + super().replaceContainer(index, container, postpone_emit) ## Overridden from ContainerStack @@ -391,243 +282,6 @@ class CuraContainerStack(ContainerStack): self._containers = new_containers - ## Find the variant that should be used as "default" variant. - # - # This will search for variants that match the current definition and pick the preferred one, - # if specified by the machine definition. - # - # The following criteria are used to find the default variant: - # - If the machine definition does not have a metadata entry "has_variants" set to True, return None - # - The definition of the variant should be the same as the machine definition for this stack. - # - The container should have a metadata entry "type" with value "variant". - # - If the machine definition has a metadata entry "preferred_variant", filter the variant IDs based on that. - # - # \return The container that should be used as default, or None if nothing was found or the machine does not use variants. - # - # \note This method assumes the stack has a valid machine definition. - def findDefaultVariant(self) -> Optional[ContainerInterface]: - definition = self._getMachineDefinition() - # has_variants can be overridden in other containers and stacks. - # In the case of UM2, it is overridden in the GlobalStack - if not self.getMetaDataEntry("has_variants"): - # If the machine does not use variants, we should never set a variant. - return None - - # First add any variant. Later, overwrite with preference if the preference is valid. - variant = None - definition_id = self._findInstanceContainerDefinitionId(definition) - variants = ContainerRegistry.getInstance().findInstanceContainers(definition = definition_id, type = "variant") - if variants: - variant = variants[0] - - preferred_variant_id = definition.getMetaDataEntry("preferred_variant") - if preferred_variant_id: - preferred_variants = ContainerRegistry.getInstance().findInstanceContainers(id = preferred_variant_id, definition = definition_id, type = "variant") - if preferred_variants: - variant = preferred_variants[0] - else: - Logger.log("w", "The preferred variant \"{variant}\" of stack {stack} does not exist or is not a variant.", variant = preferred_variant_id, stack = self.id) - # And leave it at the default variant. - - if variant: - return variant - - Logger.log("w", "Could not find a valid default variant for stack {stack}", stack = self.id) - return None - - ## Find the global variant that should be used as "default". This is used for the buildplates. - # - # This will search for variants that match the current definition and pick the preferred one, - # if specified by the machine definition. - # - # The following criteria are used to find the default global variant: - # - If the machine definition does not have a metadata entry "has_variant_buildplates" set to True, return None - # - The definition of the variant should be the same as the machine definition for this stack. - # - The container should have a metadata entry "type" with value "variant" and "hardware_type" with value "buildplate". - # - If the machine definition has a metadata entry "preferred_variant_buildplate", filter the variant IDs based on that. - # - # \return The container that should be used as default, or None if nothing was found or the machine does not use variants. - # - # \note This method assumes the stack has a valid machine definition. - def findDefaultVariantBuildplate(self) -> Optional[ContainerInterface]: - definition = self._getMachineDefinition() - # has_variant_buildplates can be overridden in other containers and stacks. - # In the case of UM2, it is overridden in the GlobalStack - if not self.getMetaDataEntry("has_variant_buildplates"): - # If the machine does not use variants, we should never set a variant. - return None - - # First add any variant. Later, overwrite with preference if the preference is valid. - variant = None - definition_id = self._findInstanceContainerDefinitionId(definition) - variants = ContainerRegistry.getInstance().findInstanceContainers(definition = definition_id, type = "variant", hardware_type = "buildplate") - if variants: - variant = variants[0] - - preferred_variant_buildplate_id = definition.getMetaDataEntry("preferred_variant_buildplate") - if preferred_variant_buildplate_id: - preferred_variant_buildplates = ContainerRegistry.getInstance().findInstanceContainers(id = preferred_variant_buildplate_id, definition = definition_id, type = "variant") - if preferred_variant_buildplates: - variant = preferred_variant_buildplates[0] - else: - Logger.log("w", "The preferred variant buildplate \"{variant}\" of stack {stack} does not exist or is not a variant.", - variant = preferred_variant_buildplate_id, stack = self.id) - # And leave it at the default variant. - - if variant: - return variant - - Logger.log("w", "Could not find a valid default buildplate variant for stack {stack}", stack = self.id) - return None - - ## Find the material that should be used as "default" material. - # - # This will search for materials that match the current definition and pick the preferred one, - # if specified by the machine definition. - # - # The following criteria are used to find the default material: - # - If the machine definition does not have a metadata entry "has_materials" set to True, return None - # - If the machine definition has a metadata entry "has_machine_materials", the definition of the material should - # be the same as the machine definition for this stack. Otherwise, the definition should be "fdmprinter". - # - The container should have a metadata entry "type" with value "material". - # - The material should have an approximate diameter that matches the machine - # - If the machine definition has a metadata entry "has_variants" and set to True, the "variant" metadata entry of - # the material should be the same as the ID of the variant in the stack. Only applies if "has_machine_materials" is also True. - # - If the stack currently has a material set, try to find a material that matches the current material by name. - # - Otherwise, if the machine definition has a metadata entry "preferred_material", try to find a material that matches the specified ID. - # - # \return The container that should be used as default, or None if nothing was found or the machine does not use materials. - def findDefaultMaterial(self) -> Optional[ContainerInterface]: - definition = self._getMachineDefinition() - if not definition.getMetaDataEntry("has_materials"): - # Machine does not use materials, never try to set it. - return None - - search_criteria = {"type": "material"} - if definition.getMetaDataEntry("has_machine_materials"): - search_criteria["definition"] = self._findInstanceContainerDefinitionId(definition) - - if definition.getMetaDataEntry("has_variants"): - search_criteria["variant"] = self.variant.id - else: - search_criteria["definition"] = "fdmprinter" - - if self.material != self._empty_material: - search_criteria["name"] = self.material.name - else: - preferred_material = definition.getMetaDataEntry("preferred_material") - if preferred_material: - search_criteria["id"] = preferred_material - - approximate_material_diameter = str(round(self.getProperty("material_diameter", "value"))) - search_criteria["approximate_diameter"] = approximate_material_diameter - - materials = ContainerRegistry.getInstance().findInstanceContainers(**search_criteria) - if not materials: - Logger.log("w", "The preferred material \"{material}\" could not be found for stack {stack}", material = preferred_material, stack = self.id) - # We failed to find any materials matching the specified criteria, drop some specific criteria and try to find - # a material that sort-of matches what we want. - search_criteria.pop("variant", None) - search_criteria.pop("id", None) - search_criteria.pop("name", None) - materials = ContainerRegistry.getInstance().findInstanceContainers(**search_criteria) - - if not materials: - Logger.log("w", "Could not find a valid material for stack {stack}", stack = self.id) - return None - - for material in materials: - # Prefer a read-only material - if ContainerRegistry.getInstance().isReadOnly(material.getId()): - return material - - return materials[0] - - - ## Find the quality that should be used as "default" quality. - # - # This will search for qualities that match the current definition and pick the preferred one, - # if specified by the machine definition. - # - # \return The container that should be used as default, or None if nothing was found. - def findDefaultQuality(self) -> Optional[ContainerInterface]: - definition = self._getMachineDefinition() - registry = ContainerRegistry.getInstance() - material_container = self.material if self.material.getId() not in (self._empty_material.getId(), self._empty_instance_container.getId()) else None - - search_criteria = {"type": "quality"} - - if definition.getMetaDataEntry("has_machine_quality"): - search_criteria["definition"] = self._findInstanceContainerDefinitionId(definition) - - if definition.getMetaDataEntry("has_materials") and material_container: - search_criteria["material"] = material_container.id - else: - search_criteria["definition"] = "fdmprinter" - - if self.quality != self._empty_quality: - search_criteria["name"] = self.quality.name - else: - preferred_quality = definition.getMetaDataEntry("preferred_quality") - if preferred_quality: - search_criteria["id"] = preferred_quality - - containers = registry.findInstanceContainers(**search_criteria) - if containers: - return containers[0] - - if "material" in search_criteria: - # First check if we can solve our material not found problem by checking if we can find quality containers - # that are assigned to the parents of this material profile. - try: - inherited_files = material_container.getInheritedFiles() - except AttributeError: # Material_container does not support inheritance. - inherited_files = [] - - if inherited_files: - for inherited_file in inherited_files: - # Extract the ID from the path we used to load the file. - search_criteria["material"] = os.path.basename(inherited_file).split(".")[0] - containers = registry.findInstanceContainers(**search_criteria) - if containers: - return containers[0] - - # We still weren't able to find a quality for this specific material. - # Try to find qualities for a generic version of the material. - material_search_criteria = {"type": "material", "material": material_container.getMetaDataEntry("material"), "color_name": "Generic"} - if definition.getMetaDataEntry("has_machine_quality"): - if self.material != self._empty_instance_container: - material_search_criteria["definition"] = material_container.getMetaDataEntry("definition") - - if definition.getMetaDataEntry("has_variants"): - material_search_criteria["variant"] = material_container.getMetaDataEntry("variant") - else: - material_search_criteria["definition"] = self._findInstanceContainerDefinitionId(definition) - - if definition.getMetaDataEntry("has_variants") and self.variant != self._empty_instance_container: - material_search_criteria["variant"] = self.variant.id - else: - material_search_criteria["definition"] = "fdmprinter" - material_containers = registry.findInstanceContainersMetadata(**material_search_criteria) - # Try all materials to see if there is a quality profile available. - for material_container in material_containers: - search_criteria["material"] = material_container["id"] - - containers = registry.findInstanceContainers(**search_criteria) - if containers: - return containers[0] - - if "name" in search_criteria or "id" in search_criteria: - # If a quality by this name can not be found, try a wider set of search criteria - search_criteria.pop("name", None) - search_criteria.pop("id", None) - - containers = registry.findInstanceContainers(**search_criteria) - if containers: - return containers[0] - - return None - ## protected: # Helper to make sure we emit a PyQt signal on container changes. diff --git a/cura/Settings/CuraStackBuilder.py b/cura/Settings/CuraStackBuilder.py index 608a13c600..a8234b9de9 100644 --- a/cura/Settings/CuraStackBuilder.py +++ b/cura/Settings/CuraStackBuilder.py @@ -1,15 +1,18 @@ -# Copyright (c) 2017 Ultimaker B.V. +# Copyright (c) 2018 Ultimaker B.V. # Cura is released under the terms of the LGPLv3 or higher. -from UM.Logger import Logger +from typing import Optional +from UM.Logger import Logger from UM.Settings.Interfaces import DefinitionContainerInterface from UM.Settings.InstanceContainer import InstanceContainer from UM.Settings.ContainerRegistry import ContainerRegistry +from UM.Settings.SettingFunction import SettingFunction +from UM.Util import parseBool +from cura.Machines.VariantManager import VariantType from .GlobalStack import GlobalStack from .ExtruderStack import ExtruderStack -from typing import Optional ## Contains helper functions to create new machines. @@ -22,7 +25,13 @@ class CuraStackBuilder: # \return The new global stack or None if an error occurred. @classmethod def createMachine(cls, name: str, definition_id: str) -> Optional[GlobalStack]: + from cura.CuraApplication import CuraApplication + application = CuraApplication.getInstance() + variant_manager = application.getVariantManager() + material_manager = application.getMaterialManager() + quality_manager = application.getQualityManager() registry = ContainerRegistry.getInstance() + definitions = registry.findDefinitionContainers(id = definition_id) if not definitions: Logger.log("w", "Definition {definition} was not found!", definition = definition_id) @@ -30,7 +39,21 @@ class CuraStackBuilder: machine_definition = definitions[0] - generated_name = registry.createUniqueName("machine", "", name, machine_definition.name) + # get variant container for the global stack + global_variant_container = application.empty_variant_container + global_variant_node = variant_manager.getDefaultVariantNode(machine_definition, VariantType.BUILD_PLATE) + if global_variant_node: + global_variant_container = global_variant_node.getContainer() + + # get variant container for extruders + extruder_variant_container = application.empty_variant_container + extruder_variant_node = variant_manager.getDefaultVariantNode(machine_definition, VariantType.NOZZLE) + extruder_variant_name = None + if extruder_variant_node: + extruder_variant_container = extruder_variant_node.getContainer() + extruder_variant_name = extruder_variant_container.getName() + + generated_name = registry.createUniqueName("machine", "", name, machine_definition.getName()) # Make sure the new name does not collide with any definition or (quality) profile # createUniqueName() only looks at other stacks, but not at definitions or quality profiles # Note that we don't go for uniqueName() immediately because that function matches with ignore_case set to true @@ -40,49 +63,55 @@ class CuraStackBuilder: new_global_stack = cls.createGlobalStack( new_stack_id = generated_name, definition = machine_definition, - quality = "default", - material = "default", - variant = "default", + variant_container = global_variant_container, + material_container = application.empty_material_container, + quality_container = application.empty_quality_container, ) - new_global_stack.setName(generated_name) - extruder_definition = registry.findDefinitionContainers(machine = machine_definition.getId()) + # get material container for extruders + material_container = application.empty_material_container + material_node = material_manager.getDefaultMaterial(new_global_stack, extruder_variant_name) + if material_node: + material_container = material_node.getContainer() - if not extruder_definition: - # create extruder stack for single extrusion machines that have no separate extruder definition files - extruder_definition = registry.findDefinitionContainers(id = "fdmextruder")[0] - new_extruder_id = registry.uniqueName(machine_definition.getName() + " " + extruder_definition.id) + # Create ExtruderStacks + extruder_dict = machine_definition.getMetaDataEntry("machine_extruder_trains") + + for position, extruder_definition_id in extruder_dict.items(): + # Sanity check: make sure that the positions in the extruder definitions are same as in the machine + # definition + extruder_definition = registry.findDefinitionContainers(id = extruder_definition_id)[0] + position_in_extruder_def = extruder_definition.getMetaDataEntry("position") + if position_in_extruder_def != position: + raise RuntimeError("Extruder position [%s] defined in extruder definition [%s] is not the same as in machine definition [%s] position [%s]" % + (position_in_extruder_def, extruder_definition_id, definition_id, position)) + + new_extruder_id = registry.uniqueName(extruder_definition_id) new_extruder = cls.createExtruderStack( new_extruder_id, - definition = extruder_definition, - machine_definition_id = machine_definition.getId(), - quality = "default", - material = "default", - variant = "default", - next_stack = new_global_stack + extruder_definition = extruder_definition, + machine_definition_id = definition_id, + position = position, + variant_container = extruder_variant_container, + material_container = material_container, + quality_container = application.empty_quality_container, + global_stack = new_global_stack, ) + new_extruder.setNextStack(new_global_stack) new_global_stack.addExtruder(new_extruder) registry.addContainer(new_extruder) - else: - # create extruder stack for each found extruder definition - for extruder_definition in registry.findDefinitionContainers(machine = machine_definition.id): - position = extruder_definition.getMetaDataEntry("position", None) - if not position: - Logger.log("w", "Extruder definition %s specifies no position metadata entry.", extruder_definition.id) - new_extruder_id = registry.uniqueName(extruder_definition.id) - new_extruder = cls.createExtruderStack( - new_extruder_id, - definition = extruder_definition, - machine_definition_id = machine_definition.getId(), - quality = "default", - material = "default", - variant = "default", - next_stack = new_global_stack - ) - new_global_stack.addExtruder(new_extruder) - registry.addContainer(new_extruder) + preferred_quality_type = machine_definition.getMetaDataEntry("preferred_quality_type") + quality_group_dict = quality_manager.getQualityGroups(new_global_stack) + quality_group = quality_group_dict.get(preferred_quality_type) + + new_global_stack.quality = quality_group.node_for_global.getContainer() + for position, extruder_stack in new_global_stack.extruders.items(): + if position in quality_group.nodes_for_extruders: + extruder_stack.quality = quality_group.nodes_for_extruders[position].getContainer() + else: + extruder_stack.quality = application.empty_quality_container # Register the global stack after the extruder stacks are created. This prevents the registry from adding another # extruder stack because the global stack didn't have one yet (which is enforced since Cura 3.1). @@ -100,43 +129,27 @@ class CuraStackBuilder: # # \return A new Global stack instance with the specified parameters. @classmethod - def createExtruderStack(cls, new_stack_id: str, definition: DefinitionContainerInterface, machine_definition_id: str, **kwargs) -> ExtruderStack: - stack = ExtruderStack(new_stack_id) - stack.setName(definition.getName()) - stack.setDefinition(definition) - stack.addMetaDataEntry("position", definition.getMetaDataEntry("position")) - - if "next_stack" in kwargs: - # Add stacks before containers are added, since they may trigger a setting update. - stack.setNextStack(kwargs["next_stack"]) - - user_container = InstanceContainer(new_stack_id + "_user") - user_container.addMetaDataEntry("type", "user") - user_container.addMetaDataEntry("extruder", new_stack_id) + def createExtruderStack(cls, new_stack_id: str, extruder_definition: DefinitionContainerInterface, machine_definition_id: str, + position: int, + variant_container, material_container, quality_container, global_stack) -> ExtruderStack: from cura.CuraApplication import CuraApplication - user_container.addMetaDataEntry("setting_version", CuraApplication.SettingVersion) - user_container.setDefinition(machine_definition_id) + application = CuraApplication.getInstance() - stack.setUserChanges(user_container) + stack = ExtruderStack(new_stack_id, parent = global_stack) + stack.setName(extruder_definition.getName()) + stack.setDefinition(extruder_definition) - # Important! The order here matters, because that allows the stack to - # assume the material and variant have already been set. - if "definition_changes" in kwargs: - stack.setDefinitionChangesById(kwargs["definition_changes"]) - else: - stack.setDefinitionChanges(cls.createDefinitionChangesContainer(stack, new_stack_id + "_settings")) + stack.addMetaDataEntry("position", position) - if "variant" in kwargs: - stack.setVariantById(kwargs["variant"]) + user_container = cls.createUserChangesContainer(new_stack_id + "_user", machine_definition_id, new_stack_id, + is_global_stack = False) - if "material" in kwargs: - stack.setMaterialById(kwargs["material"]) - - if "quality" in kwargs: - stack.setQualityById(kwargs["quality"]) - - if "quality_changes" in kwargs: - stack.setQualityChangesById(kwargs["quality_changes"]) + stack.definitionChanges = cls.createDefinitionChangesContainer(stack, new_stack_id + "_settings") + stack.variant = variant_container + stack.material = material_container + stack.quality = quality_container + stack.qualityChanges = application.empty_quality_changes_container + stack.userChanges = user_container # Only add the created containers to the registry after we have set all the other # properties. This makes the create operation more transactional, since any problems @@ -153,44 +166,48 @@ class CuraStackBuilder: # # \return A new Global stack instance with the specified parameters. @classmethod - def createGlobalStack(cls, new_stack_id: str, definition: DefinitionContainerInterface, **kwargs) -> GlobalStack: + def createGlobalStack(cls, new_stack_id: str, definition: DefinitionContainerInterface, + variant_container, material_container, quality_container) -> GlobalStack: + from cura.CuraApplication import CuraApplication + application = CuraApplication.getInstance() + stack = GlobalStack(new_stack_id) stack.setDefinition(definition) - user_container = InstanceContainer(new_stack_id + "_user") - user_container.addMetaDataEntry("type", "user") - user_container.addMetaDataEntry("machine", new_stack_id) - from cura.CuraApplication import CuraApplication - user_container.addMetaDataEntry("setting_version", CuraApplication.SettingVersion) - user_container.setDefinition(definition.getId()) + # Create user container + user_container = cls.createUserChangesContainer(new_stack_id + "_user", definition.getId(), new_stack_id, + is_global_stack = True) - stack.setUserChanges(user_container) - - # Important! The order here matters, because that allows the stack to - # assume the material and variant have already been set. - if "definition_changes" in kwargs: - stack.setDefinitionChangesById(kwargs["definition_changes"]) - else: - stack.setDefinitionChanges(cls.createDefinitionChangesContainer(stack, new_stack_id + "_settings")) - - if "variant" in kwargs: - stack.setVariantById(kwargs["variant"]) - - if "material" in kwargs: - stack.setMaterialById(kwargs["material"]) - - if "quality" in kwargs: - stack.setQualityById(kwargs["quality"]) - - if "quality_changes" in kwargs: - stack.setQualityChangesById(kwargs["quality_changes"]) + stack.definitionChanges = cls.createDefinitionChangesContainer(stack, new_stack_id + "_settings") + stack.variant = variant_container + stack.material = material_container + stack.quality = quality_container + stack.qualityChanges = application.empty_quality_changes_container + stack.userChanges = user_container ContainerRegistry.getInstance().addContainer(user_container) return stack @classmethod - def createDefinitionChangesContainer(cls, container_stack, container_name, container_index = None): + def createUserChangesContainer(cls, container_name: str, definition_id: str, stack_id: str, + is_global_stack: bool) -> "InstanceContainer": + from cura.CuraApplication import CuraApplication + + unique_container_name = ContainerRegistry.getInstance().uniqueName(container_name) + + container = InstanceContainer(unique_container_name) + container.setDefinition(definition_id) + container.addMetaDataEntry("type", "user") + container.addMetaDataEntry("setting_version", CuraApplication.SettingVersion) + + metadata_key_to_add = "machine" if is_global_stack else "extruder" + container.addMetaDataEntry(metadata_key_to_add, stack_id) + + return container + + @classmethod + def createDefinitionChangesContainer(cls, container_stack, container_name): from cura.CuraApplication import CuraApplication unique_container_name = ContainerRegistry.getInstance().uniqueName(container_name) diff --git a/cura/Settings/ExtruderManager.py b/cura/Settings/ExtruderManager.py index 35b5b1320b..06342b68e5 100755 --- a/cura/Settings/ExtruderManager.py +++ b/cura/Settings/ExtruderManager.py @@ -12,6 +12,7 @@ from UM.Scene.Selection import Selection from UM.Scene.Iterator.BreadthFirstIterator import BreadthFirstIterator from UM.Settings.ContainerRegistry import ContainerRegistry # Finding containers by ID. from UM.Settings.SettingFunction import SettingFunction +from UM.Settings.SettingInstance import SettingInstance from UM.Settings.ContainerStack import ContainerStack from UM.Settings.PropertyEvaluationContext import PropertyEvaluationContext from typing import Optional, List, TYPE_CHECKING, Union @@ -30,28 +31,22 @@ class ExtruderManager(QObject): def __init__(self, parent = None): super().__init__(parent) + self._application = Application.getInstance() + self._extruder_trains = {} # Per machine, a dictionary of extruder container stack IDs. Only for separately defined extruders. self._active_extruder_index = -1 # Indicates the index of the active extruder stack. -1 means no active extruder stack self._selected_object_extruders = [] - self._global_container_stack_definition_id = None self._addCurrentMachineExtruders() - Application.getInstance().globalContainerStackChanged.connect(self.__globalContainerStackChanged) + #Application.getInstance().globalContainerStackChanged.connect(self._globalContainerStackChanged) Selection.selectionChanged.connect(self.resetSelectedObjectExtruders) ## Signal to notify other components when the list of extruders for a machine definition changes. extrudersChanged = pyqtSignal(QVariant) - ## Signal to notify other components when the global container stack is switched to a definition - # that has different extruders than the previous global container stack - globalContainerStackDefinitionChanged = pyqtSignal() - ## Notify when the user switches the currently active extruder. activeExtruderChanged = pyqtSignal() - ## The signal notifies subscribers if extruders are added - extrudersAdded = pyqtSignal() - ## Gets the unique identifier of the currently active extruder stack. # # The currently active extruder stack is the stack that is currently being @@ -184,6 +179,7 @@ class ExtruderManager(QObject): self._selected_object_extruders = [] self.selectedObjectExtrudersChanged.emit() + @pyqtSlot(result = QObject) def getActiveExtruderStack(self) -> Optional["ExtruderStack"]: global_container_stack = Application.getInstance().getGlobalContainerStack() @@ -371,12 +367,7 @@ class ExtruderManager(QObject): return result[:machine_extruder_count] - def __globalContainerStackChanged(self) -> None: - global_container_stack = Application.getInstance().getGlobalContainerStack() - if global_container_stack and global_container_stack.getBottom() and global_container_stack.getBottom().getId() != self._global_container_stack_definition_id: - self._global_container_stack_definition_id = global_container_stack.getBottom().getId() - self.globalContainerStackDefinitionChanged.emit() - + def _globalContainerStackChanged(self) -> None: # If the global container changed, the machine changed and might have extruders that were not registered yet self._addCurrentMachineExtruders() @@ -384,7 +375,7 @@ class ExtruderManager(QObject): ## Adds the extruders of the currently active machine. def _addCurrentMachineExtruders(self) -> None: - global_stack = Application.getInstance().getGlobalContainerStack() + global_stack = self._application.getGlobalContainerStack() extruders_changed = False if global_stack: @@ -404,20 +395,82 @@ class ExtruderManager(QObject): self._extruder_trains[global_stack_id][extruder_train.getMetaDataEntry("position")] = extruder_train # regardless of what the next stack is, we have to set it again, because of signal routing. ??? + extruder_train.setParent(global_stack) extruder_train.setNextStack(global_stack) extruders_changed = True - # FIX: We have to remove those settings here because we know that those values have been copied to all - # the extruders at this point. - for key in ("material_diameter", "machine_nozzle_size"): - if global_stack.definitionChanges.hasProperty(key, "value"): - global_stack.definitionChanges.removeInstance(key, postpone_emit = True) - + self._fixMaterialDiameterAndNozzleSize(global_stack, extruder_trains) if extruders_changed: self.extrudersChanged.emit(global_stack_id) - self.extrudersAdded.emit() self.setActiveExtruderIndex(0) + # + # This function tries to fix the problem with per-extruder-settable nozzle size and material diameter problems + # in early versions (3.0 - 3.2.1). + # + # In earlier versions, "nozzle size" and "material diameter" are only applicable to the complete machine, so all + # extruders share the same values. In this case, "nozzle size" and "material diameter" are saved in the + # GlobalStack's DefinitionChanges container. + # + # Later, we could have different "nozzle size" for each extruder, but "material diameter" could only be set for + # the entire machine. In this case, "nozzle size" should be saved in each ExtruderStack's DefinitionChanges, but + # "material diameter" still remains in the GlobalStack's DefinitionChanges. + # + # Lateer, both "nozzle size" and "material diameter" are settable per-extruder, and both settings should be saved + # in the ExtruderStack's DefinitionChanges. + # + # There were some bugs in upgrade so the data weren't saved correct as described above. This function tries fix + # this. + # + # One more thing is about material diameter and single-extrusion machines. Most single-extrusion machines don't + # specifically define their extruder definition, so they reuse "fdmextruder", but for those machines, they may + # define "material diameter = 1.75" in their machine definition, but in "fdmextruder", it's still "2.85". This + # causes a problem with incorrect default values. + # + # This is also fixed here in this way: If no "material diameter" is specified, it will look for the default value + # in both the Extruder's definition and the Global's definition. If 2 values don't match, we will use the value + # from the Global definition by setting it in the Extruder's DefinitionChanges container. + # + def _fixMaterialDiameterAndNozzleSize(self, global_stack, extruder_stack_list): + keys_to_copy = ["material_diameter", "machine_nozzle_size"] # these will be copied over to all extruders + + extruder_positions_to_update = set() + for extruder_stack in extruder_stack_list: + for key in keys_to_copy: + # Only copy the value when this extruder doesn't have the value. + if extruder_stack.definitionChanges.hasProperty(key, "value"): + continue + + setting_value_in_global_def_changes = global_stack.definitionChanges.getProperty(key, "value") + setting_value_in_global_def = global_stack.definition.getProperty(key, "value") + setting_value = setting_value_in_global_def + if setting_value_in_global_def_changes is not None: + setting_value = setting_value_in_global_def_changes + if setting_value == extruder_stack.definition.getProperty(key, "value"): + continue + + setting_definition = global_stack.getSettingDefinition(key) + new_instance = SettingInstance(setting_definition, extruder_stack.definitionChanges) + new_instance.setProperty("value", setting_value) + new_instance.resetState() # Ensure that the state is not seen as a user state. + extruder_stack.definitionChanges.addInstance(new_instance) + extruder_stack.definitionChanges.setDirty(True) + + # Make sure the material diameter is up to date for the extruder stack. + if key == "material_diameter": + position = int(extruder_stack.getMetaDataEntry("position")) + extruder_positions_to_update.add(position) + + # We have to remove those settings here because we know that those values have been copied to all + # the extruders at this point. + for key in keys_to_copy: + if global_stack.definitionChanges.hasProperty(key, "value"): + global_stack.definitionChanges.removeInstance(key, postpone_emit = True) + + # Update material diameter for extruders + for position in extruder_positions_to_update: + self.updateMaterialForDiameter(position, global_stack = global_stack) + ## Get all extruder values for a certain setting. # # This is exposed to SettingFunction so it can be used in value functions. @@ -503,10 +556,11 @@ class ExtruderManager(QObject): return ExtruderManager.getExtruderValues(key) ## Updates the material container to a material that matches the material diameter set for the printer - def updateMaterialForDiameter(self, extruder_position: int): - global_stack = Application.getInstance().getGlobalContainerStack() + def updateMaterialForDiameter(self, extruder_position: int, global_stack = None): if not global_stack: - return + global_stack = Application.getInstance().getGlobalContainerStack() + if not global_stack: + return if not global_stack.getMetaDataEntry("has_materials", False): return diff --git a/cura/Settings/ExtruderStack.py b/cura/Settings/ExtruderStack.py index 6f89d33393..4400f621c6 100644 --- a/cura/Settings/ExtruderStack.py +++ b/cura/Settings/ExtruderStack.py @@ -3,16 +3,16 @@ from typing import Any, TYPE_CHECKING, Optional -from UM.Application import Application +from PyQt5.QtCore import pyqtProperty + from UM.Decorators import override from UM.MimeTypeDatabase import MimeType, MimeTypeDatabase from UM.Settings.ContainerStack import ContainerStack from UM.Settings.ContainerRegistry import ContainerRegistry from UM.Settings.Interfaces import ContainerInterface, PropertyEvaluationContext -from UM.Settings.SettingInstance import SettingInstance from . import Exceptions -from .CuraContainerStack import CuraContainerStack +from .CuraContainerStack import CuraContainerStack, _ContainerIndexes from .ExtruderManager import ExtruderManager if TYPE_CHECKING: @@ -34,7 +34,7 @@ class ExtruderStack(CuraContainerStack): # # This will set the next stack and ensure that we register this stack as an extruder. @override(ContainerStack) - def setNextStack(self, stack: ContainerStack) -> None: + def setNextStack(self, stack: CuraContainerStack) -> None: super().setNextStack(stack) stack.addExtruder(self) self.addMetaDataEntry("machine", stack.id) @@ -42,75 +42,6 @@ class ExtruderStack(CuraContainerStack): # For backward compatibility: Register the extruder with the Extruder Manager ExtruderManager.getInstance().registerExtruder(self, stack.id) - # Now each machine will have at least one extruder stack. If this is the first extruder, the extruder-specific - # settings such as nozzle size and material diameter should be moved from the machine's definition_changes to - # the this extruder's definition_changes. - # - # We do this here because it is tooooo expansive to do it in the version upgrade: During the version upgrade, - # when we are upgrading a definition_changes container file, there is NO guarantee that other files such as - # machine an extruder stack files are upgraded before this, so we cannot read those files assuming they are in - # the latest format. - # - # MORE: - # For single-extrusion machines, nozzle size is saved in the global stack, so the nozzle size value should be - # carried to the first extruder. - # For material diameter, it was supposed to be applied to all extruders, so its value should be copied to all - # extruders. - - keys_to_copy = ["material_diameter", "machine_nozzle_size"] # these will be copied over to all extruders - - for key in keys_to_copy: - # Only copy the value when this extruder doesn't have the value. - if self.definitionChanges.hasProperty(key, "value"): - continue - - # WARNING: this might be very dangerous and should be refactored ASAP! - # - # We cannot add a setting definition of "material_diameter" into the extruder's definition at runtime - # because all other machines which uses "fdmextruder" as the extruder definition will be affected. - # - # The problem is that single extrusion machines have their default material diameter defined in the global - # definitions. Now we automatically create an extruder stack for those machines using "fdmextruder" - # definition, which doesn't have the specific "material_diameter" and "machine_nozzle_size" defined for - # each machine. This results in wrong values which can be found in the MachineSettings dialog. - # - # To solve this, we put "material_diameter" back into the "fdmextruder" definition because modifying it in - # the extruder definition will affect all machines which uses the "fdmextruder" definition. Moreover, now - # we also check the value defined in the machine definition. If present, the value defined in the global - # stack's definition changes container will be copied. Otherwise, we will check if the default values in the - # machine definition and the extruder definition are the same, and if not, the default value in the machine - # definition will be copied to the extruder stack's definition changes. - # - setting_value_in_global_def_changes = stack.definitionChanges.getProperty(key, "value") - setting_value_in_global_def = stack.definition.getProperty(key, "value") - setting_value = setting_value_in_global_def - if setting_value_in_global_def_changes is not None: - setting_value = setting_value_in_global_def_changes - if setting_value == self.definition.getProperty(key, "value"): - continue - - setting_definition = stack.getSettingDefinition(key) - new_instance = SettingInstance(setting_definition, self.definitionChanges) - new_instance.setProperty("value", setting_value) - new_instance.resetState() # Ensure that the state is not seen as a user state. - self.definitionChanges.addInstance(new_instance) - self.definitionChanges.setDirty(True) - - # Make sure the material diameter is up to date for the extruder stack. - if key == "material_diameter": - from cura.CuraApplication import CuraApplication - machine_manager = CuraApplication.getInstance().getMachineManager() - position = self.getMetaDataEntry("position", "0") - func = lambda p = position: CuraApplication.getInstance().getExtruderManager().updateMaterialForDiameter(p) - machine_manager.machine_extruder_material_update_dict[stack.getId()].append(func) - - # NOTE: We cannot remove the setting from the global stack's definition changes container because for - # material diameter, it needs to be applied to all extruders, but here we don't know how many extruders - # a machine actually has and how many extruders has already been loaded for that machine, so we have to - # keep this setting for any remaining extruders that haven't been loaded yet. - # - # Those settings will be removed in ExtruderManager which knows all those info. - @override(ContainerStack) def getNextStack(self) -> Optional["GlobalStack"]: return super().getNextStack() @@ -119,6 +50,29 @@ class ExtruderStack(CuraContainerStack): def getLoadingPriority(cls) -> int: return 3 + ## Return the filament diameter that the machine requires. + # + # If the machine has no requirement for the diameter, -1 is returned. + # \return The filament diameter for the printer + @property + def materialDiameter(self) -> float: + context = PropertyEvaluationContext(self) + context.context["evaluate_from_container_index"] = _ContainerIndexes.Variant + + return self.getProperty("material_diameter", "value", context = context) + + ## Return the approximate filament diameter that the machine requires. + # + # The approximate material diameter is the material diameter rounded to + # the nearest millimetre. + # + # If the machine has no requirement for the diameter, -1 is returned. + # + # \return The approximate filament diameter for the printer + @pyqtProperty(float) + def approximateMaterialDiameter(self) -> float: + return round(float(self.materialDiameter)) + ## Overridden from ContainerStack # # It will perform a few extra checks when trying to get properties. @@ -187,11 +141,6 @@ class ExtruderStack(CuraContainerStack): if has_global_dependencies: self.getNextStack().propertiesChanged.emit(key, properties) - def findDefaultVariant(self): - # The default variant is defined in the machine stack and/or definition, so use the machine stack to find - # the default variant. - return self.getNextStack().findDefaultVariant() - extruder_stack_mime = MimeType( name = "application/x-cura-extruderstack", diff --git a/cura/Settings/GlobalStack.py b/cura/Settings/GlobalStack.py index 6d18bf615b..ae1f1370ed 100755 --- a/cura/Settings/GlobalStack.py +++ b/cura/Settings/GlobalStack.py @@ -125,21 +125,6 @@ class GlobalStack(CuraContainerStack): def setNextStack(self, next_stack: ContainerStack) -> None: raise Exceptions.InvalidOperationError("Global stack cannot have a next stack!") - ## Gets the approximate filament diameter that the machine requires. - # - # The approximate material diameter is the material diameter rounded to - # the nearest millimetre. - # - # If the machine has no requirement for the diameter, -1 is returned. - # - # \return The approximate filament diameter for the printer, as a string. - @pyqtProperty(str) - def approximateMaterialDiameter(self) -> str: - material_diameter = self.definition.getProperty("material_diameter", "value") - if material_diameter is None: - return "-1" - return str(round(float(material_diameter))) #Round, then convert back to string. - # protected: # Determine whether or not we should try to get the "resolve" property instead of the diff --git a/cura/Settings/MachineManager.py b/cura/Settings/MachineManager.py index 6cdb9322b6..e357d778ca 100755 --- a/cura/Settings/MachineManager.py +++ b/cura/Settings/MachineManager.py @@ -12,23 +12,20 @@ from UM.Signal import Signal from PyQt5.QtCore import QObject, pyqtProperty, pyqtSignal, QTimer import UM.FlameProfiler from UM.FlameProfiler import pyqtSlot -from PyQt5.QtWidgets import QMessageBox from UM import Util from UM.Application import Application from UM.Preferences import Preferences from UM.Logger import Logger from UM.Message import Message -from UM.Decorators import deprecated from UM.Settings.ContainerRegistry import ContainerRegistry -from UM.Settings.ContainerStack import ContainerStack from UM.Settings.InstanceContainer import InstanceContainer from UM.Settings.SettingFunction import SettingFunction from UM.Signal import postponeSignals, CompressTechnique +from cura.Machines.QualityManager import getMachineDefinitionIDForQualitySearch -from cura.QualityManager import QualityManager from cura.PrinterOutputDevice import PrinterOutputDevice from cura.Settings.ExtruderManager import ExtruderManager @@ -37,28 +34,25 @@ from .CuraStackBuilder import CuraStackBuilder from UM.i18n import i18nCatalog catalog = i18nCatalog("cura") -from cura.Settings.ProfilesModel import ProfilesModel - if TYPE_CHECKING: - from UM.Settings.DefinitionContainer import DefinitionContainer from cura.Settings.CuraContainerStack import CuraContainerStack from cura.Settings.GlobalStack import GlobalStack class MachineManager(QObject): + def __init__(self, parent = None): super().__init__(parent) self._active_container_stack = None # type: CuraContainerStack self._global_container_stack = None # type: GlobalStack - self.machine_extruder_material_update_dict = collections.defaultdict(list) + self._current_root_material_id = {} + self._current_root_material_name = {} + self._current_quality_group = None + self._current_quality_changes_group = None - # Used to store the new containers until after confirming the dialog - self._new_variant_container = None # type: Optional[InstanceContainer] - self._new_buildplate_container = None # type: Optional[InstanceContainer] - self._new_material_container = None # type: Optional[InstanceContainer] - self._new_quality_containers = [] # type: List[Dict] + self.machine_extruder_material_update_dict = collections.defaultdict(list) self._error_check_timer = QTimer() self._error_check_timer.setInterval(250) @@ -70,15 +64,18 @@ class MachineManager(QObject): self._instance_container_timer.setSingleShot(True) self._instance_container_timer.timeout.connect(self.__emitChangedSignals) - Application.getInstance().globalContainerStackChanged.connect(self._onGlobalContainerChanged) - Application.getInstance().getContainerRegistry().containerLoadComplete.connect(self._onInstanceContainersChanged) - self._connected_to_profiles_model = False + self._application = Application.getInstance() + self._application.globalContainerStackChanged.connect(self._onGlobalContainerChanged) + self._application.getContainerRegistry().containerLoadComplete.connect(self._onInstanceContainersChanged) ## When the global container is changed, active material probably needs to be updated. self.globalContainerChanged.connect(self.activeMaterialChanged) self.globalContainerChanged.connect(self.activeVariantChanged) self.globalContainerChanged.connect(self.activeQualityChanged) + self.globalContainerChanged.connect(self.activeQualityChangesGroupChanged) + self.globalContainerChanged.connect(self.activeQualityGroupChanged) + self._stacks_have_errors = None # type:Optional[bool] self._empty_definition_changes_container = ContainerRegistry.getInstance().findContainers(id = "empty_definition_changes")[0] @@ -101,28 +98,16 @@ class MachineManager(QObject): ExtruderManager.getInstance().activeExtruderChanged.connect(self.activeStackChanged) self.activeStackChanged.connect(self.activeStackValueChanged) - # when a user closed dialog check if any delayed material or variant changes need to be applied - Application.getInstance().onDiscardOrKeepProfileChangesClosed.connect(self._executeDelayedActiveContainerStackChanges) - Preferences.getInstance().addPreference("cura/active_machine", "") self._global_event_keys = set() - active_machine_id = Preferences.getInstance().getValue("cura/active_machine") - self._printer_output_devices = [] Application.getInstance().getOutputDeviceManager().outputDevicesChanged.connect(self._onOutputDevicesChanged) # There might already be some output devices by the time the signal is connected self._onOutputDevicesChanged() - if active_machine_id != "" and ContainerRegistry.getInstance().findContainerStacksMetadata(id = active_machine_id): - # An active machine was saved, so restore it. - self.setActiveMachine(active_machine_id) - # Make sure _active_container_stack is properly initiated - ExtruderManager.getInstance().setActiveExtruderIndex(0) - - self._auto_materials_changed = {} - self._auto_hotends_changed = {} + self._application.callLater(self.setInitialActiveMachine) self._material_incompatible_message = Message(catalog.i18nc("@info:status", "The selected material is incompatible with the selected machine or configuration."), @@ -132,6 +117,16 @@ class MachineManager(QObject): if containers: containers[0].nameChanged.connect(self._onMaterialNameChanged) + self._material_manager = self._application._material_manager + self._quality_manager = self._application.getQualityManager() + + # When the materials lookup table gets updated, it can mean that a material has its name changed, which should + # be reflected on the GUI. This signal emission makes sure that it happens. + self._material_manager.materialsUpdated.connect(self.rootMaterialChanged) + + activeQualityGroupChanged = pyqtSignal() + activeQualityChangesGroupChanged = pyqtSignal() + globalContainerChanged = pyqtSignal() # Emitted whenever the global stack is changed (ie: when changing between printers, changing a global profile, but not when changing a value) activeMaterialChanged = pyqtSignal() activeVariantChanged = pyqtSignal() @@ -147,32 +142,24 @@ class MachineManager(QObject): outputDevicesChanged = pyqtSignal() - def _onOutputDevicesChanged(self) -> None: - for printer_output_device in self._printer_output_devices: - printer_output_device.hotendIdChanged.disconnect(self._onHotendIdChanged) - printer_output_device.materialIdChanged.disconnect(self._onMaterialIdChanged) + rootMaterialChanged = pyqtSignal() + def setInitialActiveMachine(self): + active_machine_id = Preferences.getInstance().getValue("cura/active_machine") + if active_machine_id != "" and ContainerRegistry.getInstance().findContainerStacksMetadata(id = active_machine_id): + # An active machine was saved, so restore it. + self.setActiveMachine(active_machine_id) + # Make sure _active_container_stack is properly initiated + ExtruderManager.getInstance().setActiveExtruderIndex(0) + + def _onOutputDevicesChanged(self) -> None: self._printer_output_devices = [] for printer_output_device in Application.getInstance().getOutputDeviceManager().getOutputDevices(): if isinstance(printer_output_device, PrinterOutputDevice): self._printer_output_devices.append(printer_output_device) - printer_output_device.hotendIdChanged.connect(self._onHotendIdChanged) - printer_output_device.materialIdChanged.connect(self._onMaterialIdChanged) self.outputDevicesChanged.emit() - @property - def newVariant(self): - return self._new_variant_container - - @property - def newBuildplate(self): - return self._new_buildplate_container - - @property - def newMaterial(self): - return self._new_material_container - @pyqtProperty("QVariantList", notify = outputDevicesChanged) def printerOutputDevices(self): return self._printer_output_devices @@ -181,114 +168,6 @@ class MachineManager(QObject): def totalNumberOfSettings(self) -> int: return len(ContainerRegistry.getInstance().findDefinitionContainers(id = "fdmprinter")[0].getAllKeys()) - def _onHotendIdChanged(self) -> None: - if not self._global_container_stack or not self._printer_output_devices: - return - - active_printer_model = self._printer_output_devices[0].activePrinter - if not active_printer_model: - return - - change_found = False - machine_id = self.activeMachineId - extruders = sorted(ExtruderManager.getInstance().getMachineExtruders(machine_id), - key=lambda k: k.getMetaDataEntry("position")) - - for extruder_model, extruder in zip(active_printer_model.extruders, extruders): - containers = ContainerRegistry.getInstance().findInstanceContainersMetadata(type="variant", - definition=self._global_container_stack.definition.getId(), - name=extruder_model.hotendID) - if containers: - # The hotend ID is known. - machine_id = self.activeMachineId - if extruder.variant.getName() != extruder_model.hotendID: - change_found = True - self._auto_hotends_changed[extruder.getMetaDataEntry("position")] = containers[0]["id"] - - if change_found: - # A change was found, let the output device handle this. - self._printer_output_devices[0].materialHotendChangedMessage(self._materialHotendChangedCallback) - - def _onMaterialIdChanged(self) -> None: - if not self._global_container_stack or not self._printer_output_devices: - return - - active_printer_model = self._printer_output_devices[0].activePrinter - if not active_printer_model: - return - - change_found = False - machine_id = self.activeMachineId - extruders = sorted(ExtruderManager.getInstance().getMachineExtruders(machine_id), - key=lambda k: k.getMetaDataEntry("position")) - - for extruder_model, extruder in zip(active_printer_model.extruders, extruders): - if extruder_model.activeMaterial is None: - continue - containers = ContainerRegistry.getInstance().findInstanceContainersMetadata(type="material", - definition=self._global_container_stack.definition.getId(), - GUID=extruder_model.activeMaterial.guid) - if containers: - # The material is known. - if extruder.material.getMetaDataEntry("GUID") != extruder_model.activeMaterial.guid: - change_found = True - if self._global_container_stack.definition.getMetaDataEntry("has_variants") and extruder.variant: - variant_id = self.getQualityVariantId(self._global_container_stack.definition, - extruder.variant) - for container in containers: - if container.get("variant") == variant_id: - self._auto_materials_changed[extruder.getMetaDataEntry("position")] = container["id"] - break - else: - # Just use the first result we found. - self._auto_materials_changed[extruder.getMetaDataEntry("position")] = containers[0]["id"] - if change_found: - # A change was found, let the output device handle this. - self._printer_output_devices[0].materialHotendChangedMessage(self._materialHotendChangedCallback) - - def _materialHotendChangedCallback(self, button) -> None: - if button == QMessageBox.No: - self._auto_materials_changed = {} - self._auto_hotends_changed = {} - return - self._autoUpdateMaterials() - self._autoUpdateHotends() - - def _autoUpdateMaterials(self) -> None: - extruder_manager = ExtruderManager.getInstance() - for position in self._auto_materials_changed: - material_id = self._auto_materials_changed[position] - old_index = extruder_manager.activeExtruderIndex - - if old_index != int(position): - extruder_manager.setActiveExtruderIndex(int(position)) - else: - old_index = None - - Logger.log("d", "Setting material of hotend %s to %s" % (position, material_id)) - self.setActiveMaterial(material_id) - - if old_index is not None: - extruder_manager.setActiveExtruderIndex(old_index) - self._auto_materials_changed = {} # Processed all of them now. - - def _autoUpdateHotends(self) -> None: - extruder_manager = ExtruderManager.getInstance() - for position in self._auto_hotends_changed: - hotend_id = self._auto_hotends_changed[position] - old_index = extruder_manager.activeExtruderIndex - - if old_index != int(position): - extruder_manager.setActiveExtruderIndex(int(position)) - else: - old_index = None - Logger.log("d", "Setting hotend variant of hotend %s to %s" % (position, hotend_id)) - self.setActiveVariant(hotend_id) - - if old_index is not None: - extruder_manager.setActiveExtruderIndex(old_index) - self._auto_hotends_changed = {} # Processed all of them now. - def _onGlobalContainerChanged(self) -> None: if self._global_container_stack: try: @@ -342,6 +221,7 @@ class MachineManager(QObject): Application.getInstance().callLater(func) del self.machine_extruder_material_update_dict[self._global_container_stack.getId()] + self.activeQualityGroupChanged.emit() self._error_check_timer.start() ## Update self._stacks_valid according to _checkStacksForErrors and emit if change. @@ -358,8 +238,6 @@ class MachineManager(QObject): self._active_container_stack = ExtruderManager.getInstance().getActiveExtruderStack() - self._error_check_timer.start() - if old_active_container_stack != self._active_container_stack: # Many methods and properties related to the active quality actually depend # on _active_container_stack. If it changes, then the properties change. @@ -369,19 +247,12 @@ class MachineManager(QObject): self.activeQualityChanged.emit() self.activeVariantChanged.emit() self.activeMaterialChanged.emit() + + self.rootMaterialChanged.emit() + self._error_check_timer.start() - def _onProfilesModelChanged(self, *args) -> None: - self.__emitChangedSignals() - def _onInstanceContainersChanged(self, container) -> None: - # This should not trigger the ProfilesModel to be created, or there will be an infinite recursion - if not self._connected_to_profiles_model and ProfilesModel.hasInstance(): - # This triggers updating the qualityModel in SidebarSimple whenever ProfilesModel is updated - Logger.log("d", "Connecting profiles model...") - ProfilesModel.getInstance().itemsChanged.connect(self._onProfilesModelChanged) - self._connected_to_profiles_model = True - self._instance_container_timer.start() def _onPropertyChanged(self, key: str, property_name: str) -> None: @@ -392,16 +263,46 @@ class MachineManager(QObject): elif property_name == "validationState": self._error_check_timer.start() + ## Given a global_stack, make sure that it's all valid by searching for this quality group and applying it again + def _initMachineState(self, global_stack): + material_dict = {} + for position, extruder in global_stack.extruders.items(): + material_dict[position] = extruder.material.getMetaDataEntry("base_file") + self._current_root_material_id = material_dict + global_quality = global_stack.quality + quality_type = global_quality.getMetaDataEntry("quality_type") + global_quality_changes = global_stack.qualityChanges + global_quality_changes_name = global_quality_changes.getName() + + if global_quality_changes.getId() != "empty_quality_changes": + quality_changes_groups = self._application._quality_manager.getQualityChangesGroups(global_stack) + if global_quality_changes_name in quality_changes_groups: + new_quality_changes_group = quality_changes_groups[global_quality_changes_name] + self._setQualityChangesGroup(new_quality_changes_group) + else: + quality_groups = self._application._quality_manager.getQualityGroups(global_stack) + if quality_type not in quality_groups: + Logger.log("w", "Quality type [%s] not found in available qualities [%s]", quality_type, str(quality_groups.values())) + self._setEmptyQuality() + return + new_quality_group = quality_groups[quality_type] + self._setQualityGroup(new_quality_group, empty_quality_changes = True) + @pyqtSlot(str) def setActiveMachine(self, stack_id: str) -> None: self.blurSettings.emit() # Ensure no-one has focus. - self._cancelDelayedActiveContainerStackChanges() container_registry = ContainerRegistry.getInstance() containers = container_registry.findContainerStacks(id = stack_id) if containers: - Application.getInstance().setGlobalContainerStack(containers[0]) + global_stack = containers[0] + ExtruderManager.getInstance().setActiveExtruderIndex(0) # Switch to first extruder + self._global_container_stack = global_stack + Application.getInstance().setGlobalContainerStack(global_stack) + ExtruderManager.getInstance()._globalContainerStackChanged() + self._initMachineState(containers[0]) + self._onGlobalContainerChanged() self.__emitChangedSignals() @@ -439,16 +340,6 @@ class MachineManager(QObject): Logger.log("d", "Checking %s stacks for errors took %.2f s" % (count, time.time() - time_start)) return False - ## Remove all instances from the top instanceContainer (effectively removing all user-changed settings) - @pyqtSlot() - def clearUserSettings(self) -> None: - if not self._active_container_stack: - return - - self.blurSettings.emit() - user_settings = self._active_container_stack.getTop() - user_settings.clear() - ## Check if the global_container has instances in the user container @pyqtProperty(bool, notify = activeStackValueChanged) def hasUserSettings(self) -> bool: @@ -514,25 +405,16 @@ class MachineManager(QObject): def stacksHaveErrors(self) -> bool: return bool(self._stacks_have_errors) - @pyqtProperty(str, notify = activeStackChanged) - def activeUserProfileId(self) -> str: - if self._active_container_stack: - return self._active_container_stack.getTop().getId() - - return "" - @pyqtProperty(str, notify = globalContainerChanged) def activeMachineName(self) -> str: if self._global_container_stack: return self._global_container_stack.getName() - return "" @pyqtProperty(str, notify = globalContainerChanged) def activeMachineId(self) -> str: if self._global_container_stack: return self._global_container_stack.getId() - return "" @pyqtProperty(QObject, notify = globalContainerChanged) @@ -543,43 +425,11 @@ class MachineManager(QObject): def activeStackId(self) -> str: if self._active_container_stack: return self._active_container_stack.getId() - return "" - @pyqtProperty(str, notify = activeMaterialChanged) - def activeMaterialName(self) -> str: - if self._active_container_stack: - material = self._active_container_stack.material - if material: - return material.getName() - - return "" - - @pyqtProperty("QVariantList", notify=activeVariantChanged) - def activeVariantNames(self) -> List[str]: - result = [] - - # Just return the variants in the extruder stack(s). For the variant in the global stack, use activeVariantBuildplateName - active_stacks = ExtruderManager.getInstance().getActiveExtruderStacks() - if active_stacks is not None: - for stack in active_stacks: - variant_container = stack.variant - if variant_container and variant_container != self._empty_variant_container: - result.append(variant_container.getName()) - - return result - - @pyqtProperty("QVariantList", notify = activeMaterialChanged) - def activeMaterialNames(self) -> List[str]: - result = [] - - active_stacks = ExtruderManager.getInstance().getActiveGlobalAndExtruderStacks() - if active_stacks is not None: - for stack in active_stacks: - material_container = stack.material - if material_container and material_container != self._empty_material_container: - result.append(material_container.getName()) - return result + @pyqtProperty(QObject, notify = activeStackChanged) + def activeStack(self) -> Optional["ExtruderStack"]: + return self._active_container_stack @pyqtProperty(str, notify=activeMaterialChanged) def activeMaterialId(self) -> str: @@ -587,24 +437,8 @@ class MachineManager(QObject): material = self._active_container_stack.material if material: return material.getId() - return "" - @pyqtProperty("QVariantMap", notify = activeVariantChanged) - def allActiveVariantIds(self) -> Dict[str, str]: - result = {} - - active_stacks = ExtruderManager.getInstance().getActiveExtruderStacks() - if active_stacks is not None: #If we have a global stack. - for stack in active_stacks: - variant_container = stack.variant - if not variant_container: - continue - - result[stack.getId()] = variant_container.getId() - - return result - ## Gets a dict with the active materials ids set in all extruder stacks and the global stack # (when there is one extruder, the material is set in the global stack) # @@ -629,106 +463,45 @@ class MachineManager(QObject): # # \return The layer height of the currently active quality profile. If # there is no quality profile, this returns 0. - @pyqtProperty(float, notify=activeQualityChanged) + @pyqtProperty(float, notify = activeQualityGroupChanged) def activeQualityLayerHeight(self) -> float: if not self._global_container_stack: return 0 - - quality_changes = self._global_container_stack.qualityChanges - if quality_changes: - value = self._global_container_stack.getRawProperty("layer_height", "value", skip_until_container = quality_changes.getId()) + if self._current_quality_changes_group: + value = self._global_container_stack.getRawProperty("layer_height", "value", skip_until_container = self._global_container_stack.qualityChanges.getId()) if isinstance(value, SettingFunction): value = value(self._global_container_stack) return value - quality = self._global_container_stack.quality - if quality: - value = self._global_container_stack.getRawProperty("layer_height", "value", skip_until_container = quality.getId()) + elif self._current_quality_group: + value = self._global_container_stack.getRawProperty("layer_height", "value", skip_until_container = self._global_container_stack.quality.getId()) if isinstance(value, SettingFunction): value = value(self._global_container_stack) return value + return 0 - return 0 # No quality profile. - - ## Get the Material ID associated with the currently active material - # \returns MaterialID (string) if found, empty string otherwise - @pyqtProperty(str, notify=activeQualityChanged) - def activeQualityMaterialId(self) -> str: - if self._active_container_stack: - quality = self._active_container_stack.quality - if quality: - material_id = quality.getMetaDataEntry("material") - if material_id: - # if the currently active machine inherits its qualities from a different machine - # definition, make sure to return a material that is relevant to that machine definition - definition_id = self.activeDefinitionId - quality_definition_id = self.activeQualityDefinitionId - if definition_id != quality_definition_id: - material_id = material_id.replace(definition_id, quality_definition_id, 1) - - return material_id - return "" - - @pyqtProperty(str, notify=activeQualityChanged) - def activeQualityName(self) -> str: - if self._active_container_stack and self._global_container_stack: - quality = self._global_container_stack.qualityChanges - if quality and not isinstance(quality, type(self._empty_quality_changes_container)): - return quality.getName() - quality = self._active_container_stack.quality - if quality: - return quality.getName() - return "" - - @pyqtProperty(str, notify=activeQualityChanged) - def activeQualityId(self) -> str: - if self._active_container_stack: - quality = self._active_container_stack.quality - if isinstance(quality, type(self._empty_quality_container)): - return "" - quality_changes = self._active_container_stack.qualityChanges - if quality and quality_changes: - if isinstance(quality_changes, type(self._empty_quality_changes_container)): - # It's a built-in profile - return quality.getId() - else: - # Custom profile - return quality_changes.getId() - return "" - - @pyqtProperty(str, notify=activeQualityChanged) - def globalQualityId(self) -> str: - if self._global_container_stack: - quality = self._global_container_stack.qualityChanges - if quality and not isinstance(quality, type(self._empty_quality_changes_container)): - return quality.getId() - quality = self._global_container_stack.quality - if quality: - return quality.getId() - return "" - - @pyqtProperty(str, notify=activeVariantChanged) - def globalVariantId(self) -> str: + @pyqtProperty(str, notify = activeVariantChanged) + def globalVariantName(self) -> str: if self._global_container_stack: variant = self._global_container_stack.variant if variant and not isinstance(variant, type(self._empty_variant_container)): - return variant.getId() + return variant.getName() return "" - @pyqtProperty(str, notify = activeQualityChanged) + @pyqtProperty(str, notify = activeQualityGroupChanged) def activeQualityType(self) -> str: + quality_type = "" if self._active_container_stack: - quality = self._active_container_stack.quality - if quality: - return quality.getMetaDataEntry("quality_type") - return "" + if self._current_quality_group: + quality_type = self._current_quality_group.quality_type + return quality_type - @pyqtProperty(bool, notify = activeQualityChanged) + @pyqtProperty(bool, notify = activeQualityGroupChanged) def isActiveQualitySupported(self) -> bool: - if self._active_container_stack: - quality = self._active_container_stack.quality - if quality: - return Util.parseBool(quality.getMetaDataEntry("supported", True)) - return False + is_supported = False + if self._global_container_stack: + if self._current_quality_group: + is_supported = self._current_quality_group.is_available + return is_supported ## Returns whether there is anything unsupported in the current set-up. # @@ -747,29 +520,6 @@ class MachineManager(QObject): return False return True - ## Get the Quality ID associated with the currently active extruder - # Note that this only returns the "quality", not the "quality_changes" - # \returns QualityID (string) if found, empty string otherwise - # \sa activeQualityId() - # \todo Ideally, this method would be named activeQualityId(), and the other one - # would be named something like activeQualityOrQualityChanges() for consistency - @pyqtProperty(str, notify = activeQualityChanged) - def activeQualityContainerId(self) -> str: - # We're using the active stack instead of the global stack in case the list of qualities differs per extruder - if self._global_container_stack: - quality = self._active_container_stack.quality - if quality: - return quality.getId() - return "" - - @pyqtProperty(str, notify = activeQualityChanged) - def activeQualityChangesId(self) -> str: - if self._active_container_stack: - quality_changes = self._active_container_stack.qualityChanges - if quality_changes and not isinstance(quality_changes, type(self._empty_quality_changes_container)): - return quality_changes.getId() - return "" - ## Check if a container is read_only @pyqtSlot(str, result = bool) def isReadOnly(self, container_id: str) -> bool: @@ -786,389 +536,6 @@ class MachineManager(QObject): if extruder_stack != self._active_container_stack and extruder_stack.getProperty(key, "value") != new_value: extruder_stack.userChanges.setProperty(key, "value", new_value) # TODO: nested property access, should be improved - ## Set the active material by switching out a container - # Depending on from/to material+current variant, a quality profile is chosen and set. - @pyqtSlot(str) - def setActiveMaterial(self, material_id: str, always_discard_changes = False): - with postponeSignals(*self._getContainerChangedSignals(), compress = CompressTechnique.CompressPerParameterValue): - containers = ContainerRegistry.getInstance().findInstanceContainers(id = material_id) - if not containers or not self._active_container_stack: - return - material_container = containers[0] - - Logger.log("d", "Attempting to change the active material to %s", material_id) - - old_material = self._active_container_stack.material - old_quality = self._active_container_stack.quality - old_quality_type = None - if old_quality and old_quality.getId() != self._empty_quality_container.getId(): - old_quality_type = old_quality.getMetaDataEntry("quality_type") - old_quality_changes = self._active_container_stack.qualityChanges - if not old_material: - Logger.log("w", "While trying to set the active material, no material was found to replace it.") - return - - if old_quality_changes and isinstance(old_quality_changes, type(self._empty_quality_changes_container)): - old_quality_changes = None - - self.blurSettings.emit() - old_material.nameChanged.disconnect(self._onMaterialNameChanged) - - self._new_material_container = material_container # self._active_container_stack will be updated with a delay - Logger.log("d", "Active material changed") - - material_container.nameChanged.connect(self._onMaterialNameChanged) - - if material_container.getMetaDataEntry("compatible") == False: - self._material_incompatible_message.show() - else: - self._material_incompatible_message.hide() - - quality_type = None - new_quality_id = None - if old_quality: - new_quality_id = old_quality.getId() - quality_type = old_quality.getMetaDataEntry("quality_type") - if old_quality_changes: - quality_type = old_quality_changes.getMetaDataEntry("quality_type") - new_quality_id = old_quality_changes.getId() - - global_stack = Application.getInstance().getGlobalContainerStack() - if global_stack: - quality_manager = QualityManager.getInstance() - - candidate_quality = None - if quality_type: - candidate_quality = quality_manager.findQualityByQualityType(quality_type, - quality_manager.getWholeMachineDefinition(global_stack.definition), - [material_container.getMetaData()]) - - if not candidate_quality or candidate_quality.getId() == self._empty_quality_changes_container: - Logger.log("d", "Attempting to find fallback quality") - # Fall back to a quality (which must be compatible with all other extruders) - new_qualities = quality_manager.findAllUsableQualitiesForMachineAndExtruders( - self._global_container_stack, ExtruderManager.getInstance().getExtruderStacks()) - - quality_types = sorted([q.getMetaDataEntry("quality_type") for q in new_qualities], reverse = True) - quality_type_to_use = None - if quality_types: - # try to use the same quality as before, otherwise the first one in the quality_types - quality_type_to_use = quality_types[0] - if old_quality_type is not None and old_quality_type in quality_type_to_use: - quality_type_to_use = old_quality_type - - new_quality = None - for q in new_qualities: - if quality_type_to_use is not None and q.getMetaDataEntry("quality_type") == quality_type_to_use: - new_quality = q - break - - if new_quality is not None: - new_quality_id = new_quality.getId() # Just pick the first available one - else: - Logger.log("w", "No quality profile found that matches the current machine and extruders.") - else: - if not old_quality_changes: - new_quality_id = candidate_quality.getId() - - self.setActiveQuality(new_quality_id, always_discard_changes = always_discard_changes) - - @pyqtSlot(str) - def setActiveVariant(self, variant_id: str, always_discard_changes = False): - with postponeSignals(*self._getContainerChangedSignals(), compress = CompressTechnique.CompressPerParameterValue): - containers = ContainerRegistry.getInstance().findInstanceContainers(id = variant_id) - if not containers or not self._active_container_stack: - return - Logger.log("d", "Attempting to change the active variant to %s", variant_id) - old_variant = self._active_container_stack.variant - old_material = self._active_container_stack.material - if old_variant: - self.blurSettings.emit() - self._new_variant_container = containers[0] # self._active_container_stack will be updated with a delay - Logger.log("d", "Active variant changed to {active_variant_id}".format(active_variant_id = containers[0].getId())) - preferred_material_name = None - if old_material: - preferred_material_name = old_material.getName() - preferred_material_id = self._updateMaterialContainer(self._global_container_stack.definition, self._global_container_stack, containers[0], preferred_material_name).id - self.setActiveMaterial(preferred_material_id, always_discard_changes = always_discard_changes) - else: - Logger.log("w", "While trying to set the active variant, no variant was found to replace.") - - @pyqtSlot(str) - def setActiveVariantBuildplate(self, variant_buildplate_id: str): - with postponeSignals(*self._getContainerChangedSignals(), compress = CompressTechnique.CompressPerParameterValue): - containers = ContainerRegistry.getInstance().findInstanceContainers(id = variant_buildplate_id) - if not containers or not self._global_container_stack: - return - Logger.log("d", "Attempting to change the active buildplate to %s", variant_buildplate_id) - old_buildplate = self._global_container_stack.variant - if old_buildplate: - self.blurSettings.emit() - self._new_buildplate_container = containers[0] # self._active_container_stack will be updated with a delay - Logger.log("d", "Active buildplate changed to {active_variant_buildplate_id}".format(active_variant_buildplate_id = containers[0].getId())) - - # Force set the active quality as it is so the values are updated - self.setActiveMaterial(self._active_container_stack.material.getId()) - else: - Logger.log("w", "While trying to set the active buildplate, no buildplate was found to replace.") - - ## set the active quality - # \param quality_id The quality_id of either a quality or a quality_changes - @pyqtSlot(str) - def setActiveQuality(self, quality_id: str, always_discard_changes = False): - with postponeSignals(*self._getContainerChangedSignals(), compress = CompressTechnique.CompressPerParameterValue): - self.blurSettings.emit() - - Logger.log("d", "Attempting to change the active quality to %s", quality_id) - - containers = ContainerRegistry.getInstance().findInstanceContainersMetadata(id = quality_id) - if not containers or not self._global_container_stack: - return - - # Quality profile come in two flavours: type=quality and type=quality_changes - # If we found a quality_changes profile then look up its parent quality profile. - container_type = containers[0].get("type") - quality_name = containers[0]["name"] - quality_type = containers[0].get("quality_type") - - # Get quality container and optionally the quality_changes container. - if container_type == "quality": - new_quality_settings_list = self.determineQualityAndQualityChangesForQualityType(quality_type) - elif container_type == "quality_changes": - new_quality_settings_list = self._determineQualityAndQualityChangesForQualityChanges(quality_name) - else: - Logger.log("e", "Tried to set quality to a container that is not of the right type: {container_id}".format(container_id = containers[0]["id"])) - return - - # Check if it was at all possible to find new settings - if new_quality_settings_list is None: - return - - # check if any of the stacks have a not supported profile - # if that is the case, all stacks should have a not supported state (otherwise it will show quality_type normal) - has_not_supported_quality = False - - # check all stacks for not supported - for setting_info in new_quality_settings_list: - if setting_info["quality"].getMetaDataEntry("quality_type") == "not_supported": - has_not_supported_quality = True - break - - # set all stacks to not supported if that's the case - if has_not_supported_quality: - for setting_info in new_quality_settings_list: - setting_info["quality"] = self._empty_quality_container - - self._new_quality_containers.clear() - - # store the upcoming quality profile changes per stack for later execution - # this prevents re-slicing before the user has made a choice in the discard or keep dialog - # (see _executeDelayedActiveContainerStackChanges) - for setting_info in new_quality_settings_list: - stack = setting_info["stack"] - stack_quality = setting_info["quality"] - stack_quality_changes = setting_info["quality_changes"] - - self._new_quality_containers.append({ - "stack": stack, - "quality": stack_quality, - "quality_changes": stack_quality_changes - }) - - Logger.log("d", "Active quality changed") - - # show the keep/discard dialog after the containers have been switched. Otherwise, the default values on - # the dialog will be the those before the switching. - self._executeDelayedActiveContainerStackChanges() - - if self.hasUserSettings and Preferences.getInstance().getValue("cura/active_mode") == 1 and not always_discard_changes: - Application.getInstance().discardOrKeepProfileChanges() - - ## Used to update material and variant in the active container stack with a delay. - # This delay prevents the stack from triggering a lot of signals (eventually resulting in slicing) - # before the user decided to keep or discard any of their changes using the dialog. - # The Application.onDiscardOrKeepProfileChangesClosed signal triggers this method. - def _executeDelayedActiveContainerStackChanges(self): - - Logger.log("d", "Applying configuration changes...") - - if self._new_variant_container is not None: - self._active_container_stack.variant = self._new_variant_container - self._new_variant_container = None - - if self._new_buildplate_container is not None: - self._global_container_stack.variant = self._new_buildplate_container - self._new_buildplate_container = None - - if self._new_material_container is not None: - self._active_container_stack.material = self._new_material_container - self._new_material_container = None - - # apply the new quality to all stacks - if self._new_quality_containers: - for new_quality in self._new_quality_containers: - self._replaceQualityOrQualityChangesInStack(new_quality["stack"], new_quality["quality"], postpone_emit = True) - self._replaceQualityOrQualityChangesInStack(new_quality["stack"], new_quality["quality_changes"], postpone_emit = True) - - for new_quality in self._new_quality_containers: - new_quality["stack"].nameChanged.connect(self._onQualityNameChanged) - new_quality["stack"].sendPostponedEmits() # Send the signals that were postponed in _replaceQualityOrQualityChangesInStack - - self._new_quality_containers.clear() - - Logger.log("d", "New configuration applied") - - ## Cancel set changes for material and variant in the active container stack. - # Used for ignoring any changes when switching between printers (setActiveMachine) - def _cancelDelayedActiveContainerStackChanges(self): - self._new_material_container = None - self._new_buildplate_container = None - self._new_variant_container = None - - ## Determine the quality and quality changes settings for the current machine for a quality name. - # - # \param quality_name \type{str} the name of the quality. - # \return \type{List[Dict]} with keys "stack", "quality" and "quality_changes". - @UM.FlameProfiler.profile - def determineQualityAndQualityChangesForQualityType(self, quality_type: str) -> List[Dict[str, Union["CuraContainerStack", InstanceContainer]]]: - quality_manager = QualityManager.getInstance() - result = [] - empty_quality_changes = self._empty_quality_changes_container - global_container_stack = self._global_container_stack - if not global_container_stack: - return [] - - global_machine_definition = quality_manager.getParentMachineDefinition(global_container_stack.definition) - extruder_stacks = ExtruderManager.getInstance().getActiveExtruderStacks() - - # find qualities for extruders - for extruder_stack in extruder_stacks: - material_metadata = extruder_stack.material.getMetaData() - - # TODO: fix this - if self._new_material_container and extruder_stack.getId() == self._active_container_stack.getId(): - material_metadata = self._new_material_container.getMetaData() - - quality = quality_manager.findQualityByQualityType(quality_type, global_machine_definition, [material_metadata]) - - if not quality: - # No quality profile is found for this quality type. - quality = self._empty_quality_container - - result.append({ - "stack": extruder_stack, - "quality": quality, - "quality_changes": empty_quality_changes - }) - - # also find a global quality for the machine - global_quality = quality_manager.findQualityByQualityType(quality_type, global_machine_definition, [], global_quality = "True") - - # if there is not global quality but we're using a single extrusion machine, copy the quality of the first extruder - CURA-4482 - if not global_quality and len(extruder_stacks) == 1: - global_quality = result[0]["quality"] - - # if there is still no global quality, set it to empty (not supported) - if not global_quality: - global_quality = self._empty_quality_container - - result.append({ - "stack": global_container_stack, - "quality": global_quality, - "quality_changes": empty_quality_changes - }) - - return result - - ## Determine the quality and quality changes settings for the current machine for a quality changes name. - # - # \param quality_changes_name \type{str} the name of the quality changes. - # \return \type{List[Dict]} with keys "stack", "quality" and "quality_changes". - def _determineQualityAndQualityChangesForQualityChanges(self, quality_changes_name: str) -> Optional[List[Dict[str, Union["CuraContainerStack", InstanceContainer]]]]: - result = [] - quality_manager = QualityManager.getInstance() - - global_container_stack = self._global_container_stack - global_machine_definition = quality_manager.getParentMachineDefinition(global_container_stack.definition) - quality_changes_profiles = quality_manager.findQualityChangesByName(quality_changes_name, global_machine_definition) - - global_quality_changes = [qcp for qcp in quality_changes_profiles if qcp.getMetaDataEntry("extruder") is None] - if global_quality_changes: - global_quality_changes = global_quality_changes[0] - else: - Logger.log("e", "Could not find the global quality changes container with name %s", quality_changes_name) - return None - - # For the global stack, find a quality which matches the quality_type in - # the quality changes profile and also satisfies any material constraints. - quality_type = global_quality_changes.getMetaDataEntry("quality_type") - - extruder_stacks = ExtruderManager.getInstance().getActiveExtruderStacks() - - # append the extruder quality changes - for extruder_stack in extruder_stacks: - extruder_definition = quality_manager.getParentMachineDefinition(extruder_stack.definition) - - quality_changes_list = [qcp for qcp in quality_changes_profiles if qcp.getMetaDataEntry("extruder") == extruder_definition.getId()] - - if quality_changes_list: - quality_changes = quality_changes_list[0] - else: - quality_changes = global_quality_changes - if not quality_changes: - quality_changes = self._empty_quality_changes_container - - material_metadata = extruder_stack.material.getMetaData() - - if self._new_material_container and self._active_container_stack.getId() == extruder_stack.getId(): - material_metadata = self._new_material_container.getMetaData() - - quality = quality_manager.findQualityByQualityType(quality_type, global_machine_definition, [material_metadata]) - - if not quality: - # No quality profile found for this quality type. - quality = self._empty_quality_container - - result.append({ - "stack": extruder_stack, - "quality": quality, - "quality_changes": quality_changes - }) - - # append the global quality changes - global_quality = quality_manager.findQualityByQualityType(quality_type, global_machine_definition, global_quality = "True") - - # if there is not global quality but we're using a single extrusion machine, copy the quality of the first extruder - CURA-4482 - if not global_quality and len(extruder_stacks) == 1: - global_quality = result[0]["quality"] - - # if still no global quality changes are found we set it to empty (not supported) - if not global_quality: - global_quality = self._empty_quality_container - - result.append({ - "stack": global_container_stack, - "quality": global_quality, - "quality_changes": global_quality_changes - }) - - return result - - def _replaceQualityOrQualityChangesInStack(self, stack: "CuraContainerStack", container: "InstanceContainer", postpone_emit = False): - # Disconnect the signal handling from the old container. - container_type = container.getMetaDataEntry("type") - if container_type == "quality": - stack.quality.nameChanged.disconnect(self._onQualityNameChanged) - stack.setQuality(container, postpone_emit = postpone_emit) - stack.quality.nameChanged.connect(self._onQualityNameChanged) - elif container_type == "quality_changes" or container_type is None: - # If the container is an empty container, we need to change the quality_changes. - # Quality can never be set to empty. - stack.qualityChanges.nameChanged.disconnect(self._onQualityNameChanged) - stack.setQualityChanges(container, postpone_emit = postpone_emit) - stack.qualityChanges.nameChanged.connect(self._onQualityNameChanged) - self._onQualityNameChanged() - @pyqtProperty(str, notify = activeVariantChanged) def activeVariantName(self) -> str: if self._active_container_stack: @@ -1178,15 +545,6 @@ class MachineManager(QObject): return "" - @pyqtProperty(str, notify = activeVariantChanged) - def activeVariantId(self) -> str: - if self._active_container_stack: - variant = self._active_container_stack.variant - if variant: - return variant.getId() - - return "" - @pyqtProperty(str, notify = activeVariantChanged) def activeVariantBuildplateName(self) -> str: if self._global_container_stack: @@ -1203,55 +561,14 @@ class MachineManager(QObject): return "" - @pyqtProperty(str, notify=globalContainerChanged) - def activeDefinitionName(self) -> str: - if self._global_container_stack: - return self._global_container_stack.definition.getName() - - return "" - ## Get the Definition ID to use to select quality profiles for the currently active machine # \returns DefinitionID (string) if found, empty string otherwise - # \sa getQualityDefinitionId @pyqtProperty(str, notify = globalContainerChanged) def activeQualityDefinitionId(self) -> str: if self._global_container_stack: - return self.getQualityDefinitionId(self._global_container_stack.definition) + return getMachineDefinitionIDForQualitySearch(self._global_container_stack) return "" - ## Get the Definition ID to use to select quality profiles for machines of the specified definition - # This is normally the id of the definition itself, but machines can specify a different definition to inherit qualities from - # \param definition (DefinitionContainer) machine definition - # \returns DefinitionID (string) if found, empty string otherwise - def getQualityDefinitionId(self, definition: "DefinitionContainer") -> str: - return QualityManager.getInstance().getParentMachineDefinition(definition).getId() - - ## Get the Variant ID to use to select quality profiles for the currently active variant - # \returns VariantID (string) if found, empty string otherwise - # \sa getQualityVariantId - @pyqtProperty(str, notify = activeVariantChanged) - def activeQualityVariantId(self) -> str: - if self._active_container_stack: - variant = self._active_container_stack.variant - if variant: - return self.getQualityVariantId(self._global_container_stack.definition, variant) - return "" - - ## Get the Variant ID to use to select quality profiles for variants of the specified definitions - # This is normally the id of the variant itself, but machines can specify a different definition - # to inherit qualities from, which has consequences for the variant to use as well - # \param definition (DefinitionContainer) machine definition - # \param variant (InstanceContainer) variant definition - # \returns VariantID (string) if found, empty string otherwise - def getQualityVariantId(self, definition: "DefinitionContainer", variant: "InstanceContainer") -> str: - variant_id = variant.getId() - definition_id = definition.getId() - quality_definition_id = self.getQualityDefinitionId(definition) - - if definition_id != quality_definition_id: - variant_id = variant_id.replace(definition_id, quality_definition_id, 1) - return variant_id - ## Gets how the active definition calls variants # Caveat: per-definition-variant-title is currently not translated (though the fallback is) @pyqtProperty(str, notify = globalContainerChanged) @@ -1435,47 +752,12 @@ class MachineManager(QObject): # Signal that the global stack has changed Application.getInstance().globalContainerStackChanged.emit() - @staticmethod - def createMachineManager(): - return MachineManager() - - @deprecated("Use ExtruderStack.material = ... and it won't be necessary", "2.7") - def _updateMaterialContainer(self, definition: "DefinitionContainer", stack: "ContainerStack", variant_container: Optional["InstanceContainer"] = None, preferred_material_name: Optional[str] = None) -> InstanceContainer: - if not definition.getMetaDataEntry("has_materials"): - return self._empty_material_container - - approximate_material_diameter = str(round(stack.getProperty("material_diameter", "value"))) - search_criteria = { "type": "material", "approximate_diameter": approximate_material_diameter } - - if definition.getMetaDataEntry("has_machine_materials"): - search_criteria["definition"] = self.getQualityDefinitionId(definition) - - if definition.getMetaDataEntry("has_variants") and variant_container: - search_criteria["variant"] = self.getQualityVariantId(definition, variant_container) - else: - search_criteria["definition"] = "fdmprinter" - - if preferred_material_name: - search_criteria["name"] = preferred_material_name - else: - preferred_material = definition.getMetaDataEntry("preferred_material") - if preferred_material: - search_criteria["id"] = preferred_material - - containers = ContainerRegistry.getInstance().findInstanceContainers(**search_criteria) - if containers: - return containers[0] - - if "variant" in search_criteria or "id" in search_criteria: - # If a material by this name can not be found, try a wider set of search criteria - search_criteria.pop("variant", None) - search_criteria.pop("id", None) - - containers = ContainerRegistry.getInstance().findInstanceContainers(**search_criteria) - if containers: - return containers[0] - Logger.log("w", "Unable to find a material container with provided criteria, returning an empty one instead.") - return self._empty_material_container + @pyqtSlot(int, result = QObject) + def getExtruder(self, position: int): + extruder = None + if self._global_container_stack: + extruder = self._global_container_stack.extruders.get(str(position)) + return extruder def _onMachineNameChanged(self): self.globalContainerChanged.emit() @@ -1496,3 +778,257 @@ class MachineManager(QObject): for key, extruder in self._global_container_stack.extruders.items(): container = extruder.userChanges container.setProperty(setting_name, property_name, property_value) + + @pyqtProperty("QVariantList", notify = rootMaterialChanged) + def currentExtruderPositions(self): + return sorted(list(self._current_root_material_id.keys())) + + @pyqtProperty("QVariant", notify = rootMaterialChanged) + def currentRootMaterialId(self): + # initial filling the current_root_material_id + self._current_root_material_id = {} + for position in self._global_container_stack.extruders: + self._current_root_material_id[position] = self._global_container_stack.extruders[position].material.getMetaDataEntry("base_file") + return self._current_root_material_id + + @pyqtProperty("QVariant", notify = rootMaterialChanged) + def currentRootMaterialName(self): + # initial filling the current_root_material_name + if self._global_container_stack: + self._current_root_material_name = {} + for position in self._global_container_stack.extruders: + if position not in self._current_root_material_name: + material = self._global_container_stack.extruders[position].material + self._current_root_material_name[position] = material.getName() + return self._current_root_material_name + + ## Return the variant names in the extruder stack(s). + ## For the variant in the global stack, use activeVariantBuildplateName + @pyqtProperty("QVariant", notify = activeVariantChanged) + def activeVariantNames(self): + result = {} + + active_stacks = ExtruderManager.getInstance().getActiveExtruderStacks() + if active_stacks is not None: + for stack in active_stacks: + variant_container = stack.variant + position = stack.getMetaDataEntry("position") + if variant_container and variant_container != self._empty_variant_container: + result[position] = variant_container.getName() + + return result + + # + # Sets all quality and quality_changes containers to empty_quality and empty_quality_changes containers + # for all stacks in the currently active machine. + # + def _setEmptyQuality(self): + self._current_quality_group = None + self._current_quality_changes_group = None + self._global_container_stack.quality = self._empty_quality_container + self._global_container_stack.qualityChanges = self._empty_quality_changes_container + for extruder in self._global_container_stack.extruders.values(): + extruder.quality = self._empty_quality_container + extruder.qualityChanges = self._empty_quality_changes_container + + self.activeQualityGroupChanged.emit() + self.activeQualityChangesGroupChanged.emit() + + def _setQualityGroup(self, quality_group, empty_quality_changes = True): + self._current_quality_group = quality_group + if empty_quality_changes: + self._current_quality_changes_group = None + + # Set quality and quality_changes for the GlobalStack + self._global_container_stack.quality = quality_group.node_for_global.getContainer() + if empty_quality_changes: + self._global_container_stack.qualityChanges = self._empty_quality_changes_container + + # Set quality and quality_changes for each ExtruderStack + for position, node in quality_group.nodes_for_extruders.items(): + self._global_container_stack.extruders[position].quality = node.getContainer() + if empty_quality_changes: + self._global_container_stack.extruders[position].qualityChanges = self._empty_quality_changes_container + + self.activeQualityGroupChanged.emit() + self.activeQualityChangesGroupChanged.emit() + + def _setQualityChangesGroup(self, quality_changes_group): + quality_type = quality_changes_group.quality_type + quality_group_dict = self._quality_manager.getQualityGroups(self._global_container_stack) + quality_group = quality_group_dict[quality_type] + + quality_changes_container = self._empty_quality_changes_container + quality_container = self._empty_quality_changes_container + if quality_changes_group.node_for_global: + quality_changes_container = quality_changes_group.node_for_global.getContainer() + if quality_group.node_for_global: + quality_container = quality_group.node_for_global.getContainer() + + self._global_container_stack.quality = quality_container + self._global_container_stack.qualityChanges = quality_changes_container + + for position, extruder in self._global_container_stack.extruders.items(): + quality_changes_node = quality_changes_group.nodes_for_extruders.get(position) + quality_node = quality_group.nodes_for_extruders.get(position) + + quality_changes_container = self._empty_quality_changes_container + quality_container = self._empty_quality_changes_container + if quality_changes_node: + quality_changes_container = quality_changes_node.getContainer() + if quality_node: + quality_container = quality_node.getContainer() + + extruder.quality = quality_container + extruder.qualityChanges = quality_changes_container + + self._current_quality_group = quality_group + self._current_quality_changes_group = quality_changes_group + self.activeQualityGroupChanged.emit() + self.activeQualityChangesGroupChanged.emit() + + def _setVariantNode(self, position, container_node): + self._global_container_stack.extruders[position].variant = container_node.getContainer() + self.activeVariantChanged.emit() + + def _setGlobalVariant(self, container_node): + self._global_container_stack.variant = container_node.getContainer() + + def _setMaterial(self, position, container_node = None): + if container_node: + self._global_container_stack.extruders[position].material = container_node.getContainer() + else: + self._global_container_stack.extruders[position].material = self._empty_material_container + # The _current_root_material_id is used in the MaterialMenu to see which material is selected + root_material_id = container_node.metadata["base_file"] + root_material_name = container_node.getContainer().getName() + if root_material_id != self._current_root_material_id[position]: + self._current_root_material_id[position] = root_material_id + self._current_root_material_name[position] = root_material_name + self.rootMaterialChanged.emit() + + def activeMaterialsCompatible(self): + # check material - variant compatibility + if Util.parseBool(self._global_container_stack.getMetaDataEntry("has_materials", False)): + for position, extruder in self._global_container_stack.extruders.items(): + if not extruder.material.getMetaDataEntry("compatible"): + return False + return True + + ## Update current quality type and machine after setting material + def _updateQualityWithMaterial(self): + current_quality = None + if self._current_quality_group: + current_quality = self._current_quality_group.quality_type + quality_manager = Application.getInstance()._quality_manager + candidate_quality_groups = quality_manager.getQualityGroups(self._global_container_stack) + available_quality_types = {qt for qt, g in candidate_quality_groups.items() if g.is_available} + + if not self.activeMaterialsCompatible(): + self._setEmptyQuality() + return + + if not available_quality_types: + self._setEmptyQuality() + return + + if current_quality in available_quality_types: + self._setQualityGroup(candidate_quality_groups[current_quality], empty_quality_changes = False) + return + + quality_type = sorted(list(available_quality_types))[0] + preferred_quality_type = self._global_container_stack.getMetaDataEntry("preferred_quality_type") + if preferred_quality_type in available_quality_types: + quality_type = preferred_quality_type + + self._setQualityGroup(candidate_quality_groups[quality_type], empty_quality_changes = True) + + def _updateMaterialWithVariant(self, position: Optional[str]): + if position is None: + position_list = list(self._global_container_stack.extruders.keys()) + else: + position_list = [position] + + for position in position_list: + extruder = self._global_container_stack.extruders[position] + + current_material_base_name = extruder.material.getMetaDataEntry("base_file") + current_variant_name = extruder.variant.getMetaDataEntry("name") + + material_manager = Application.getInstance()._material_manager + material_diameter = self._global_container_stack.getProperty("material_diameter", "value") + candidate_materials = material_manager.getAvailableMaterials( + self._global_container_stack.definition.getId(), + current_variant_name, + material_diameter) + + if not candidate_materials: + self._setMaterial(position, container_node = None) + continue + + if current_material_base_name in candidate_materials: + new_material = candidate_materials[current_material_base_name] + self._setMaterial(position, new_material) + continue + + @pyqtSlot("QVariant") + def setGlobalVariant(self, container_node): + self.blurSettings.emit() + with postponeSignals(*self._getContainerChangedSignals(), compress = CompressTechnique.CompressPerParameterValue): + self._setGlobalVariant(container_node) + self._updateMaterialWithVariant(None) # Update all materials + self._updateQualityWithMaterial() + + @pyqtSlot(str, "QVariant") + def setMaterial(self, position, container_node): + position = str(position) + self.blurSettings.emit() + with postponeSignals(*self._getContainerChangedSignals(), compress = CompressTechnique.CompressPerParameterValue): + self._setMaterial(position, container_node) + self._updateQualityWithMaterial() + + @pyqtSlot(str, "QVariant") + def setVariantGroup(self, position, container_node): + position = str(position) + self.blurSettings.emit() + with postponeSignals(*self._getContainerChangedSignals(), compress = CompressTechnique.CompressPerParameterValue): + self._setVariantNode(position, container_node) + self._updateMaterialWithVariant(position) + self._updateQualityWithMaterial() + + @pyqtSlot(QObject) + def setQualityGroup(self, quality_group): + self.blurSettings.emit() + with postponeSignals(*self._getContainerChangedSignals(), compress = CompressTechnique.CompressPerParameterValue): + self._setQualityGroup(quality_group) + + # See if we need to show the Discard or Keep changes screen + if self.hasUserSettings and Preferences.getInstance().getValue("cura/active_mode") == 1: + Application.getInstance().discardOrKeepProfileChanges() + + @pyqtProperty(QObject, fset = setQualityGroup, notify = activeQualityGroupChanged) + def activeQualityGroup(self): + return self._current_quality_group + + @pyqtSlot(QObject) + def setQualityChangesGroup(self, quality_changes_group): + self.blurSettings.emit() + with postponeSignals(*self._getContainerChangedSignals(), compress = CompressTechnique.CompressPerParameterValue): + self._setQualityChangesGroup(quality_changes_group) + + # See if we need to show the Discard or Keep changes screen + if self.hasUserSettings and Preferences.getInstance().getValue("cura/active_mode") == 1: + Application.getInstance().discardOrKeepProfileChanges() + + @pyqtProperty(QObject, fset = setQualityChangesGroup, notify = activeQualityChangesGroupChanged) + def activeQualityChangesGroup(self): + return self._current_quality_changes_group + + @pyqtProperty(str, notify = activeQualityGroupChanged) + def activeQualityOrQualityChangesName(self): + name = self._empty_quality_container.getName() + if self._current_quality_changes_group: + name = self._current_quality_changes_group.name + elif self._current_quality_group: + name = self._current_quality_group.name + return name diff --git a/cura/Settings/MaterialManager.py b/cura/Settings/MaterialManager.py deleted file mode 100644 index 80d2723438..0000000000 --- a/cura/Settings/MaterialManager.py +++ /dev/null @@ -1,57 +0,0 @@ -# Copyright (c) 2017 Ultimaker B.V. -# Cura is released under the terms of the LGPLv3 or higher. - -from PyQt5.QtCore import QObject, pyqtSlot #To expose data to QML. - -from cura.Settings.ContainerManager import ContainerManager -from UM.Logger import Logger -from UM.Message import Message #To create a warning message about material diameter. -from UM.i18n import i18nCatalog #Translated strings. - -catalog = i18nCatalog("cura") - -## Handles material-related data, processing requests to change them and -# providing data for the GUI. -# -# TODO: Move material-related managing over from the machine manager to here. -class MaterialManager(QObject): - ## Creates the global values for the material manager to use. - def __init__(self, parent = None): - super().__init__(parent) - - #Material diameter changed warning message. - self._material_diameter_warning_message = Message(catalog.i18nc("@info:status Has a cancel button next to it.", - "The selected material diameter causes the material to become incompatible with the current printer."), title = catalog.i18nc("@info:title", "Incompatible Material")) - self._material_diameter_warning_message.addAction("Undo", catalog.i18nc("@action:button", "Undo"), None, catalog.i18nc("@action", "Undo changing the material diameter.")) - self._material_diameter_warning_message.actionTriggered.connect(self._materialWarningMessageAction) - - ## Creates an instance of the MaterialManager. - # - # This should only be called by PyQt to create the singleton instance of - # this class. - @staticmethod - def createMaterialManager(engine = None, script_engine = None): - return MaterialManager() - - @pyqtSlot(str, str) - def showMaterialWarningMessage(self, material_id, previous_diameter): - self._material_diameter_warning_message.previous_diameter = previous_diameter #Make sure that the undo button can properly undo the action. - self._material_diameter_warning_message.material_id = material_id - self._material_diameter_warning_message.show() - - ## Called when clicking "undo" on the warning dialogue for disappeared - # materials. - # - # This executes the undo action, restoring the material diameter. - # - # \param button The identifier of the button that was pressed. - def _materialWarningMessageAction(self, message, button): - if button == "Undo": - container_manager = ContainerManager.getInstance() - container_manager.setContainerMetaDataEntry(self._material_diameter_warning_message.material_id, "properties/diameter", self._material_diameter_warning_message.previous_diameter) - approximate_previous_diameter = str(round(float(self._material_diameter_warning_message.previous_diameter))) - container_manager.setContainerMetaDataEntry(self._material_diameter_warning_message.material_id, "approximate_diameter", approximate_previous_diameter) - container_manager.setContainerProperty(self._material_diameter_warning_message.material_id, "material_diameter", "value", self._material_diameter_warning_message.previous_diameter); - message.hide() - else: - Logger.log("w", "Unknown button action for material diameter warning message: {action}".format(action = button)) \ No newline at end of file diff --git a/cura/Settings/MaterialSettingsVisibilityHandler.py b/cura/Settings/MaterialSettingsVisibilityHandler.py index 530284991d..ce545f4551 100644 --- a/cura/Settings/MaterialSettingsVisibilityHandler.py +++ b/cura/Settings/MaterialSettingsVisibilityHandler.py @@ -3,6 +3,7 @@ import UM.Settings.Models.SettingVisibilityHandler + class MaterialSettingsVisibilityHandler(UM.Settings.Models.SettingVisibilityHandler.SettingVisibilityHandler): def __init__(self, parent = None, *args, **kwargs): super().__init__(parent = parent, *args, **kwargs) diff --git a/cura/Settings/MaterialsModel.py b/cura/Settings/MaterialsModel.py deleted file mode 100644 index c4b0329336..0000000000 --- a/cura/Settings/MaterialsModel.py +++ /dev/null @@ -1,37 +0,0 @@ -# Copyright (c) 2017 Ultimaker B.V. -# Cura is released under the terms of the LGPLv3 or higher. - -from typing import Any, List -from UM.Settings.ContainerRegistry import ContainerRegistry #To listen for changes to the materials. -from UM.Settings.Models.InstanceContainersModel import InstanceContainersModel #We're extending this class. - -## A model that shows a list of currently valid materials. -class MaterialsModel(InstanceContainersModel): - def __init__(self, parent = None): - super().__init__(parent) - - ContainerRegistry.getInstance().containerMetaDataChanged.connect(self._onContainerMetaDataChanged) - - ## Called when the metadata of the container was changed. - # - # This makes sure that we only update when it was a material that changed. - # - # \param container The container whose metadata was changed. - def _onContainerMetaDataChanged(self, container): - if container.getMetaDataEntry("type") == "material": #Only need to update if a material was changed. - self._container_change_timer.start() - - def _onContainerChanged(self, container): - if container.getMetaDataEntry("type", "") == "material": - super()._onContainerChanged(container) - - ## Group brand together - def _sortKey(self, item) -> List[Any]: - result = [] - result.append(item["metadata"]["brand"]) - result.append(item["metadata"]["material"]) - result.append(item["metadata"]["name"]) - result.append(item["metadata"]["color_name"]) - result.append(item["metadata"]["id"]) - result.extend(super()._sortKey(item)) - return result diff --git a/cura/Settings/ProfilesModel.py b/cura/Settings/ProfilesModel.py deleted file mode 100644 index 77cd407457..0000000000 --- a/cura/Settings/ProfilesModel.py +++ /dev/null @@ -1,222 +0,0 @@ -# Copyright (c) 2017 Ultimaker B.V. -# Cura is released under the terms of the LGPLv3 or higher. - -from collections import OrderedDict - -from PyQt5.QtCore import Qt - -from UM.Application import Application -from UM.Settings.ContainerRegistry import ContainerRegistry -from UM.Settings.Models.InstanceContainersModel import InstanceContainersModel - -from cura.QualityManager import QualityManager -from cura.Settings.ExtruderManager import ExtruderManager - -from typing import List, TYPE_CHECKING - -if TYPE_CHECKING: - from cura.Settings.ExtruderStack import ExtruderStack - - -## QML Model for listing the current list of valid quality profiles. -# -class ProfilesModel(InstanceContainersModel): - LayerHeightRole = Qt.UserRole + 1001 - LayerHeightWithoutUnitRole = Qt.UserRole + 1002 - AvailableRole = Qt.UserRole + 1003 - - def __init__(self, parent = None): - super().__init__(parent) - self.addRoleName(self.LayerHeightRole, "layer_height") - self.addRoleName(self.LayerHeightWithoutUnitRole, "layer_height_without_unit") - self.addRoleName(self.AvailableRole, "available") - - Application.getInstance().globalContainerStackChanged.connect(self._update) - Application.getInstance().getMachineManager().activeVariantChanged.connect(self._update) - Application.getInstance().getMachineManager().activeStackChanged.connect(self._update) - Application.getInstance().getMachineManager().activeMaterialChanged.connect(self._update) - - self._empty_quality = ContainerRegistry.getInstance().findContainers(id = "empty_quality")[0] - - # Factory function, used by QML - @staticmethod - def createProfilesModel(engine, js_engine): - return ProfilesModel.getInstance() - - ## Get the singleton instance for this class. - @classmethod - def getInstance(cls) -> "ProfilesModel": - # Note: Explicit use of class name to prevent issues with inheritance. - if not ProfilesModel.__instance: - ProfilesModel.__instance = cls() - return ProfilesModel.__instance - - @classmethod - def hasInstance(cls) -> bool: - return ProfilesModel.__instance is not None - - __instance = None # type: "ProfilesModel" - - ## Fetch the list of containers to display. - # - # See UM.Settings.Models.InstanceContainersModel._fetchInstanceContainers(). - def _fetchInstanceContainers(self): - global_container_stack = Application.getInstance().getGlobalContainerStack() - if global_container_stack is None: - return {}, {} - global_stack_definition = global_container_stack.definition - - # Get the list of extruders and place the selected extruder at the front of the list. - extruder_stacks = self._getOrderedExtruderStacksList() - materials = [extruder.material for extruder in extruder_stacks] - - # Fetch the list of usable qualities across all extruders. - # The actual list of quality profiles come from the first extruder in the extruder list. - result = QualityManager.getInstance().findAllUsableQualitiesForMachineAndExtruders(global_container_stack, extruder_stacks) - - # The usable quality types are set - quality_type_set = set([x.getMetaDataEntry("quality_type") for x in result]) - - # Fetch all qualities available for this machine and the materials selected in extruders - all_qualities = QualityManager.getInstance().findAllQualitiesForMachineAndMaterials(global_stack_definition, materials) - - # If in the all qualities there is some of them that are not available due to incompatibility with materials - # we also add it so that they will appear in the slide quality bar. However in recomputeItems will be marked as - # not available so they will be shown in gray - for quality in all_qualities: - if quality.getMetaDataEntry("quality_type") not in quality_type_set: - result.append(quality) - - if len(result) > 1 and self._empty_quality in result: - result.remove(self._empty_quality) - - return {item.getId(): item for item in result}, {} #Only return true profiles for now, no metadata. The quality manager is not able to get only metadata yet. - - ## Re-computes the items in this model, and adds the layer height role. - def _recomputeItems(self): - # Some globals that we can re-use. - global_container_stack = Application.getInstance().getGlobalContainerStack() - if global_container_stack is None: - return - - extruder_stacks = self._getOrderedExtruderStacksList() - container_registry = ContainerRegistry.getInstance() - - # Get a list of usable/available qualities for this machine and material - qualities = QualityManager.getInstance().findAllUsableQualitiesForMachineAndExtruders(global_container_stack, extruder_stacks) - - unit = global_container_stack.getBottom().getProperty("layer_height", "unit") - if not unit: - unit = "" - - # group all quality items according to quality_types, so we know which profile suits the currently - # active machine and material, and later yield the right ones. - tmp_all_quality_items = OrderedDict() - for item in super()._recomputeItems(): - profiles = container_registry.findContainersMetadata(id = item["id"]) - if not profiles or "quality_type" not in profiles[0]: - quality_type = "" - else: - quality_type = profiles[0]["quality_type"] - - if quality_type not in tmp_all_quality_items: - tmp_all_quality_items[quality_type] = {"suitable_container": None, "all_containers": []} - - tmp_all_quality_items[quality_type]["all_containers"].append(item) - if tmp_all_quality_items[quality_type]["suitable_container"] is None: - tmp_all_quality_items[quality_type]["suitable_container"] = item - - # reverse the ordering (finest first, coarsest last) - all_quality_items = OrderedDict() - for key in reversed(tmp_all_quality_items.keys()): - all_quality_items[key] = tmp_all_quality_items[key] - - # First the suitable containers are set in the model - containers = [] - for data_item in all_quality_items.values(): - suitable_item = data_item["suitable_container"] - if suitable_item is not None: - containers.append(suitable_item) - - # Once the suitable containers are collected, the rest of the containers are appended - for data_item in all_quality_items.values(): - for item in data_item["all_containers"]: - if item not in containers: - containers.append(item) - - # Now all the containers are set - for item in containers: - profile = container_registry.findContainers(id = item["id"]) - - # When for some reason there is no profile container in the registry - if not profile: - self._setItemLayerHeight(item, "", "") - item["available"] = False - yield item - continue - - profile = profile[0] - - # When there is a profile but it's an empty quality should. It's shown in the list (they are "Not Supported" profiles) - if profile.getId() == "empty_quality": - self._setItemLayerHeight(item, "", "") - item["available"] = True - yield item - continue - - item["available"] = profile in qualities - - # Easy case: This profile defines its own layer height. - if profile.hasProperty("layer_height", "value"): - self._setItemLayerHeight(item, profile.getProperty("layer_height", "value"), unit) - yield item - continue - - machine_manager = Application.getInstance().getMachineManager() - - # Quality-changes profile that has no value for layer height. Get the corresponding quality profile and ask that profile. - quality_type = profile.getMetaDataEntry("quality_type", None) - if quality_type: - quality_results = machine_manager.determineQualityAndQualityChangesForQualityType(quality_type) - for quality_result in quality_results: - if quality_result["stack"] is global_container_stack: - quality = quality_result["quality"] - break - else: - # No global container stack in the results: - if quality_results: - # Take any of the extruders. - quality = quality_results[0]["quality"] - else: - quality = None - if quality and quality.hasProperty("layer_height", "value"): - self._setItemLayerHeight(item, quality.getProperty("layer_height", "value"), unit) - yield item - continue - - # Quality has no value for layer height either. Get the layer height from somewhere lower in the stack. - skip_until_container = global_container_stack.material - if not skip_until_container or skip_until_container == ContainerRegistry.getInstance().getEmptyInstanceContainer(): # No material in stack. - skip_until_container = global_container_stack.variant - if not skip_until_container or skip_until_container == ContainerRegistry.getInstance().getEmptyInstanceContainer(): # No variant in stack. - skip_until_container = global_container_stack.getBottom() - self._setItemLayerHeight(item, global_container_stack.getRawProperty("layer_height", "value", skip_until_container = skip_until_container.getId()), unit) # Fall through to the currently loaded material. - yield item - - ## Get a list of extruder stacks with the active extruder at the front of the list. - @staticmethod - def _getOrderedExtruderStacksList() -> List["ExtruderStack"]: - extruder_manager = ExtruderManager.getInstance() - extruder_stacks = extruder_manager.getActiveExtruderStacks() - active_extruder = extruder_manager.getActiveExtruderStack() - - if active_extruder in extruder_stacks: - extruder_stacks.remove(active_extruder) - extruder_stacks = [active_extruder] + extruder_stacks - - return extruder_stacks - - @staticmethod - def _setItemLayerHeight(item, value, unit): - item["layer_height"] = str(value) + unit - item["layer_height_without_unit"] = str(value) diff --git a/cura/Settings/QualityAndUserProfilesModel.py b/cura/Settings/QualityAndUserProfilesModel.py deleted file mode 100644 index 645e63acdb..0000000000 --- a/cura/Settings/QualityAndUserProfilesModel.py +++ /dev/null @@ -1,54 +0,0 @@ -# Copyright (c) 2016 Ultimaker B.V. -# Cura is released under the terms of the LGPLv3 or higher. -from UM.Application import Application -from UM.Settings.ContainerRegistry import ContainerRegistry - -from cura.QualityManager import QualityManager -from cura.Settings.ProfilesModel import ProfilesModel -from cura.Settings.ExtruderManager import ExtruderManager - - -## QML Model for listing the current list of valid quality and quality changes profiles. -# -class QualityAndUserProfilesModel(ProfilesModel): - def __init__(self, parent = None): - super().__init__(parent) - - self._empty_quality = ContainerRegistry.getInstance().findInstanceContainers(id = "empty_quality")[0] - - ## Fetch the list of containers to display. - # - # See UM.Settings.Models.InstanceContainersModel._fetchInstanceContainers(). - def _fetchInstanceContainers(self): - global_container_stack = Application.getInstance().getGlobalContainerStack() - if not global_container_stack: - return {}, {} - - # Fetch the list of quality changes. - quality_manager = QualityManager.getInstance() - machine_definition = quality_manager.getParentMachineDefinition(global_container_stack.definition) - quality_changes_list = quality_manager.findAllQualityChangesForMachine(machine_definition) - - extruder_manager = ExtruderManager.getInstance() - active_extruder = extruder_manager.getActiveExtruderStack() - extruder_stacks = self._getOrderedExtruderStacksList() - - # Fetch the list of usable qualities across all extruders. - # The actual list of quality profiles come from the first extruder in the extruder list. - quality_list = quality_manager.findAllUsableQualitiesForMachineAndExtruders(global_container_stack, extruder_stacks) - - # Filter the quality_change by the list of available quality_types - quality_type_set = set([x.getMetaDataEntry("quality_type") for x in quality_list]) - # Also show custom profiles based on "Not Supported" quality profile - quality_type_set.add(self._empty_quality.getMetaDataEntry("quality_type")) - filtered_quality_changes = {qc.getId(): qc for qc in quality_changes_list if - qc.getMetaDataEntry("quality_type") in quality_type_set and - qc.getMetaDataEntry("extruder") is not None and - (qc.getMetaDataEntry("extruder") == active_extruder.definition.getMetaDataEntry("quality_definition") or - qc.getMetaDataEntry("extruder") == active_extruder.definition.getId())} - - result = filtered_quality_changes - for q in quality_list: - if q.getId() != "empty_quality": - result[q.getId()] = q - return result, {} #Only return true profiles for now, no metadata. The quality manager is not able to get only metadata yet. diff --git a/cura/Settings/QualitySettingsModel.py b/cura/Settings/QualitySettingsModel.py deleted file mode 100644 index fb1aa9a6b2..0000000000 --- a/cura/Settings/QualitySettingsModel.py +++ /dev/null @@ -1,249 +0,0 @@ -# Copyright (c) 2017 Ultimaker B.V. -# Cura is released under the terms of the LGPLv3 or higher. - -from PyQt5.QtCore import pyqtProperty, pyqtSignal, Qt - -from UM.Logger import Logger -import UM.Qt -from UM.Application import Application -from UM.Settings.ContainerRegistry import ContainerRegistry -import os - -from UM.i18n import i18nCatalog - - -class QualitySettingsModel(UM.Qt.ListModel.ListModel): - KeyRole = Qt.UserRole + 1 - LabelRole = Qt.UserRole + 2 - UnitRole = Qt.UserRole + 3 - ProfileValueRole = Qt.UserRole + 4 - ProfileValueSourceRole = Qt.UserRole + 5 - UserValueRole = Qt.UserRole + 6 - CategoryRole = Qt.UserRole + 7 - - def __init__(self, parent = None): - super().__init__(parent = parent) - - self._container_registry = ContainerRegistry.getInstance() - - self._extruder_id = None - self._extruder_definition_id = None - self._quality_id = None - self._material_id = None - self._i18n_catalog = None - - self.addRoleName(self.KeyRole, "key") - self.addRoleName(self.LabelRole, "label") - self.addRoleName(self.UnitRole, "unit") - self.addRoleName(self.ProfileValueRole, "profile_value") - self.addRoleName(self.ProfileValueSourceRole, "profile_value_source") - self.addRoleName(self.UserValueRole, "user_value") - self.addRoleName(self.CategoryRole, "category") - - self._empty_quality = self._container_registry.findInstanceContainers(id = "empty_quality")[0] - - def setExtruderId(self, extruder_id): - if extruder_id != self._extruder_id: - self._extruder_id = extruder_id - self._update() - self.extruderIdChanged.emit() - - extruderIdChanged = pyqtSignal() - @pyqtProperty(str, fset = setExtruderId, notify = extruderIdChanged) - def extruderId(self): - return self._extruder_id - - def setExtruderDefinition(self, extruder_definition): - if extruder_definition != self._extruder_definition_id: - self._extruder_definition_id = extruder_definition - self._update() - self.extruderDefinitionChanged.emit() - - extruderDefinitionChanged = pyqtSignal() - @pyqtProperty(str, fset = setExtruderDefinition, notify = extruderDefinitionChanged) - def extruderDefinition(self): - return self._extruder_definition_id - - def setQuality(self, quality): - if quality != self._quality_id: - self._quality_id = quality - self._update() - self.qualityChanged.emit() - - qualityChanged = pyqtSignal() - @pyqtProperty(str, fset = setQuality, notify = qualityChanged) - def quality(self): - return self._quality_id - - def setMaterial(self, material): - if material != self._material_id: - self._material_id = material - self._update() - self.materialChanged.emit() - - materialChanged = pyqtSignal() - @pyqtProperty(str, fset = setMaterial, notify = materialChanged) - def material(self): - return self._material_id - - def _update(self): - if not self._quality_id: - return - - items = [] - - definition_container = Application.getInstance().getGlobalContainerStack().getBottom() - - containers = self._container_registry.findInstanceContainers(id = self._quality_id) - if not containers: - Logger.log("w", "Could not find a quality container with id %s", self._quality_id) - return - - quality_container = None - quality_changes_container = None - - if containers[0].getMetaDataEntry("type") == "quality": - quality_container = containers[0] - else: - quality_changes_container = containers[0] - - if quality_changes_container.getMetaDataEntry("quality_type") == self._empty_quality.getMetaDataEntry("quality_type"): - quality_container = self._empty_quality - else: - criteria = { - "type": "quality", - "quality_type": quality_changes_container.getMetaDataEntry("quality_type"), - "definition": quality_changes_container.getDefinition().getId() - } - - quality_container = self._container_registry.findInstanceContainers(**criteria) - if not quality_container: - Logger.log("w", "Could not find a quality container matching quality changes %s", quality_changes_container.getId()) - return - - quality_container = quality_container[0] - - quality_type = quality_container.getMetaDataEntry("quality_type") - - if quality_type == "not_supported": - containers = [] - else: - definition_id = Application.getInstance().getMachineManager().getQualityDefinitionId(quality_container.getDefinition()) - definition = quality_container.getDefinition() - - # Check if the definition container has a translation file. - definition_suffix = ContainerRegistry.getMimeTypeForContainer(type(definition)).preferredSuffix - catalog = i18nCatalog(os.path.basename(definition_id + "." + definition_suffix)) - if catalog.hasTranslationLoaded(): - self._i18n_catalog = catalog - - for file_name in quality_container.getDefinition().getInheritedFiles(): - catalog = i18nCatalog(os.path.basename(file_name)) - if catalog.hasTranslationLoaded(): - self._i18n_catalog = catalog - - criteria = {"type": "quality", "quality_type": quality_type, "definition": definition_id} - - if self._material_id and self._material_id != "empty_material": - criteria["material"] = self._material_id - - criteria["extruder"] = self._extruder_id - - containers = self._container_registry.findInstanceContainers(**criteria) - if not containers: - # Try again, this time without extruder - new_criteria = criteria.copy() - new_criteria.pop("extruder") - containers = self._container_registry.findInstanceContainers(**new_criteria) - - if not containers and "material" in criteria: - # Try again, this time without material - criteria.pop("material", None) - containers = self._container_registry.findInstanceContainers(**criteria) - - if not containers: - # Try again, this time without material or extruder - criteria.pop("extruder") # "material" has already been popped - containers = self._container_registry.findInstanceContainers(**criteria) - - if not containers: - Logger.log("w", "Could not find any quality containers matching the search criteria %s" % str(criteria)) - return - - if quality_changes_container: - if quality_type == "not_supported": - criteria = {"type": "quality_changes", "quality_type": quality_type, "name": quality_changes_container.getName()} - else: - criteria = {"type": "quality_changes", "quality_type": quality_type, "definition": definition_id, "name": quality_changes_container.getName()} - if self._extruder_definition_id != "": - extruder_definitions = self._container_registry.findDefinitionContainers(id = self._extruder_definition_id) - if extruder_definitions: - criteria["extruder"] = Application.getInstance().getMachineManager().getQualityDefinitionId(extruder_definitions[0]) - criteria["name"] = quality_changes_container.getName() - else: - criteria["extruder"] = None - - changes = self._container_registry.findInstanceContainers(**criteria) - if changes: - containers.extend(changes) - - global_container_stack = Application.getInstance().getGlobalContainerStack() - - current_category = "" - for definition in definition_container.findDefinitions(): - if definition.type == "category": - current_category = definition.label - if self._i18n_catalog: - current_category = self._i18n_catalog.i18nc(definition.key + " label", definition.label) - continue - - profile_value = None - profile_value_source = "" - for container in containers: - new_value = container.getProperty(definition.key, "value") - - if new_value is not None: - profile_value_source = container.getMetaDataEntry("type") - profile_value = new_value - - # Global tab should use resolve (if there is one) - if not self._extruder_id: - resolve_value = global_container_stack.getProperty(definition.key, "resolve") - if resolve_value is not None and profile_value is not None and profile_value_source != "quality_changes": - profile_value = resolve_value - - user_value = None - if not self._extruder_id: - user_value = global_container_stack.getTop().getProperty(definition.key, "value") - else: - extruder_stack = self._container_registry.findContainerStacks(id = self._extruder_id) - if extruder_stack: - user_value = extruder_stack[0].getTop().getProperty(definition.key, "value") - - if profile_value is None and user_value is None: - continue - - settable_per_extruder = global_container_stack.getProperty(definition.key, "settable_per_extruder") - # If a setting is not settable per extruder (global) and we're looking at an extruder tab, don't show this value. - if self._extruder_id != "" and not settable_per_extruder: - continue - - # If a setting is settable per extruder (not global) and we're looking at global tab, don't show this value. - if self._extruder_id == "" and settable_per_extruder: - continue - - label = definition.label - if self._i18n_catalog: - label = self._i18n_catalog.i18nc(definition.key + " label", label) - - items.append({ - "key": definition.key, - "label": label, - "unit": definition.unit, - "profile_value": "" if profile_value is None else str(profile_value), # it is for display only - "profile_value_source": profile_value_source, - "user_value": "" if user_value is None else str(user_value), - "category": current_category - }) - - self.setItems(items) diff --git a/cura/Settings/UserProfilesModel.py b/cura/Settings/UserProfilesModel.py deleted file mode 100644 index 6605f52f8a..0000000000 --- a/cura/Settings/UserProfilesModel.py +++ /dev/null @@ -1,85 +0,0 @@ -# Copyright (c) 2017 Ultimaker B.V. -# Cura is released under the terms of the LGPLv3 or higher. - -from UM.Application import Application -from UM.Settings.ContainerRegistry import ContainerRegistry - -from cura.QualityManager import QualityManager -from cura.Settings.ProfilesModel import ProfilesModel -from cura.Settings.ExtruderManager import ExtruderManager - -## QML Model for listing the current list of valid quality changes profiles. -# -class UserProfilesModel(ProfilesModel): - def __init__(self, parent = None): - super().__init__(parent) - - #Need to connect to the metaDataChanged signal of the active materials. - self.__current_extruders = [] - self.__current_materials = [] - - Application.getInstance().getExtruderManager().extrudersChanged.connect(self.__onExtrudersChanged) - self.__onExtrudersChanged() - self.__current_materials = [extruder.material for extruder in self.__current_extruders] - for material in self.__current_materials: - material.metaDataChanged.connect(self._onContainerChanged) - - self._empty_quality = ContainerRegistry.getInstance().findContainers(id = "empty_quality")[0] - - ## Fetch the list of containers to display. - # - # See UM.Settings.Models.InstanceContainersModel._fetchInstanceContainers(). - def _fetchInstanceContainers(self): - global_container_stack = Application.getInstance().getGlobalContainerStack() - if not global_container_stack: - return {}, {} - - # Fetch the list of quality changes. - quality_manager = QualityManager.getInstance() - machine_definition = quality_manager.getParentMachineDefinition(global_container_stack.definition) - quality_changes_list = quality_manager.findAllQualityChangesForMachine(machine_definition) - - extruder_manager = ExtruderManager.getInstance() - active_extruder = extruder_manager.getActiveExtruderStack() - extruder_stacks = self._getOrderedExtruderStacksList() - - # Fetch the list of usable qualities across all extruders. - # The actual list of quality profiles come from the first extruder in the extruder list. - quality_list = quality_manager.findAllUsableQualitiesForMachineAndExtruders(global_container_stack, extruder_stacks) - - # Filter the quality_change by the list of available quality_types - quality_type_set = set([x.getMetaDataEntry("quality_type") for x in quality_list]) - quality_type_set.add(self._empty_quality.getMetaDataEntry("quality_type")) - - filtered_quality_changes = {qc.getId():qc for qc in quality_changes_list if - qc.getMetaDataEntry("quality_type") in quality_type_set and - qc.getMetaDataEntry("extruder") is not None and - (qc.getMetaDataEntry("extruder") == active_extruder.definition.getMetaDataEntry("quality_definition") or - qc.getMetaDataEntry("extruder") == active_extruder.definition.getId())} - - return filtered_quality_changes, {} #Only return true profiles for now, no metadata. The quality manager is not able to get only metadata yet. - - ## Called when a container changed on an extruder stack. - # - # If it's the material we need to connect to the metaDataChanged signal of - # that. - def __onContainerChanged(self, new_container): - #Careful not to update when a quality or quality changes profile changed! - #If you then update you're going to have an infinite recursion because the update may change the container. - if new_container.getMetaDataEntry("type") == "material": - for material in self.__current_materials: - material.metaDataChanged.disconnect(self._onContainerChanged) - self.__current_materials = [extruder.material for extruder in self.__current_extruders] - for material in self.__current_materials: - material.metaDataChanged.connect(self._onContainerChanged) - - ## Called when the current set of extruders change. - # - # This makes sure that we are listening to the signal for when the - # materials change. - def __onExtrudersChanged(self): - for extruder in self.__current_extruders: - extruder.containersChanged.disconnect(self.__onContainerChanged) - self.__current_extruders = Application.getInstance().getExtruderManager().getExtruderStacks() - for extruder in self.__current_extruders: - extruder.containersChanged.connect(self.__onContainerChanged) \ No newline at end of file diff --git a/plugins/3MFReader/ThreeMFReader.py b/plugins/3MFReader/ThreeMFReader.py index 1726818100..ec590a0212 100755 --- a/plugins/3MFReader/ThreeMFReader.py +++ b/plugins/3MFReader/ThreeMFReader.py @@ -4,26 +4,28 @@ import os.path import zipfile +import numpy + +import Savitar + +from UM.Application import Application from UM.Logger import Logger from UM.Math.Matrix import Matrix from UM.Math.Vector import Vector from UM.Mesh.MeshBuilder import MeshBuilder from UM.Mesh.MeshReader import MeshReader from UM.Scene.GroupDecorator import GroupDecorator + from cura.Settings.SettingOverrideDecorator import SettingOverrideDecorator -from UM.Application import Application from cura.Settings.ExtruderManager import ExtruderManager -from cura.QualityManager import QualityManager from cura.Scene.CuraSceneNode import CuraSceneNode from cura.Scene.BuildPlateDecorator import BuildPlateDecorator from cura.Scene.SliceableObjectDecorator import SliceableObjectDecorator from cura.Scene.ZOffsetDecorator import ZOffsetDecorator +from cura.Machines.QualityManager import getMachineDefinitionIDForQualitySearch MYPY = False -import Savitar -import numpy - try: if not MYPY: import xml.etree.cElementTree as ET @@ -77,7 +79,7 @@ class ThreeMFReader(MeshReader): self._object_count += 1 node_name = "Object %s" % self._object_count - active_build_plate = Application.getInstance().getBuildPlateModel().activeBuildPlate + active_build_plate = Application.getInstance().getMultiBuildPlateModel().activeBuildPlate um_node = CuraSceneNode() um_node.addDecorator(BuildPlateDecorator(active_build_plate)) @@ -120,8 +122,8 @@ class ThreeMFReader(MeshReader): um_node.callDecoration("setActiveExtruder", default_stack.getId()) # Get the definition & set it - definition = QualityManager.getInstance().getParentMachineDefinition(global_container_stack.getBottom()) - um_node.callDecoration("getStack").getTop().setDefinition(definition.getId()) + definition_id = getMachineDefinitionIDForQualitySearch(global_container_stack) + um_node.callDecoration("getStack").getTop().setDefinition(definition_id) setting_container = um_node.callDecoration("getStack").getTop() diff --git a/plugins/3MFReader/ThreeMFWorkspaceReader.py b/plugins/3MFReader/ThreeMFWorkspaceReader.py index 08234aa8be..cbe882f253 100755 --- a/plugins/3MFReader/ThreeMFWorkspaceReader.py +++ b/plugins/3MFReader/ThreeMFWorkspaceReader.py @@ -23,7 +23,6 @@ from cura.Settings.ExtruderManager import ExtruderManager from cura.Settings.ExtruderStack import ExtruderStack from cura.Settings.GlobalStack import GlobalStack from cura.Settings.CuraContainerStack import _ContainerIndexes -from cura.QualityManager import QualityManager from cura.CuraApplication import CuraApplication from configparser import ConfigParser @@ -855,10 +854,11 @@ class ThreeMFWorkspaceReader(WorkspaceReader): if machine_extruder_count is not None: extruder_stacks_in_use = extruder_stacks[:machine_extruder_count] - available_quality = QualityManager.getInstance().findAllUsableQualitiesForMachineAndExtruders(global_stack, - extruder_stacks_in_use) + quality_manager = CuraApplication.getInstance()._quality_manager + all_quality_groups = quality_manager.getQualityGroups(global_stack) + available_quality_types = [qt for qt, qg in all_quality_groups.items() if qg.is_available] if not has_not_supported: - has_not_supported = not available_quality + has_not_supported = not available_quality_types quality_has_been_changed = False @@ -872,8 +872,6 @@ class ThreeMFWorkspaceReader(WorkspaceReader): # The machine in the project has non-empty quality and there are usable qualities for this machine. # We need to check if the current quality_type is still usable for this machine, if not, then the quality # will be reset to the "preferred quality" if present, otherwise "normal". - available_quality_types = [q.getMetaDataEntry("quality_type") for q in available_quality] - if global_stack.quality.getMetaDataEntry("quality_type") not in available_quality_types: # We are here because the quality_type specified in the project is not supported any more, # so we need to switch it to the "preferred quality" if present, otherwise "normal". @@ -1084,10 +1082,13 @@ class ThreeMFWorkspaceReader(WorkspaceReader): CuraApplication.getInstance().getMachineManager().activeQualityChanged.emit() # Actually change the active machine. - Application.getInstance().setGlobalContainerStack(global_stack) - - # Notify everything/one that is to notify about changes. - global_stack.containersChanged.emit(global_stack.getTop()) + # + # This is scheduled for later is because it depends on the Variant/Material/Qualitiy Managers to have the latest + # data, but those managers will only update upon a container/container metadata changed signal. Because this + # function is running on the main thread (Qt thread), although those "changed" signals have been emitted, but + # they won't take effect until this function is done. + # To solve this, we schedule _updateActiveMachine() for later so it will have the latest data. + CuraApplication.getInstance().callLater(self._updateActiveMachine, global_stack) # Load all the nodes / meshdata of the workspace nodes = self._3mf_mesh_reader.read(file_name) @@ -1100,6 +1101,14 @@ class ThreeMFWorkspaceReader(WorkspaceReader): self.setWorkspaceName(base_file_name) return nodes + def _updateActiveMachine(self, global_stack): + # Actually change the active machine. + machine_manager = Application.getInstance().getMachineManager() + machine_manager.setActiveMachine(global_stack.getId()) + + # Notify everything/one that is to notify about changes. + global_stack.containersChanged.emit(global_stack.getTop()) + ## HACK: Replaces the material container in the given stack with a newly created material container. # This function is used when the user chooses to resolve material conflicts by creating new ones. def _replaceStackMaterialWithNew(self, stack, old_new_material_dict): diff --git a/plugins/3MFWriter/ThreeMFWriter.py b/plugins/3MFWriter/ThreeMFWriter.py index c4b7035cf1..ff6333763a 100644 --- a/plugins/3MFWriter/ThreeMFWriter.py +++ b/plugins/3MFWriter/ThreeMFWriter.py @@ -68,7 +68,7 @@ class ThreeMFWriter(MeshWriter): if not isinstance(um_node, SceneNode): return None - active_build_plate_nr = CuraApplication.getInstance().getBuildPlateModel().activeBuildPlate + active_build_plate_nr = CuraApplication.getInstance().getMultiBuildPlateModel().activeBuildPlate if um_node.callDecoration("getBuildPlateNumber") != active_build_plate_nr: return diff --git a/plugins/CuraEngineBackend/CuraEngineBackend.py b/plugins/CuraEngineBackend/CuraEngineBackend.py index 79fa12114f..3982a0ad06 100755 --- a/plugins/CuraEngineBackend/CuraEngineBackend.py +++ b/plugins/CuraEngineBackend/CuraEngineBackend.py @@ -70,7 +70,7 @@ class CuraEngineBackend(QObject, Backend): # Workaround to disable layer view processing if layer view is not active. self._layer_view_active = False Application.getInstance().getController().activeViewChanged.connect(self._onActiveViewChanged) - Application.getInstance().getBuildPlateModel().activeBuildPlateChanged.connect(self._onActiveViewChanged) + Application.getInstance().getMultiBuildPlateModel().activeBuildPlateChanged.connect(self._onActiveViewChanged) self._onActiveViewChanged() self._stored_layer_data = [] self._stored_optimized_layer_data = {} # key is build plate number, then arrays are stored until they go to the ProcessSlicesLayersJob @@ -88,7 +88,6 @@ class CuraEngineBackend(QObject, Backend): # self._global_container_stack = None Application.getInstance().globalContainerStackChanged.connect(self._onGlobalStackChanged) - Application.getInstance().getExtruderManager().extrudersAdded.connect(self._onGlobalStackChanged) self._onGlobalStackChanged() Application.getInstance().stacksValidationFinished.connect(self._onStackErrorCheckFinished) @@ -207,7 +206,7 @@ class CuraEngineBackend(QObject, Backend): self._scene.gcode_dict = {} # see if we really have to slice - active_build_plate = Application.getInstance().getBuildPlateModel().activeBuildPlate + active_build_plate = Application.getInstance().getMultiBuildPlateModel().activeBuildPlate build_plate_to_be_sliced = self._build_plates_to_be_sliced.pop(0) Logger.log("d", "Going to slice build plate [%s]!" % build_plate_to_be_sliced) num_objects = self._numObjects() @@ -497,7 +496,7 @@ class CuraEngineBackend(QObject, Backend): node.getParent().removeChild(node) def markSliceAll(self): - for build_plate_number in range(Application.getInstance().getBuildPlateModel().maxBuildPlate + 1): + for build_plate_number in range(Application.getInstance().getMultiBuildPlateModel().maxBuildPlate + 1): if build_plate_number not in self._build_plates_to_be_sliced: self._build_plates_to_be_sliced.append(build_plate_number) @@ -582,7 +581,7 @@ class CuraEngineBackend(QObject, Backend): Logger.log("d", "Slicing took %s seconds", time() - self._slice_start_time ) # See if we need to process the sliced layers job. - active_build_plate = Application.getInstance().getBuildPlateModel().activeBuildPlate + active_build_plate = Application.getInstance().getMultiBuildPlateModel().activeBuildPlate if self._layer_view_active and (self._process_layers_job is None or not self._process_layers_job.isRunning()) and active_build_plate == self._start_slice_job_build_plate: self._startProcessSlicedLayersJob(active_build_plate) # self._onActiveViewChanged() @@ -702,7 +701,7 @@ class CuraEngineBackend(QObject, Backend): application = Application.getInstance() view = application.getController().getActiveView() if view: - active_build_plate = application.getBuildPlateModel().activeBuildPlate + active_build_plate = application.getMultiBuildPlateModel().activeBuildPlate if view.getPluginId() == "SimulationView": # If switching to layer view, we should process the layers if that hasn't been done yet. self._layer_view_active = True # There is data and we're not slicing at the moment diff --git a/plugins/CuraEngineBackend/ProcessGCodeJob.py b/plugins/CuraEngineBackend/ProcessGCodeJob.py index ed430f8fa9..817daa9f85 100644 --- a/plugins/CuraEngineBackend/ProcessGCodeJob.py +++ b/plugins/CuraEngineBackend/ProcessGCodeJob.py @@ -12,6 +12,6 @@ class ProcessGCodeLayerJob(Job): self._message = message def run(self): - active_build_plate_id = Application.getInstance().getBuildPlateModel().activeBuildPlate + active_build_plate_id = Application.getInstance().getMultiBuildPlateModel().activeBuildPlate gcode_list = self._scene.gcode_dict[active_build_plate_id] gcode_list.append(self._message.data.decode("utf-8", "replace")) diff --git a/plugins/GCodeReader/FlavorParser.py b/plugins/GCodeReader/FlavorParser.py index f63ba3ca69..c064ffbf10 100644 --- a/plugins/GCodeReader/FlavorParser.py +++ b/plugins/GCodeReader/FlavorParser.py @@ -437,7 +437,7 @@ class FlavorParser: scene_node.addDecorator(gcode_list_decorator) # gcode_dict stores gcode_lists for a number of build plates. - active_build_plate_id = Application.getInstance().getBuildPlateModel().activeBuildPlate + active_build_plate_id = Application.getInstance().getMultiBuildPlateModel().activeBuildPlate gcode_dict = {active_build_plate_id: gcode_list} Application.getInstance().getController().getScene().gcode_dict = gcode_dict diff --git a/plugins/GCodeWriter/GCodeWriter.py b/plugins/GCodeWriter/GCodeWriter.py index 225800454f..1b3b7264a1 100644 --- a/plugins/GCodeWriter/GCodeWriter.py +++ b/plugins/GCodeWriter/GCodeWriter.py @@ -60,7 +60,7 @@ class GCodeWriter(MeshWriter): Logger.log("e", "GCodeWriter does not support non-text mode.") return False - active_build_plate = Application.getInstance().getBuildPlateModel().activeBuildPlate + active_build_plate = Application.getInstance().getMultiBuildPlateModel().activeBuildPlate scene = Application.getInstance().getController().getScene() gcode_dict = getattr(scene, "gcode_dict") if not gcode_dict: diff --git a/plugins/PerObjectSettingsTool/PerObjectItem.qml b/plugins/PerObjectSettingsTool/PerObjectItem.qml index 89679b57a2..1317c00b19 100644 --- a/plugins/PerObjectSettingsTool/PerObjectItem.qml +++ b/plugins/PerObjectSettingsTool/PerObjectItem.qml @@ -32,11 +32,11 @@ UM.TooltipArea if(checked) { addedSettingsModel.setVisible(model.key, checked); - UM.ActiveTool.triggerAction("subscribeForSettingValidation", model.key) + UM.ActiveTool.triggerActionWithData("subscribeForSettingValidation", model.key) } else { - UM.ActiveTool.triggerAction("unsubscribeForSettingValidation", model.key) + UM.ActiveTool.triggerActionWithData("unsubscribeForSettingValidation", model.key) addedSettingsModel.setVisible(model.key, checked); } UM.ActiveTool.forceUpdate(); diff --git a/plugins/PerObjectSettingsTool/PerObjectSettingsPanel.qml b/plugins/PerObjectSettingsTool/PerObjectSettingsPanel.qml index 4b5d2a5708..e72e1224df 100644 --- a/plugins/PerObjectSettingsTool/PerObjectSettingsPanel.qml +++ b/plugins/PerObjectSettingsTool/PerObjectSettingsPanel.qml @@ -242,7 +242,7 @@ Item { onClicked: { addedSettingsModel.setVisible(model.key, false) - UM.ActiveTool.triggerAction("unsubscribeForSettingValidation", model.key) + UM.ActiveTool.triggerActionWithData("unsubscribeForSettingValidation", model.key) } style: ButtonStyle diff --git a/plugins/PostProcessingPlugin/PostProcessingPlugin.py b/plugins/PostProcessingPlugin/PostProcessingPlugin.py index f491afbec0..566b05abf3 100644 --- a/plugins/PostProcessingPlugin/PostProcessingPlugin.py +++ b/plugins/PostProcessingPlugin/PostProcessingPlugin.py @@ -62,7 +62,7 @@ class PostProcessingPlugin(QObject, Extension): return # get gcode list for the active build plate - active_build_plate_id = Application.getInstance().getBuildPlateModel().activeBuildPlate + active_build_plate_id = Application.getInstance().getMultiBuildPlateModel().activeBuildPlate gcode_list = gcode_dict[active_build_plate_id] if not gcode_list: return diff --git a/plugins/SimulationView/SimulationPass.py b/plugins/SimulationView/SimulationPass.py index 76d7127534..cd0eda2929 100644 --- a/plugins/SimulationView/SimulationPass.py +++ b/plugins/SimulationView/SimulationPass.py @@ -93,7 +93,7 @@ class SimulationPass(RenderPass): self.bind() tool_handle_batch = RenderBatch(self._tool_handle_shader, type = RenderBatch.RenderType.Overlay, backface_cull = True) - active_build_plate = Application.getInstance().getBuildPlateModel().activeBuildPlate + active_build_plate = Application.getInstance().getMultiBuildPlateModel().activeBuildPlate head_position = None # Indicates the current position of the print head nozzle_node = None diff --git a/plugins/SupportEraser/SupportEraser.py b/plugins/SupportEraser/SupportEraser.py index 4e55702687..8b3ad0f4dd 100644 --- a/plugins/SupportEraser/SupportEraser.py +++ b/plugins/SupportEraser/SupportEraser.py @@ -45,7 +45,7 @@ class SupportEraser(Tool): move_vector = Vector(0, 5, 0) node.setPosition(move_vector) - active_build_plate = Application.getInstance().getBuildPlateModel().activeBuildPlate + active_build_plate = Application.getInstance().getMultiBuildPlateModel().activeBuildPlate node.addDecorator(SettingOverrideDecorator()) node.addDecorator(BuildPlateDecorator(active_build_plate)) diff --git a/plugins/UM3NetworkPrinting/ClusterUM3OutputDevice.py b/plugins/UM3NetworkPrinting/ClusterUM3OutputDevice.py index a4d6998131..fa9abb8d4e 100644 --- a/plugins/UM3NetworkPrinting/ClusterUM3OutputDevice.py +++ b/plugins/UM3NetworkPrinting/ClusterUM3OutputDevice.py @@ -81,7 +81,7 @@ class ClusterUM3OutputDevice(NetworkedPrinterOutputDevice): self.writeStarted.emit(self) gcode_dict = getattr(Application.getInstance().getController().getScene(), "gcode_dict", []) - active_build_plate_id = Application.getInstance().getBuildPlateModel().activeBuildPlate + active_build_plate_id = Application.getInstance().getMultiBuildPlateModel().activeBuildPlate gcode_list = gcode_dict[active_build_plate_id] if not gcode_list: diff --git a/plugins/UM3NetworkPrinting/LegacyUM3OutputDevice.py b/plugins/UM3NetworkPrinting/LegacyUM3OutputDevice.py index 87d4b9ec0a..42f00beceb 100644 --- a/plugins/UM3NetworkPrinting/LegacyUM3OutputDevice.py +++ b/plugins/UM3NetworkPrinting/LegacyUM3OutputDevice.py @@ -184,7 +184,7 @@ class LegacyUM3OutputDevice(NetworkedPrinterOutputDevice): self.writeStarted.emit(self) gcode_dict = getattr(Application.getInstance().getController().getScene(), "gcode_dict", []) - active_build_plate_id = Application.getInstance().getBuildPlateModel().activeBuildPlate + active_build_plate_id = Application.getInstance().getMultiBuildPlateModel().activeBuildPlate gcode_list = gcode_dict[active_build_plate_id] if not gcode_list: diff --git a/plugins/USBPrinting/USBPrinterOutputDevice.py b/plugins/USBPrinting/USBPrinterOutputDevice.py index b53f502d81..6e2b5153db 100644 --- a/plugins/USBPrinting/USBPrinterOutputDevice.py +++ b/plugins/USBPrinting/USBPrinterOutputDevice.py @@ -99,7 +99,7 @@ class USBPrinterOutputDevice(PrinterOutputDevice): Application.getInstance().getController().setActiveStage("MonitorStage") # find the G-code for the active build plate to print - active_build_plate_id = Application.getInstance().getBuildPlateModel().activeBuildPlate + active_build_plate_id = Application.getInstance().getMultiBuildPlateModel().activeBuildPlate gcode_dict = getattr(Application.getInstance().getController().getScene(), "gcode_dict") gcode_list = gcode_dict[active_build_plate_id] diff --git a/plugins/VersionUpgrade/VersionUpgrade30to31/VersionUpgrade30to31.py b/plugins/VersionUpgrade/VersionUpgrade30to31/VersionUpgrade30to31.py index d7b2c1a001..a88ff5ac1c 100644 --- a/plugins/VersionUpgrade/VersionUpgrade30to31/VersionUpgrade30to31.py +++ b/plugins/VersionUpgrade/VersionUpgrade30to31/VersionUpgrade30to31.py @@ -3,14 +3,9 @@ import configparser #To parse preference files. import io #To serialise the preference files afterwards. -import os -from urllib.parse import quote_plus -from UM.Resources import Resources from UM.VersionUpgrade import VersionUpgrade #We're inheriting from this. -from cura.CuraApplication import CuraApplication - # a list of all legacy "Not Supported" quality profiles _OLD_NOT_SUPPORTED_PROFILES = [ @@ -130,7 +125,6 @@ class VersionUpgrade30to31(VersionUpgrade): parser.write(output) return [filename], [output.getvalue()] - ## Upgrades a container stack from version 3.0 to 3.1. # # \param serialised The serialised form of a container stack. @@ -172,71 +166,3 @@ class VersionUpgrade30to31(VersionUpgrade): output = io.StringIO() parser.write(output) return [filename], [output.getvalue()] - - def _getSingleExtrusionMachineQualityChanges(self, quality_changes_container): - quality_changes_dir = Resources.getPath(CuraApplication.ResourceTypes.QualityInstanceContainer) - quality_changes_containers = [] - - for item in os.listdir(quality_changes_dir): - file_path = os.path.join(quality_changes_dir, item) - if not os.path.isfile(file_path): - continue - - parser = configparser.ConfigParser(interpolation = None) - try: - parser.read([file_path]) - except: - # skip, it is not a valid stack file - continue - - if not parser.has_option("metadata", "type"): - continue - if "quality_changes" != parser["metadata"]["type"]: - continue - - if not parser.has_option("general", "name"): - continue - if quality_changes_container["general"]["name"] != parser["general"]["name"]: - continue - - quality_changes_containers.append(parser) - - return quality_changes_containers - - def _createExtruderQualityChangesForSingleExtrusionMachine(self, filename, global_quality_changes): - suffix = "_" + quote_plus(global_quality_changes["general"]["name"].lower()) - machine_name = os.path.os.path.basename(filename).replace(".inst.cfg", "").replace(suffix, "") - - # Why is this here?! - # When we load a .curaprofile file the deserialize will trigger a version upgrade, creating a dangling file. - # This file can be recognized by it's lack of a machine name in the target filename. - # So when we detect that situation here, we don't create the file and return. - if machine_name == "": - return - - new_filename = machine_name + "_" + "fdmextruder" + suffix - - extruder_quality_changes_parser = configparser.ConfigParser(interpolation = None) - extruder_quality_changes_parser.add_section("general") - extruder_quality_changes_parser["general"]["version"] = str(2) - extruder_quality_changes_parser["general"]["name"] = global_quality_changes["general"]["name"] - extruder_quality_changes_parser["general"]["definition"] = global_quality_changes["general"]["definition"] - - # check renamed definition - if extruder_quality_changes_parser["general"]["definition"] in _RENAMED_DEFINITION_DICT: - extruder_quality_changes_parser["general"]["definition"] = _RENAMED_DEFINITION_DICT[extruder_quality_changes_parser["general"]["definition"]] - - extruder_quality_changes_parser.add_section("metadata") - extruder_quality_changes_parser["metadata"]["quality_type"] = global_quality_changes["metadata"]["quality_type"] - extruder_quality_changes_parser["metadata"]["type"] = global_quality_changes["metadata"]["type"] - extruder_quality_changes_parser["metadata"]["setting_version"] = str(4) - extruder_quality_changes_parser["metadata"]["extruder"] = "fdmextruder" - - extruder_quality_changes_output = io.StringIO() - extruder_quality_changes_parser.write(extruder_quality_changes_output) - extruder_quality_changes_filename = quote_plus(new_filename) + ".inst.cfg" - - quality_changes_dir = Resources.getPath(CuraApplication.ResourceTypes.QualityInstanceContainer) - - with open(os.path.join(quality_changes_dir, extruder_quality_changes_filename), "w", encoding = "utf-8") as f: - f.write(extruder_quality_changes_output.getvalue()) diff --git a/plugins/XmlMaterialProfile/XmlMaterialProfile.py b/plugins/XmlMaterialProfile/XmlMaterialProfile.py index f0d016025e..edc782cc9e 100644 --- a/plugins/XmlMaterialProfile/XmlMaterialProfile.py +++ b/plugins/XmlMaterialProfile/XmlMaterialProfile.py @@ -48,18 +48,35 @@ class XmlMaterialProfile(InstanceContainer): ## Overridden from InstanceContainer # set the meta data for all machine / variant combinations - def setMetaDataEntry(self, key, value): + # + # The "apply_to_all" flag indicates whether this piece of metadata should be applied to all material containers + # or just this specific container. + # For example, when you change the material name, you want to apply it to all its derived containers, but for + # some specific settings, they should only be applied to a machine/variant-specific container. + # + def setMetaDataEntry(self, key, value, apply_to_all = True): registry = ContainerRegistry.getInstance() if registry.isReadOnly(self.getId()): return - super().setMetaDataEntry(key, value) + # Prevent recursion + if not apply_to_all: + super().setMetaDataEntry(key, value) + return - basefile = self.getMetaDataEntry("base_file", self.getId()) #if basefile is self.getId, this is a basefile. - # Update all containers that share basefile - for container in registry.findInstanceContainers(base_file = basefile): - if container.getMetaDataEntry(key, None) != value: # Prevent recursion - container.setMetaDataEntry(key, value) + # Get the MaterialGroup + material_manager = CuraApplication.getInstance().getMaterialManager() + root_material_id = self.getMetaDataEntry("base_file") #if basefile is self.getId, this is a basefile. + material_group = material_manager.getMaterialGroup(root_material_id) + + # Update the root material container + root_material_container = material_group.root_material_node.getContainer() + root_material_container.setMetaDataEntry(key, value, apply_to_all = False) + + # Update all containers derived from it + for node in material_group.derived_material_node_list: + container = node.getContainer() + container.setMetaDataEntry(key, value, apply_to_all = False) ## Overridden from InstanceContainer, similar to setMetaDataEntry. # without this function the setName would only set the name of the specific nozzle / material / machine combination container @@ -190,6 +207,8 @@ class XmlMaterialProfile(InstanceContainer): machine_container_map = {} machine_nozzle_map = {} + variant_manager = CuraApplication.getInstance()._variant_manager + all_containers = registry.findInstanceContainers(GUID = self.getMetaDataEntry("GUID"), base_file = self.getId()) for container in all_containers: definition_id = container.getDefinition().getId() @@ -202,9 +221,10 @@ class XmlMaterialProfile(InstanceContainer): if definition_id not in machine_nozzle_map: machine_nozzle_map[definition_id] = {} - variant = container.getMetaDataEntry("variant") - if variant: - machine_nozzle_map[definition_id][variant] = container + variant_name = container.getMetaDataEntry("variant_name") + if variant_name: + machine_nozzle_map[definition_id][variant_name] = variant_manager.getVariantNode(definition_id, + variant_name) continue machine_container_map[definition_id] = container @@ -236,16 +256,12 @@ class XmlMaterialProfile(InstanceContainer): self._addSettingElement(builder, instance) # Find all hotend sub-profiles corresponding to this material and machine and add them to this profile. - for hotend_id, hotend in machine_nozzle_map[definition_id].items(): - variant_containers = registry.findInstanceContainersMetadata(id = hotend.getMetaDataEntry("variant")) - if not variant_containers: - continue - + for hotend_name, variant_node in machine_nozzle_map[definition_id].items(): # The hotend identifier is not the containers name, but its "name". - builder.start("hotend", {"id": variant_containers[0]["name"]}) + builder.start("hotend", {"id": hotend_name}) # Compatible is a special case, as it's added as a meta data entry (instead of an instance). - compatible = hotend.getMetaDataEntry("compatible") + compatible = variant_node.metadata.get("compatible") if compatible is not None: builder.start("setting", {"key": "hardware compatible"}) if compatible: @@ -254,7 +270,7 @@ class XmlMaterialProfile(InstanceContainer): builder.data("no") builder.end("setting") - for instance in hotend.findInstances(): + for instance in variant_node.getContainer().findInstances(): if container.getInstance(instance.definition.key) and container.getProperty(instance.definition.key, "value") == instance.value: # If the settings match that of the machine profile, just skip since we inherit the machine profile. continue @@ -590,14 +606,10 @@ class XmlMaterialProfile(InstanceContainer): if buildplate_id is None: continue - variant_containers = ContainerRegistry.getInstance().findInstanceContainersMetadata( - id = buildplate_id) - if not variant_containers: - # It is not really properly defined what "ID" is so also search for variants by name. - variant_containers = ContainerRegistry.getInstance().findInstanceContainersMetadata( - definition = machine_id, name = buildplate_id) - - if not variant_containers: + from cura.Machines.VariantManager import VariantType + variant_manager = CuraApplication.getInstance().getVariantManager() + variant_node = variant_manager.getVariantNode(machine_id, buildplate_id) + if not variant_node: continue buildplate_compatibility = machine_compatibility @@ -618,16 +630,14 @@ class XmlMaterialProfile(InstanceContainer): hotends = machine.iterfind("./um:hotend", self.__namespaces) for hotend in hotends: - hotend_id = hotend.get("id") - if hotend_id is None: + # The "id" field for hotends in material profiles are actually + hotend_name = hotend.get("id") + if hotend_name is None: continue - variant_containers = ContainerRegistry.getInstance().findInstanceContainersMetadata(id = hotend_id) - if not variant_containers: - # It is not really properly defined what "ID" is so also search for variants by name. - variant_containers = ContainerRegistry.getInstance().findInstanceContainersMetadata(definition = machine_id, name = hotend_id) - - if not variant_containers: + variant_manager = CuraApplication.getInstance().getVariantManager() + variant_node = variant_manager.getVariantNode(machine_id, hotend_name) + if not variant_node: continue hotend_compatibility = machine_compatibility @@ -643,20 +653,20 @@ class XmlMaterialProfile(InstanceContainer): else: Logger.log("d", "Unsupported material setting %s", key) - new_hotend_id = self.getId() + "_" + machine_id + "_" + hotend_id.replace(" ", "_") + new_hotend_specific_material_id = self.getId() + "_" + machine_id + "_" + hotend_name.replace(" ", "_") # Same as machine compatibility, keep the derived material containers consistent with the parent material - if ContainerRegistry.getInstance().isLoaded(new_hotend_id): - new_hotend_material = ContainerRegistry.getInstance().findContainers(id = new_hotend_id)[0] + if ContainerRegistry.getInstance().isLoaded(new_hotend_specific_material_id): + new_hotend_material = ContainerRegistry.getInstance().findContainers(id = new_hotend_specific_material_id)[0] is_new_material = False else: - new_hotend_material = XmlMaterialProfile(new_hotend_id) + new_hotend_material = XmlMaterialProfile(new_hotend_specific_material_id) is_new_material = True new_hotend_material.setMetaData(copy.deepcopy(self.getMetaData())) - new_hotend_material.getMetaData()["id"] = new_hotend_id + new_hotend_material.getMetaData()["id"] = new_hotend_specific_material_id new_hotend_material.getMetaData()["name"] = self.getName() - new_hotend_material.getMetaData()["variant"] = variant_containers[0]["id"] + new_hotend_material.getMetaData()["variant_name"] = hotend_name new_hotend_material.setDefinition(machine_id) # Don't use setMetadata, as that overrides it for all materials with same base file new_hotend_material.getMetaData()["compatible"] = hotend_compatibility @@ -833,39 +843,30 @@ class XmlMaterialProfile(InstanceContainer): buildplate_map["buildplate_recommended"][buildplate_id] = buildplate_map["buildplate_recommended"] for hotend in machine.iterfind("./um:hotend", cls.__namespaces): - hotend_id = hotend.get("id") - if hotend_id is None: + hotend_name = hotend.get("id") + if hotend_name is None: continue - variant_containers = ContainerRegistry.getInstance().findInstanceContainersMetadata(id = hotend_id) - if not variant_containers: - # It is not really properly defined what "ID" is so also search for variants by name. - variant_containers = ContainerRegistry.getInstance().findInstanceContainersMetadata(definition = machine_id, name = hotend_id) - hotend_compatibility = machine_compatibility for entry in hotend.iterfind("./um:setting", cls.__namespaces): key = entry.get("key") if key == "hardware compatible": hotend_compatibility = cls._parseCompatibleValue(entry.text) - new_hotend_id = container_id + "_" + machine_id + "_" + hotend_id.replace(" ", "_") + new_hotend_specific_material_id = container_id + "_" + machine_id + "_" + hotend_name.replace(" ", "_") # Same as machine compatibility, keep the derived material containers consistent with the parent material - found_materials = ContainerRegistry.getInstance().findInstanceContainersMetadata(id = new_hotend_id) + found_materials = ContainerRegistry.getInstance().findInstanceContainersMetadata(id = new_hotend_specific_material_id) if found_materials: new_hotend_material_metadata = found_materials[0] else: new_hotend_material_metadata = {} new_hotend_material_metadata.update(base_metadata) - if variant_containers: - new_hotend_material_metadata["variant"] = variant_containers[0]["id"] - else: - new_hotend_material_metadata["variant"] = hotend_id - _with_missing_variants.append(new_hotend_material_metadata) + new_hotend_material_metadata["variant_name"] = hotend_name new_hotend_material_metadata["compatible"] = hotend_compatibility new_hotend_material_metadata["machine_manufacturer"] = machine_manufacturer - new_hotend_material_metadata["id"] = new_hotend_id + new_hotend_material_metadata["id"] = new_hotend_specific_material_id new_hotend_material_metadata["definition"] = machine_id if buildplate_map["buildplate_compatible"]: new_hotend_material_metadata["buildplate_compatible"] = buildplate_map["buildplate_compatible"] @@ -992,21 +993,3 @@ def _indent(elem, level = 0): # before the last } def _tag_without_namespace(element): return element.tag[element.tag.rfind("}") + 1:] - -#While loading XML profiles, some of these profiles don't know what variant -#they belong to. We'd like to search by the machine ID and the variant's -#name, but we don't know the variant's ID. Not all variants have been loaded -#yet so we can't run a filter on the name and machine. The ID is unknown -#so we can't lazily load the variant either. So we have to wait until all -#the rest is loaded properly and then assign the correct variant to the -#material files that were missing it. -_with_missing_variants = [] -def _fillMissingVariants(): - registry = ContainerRegistry.getInstance() - for variant_metadata in _with_missing_variants: - variants = registry.findContainersMetadata(definition = variant_metadata["definition"], name = variant_metadata["variant"]) - if not variants: - Logger.log("w", "Could not find variant for variant-specific material {material_id}.".format(material_id = variant_metadata["id"])) - continue - variant_metadata["variant"] = variants[0]["id"] -ContainerRegistry.allMetadataLoaded.connect(_fillMissingVariants) diff --git a/resources/definitions/anycubic_i3_mega.def.json b/resources/definitions/anycubic_i3_mega.def.json index cba868900c..7106038193 100644 --- a/resources/definitions/anycubic_i3_mega.def.json +++ b/resources/definitions/anycubic_i3_mega.def.json @@ -12,7 +12,7 @@ "platform": "anycubic_i3_mega_platform.stl", "has_materials": false, "has_machine_quality": true, - "preferred_quality": "*normal*" + "preferred_quality_type": "normal" }, "overrides": diff --git a/resources/definitions/builder_premium_large.def.json b/resources/definitions/builder_premium_large.def.json index b496dc524e..deb1539a9a 100644 --- a/resources/definitions/builder_premium_large.def.json +++ b/resources/definitions/builder_premium_large.def.json @@ -12,16 +12,14 @@ "platform": "builder_premium_platform.stl", "platform_offset": [-126, -36, 117], "has_machine_quality": true, - "preferred_quality": "*Normal*", + "preferred_quality_type": "normal", "machine_extruder_trains": { "0": "builder_premium_large_rear", "1": "builder_premium_large_front" } }, - - - + "overrides": { "machine_name": { "default_value": "Builder Premium Large" }, "machine_heated_bed": { "default_value": true }, @@ -36,7 +34,7 @@ "default_material_print_temperature": { "value": "215" }, "material_print_temperature_layer_0": { "value": "material_print_temperature + 5" }, "material_standby_temperature": { "value": "material_print_temperature" }, - + "switch_extruder_retraction_speeds": {"default_value": 15 }, "switch_extruder_retraction_speed": {"default_value": 15 }, "switch_extruder_prime_speed": {"default_value": 15 }, @@ -58,9 +56,9 @@ "prime_tower_wipe_enabled": { "default_value": false }, "prime_tower_min_volume": { "default_value": 50 }, "dual_pre_wipe": { "default_value": false }, - + "prime_blob_enable": { "enabled": true }, - + "acceleration_enabled": { "value": "True" }, "acceleration_layer_0": { "value": "acceleration_topbottom" }, "acceleration_prime_tower": { "value": "math.ceil(acceleration_print * 2000 / 4000)" }, @@ -71,7 +69,7 @@ "acceleration_travel": { "value": "acceleration_print" }, "acceleration_wall": { "value": "math.ceil(acceleration_print * 1000 / 3000)" }, "acceleration_wall_0": { "value": "math.ceil(acceleration_wall * 1000 / 1000)" }, - + "cool_fan_full_at_height": { "value": "layer_height_0 + 2 * layer_height" }, "cool_min_layer_time": { "default_value": 10 }, @@ -84,9 +82,9 @@ "jerk_topbottom": { "value": "math.ceil(jerk_print * 5 / 25)" }, "jerk_wall": { "value": "math.ceil(jerk_print * 10 / 25)" }, "jerk_wall_0": { "value": "math.ceil(jerk_wall * 5 / 10)" }, - + "wall_thickness": { "value": "1.2" }, - + "retraction_amount": { "default_value": 3 }, "retraction_speed": { "default_value": 15 }, "retraction_retract_speed": { "default_value": 15 }, @@ -113,4 +111,4 @@ }, "machine_extruder_count": { "default_value": 2 } } -} \ No newline at end of file +} diff --git a/resources/definitions/builder_premium_medium.def.json b/resources/definitions/builder_premium_medium.def.json index fe8a039fc4..c28c7c5de6 100644 --- a/resources/definitions/builder_premium_medium.def.json +++ b/resources/definitions/builder_premium_medium.def.json @@ -12,16 +12,14 @@ "platform": "builder_premium_platform.stl", "platform_offset": [-126, -36, 117], "has_machine_quality": true, - "preferred_quality": "*Normal*", + "preferred_quality_type": "normal", "machine_extruder_trains": { "0": "builder_premium_medium_rear", "1": "builder_premium_medium_front" } }, - - - + "overrides": { "machine_name": { "default_value": "Builder Premium Medium" }, "machine_heated_bed": { "default_value": true }, @@ -36,7 +34,7 @@ "default_material_print_temperature": { "value": "215" }, "material_print_temperature_layer_0": { "value": "material_print_temperature + 5" }, "material_standby_temperature": { "value": "material_print_temperature" }, - + "switch_extruder_retraction_speeds": {"default_value": 15 }, "switch_extruder_retraction_speed": {"default_value": 15 }, "switch_extruder_prime_speed": {"default_value": 15 }, @@ -58,9 +56,9 @@ "prime_tower_wipe_enabled": { "default_value": false }, "prime_tower_min_volume": { "default_value": 50 }, "dual_pre_wipe": { "default_value": false }, - + "prime_blob_enable": { "enabled": true }, - + "acceleration_enabled": { "value": "True" }, "acceleration_layer_0": { "value": "acceleration_topbottom" }, "acceleration_prime_tower": { "value": "math.ceil(acceleration_print * 2000 / 4000)" }, @@ -71,7 +69,7 @@ "acceleration_travel": { "value": "acceleration_print" }, "acceleration_wall": { "value": "math.ceil(acceleration_print * 1000 / 3000)" }, "acceleration_wall_0": { "value": "math.ceil(acceleration_wall * 1000 / 1000)" }, - + "cool_fan_full_at_height": { "value": "layer_height_0 + 2 * layer_height" }, "cool_min_layer_time": { "default_value": 10 }, @@ -84,9 +82,9 @@ "jerk_topbottom": { "value": "math.ceil(jerk_print * 5 / 25)" }, "jerk_wall": { "value": "math.ceil(jerk_print * 10 / 25)" }, "jerk_wall_0": { "value": "math.ceil(jerk_wall * 5 / 10)" }, - + "wall_thickness": { "value": "1.2" }, - + "retraction_amount": { "default_value": 3 }, "retraction_speed": { "default_value": 15 }, "retraction_retract_speed": { "default_value": 15 }, @@ -113,4 +111,4 @@ }, "machine_extruder_count": { "default_value": 2 } } -} \ No newline at end of file +} diff --git a/resources/definitions/builder_premium_small.def.json b/resources/definitions/builder_premium_small.def.json index a1660b63cf..8e2fe44631 100644 --- a/resources/definitions/builder_premium_small.def.json +++ b/resources/definitions/builder_premium_small.def.json @@ -11,16 +11,14 @@ "platform": "builder_premium_platform.stl", "platform_offset": [-126, -36, 117], "has_machine_quality": true, - "preferred_quality": "*Normal*", + "preferred_quality_type": "normal", "machine_extruder_trains": { "0": "builder_premium_small_rear", "1": "builder_premium_small_front" } }, - - - + "overrides": { "machine_name": { "default_value": "Builder Premium Small" }, "machine_heated_bed": { "default_value": true }, @@ -35,7 +33,7 @@ "default_material_print_temperature": { "value": "215" }, "material_print_temperature_layer_0": { "value": "material_print_temperature + 5" }, "material_standby_temperature": { "value": "material_print_temperature" }, - + "switch_extruder_retraction_speeds": {"default_value": 15 }, "switch_extruder_retraction_speed": {"default_value": 15 }, "switch_extruder_prime_speed": {"default_value": 15 }, @@ -57,9 +55,9 @@ "prime_tower_wipe_enabled": { "default_value": false }, "prime_tower_min_volume": { "default_value": 50 }, "dual_pre_wipe": { "default_value": false }, - + "prime_blob_enable": { "enabled": true }, - + "acceleration_enabled": { "value": "True" }, "acceleration_layer_0": { "value": "acceleration_topbottom" }, "acceleration_prime_tower": { "value": "math.ceil(acceleration_print * 2000 / 4000)" }, @@ -70,7 +68,7 @@ "acceleration_travel": { "value": "acceleration_print" }, "acceleration_wall": { "value": "math.ceil(acceleration_print * 1000 / 3000)" }, "acceleration_wall_0": { "value": "math.ceil(acceleration_wall * 1000 / 1000)" }, - + "cool_fan_full_at_height": { "value": "layer_height_0 + 2 * layer_height" }, "cool_min_layer_time": { "default_value": 10 }, @@ -83,9 +81,9 @@ "jerk_topbottom": { "value": "math.ceil(jerk_print * 5 / 25)" }, "jerk_wall": { "value": "math.ceil(jerk_print * 10 / 25)" }, "jerk_wall_0": { "value": "math.ceil(jerk_wall * 5 / 10)" }, - + "wall_thickness": { "value": "1.2" }, - + "retraction_amount": { "default_value": 3 }, "retraction_speed": { "default_value": 15 }, "retraction_retract_speed": { "default_value": 15 }, @@ -112,4 +110,4 @@ }, "machine_extruder_count": { "default_value": 2 } } -} \ No newline at end of file +} diff --git a/resources/definitions/cartesio.def.json b/resources/definitions/cartesio.def.json index a4bab6432d..5ca891d6c5 100644 --- a/resources/definitions/cartesio.def.json +++ b/resources/definitions/cartesio.def.json @@ -15,9 +15,9 @@ "has_variants": true, "variants_name": "Tool", - "preferred_variant": "*0.8*", - "preferred_material": "*pla*", - "preferred_quality": "*normal*", + "preferred_variant_name": "0.8 mm", + "preferred_material": "generic_pla", + "preferred_quality_type": "normal", "machine_extruder_trains": { diff --git a/resources/definitions/creality_cr10.def.json b/resources/definitions/creality_cr10.def.json index 7a58adcd4d..eb0b8c7306 100644 --- a/resources/definitions/creality_cr10.def.json +++ b/resources/definitions/creality_cr10.def.json @@ -7,7 +7,7 @@ "author": "Michael Wildermuth", "manufacturer": "Creality3D", "file_formats": "text/x-gcode", - "preferred_quality": "*Draft*" + "preferred_quality_type": "draft" }, "overrides": { "machine_width": { diff --git a/resources/definitions/fabtotum.def.json b/resources/definitions/fabtotum.def.json index 1f5d9dab0b..d66de07c4a 100644 --- a/resources/definitions/fabtotum.def.json +++ b/resources/definitions/fabtotum.def.json @@ -13,8 +13,8 @@ "has_machine_quality": true, "has_variants": true, "variants_name": "Head", - "preferred_variant": "*lite04*", - "preferred_material": "*fabtotum_pla*", + "preferred_variant_name": "Lite 0.4 mm", + "preferred_material": "fabtotum_pla", "supports_usb_connection": false }, diff --git a/resources/definitions/fdmprinter.def.json b/resources/definitions/fdmprinter.def.json index d282eeae0a..8c67462667 100644 --- a/resources/definitions/fdmprinter.def.json +++ b/resources/definitions/fdmprinter.def.json @@ -11,8 +11,8 @@ "file_formats": "text/x-gcode;application/x-stl-ascii;application/x-stl-binary;application/x-wavefront-obj;application/x3g", "visible": false, "has_materials": true, - "preferred_material": "*generic_pla*", - "preferred_quality": "*normal*", + "preferred_material": "generic_pla", + "preferred_quality_type": "normal", "machine_extruder_trains": { "0": "fdmextruder" diff --git a/resources/definitions/gmax15plus.def.json b/resources/definitions/gmax15plus.def.json index d651a86bb3..897d492bb2 100644 --- a/resources/definitions/gmax15plus.def.json +++ b/resources/definitions/gmax15plus.def.json @@ -10,11 +10,10 @@ "category": "Other", "file_formats": "text/x-gcode", "platform": "gmax_1-5_xt-plus_s3d_full model_150707.stl", + "has_machine_quality": true, "has_variants": true, "variants_name": "Hotend", - "preferred_variant": "*0.5mm E3D (Default)*" - - + "preferred_variant_name": "0.5mm E3D (Default)" }, "overrides": { diff --git a/resources/definitions/gmax15plus_dual.def.json b/resources/definitions/gmax15plus_dual.def.json index 4e9a91e88d..8c57c8af63 100644 --- a/resources/definitions/gmax15plus_dual.def.json +++ b/resources/definitions/gmax15plus_dual.def.json @@ -11,12 +11,13 @@ "file_formats": "text/x-gcode", "platform": "gmax_1-5_xt-plus_s3d_full model_150707.stl", "has_variants": true, + "has_machine_quality": true, "variants_name": "Hotend", - "preferred_variant": "*0.5mm E3D (Default)*", + "preferred_variant_name": "0.5mm E3D (Default)", "machine_extruder_trains": { "0": "gmax15plus_dual_extruder_0", "1": "gmax15plus_dual_extruder_1" - } + } }, "overrides": { diff --git a/resources/definitions/imade3d_jellybox.def.json b/resources/definitions/imade3d_jellybox.def.json index 11df730408..b234e4b2cd 100644 --- a/resources/definitions/imade3d_jellybox.def.json +++ b/resources/definitions/imade3d_jellybox.def.json @@ -9,9 +9,8 @@ "platform": "imade3d_jellybox_platform.stl", "platform_offset": [ 0, -0.3, 0], "file_formats": "text/x-gcode", - "preferred_variant": "*0.4*", - "preferred_material": "*generic_pla*", - "preferred_quality": "*fast*", + "preferred_variant_name": "0.4 mm", + "preferred_quality_type": "fast", "has_materials": true, "has_variants": true, "has_machine_materials": true, diff --git a/resources/definitions/malyan_m200.def.json b/resources/definitions/malyan_m200.def.json index 365b031c43..a3f4f81ecf 100644 --- a/resources/definitions/malyan_m200.def.json +++ b/resources/definitions/malyan_m200.def.json @@ -11,7 +11,7 @@ "platform": "malyan_m200_platform.stl", "has_machine_quality": true, "has_materials": true, - "preferred_quality": "*normal*", + "preferred_quality_type": "normal", "supports_usb_connection": true, "visible": true, "first_start_actions": ["MachineSettingsAction"], diff --git a/resources/definitions/monoprice_select_mini_v2.def.json b/resources/definitions/monoprice_select_mini_v2.def.json index 87014c136b..99bb7ef50a 100644 --- a/resources/definitions/monoprice_select_mini_v2.def.json +++ b/resources/definitions/monoprice_select_mini_v2.def.json @@ -10,7 +10,7 @@ "file_formats": "text/x-gcode", "has_machine_quality": true, "has_materials": true, - "preferred_quality": "*normal*", + "preferred_quality_type": "normal", "visible": true }, diff --git a/resources/definitions/tevo_blackwidow.def.json b/resources/definitions/tevo_blackwidow.def.json index 04cadfb160..22f7095e17 100644 --- a/resources/definitions/tevo_blackwidow.def.json +++ b/resources/definitions/tevo_blackwidow.def.json @@ -11,7 +11,7 @@ "has_materials": false, "has_machine_quality": true, "platform": "tevo_blackwidow.stl", - "preferred_quality": "*normal*" + "preferred_quality_type": "normal" }, "overrides": { diff --git a/resources/definitions/ultimaker2_plus.def.json b/resources/definitions/ultimaker2_plus.def.json index 58833904d2..935bf5b6c0 100644 --- a/resources/definitions/ultimaker2_plus.def.json +++ b/resources/definitions/ultimaker2_plus.def.json @@ -9,7 +9,7 @@ "file_formats": "text/x-gcode", "platform": "ultimaker2_platform.obj", "platform_texture": "Ultimaker2Plusbackplate.png", - "preferred_variant": "*0.4*", + "preferred_variant_name": "0.4 mm", "has_variants": true, "has_materials": true, "has_machine_materials": true, diff --git a/resources/definitions/ultimaker3.def.json b/resources/definitions/ultimaker3.def.json index 29395e8fd5..dcf6b167c0 100644 --- a/resources/definitions/ultimaker3.def.json +++ b/resources/definitions/ultimaker3.def.json @@ -15,8 +15,8 @@ "has_machine_materials": true, "has_variant_materials": true, "has_variants": true, - "preferred_variant": "*aa04*", - "preferred_quality": "*Normal*", + "preferred_variant_name": "AA 0.4", + "preferred_quality_type": "normal", "variants_name": "Print core", "machine_extruder_trains": { diff --git a/resources/definitions/ultimaker3_extended.def.json b/resources/definitions/ultimaker3_extended.def.json index 385199f4f1..3a1be3a303 100644 --- a/resources/definitions/ultimaker3_extended.def.json +++ b/resources/definitions/ultimaker3_extended.def.json @@ -16,7 +16,7 @@ "has_variant_materials": true, "has_materials": true, "has_variants": true, - "preferred_variant": "*aa04*", + "preferred_variant_name": "AA 0.4", "variants_name": "Print core", "machine_extruder_trains": { diff --git a/resources/qml/Actions.qml b/resources/qml/Actions.qml index 819edb1fc4..7002711614 100644 --- a/resources/qml/Actions.qml +++ b/resources/qml/Actions.qml @@ -172,7 +172,7 @@ Item Action { id: updateProfileAction; - enabled: !Cura.MachineManager.stacksHaveErrors && Cura.MachineManager.hasUserSettings && !Cura.MachineManager.isReadOnly(Cura.MachineManager.activeQualityId) + enabled: !Cura.MachineManager.stacksHaveErrors && Cura.MachineManager.hasUserSettings && Cura.MachineManager.activeQualityChangesGroup != null text: catalog.i18nc("@action:inmenu menubar:profile","&Update profile with current settings/overrides"); onTriggered: Cura.ContainerManager.updateQualityChanges(); } diff --git a/resources/qml/Cura.qml b/resources/qml/Cura.qml index 0b4c8089c8..a8066e01e4 100644 --- a/resources/qml/Cura.qml +++ b/resources/qml/Cura.qml @@ -190,24 +190,25 @@ UM.MainWindow model: Cura.ExtrudersModel { simpleNames: true } Menu { title: model.name - visible: machineExtruderCount.properties.value > 1 NozzleMenu { title: Cura.MachineManager.activeDefinitionVariantsName; visible: Cura.MachineManager.hasVariants; extruderIndex: index } MaterialMenu { title: catalog.i18nc("@title:menu", "&Material"); visible: Cura.MachineManager.hasMaterials; extruderIndex: index } - ProfileMenu { title: catalog.i18nc("@title:menu", "&Profile"); } - MenuSeparator { } + MenuSeparator { + visible: Cura.MachineManager.hasVariants || Cura.MachineManager.hasMaterials + } - MenuItem { text: catalog.i18nc("@action:inmenu", "Set as Active Extruder"); onTriggered: Cura.ExtruderManager.setActiveExtruderIndex(model.index) } + MenuItem { + text: catalog.i18nc("@action:inmenu", "Set as Active Extruder") + onTriggered: Cura.ExtruderManager.setActiveExtruderIndex(model.index) + } } onObjectAdded: settingsMenu.insertItem(index, object) onObjectRemoved: settingsMenu.removeItem(object) } BuildplateMenu { title: catalog.i18nc("@title:menu", "&Build plate"); visible: Cura.MachineManager.hasVariantBuildplates } - NozzleMenu { title: Cura.MachineManager.activeDefinitionVariantsName; visible: machineExtruderCount.properties.value <= 1 && Cura.MachineManager.hasVariants } - MaterialMenu { title: catalog.i18nc("@title:menu", "&Material"); visible: machineExtruderCount.properties.value <= 1 && Cura.MachineManager.hasMaterials } - ProfileMenu { title: catalog.i18nc("@title:menu", "&Profile"); visible: machineExtruderCount.properties.value <= 1 } + ProfileMenu { title: catalog.i18nc("@title:menu", "&Profile"); } MenuSeparator { } diff --git a/resources/qml/DiscardOrKeepProfileChangesDialog.qml b/resources/qml/DiscardOrKeepProfileChangesDialog.qml index 915a11fde2..afa9fda0bd 100644 --- a/resources/qml/DiscardOrKeepProfileChangesDialog.qml +++ b/resources/qml/DiscardOrKeepProfileChangesDialog.qml @@ -7,7 +7,7 @@ import QtQuick.Dialogs 1.2 import QtQuick.Window 2.1 import UM 1.2 as UM -import Cura 1.1 as Cura +import Cura 1.0 as Cura UM.Dialog { diff --git a/resources/qml/Menus/BuildplateMenu.qml b/resources/qml/Menus/BuildplateMenu.qml index 4b85aa9e93..0b67b37cc1 100644 --- a/resources/qml/Menus/BuildplateMenu.qml +++ b/resources/qml/Menus/BuildplateMenu.qml @@ -1,8 +1,8 @@ // Copyright (c) 2018 Ultimaker B.V. // Cura is released under the terms of the LGPLv3 or higher. -import QtQuick 2.2 -import QtQuick.Controls 1.1 +import QtQuick 2.8 +import QtQuick.Controls 1.4 import UM 1.2 as UM import Cura 1.0 as Cura @@ -12,28 +12,22 @@ Menu id: menu title: "Build plate" + property Cura.BuildPlateModel buildPlateModel: CuraApplication.getBuildPlateModel() + Instantiator { - id: buildplateInstantiator - model: UM.InstanceContainersModel - { - filter: - { - "type": "variant", - "hardware_type": "buildplate", - "definition": Cura.MachineManager.activeDefinitionId //Only show variants of this machine - } - } + model: menu.buildPlateModel + MenuItem { text: model.name checkable: true - checked: model.id == Cura.MachineManager.globalVariantId + checked: model.name == Cura.MachineManager.globalVariantName exclusiveGroup: group - onTriggered: - { - Cura.MachineManager.setActiveVariantBuildplate(model.id); + onTriggered: { + Cura.MachineManager.setGlobalVariant(model.container_node); } } + onObjectAdded: menu.insertItem(index, object) onObjectRemoved: menu.removeItem(object) } diff --git a/resources/qml/Menus/ContextMenu.qml b/resources/qml/Menus/ContextMenu.qml index b5f51f4d63..656e94b336 100644 --- a/resources/qml/Menus/ContextMenu.qml +++ b/resources/qml/Menus/ContextMenu.qml @@ -7,7 +7,7 @@ import QtQuick.Dialogs 1.2 import QtQuick.Window 2.1 import UM 1.2 as UM -import Cura 1.2 as Cura +import Cura 1.0 as Cura Menu { @@ -15,6 +15,8 @@ Menu property bool shouldShowExtruders: machineExtruderCount.properties.value > 1; + property Cura.MultiBuildPlateModel multiBuildPlateModel: CuraApplication.getMultiBuildPlateModel() + // Selection-related actions. MenuItem { action: Cura.Actions.centerSelection; } MenuItem { action: Cura.Actions.deleteSelection; } @@ -45,13 +47,13 @@ Menu Instantiator { - model: Cura.BuildPlateModel + model: base.multiBuildPlateModel MenuItem { enabled: UM.Selection.hasSelection - text: Cura.BuildPlateModel.getItem(index).name; - onTriggered: CuraActions.setBuildPlateForSelection(Cura.BuildPlateModel.getItem(index).buildPlateNumber); + text: base.multiBuildPlateModel.getItem(index).name; + onTriggered: CuraActions.setBuildPlateForSelection(base.multiBuildPlateModel.getItem(index).buildPlateNumber); checkable: true - checked: Cura.BuildPlateModel.selectionBuildPlates.indexOf(Cura.BuildPlateModel.getItem(index).buildPlateNumber) != -1; + checked: base.multiBuildPlateModel.selectionBuildPlates.indexOf(base.multiBuildPlateModel.getItem(index).buildPlateNumber) != -1; visible: UM.Preferences.getValue("cura/use_multi_build_plate") } onObjectAdded: base.insertItem(index, object); @@ -62,7 +64,7 @@ Menu enabled: UM.Selection.hasSelection text: "New build plate"; onTriggered: { - CuraActions.setBuildPlateForSelection(Cura.BuildPlateModel.maxBuildPlate + 1); + CuraActions.setBuildPlateForSelection(base.multiBuildPlateModel.maxBuildPlate + 1); checked = false; } checkable: true diff --git a/resources/qml/Menus/MaterialMenu.qml b/resources/qml/Menus/MaterialMenu.qml index 3d04649f11..25fa221e9a 100644 --- a/resources/qml/Menus/MaterialMenu.qml +++ b/resources/qml/Menus/MaterialMenu.qml @@ -1,8 +1,8 @@ // Copyright (c) 2018 Ultimaker B.V. // Cura is released under the terms of the LGPLv3 or higher. -import QtQuick 2.2 -import QtQuick.Controls 1.1 +import QtQuick 2.8 +import QtQuick.Controls 1.4 import UM 1.2 as UM import Cura 1.0 as Cura @@ -13,64 +13,6 @@ Menu title: "Material" property int extruderIndex: 0 - property bool printerConnected: Cura.MachineManager.printerOutputDevices.length != 0 - property bool isClusterPrinter: - { - if(Cura.MachineManager.printerOutputDevices.length == 0) - { - return false; - } - var clusterSize = Cura.MachineManager.printerOutputDevices[0].clusterSize; - // This is not a cluster printer or the cluster it is just one printer - if(clusterSize == undefined || clusterSize == 1) - { - return false; - } - return true; - } - - UM.SettingPropertyProvider - { - id: materialDiameterProvider - - containerStackId: Cura.ExtruderManager.activeExtruderStackId - key: "material_diameter" - watchedProperties: [ "value" ] - storeIndex: 5 - } - - MenuItem - { - id: automaticMaterial - text: - { - if(visible) - { - var materialName = Cura.MachineManager.printerOutputDevices[0].materialNames[extruderIndex]; - return catalog.i18nc("@title:menuitem %1 is the automatically selected material", "Automatic: %1").arg(materialName); - } - return ""; - } - visible: printerConnected && Cura.MachineManager.printerOutputDevices[0].materialNames != undefined && Cura.MachineManager.printerOutputDevices[0].materialNames.length > extruderIndex && !isClusterPrinter - onTriggered: - { - var materialId = Cura.MachineManager.printerOutputDevices[0].materialIds[extruderIndex]; - var items = materialsModel.items; - for(var i in items) - { - if (items[i]["metadata"]["GUID"] == materialId) - { - Cura.MachineManager.setActiveMaterial(items[i].id); - break; - } - } - } - } - - MenuSeparator - { - visible: automaticMaterial.visible - } Instantiator { @@ -79,16 +21,11 @@ Menu { text: model.name checkable: true - checked: model.id == Cura.MachineManager.allActiveMaterialIds[Cura.ExtruderManager.extruderIds[extruderIndex]] + checked: model.root_material_id == Cura.MachineManager.currentRootMaterialId[extruderIndex] exclusiveGroup: group onTriggered: { - // This workaround is done because of the application menus for materials and variants for multiextrusion printers. - // The extruder menu would always act on the correspoding extruder only, instead of acting on the extruder selected in the UI. - var activeExtruderIndex = Cura.ExtruderManager.activeExtruderIndex; - Cura.ExtruderManager.setActiveExtruderIndex(extruderIndex); - Cura.MachineManager.setActiveMaterial(model.id); - Cura.ExtruderManager.setActiveExtruderIndex(activeExtruderIndex); + Cura.MachineManager.setMaterial(extruderIndex, model.container_node); } } onObjectAdded: menu.insertItem(index, object) @@ -126,12 +63,8 @@ Menu exclusiveGroup: group onTriggered: { - // This workaround is done because of the application menus for materials and variants for multiextrusion printers. - // The extruder menu would always act on the correspoding extruder only, instead of acting on the extruder selected in the UI. var activeExtruderIndex = Cura.ExtruderManager.activeExtruderIndex; - Cura.ExtruderManager.setActiveExtruderIndex(extruderIndex); - Cura.MachineManager.setActiveMaterial(model.id); - Cura.ExtruderManager.setActiveExtruderIndex(activeExtruderIndex); + Cura.MachineManager.setMaterial(activeExtruderIndex, model.container_node); } } onObjectAdded: brandMaterialsMenu.insertItem(index, object) @@ -146,24 +79,16 @@ Menu onObjectRemoved: menu.removeItem(object) } - ListModel + Cura.GenericMaterialsModel { id: genericMaterialsModel - Component.onCompleted: populateMenuModels() + extruderPosition: menu.extruderIndex } - ListModel + Cura.BrandMaterialsModel { id: brandModel - } - - //: Model used to populate the brandModel - Cura.MaterialsModel - { - id: materialsModel - filter: materialFilter() - onModelReset: populateMenuModels() - onDataChanged: populateMenuModels() + extruderPosition: menu.extruderIndex } ExclusiveGroup { id: group } @@ -171,80 +96,4 @@ Menu MenuSeparator { } MenuItem { action: Cura.Actions.manageMaterials } - - function materialFilter() - { - var result = { "type": "material", "approximate_diameter": Math.round(materialDiameterProvider.properties.value).toString() }; - if(Cura.MachineManager.filterMaterialsByMachine) - { - result.definition = Cura.MachineManager.activeQualityDefinitionId; - if(Cura.MachineManager.hasVariants) - { - result.variant = Cura.MachineManager.activeQualityVariantId; - } - } - else - { - result.definition = "fdmprinter"; - result.compatible = true; //NB: Only checks for compatibility in global version of material, but we don't have machine-specific materials anyway. - } - return result; - } - - function populateMenuModels() - { - // Create a structure of unique brands and their material-types - genericMaterialsModel.clear() - brandModel.clear(); - - var items = materialsModel.items; - var materialsByBrand = {}; - for (var i in items) { - var brandName = items[i]["metadata"]["brand"]; - var materialName = items[i]["metadata"]["material"]; - - if (brandName == "Generic") - { - // Add to top section - var materialId = items[i].id; - genericMaterialsModel.append({ - id: materialId, - name: items[i].name - }); - } - else - { - // Add to per-brand, per-material menu - if (!materialsByBrand.hasOwnProperty(brandName)) - { - materialsByBrand[brandName] = {}; - } - if (!materialsByBrand[brandName].hasOwnProperty(materialName)) - { - materialsByBrand[brandName][materialName] = []; - } - materialsByBrand[brandName][materialName].push({ - id: items[i].id, - name: items[i].name - }); - } - } - - for (var brand in materialsByBrand) - { - var materialsByBrandModel = []; - var materials = materialsByBrand[brand]; - for (var material in materials) - { - materialsByBrandModel.push({ - name: material, - colors: materials[material] - }) - } - brandModel.append({ - name: brand, - materials: materialsByBrandModel - }); - } - } } diff --git a/resources/qml/Menus/NozzleMenu.qml b/resources/qml/Menus/NozzleMenu.qml index 81db20a79d..0b961a5a11 100644 --- a/resources/qml/Menus/NozzleMenu.qml +++ b/resources/qml/Menus/NozzleMenu.qml @@ -1,8 +1,8 @@ // Copyright (c) 2017 Ultimaker B.V. // Cura is released under the terms of the LGPLv3 or higher. -import QtQuick 2.2 -import QtQuick.Controls 1.1 +import QtQuick 2.8 +import QtQuick.Controls 1.4 import UM 1.2 as UM import Cura 1.0 as Cura @@ -13,89 +13,31 @@ Menu title: "Nozzle" property int extruderIndex: 0 - property bool printerConnected: Cura.MachineManager.printerOutputDevices.length != 0 - property bool isClusterPrinter: - { - if(Cura.MachineManager.printerOutputDevices.length == 0) - { - return false; - } - var clusterSize = Cura.MachineManager.printerOutputDevices[0].clusterSize; - // This is not a cluster printer or the cluster it is just one printer - if(clusterSize == undefined || clusterSize == 1) - { - return false; - } - return true; - } - MenuItem + Cura.NozzleModel { - id: automaticNozzle - text: - { - if(visible) - { - var nozzleName = Cura.MachineManager.printerOutputDevices[0].hotendIds[extruderIndex]; - return catalog.i18nc("@title:menuitem %1 is the nozzle currently loaded in the printer", "Automatic: %1").arg(nozzleName); - } - return ""; - } - visible: printerConnected && Cura.MachineManager.printerOutputDevices[0].hotendIds != undefined && Cura.MachineManager.printerOutputDevices[0].hotendIds.length > extruderIndex && !isClusterPrinter - onTriggered: - { - var activeExtruderIndex = Cura.ExtruderManager.activeExtruderIndex; - Cura.ExtruderManager.setActiveExtruderIndex(extruderIndex); - var hotendId = Cura.MachineManager.printerOutputDevices[0].hotendIds[extruderIndex]; - var itemIndex = nozzleInstantiator.model.find("name", hotendId); - if(itemIndex > -1) - { - Cura.MachineManager.setActiveVariant(nozzleInstantiator.model.getItem(itemIndex).id); - } - Cura.ExtruderManager.setActiveExtruderIndex(activeExtruderIndex); - } - } - - MenuSeparator - { - visible: automaticNozzle.visible + id: nozzleModel } Instantiator { - id: nozzleInstantiator - model: UM.InstanceContainersModel - { - filter: - { - var filter_dict = - { - "type": "variant", - "definition": Cura.MachineManager.activeQualityDefinitionId //Only show variants of this machine - } - if (Cura.MachineManager.hasVariantBuildplates) - { - filter_dict["hardware_type"] = "nozzle" - } + model: nozzleModel - return filter_dict - } - } - MenuItem { - text: model.name + MenuItem + { + text: model.hotend_name checkable: true - checked: model.id == Cura.MachineManager.allActiveVariantIds[Cura.ExtruderManager.extruderIds[extruderIndex]] + checked: { + return Cura.MachineManager.activeVariantNames[extruderIndex] == model.hotend_name + } exclusiveGroup: group - onTriggered: - { - var activeExtruderIndex = Cura.ExtruderManager.activeExtruderIndex; - Cura.ExtruderManager.setActiveExtruderIndex(extruderIndex); - Cura.MachineManager.setActiveVariant(model.id); - Cura.ExtruderManager.setActiveExtruderIndex(activeExtruderIndex); + onTriggered: { + Cura.MachineManager.setVariantGroup(menu.extruderIndex, model.container_node); } } - onObjectAdded: menu.insertItem(index, object) - onObjectRemoved: menu.removeItem(object) + + onObjectAdded: menu.insertItem(index, object); + onObjectRemoved: menu.removeItem(object); } ExclusiveGroup { id: group } diff --git a/resources/qml/Menus/ProfileMenu.qml b/resources/qml/Menus/ProfileMenu.qml index f543bb36eb..19461f6005 100644 --- a/resources/qml/Menus/ProfileMenu.qml +++ b/resources/qml/Menus/ProfileMenu.qml @@ -1,8 +1,8 @@ -// Copyright (c) 2016 Ultimaker B.V. +// Copyright (c) 2018 Ultimaker B.V. // Cura is released under the terms of the LGPLv3 or higher. -import QtQuick 2.2 -import QtQuick.Controls 1.1 +import QtQuick 2.8 +import QtQuick.Controls 1.4 import UM 1.2 as UM import Cura 1.0 as Cura @@ -13,15 +13,17 @@ Menu Instantiator { - model: Cura.ProfilesModel + model: Cura.QualityProfilesDropDownMenuModel MenuItem { - text: (model.layer_height != "") ? model.name + " - " + model.layer_height : model.name + text: (model.layer_height != "") ? model.name + " - " + model.layer_height + model.layer_height_unit : model.name checkable: true - checked: Cura.MachineManager.activeQualityId == model.id + checked: Cura.MachineManager.activeQualityOrQualityChangesName == model.name exclusiveGroup: group - onTriggered: Cura.MachineManager.setActiveQuality(model.id) + onTriggered: { + Cura.MachineManager.setQualityGroup(model.quality_group) + } visible: model.available } @@ -32,24 +34,27 @@ Menu MenuSeparator { id: customSeparator - visible: Cura.UserProfilesModel.rowCount > 0 + visible: Cura.CustomQualityProfilesDropDownMenuModel.rowCount > 0 } Instantiator { id: customProfileInstantiator - model: Cura.UserProfilesModel + model: Cura.CustomQualityProfilesDropDownMenuModel + + Connections { - onModelReset: customSeparator.visible = rowCount() > 0 + target: Cura.CustomQualityProfilesDropDownMenuModel + onModelReset: customSeparator.visible = Cura.CustomQualityProfilesDropDownMenuModel.rowCount() > 0 } MenuItem { text: model.name - checkable: true - checked: Cura.MachineManager.activeQualityChangesId == model.id + checkable: model.available + checked: Cura.MachineManager.activeQualityOrQualityChangesName == model.name exclusiveGroup: group - onTriggered: Cura.MachineManager.setActiveQuality(model.id) + onTriggered: Cura.MachineManager.setQualityChangesGroup(model.quality_changes_group) } onObjectAdded: @@ -73,23 +78,4 @@ Menu MenuItem { action: Cura.Actions.resetProfile } MenuSeparator { } MenuItem { action: Cura.Actions.manageProfiles } - - function getFilter(initial_conditions) - { - var result = initial_conditions; - - if(Cura.MachineManager.filterQualityByMachine) - { - result.definition = Cura.MachineManager.activeQualityDefinitionId; - if(Cura.MachineManager.hasMaterials) - { - result.material = Cura.MachineManager.activeQualityMaterialId; - } - } - else - { - result.definition = "fdmprinter" - } - return result - } } diff --git a/resources/qml/Menus/ViewMenu.qml b/resources/qml/Menus/ViewMenu.qml index afc80dd314..fc0339e0c6 100644 --- a/resources/qml/Menus/ViewMenu.qml +++ b/resources/qml/Menus/ViewMenu.qml @@ -5,7 +5,7 @@ import QtQuick 2.2 import QtQuick.Controls 1.1 import UM 1.2 as UM -import Cura 1.2 as Cura +import Cura 1.0 as Cura Menu { @@ -13,6 +13,8 @@ Menu id: base enabled: !PrintInformation.preSliced + property Cura.MultiBuildPlateModel multiBuildPlateModel: CuraApplication.getMultiBuildPlateModel() + // main views Instantiator { @@ -53,12 +55,12 @@ Menu visible: UM.Preferences.getValue("cura/use_multi_build_plate") Instantiator { - model: Cura.BuildPlateModel + model: base.multiBuildPlateModel MenuItem { - text: Cura.BuildPlateModel.getItem(index).name; - onTriggered: Cura.SceneController.setActiveBuildPlate(Cura.BuildPlateModel.getItem(index).buildPlateNumber); + text: base.multiBuildPlateModel.getItem(index).name; + onTriggered: Cura.SceneController.setActiveBuildPlate(base.multiBuildPlateModel.getItem(index).buildPlateNumber); checkable: true; - checked: Cura.BuildPlateModel.getItem(index).buildPlateNumber == Cura.BuildPlateModel.activeBuildPlate; + checked: base.multiBuildPlateModel.getItem(index).buildPlateNumber == base.multiBuildPlateModel.activeBuildPlate; exclusiveGroup: buildPlateGroup; visible: UM.Preferences.getValue("cura/use_multi_build_plate") } diff --git a/resources/qml/ObjectsList.qml b/resources/qml/ObjectsList.qml index b64f08d003..e7dd63ea05 100644 --- a/resources/qml/ObjectsList.qml +++ b/resources/qml/ObjectsList.qml @@ -8,7 +8,7 @@ import QtQuick.Layouts 1.1 import QtQuick.Dialogs 1.1 import UM 1.3 as UM -import Cura 1.2 as Cura +import Cura 1.0 as Cura import "Menus" @@ -33,6 +33,8 @@ Rectangle property bool collapsed: true; + property Cura.MultiBuildPlateModel multiBuildPlateModel: CuraApplication.getMultiBuildPlateModel() + SystemPalette { id: palette } Button { @@ -67,7 +69,7 @@ Rectangle Rectangle { height: childrenRect.height - color: Cura.BuildPlateModel.getItem(index).buildPlateNumber == Cura.BuildPlateModel.activeBuildPlate ? palette.highlight : index % 2 ? palette.base : palette.alternateBase + color: multiBuildPlateModel.getItem(index).buildPlateNumber == multiBuildPlateModel.activeBuildPlate ? palette.highlight : index % 2 ? palette.base : palette.alternateBase width: parent.width Label { @@ -75,8 +77,8 @@ Rectangle anchors.left: parent.left anchors.leftMargin: UM.Theme.getSize("default_margin").width width: parent.width - 2 * UM.Theme.getSize("default_margin").width - 30 - text: Cura.BuildPlateModel.getItem(index) ? Cura.BuildPlateModel.getItem(index).name : ""; - color: Cura.BuildPlateModel.activeBuildPlate == index ? palette.highlightedText : palette.text + text: multiBuildPlateModel.getItem(index) ? multiBuildPlateModel.getItem(index).name : ""; + color: multiBuildPlateModel.activeBuildPlate == index ? palette.highlightedText : palette.text elide: Text.ElideRight } @@ -118,13 +120,12 @@ Rectangle ListView { id: buildPlateListView - model: Cura.BuildPlateModel + model: multiBuildPlateModel width: parent.width delegate: buildPlateDelegate } } - Component { id: objectDelegate Rectangle @@ -200,7 +201,6 @@ Rectangle } } - CheckBox { id: filterBuildPlateCheckbox @@ -260,6 +260,4 @@ Rectangle } action: Cura.Actions.arrangeAll; } - - } diff --git a/resources/qml/Preferences/MachinesPage.qml b/resources/qml/Preferences/MachinesPage.qml index 889dfa8d5b..49a8d286a8 100644 --- a/resources/qml/Preferences/MachinesPage.qml +++ b/resources/qml/Preferences/MachinesPage.qml @@ -1,13 +1,14 @@ // Copyright (c) 2016 Ultimaker B.V. // Cura is released under the terms of the LGPLv3 or higher. -import QtQuick 2.1 -import QtQuick.Controls 1.1 +import QtQuick 2.8 +import QtQuick.Controls 1.4 import QtQuick.Window 2.1 import UM 1.2 as UM import Cura 1.0 as Cura + UM.ManagementPage { id: base; diff --git a/resources/qml/Preferences/MaterialView.qml b/resources/qml/Preferences/MaterialView.qml index 5fdc8a24eb..0016f211e7 100644 --- a/resources/qml/Preferences/MaterialView.qml +++ b/resources/qml/Preferences/MaterialView.qml @@ -1,8 +1,8 @@ // Copyright (c) 2017 Ultimaker B.V. // Cura is released under the terms of the LGPLv3 or higher. -import QtQuick 2.1 -import QtQuick.Controls 1.3 +import QtQuick 2.8 +import QtQuick.Controls 1.4 import QtQuick.Dialogs 1.2 import UM 1.2 as UM @@ -12,7 +12,10 @@ TabView { id: base - property QtObject properties; + property QtObject materialManager: CuraApplication.getMaterialManager() + + property QtObject properties + property var currentMaterialNode: null property bool editingEnabled: false; property string currency: UM.Preferences.getValue("cura/currency") ? UM.Preferences.getValue("cura/currency") : "€" @@ -27,18 +30,23 @@ TabView property bool reevaluateLinkedMaterials: false property string linkedMaterialNames: { - if (reevaluateLinkedMaterials) - { + if (reevaluateLinkedMaterials) { reevaluateLinkedMaterials = false; } - if(!base.containerId || !base.editingEnabled) - { + if (!base.containerId || !base.editingEnabled) { + return "" + } + var linkedMaterials = Cura.ContainerManager.getLinkedMaterials(base.currentMaterialNode); + if (linkedMaterials.length <= 1) { return "" } - var linkedMaterials = Cura.ContainerManager.getLinkedMaterials(base.containerId); return linkedMaterials.join(", "); } + function getApproximateDiameter(diameter) { + return Math.round(diameter); + } + Tab { title: catalog.i18nc("@title", "Information") @@ -65,6 +73,34 @@ TabView width: base.width property real rowHeight: textField.height + UM.Theme.getSize("default_lining").height + MessageDialog + { + id: confirmDiameterChangeDialog + + icon: StandardIcon.Question; + title: catalog.i18nc("@title:window", "Confirm Diameter Change") + text: catalog.i18nc("@label (%1 is object name)", "The new material diameter is set to %1 mm, which is not compatible to the current machine. Do you wish to continue?".arg(new_diameter_value)) + standardButtons: StandardButton.Yes | StandardButton.No + modality: Qt.ApplicationModal + + property var new_diameter_value: null; + property var old_diameter_value: null; + property var old_approximate_diameter_value: null; + + onYes: + { + Cura.ContainerManager.setContainerProperty(base.containerId, "material_diameter", "value", new_diameter_value); + base.setMetaDataEntry("approximate_diameter", old_approximate_diameter_value, getApproximateDiameter(new_diameter_value).toString()); + base.setMetaDataEntry("properties/diameter", properties.diameter, new_diameter_value); + } + + onNo: + { + properties.diameter = old_diameter_value; + diameterSpinBox.value = properties.diameter; + } + } + Label { width: scrollView.columnWidth; height: parent.rowHeight; verticalAlignment: Qt.AlignVCenter; text: catalog.i18nc("@label", "Display Name") } ReadOnlyTextField { @@ -80,18 +116,18 @@ TabView { id: textField; width: scrollView.columnWidth; - text: properties.supplier; + text: properties.brand; readOnly: !base.editingEnabled; - onEditingFinished: base.updateMaterialSupplier(properties.supplier, text) + onEditingFinished: base.updateMaterialBrand(properties.brand, text) } Label { width: scrollView.columnWidth; height: parent.rowHeight; verticalAlignment: Qt.AlignVCenter; text: catalog.i18nc("@label", "Material Type") } ReadOnlyTextField { width: scrollView.columnWidth; - text: properties.material_type; + text: properties.material; readOnly: !base.editingEnabled; - onEditingFinished: base.updateMaterialType(properties.material_type, text) + onEditingFinished: base.updateMaterialType(properties.material, text) } Label { width: scrollView.columnWidth; height: parent.rowHeight; verticalAlignment: Qt.AlignVCenter; text: catalog.i18nc("@label", "Color") } @@ -172,14 +208,20 @@ TabView // which derive from the same base_file var old_diameter = Cura.ContainerManager.getContainerProperty(base.containerId, "material_diameter", "value").toString(); var old_approximate_diameter = Cura.ContainerManager.getContainerMetaDataEntry(base.containerId, "approximate_diameter"); - base.setMetaDataEntry("approximate_diameter", old_approximate_diameter, Math.round(value).toString()); - base.setMetaDataEntry("properties/diameter", properties.diameter, value); - var new_approximate_diameter = Cura.ContainerManager.getContainerMetaDataEntry(base.containerId, "approximate_diameter"); - if (Cura.MachineManager.filterMaterialsByMachine && new_approximate_diameter != Cura.MachineManager.activeMachine.approximateMaterialDiameter) + var new_approximate_diameter = getApproximateDiameter(value); + if (Cura.MachineManager.filterMaterialsByMachine && new_approximate_diameter != Cura.ExtruderManager.getActiveExtruderStack().approximateMaterialDiameter) { - Cura.MaterialManager.showMaterialWarningMessage(base.containerId, old_diameter); + confirmDiameterChangeDialog.old_diameter_value = old_diameter; + confirmDiameterChangeDialog.new_diameter_value = value; + confirmDiameterChangeDialog.old_approximate_diameter_value = old_approximate_diameter; + + confirmDiameterChangeDialog.open() + } + else { + Cura.ContainerManager.setContainerProperty(base.containerId, "material_diameter", "value", value); + base.setMetaDataEntry("approximate_diameter", old_approximate_diameter, getApproximateDiameter(value).toString()); + base.setMetaDataEntry("properties/diameter", properties.diameter, value); } - Cura.ContainerManager.setContainerProperty(base.containerId, "material_diameter", "value", value); } onValueChanged: updateCostPerMeter() } @@ -251,7 +293,7 @@ TabView visible: base.linkedMaterialNames != "" onClicked: { - Cura.ContainerManager.unlinkMaterial(base.containerId) + Cura.ContainerManager.unlinkMaterial(base.currentMaterialNode) base.reevaluateLinkedMaterials = true } } @@ -357,8 +399,20 @@ TabView onEditingFinished: materialPropertyProvider.setPropertyValue("value", value) } - UM.ContainerPropertyProvider { id: materialPropertyProvider; containerId: base.containerId; watchedProperties: [ "value" ]; key: model.key } - UM.ContainerPropertyProvider { id: machinePropertyProvider; containerId: Cura.MachineManager.activeDefinitionId; watchedProperties: [ "value" ]; key: model.key } + UM.ContainerPropertyProvider + { + id: materialPropertyProvider + containerId: base.containerId + watchedProperties: [ "value" ] + key: model.key + } + UM.ContainerPropertyProvider + { + id: machinePropertyProvider + containerId: Cura.MachineManager.activeDefinitionId + watchedProperties: [ "value" ] + key: model.key + } } } } @@ -405,7 +459,7 @@ TabView // Tiny convenience function to check if a value really changed before trying to set it. function setMetaDataEntry(entry_name, old_value, new_value) { if (old_value != new_value) { - Cura.ContainerManager.setContainerMetaDataEntry(base.containerId, entry_name, new_value) + Cura.ContainerManager.setContainerMetaDataEntry(base.currentMaterialNode, entry_name, new_value) // make sure the UI properties are updated as well since we don't re-fetch the entire model here // When the entry_name is something like properties/diameter, we take the last part of the entry_name var list = entry_name.split("/") @@ -442,26 +496,25 @@ TabView // update the display name of the material function updateMaterialDisplayName (old_name, new_name) { - // don't change when new name is the same if (old_name == new_name) { return } // update the values - Cura.ContainerManager.setContainerName(base.containerId, new_name) + base.materialManager.setMaterialName(base.currentMaterialNode, new_name) materialProperties.name = new_name } // update the type of the material function updateMaterialType (old_type, new_type) { base.setMetaDataEntry("material", old_type, new_type) - materialProperties.material_type = new_type + materialProperties.material= new_type } - // update the supplier of the material - function updateMaterialSupplier (old_supplier, new_supplier) { - base.setMetaDataEntry("brand", old_supplier, new_supplier) - materialProperties.supplier = new_supplier + // update the brand of the material + function updateMaterialBrand (old_brand, new_brand) { + base.setMetaDataEntry("brand", old_brand, new_brand) + materialProperties.brand = new_brand } } diff --git a/resources/qml/Preferences/MaterialsPage.qml b/resources/qml/Preferences/MaterialsPage.qml index 22814683ad..a5bb2f9883 100644 --- a/resources/qml/Preferences/MaterialsPage.qml +++ b/resources/qml/Preferences/MaterialsPage.qml @@ -1,412 +1,526 @@ -//Copyright (c) 2017 Ultimaker B.V. -//Cura is released under the terms of the LGPLv3 or higher. +// Copyright (c) 2018 Ultimaker B.V. +// Uranium is released under the terms of the LGPLv3 or higher. -import QtQuick 2.1 -import QtQuick.Controls 1.1 +import QtQuick 2.8 +import QtQuick.Controls 1.4 +import QtQuick.Layouts 1.3 import QtQuick.Dialogs 1.2 import UM 1.2 as UM import Cura 1.0 as Cura -UM.ManagementPage + +Item { - id: base; + id: base - title: catalog.i18nc("@title:tab", "Materials"); + property QtObject materialManager: CuraApplication.getMaterialManager() + property var resetEnabled: false // Keep PreferencesDialog happy - Component.onCompleted: - { - // Workaround to make sure all of the items are visible - objectList.positionViewAtBeginning(); + UM.I18nCatalog { id: catalog; name: "cura"; } + + Cura.MaterialManagementModel { + id: materialsModel } - model: Cura.MaterialsModel - { - filter: - { - var result = { "type": "material", "approximate_diameter": Math.round(materialDiameterProvider.properties.value).toString() } - if(Cura.MachineManager.filterMaterialsByMachine) - { - result.definition = Cura.MachineManager.activeQualityDefinitionId; - if(Cura.MachineManager.hasVariants) - { - result.variant = Cura.MachineManager.activeQualityVariantId; - } - } - else - { - result.definition = "fdmprinter"; - result.compatible = true; //NB: Only checks for compatibility in global version of material, but we don't have machine-specific materials anyway. - } - return result + Label { + id: titleLabel + + anchors { + top: parent.top + left: parent.left + right: parent.right + margins: 5 * screenScaleFactor } - sectionProperty: "brand" + font.pointSize: 18 + text: catalog.i18nc("@title:tab", "Materials") } - delegate: Rectangle - { - width: objectList.width; - height: childrenRect.height; - color: isCurrentItem ? palette.highlight : index % 2 ? palette.base : palette.alternateBase - property bool isCurrentItem: ListView.isCurrentItem + property var hasCurrentItem: materialListView.currentItem != null - Row + property var currentItem: + { // is soon to be overwritten + var current_index = materialListView.currentIndex; + return materialsModel.getItem(current_index); + } + + property var isCurrentItemActivated: + { + const extruder_position = Cura.ExtruderManager.activeExtruderIndex; + const root_material_id = Cura.MachineManager.currentRootMaterialId[extruder_position]; + return base.currentItem.root_material_id == root_material_id; + } + + Row // Button Row + { + id: buttonRow + anchors { - spacing: (UM.Theme.getSize("default_margin").width / 2) | 0 - anchors.left: parent.left - anchors.leftMargin: UM.Theme.getSize("default_margin").width - anchors.right: parent.right - Rectangle + left: parent.left + right: parent.right + top: titleLabel.bottom + } + height: childrenRect.height + + // Activate button + Button + { + text: catalog.i18nc("@action:button", "Activate") + iconName: "list-activate" + enabled: !isCurrentItemActivated + onClicked: { - width: Math.round(parent.height * 0.8) - height: Math.round(parent.height * 0.8) - color: model.metadata.color_code - border.color: isCurrentItem ? palette.highlightedText : palette.text; - anchors.verticalCenter: parent.verticalCenter - } - Label - { - width: Math.round((parent.width * 0.3)) - text: model.metadata.material - elide: Text.ElideRight - font.italic: model.id == activeId - color: isCurrentItem ? palette.highlightedText : palette.text; - } - Label - { - text: (model.name != model.metadata.material) ? model.name : "" - elide: Text.ElideRight - font.italic: model.id == activeId - color: isCurrentItem ? palette.highlightedText : palette.text; + forceActiveFocus() + + const extruder_position = Cura.ExtruderManager.activeExtruderIndex; + Cura.MachineManager.setMaterial(extruder_position, base.currentItem.container_node); } } - MouseArea + // Create button + Button { - anchors.fill: parent; + text: catalog.i18nc("@action:button", "Create") + iconName: "list-add" onClicked: { forceActiveFocus(); - if(!parent.ListView.isCurrentItem) - { - parent.ListView.view.currentIndex = index; - base.itemActivated(); - } + base.newRootMaterialIdToSwitchTo = base.materialManager.createMaterial(); + base.toActivateNewMaterial = true; } } - } - - activeId: Cura.MachineManager.activeMaterialId - activeIndex: getIndexById(activeId) - function getIndexById(material_id) - { - for(var i = 0; i < model.rowCount(); i++) { - if (model.getItem(i).id == material_id) { - return i; - } - } - return -1; - } - - scrollviewCaption: - { - var caption = catalog.i18nc("@action:label", "Printer") + ": " + Cura.MachineManager.activeMachineName; - if (Cura.MachineManager.hasVariants) - { - caption += ", " + Cura.MachineManager.activeDefinitionVariantsName + ": " + Cura.MachineManager.activeVariantName; - } - return caption; - } - detailsVisible: true - - section.property: "section" - section.delegate: Label - { - text: section - font.bold: true - anchors.left: parent.left; - anchors.leftMargin: UM.Theme.getSize("default_lining").width; - } - - buttons: [ - - // Activate button - Button { - text: catalog.i18nc("@action:button", "Activate") - iconName: "list-activate"; - enabled: base.currentItem != null && base.currentItem.id != Cura.MachineManager.activeMaterialId && Cura.MachineManager.hasMaterials - onClicked: { - forceActiveFocus() - Cura.MachineManager.setActiveMaterial(base.currentItem.id) - currentItem = base.model.getItem(base.objectList.currentIndex) // Refresh the current item. - } - }, - - // Create button - Button { - text: catalog.i18nc("@action:button", "Create") - iconName: "list-add" - onClicked: { - forceActiveFocus() - Cura.ContainerManager.createMaterial() - } - }, // Duplicate button - Button { + Button + { text: catalog.i18nc("@action:button", "Duplicate"); - iconName: "list-add"; - enabled: base.currentItem != null - onClicked: { - forceActiveFocus() - Cura.ContainerManager.duplicateOriginalMaterial(base.currentItem.id) + iconName: "list-add" + enabled: base.hasCurrentItem + onClicked: + { + forceActiveFocus(); + base.newRootMaterialIdToSwitchTo = base.materialManager.duplicateMaterial(base.currentItem.container_node); + base.toActivateNewMaterial = true; } - }, + } // Remove button - Button { + Button + { text: catalog.i18nc("@action:button", "Remove") iconName: "list-remove" - enabled: base.currentItem != null && !base.currentItem.readOnly && !Cura.ContainerManager.isContainerUsed(base.currentItem.id) - onClicked: { - forceActiveFocus() - confirmDialog.open() + enabled: base.hasCurrentItem && !base.currentItem.is_read_only && !base.isCurrentItemActivated + onClicked: + { + forceActiveFocus(); + confirmRemoveMaterialDialog.open(); } - }, + } // Import button - Button { + Button + { text: catalog.i18nc("@action:button", "Import") iconName: "document-import" - onClicked: { - forceActiveFocus() - importDialog.open() + onClicked: + { + forceActiveFocus(); + importMaterialDialog.open(); } visible: true - }, + } // Export button - Button { + Button + { text: catalog.i18nc("@action:button", "Export") iconName: "document-export" - onClicked: { - forceActiveFocus() - exportDialog.open() + onClicked: + { + forceActiveFocus(); + exportMaterialDialog.open(); } enabled: currentItem != null } + } + + property string newRootMaterialIdToSwitchTo: "" + property bool toActivateNewMaterial: false + + // This connection makes sure that we will switch to the new + Connections + { + target: materialsModel + onItemsChanged: { + var currentItemId = base.currentItem == null ? "" : base.currentItem.root_material_id; + var position = Cura.ExtruderManager.activeExtruderIndex; + + // try to pick the currently selected item; it may have been moved + if (base.newRootMaterialIdToSwitchTo == "") { + base.newRootMaterialIdToSwitchTo = currentItemId; + } + + for (var idx = 0; idx < materialsModel.rowCount(); ++idx) { + var item = materialsModel.getItem(idx); + if (item.root_material_id == base.newRootMaterialIdToSwitchTo) { + // Switch to the newly created profile if needed + materialListView.currentIndex = idx; + materialListView.activateDetailsWithIndex(materialListView.currentIndex); + if (base.toActivateNewMaterial) { + Cura.MachineManager.setMaterial(position, item.container_node); + } + base.newRootMaterialIdToSwitchTo = ""; + base.toActivateNewMaterial = false; + return + } + } + + materialListView.currentIndex = 0; + materialListView.activateDetailsWithIndex(materialListView.currentIndex); + if (base.toActivateNewMaterial) { + Cura.MachineManager.setMaterial(position, materialsModel.getItem(0).container_node); + } + base.newRootMaterialIdToSwitchTo = ""; + base.toActivateNewMaterial = false; + } + } + + MessageDialog + { + id: confirmRemoveMaterialDialog + + icon: StandardIcon.Question; + title: catalog.i18nc("@title:window", "Confirm Remove") + text: catalog.i18nc("@label (%1 is object name)", "Are you sure you wish to remove %1? This cannot be undone!").arg(base.currentItem.name) + standardButtons: StandardButton.Yes | StandardButton.No + modality: Qt.ApplicationModal + + onYes: + { + base.materialManager.removeMaterial(base.currentItem.container_node); + } + } + + FileDialog + { + id: importMaterialDialog + title: catalog.i18nc("@title:window", "Import Material") + selectExisting: true + nameFilters: Cura.ContainerManager.getContainerNameFilters("material") + folder: CuraApplication.getDefaultPath("dialog_material_path") + onAccepted: + { + var result = Cura.ContainerManager.importMaterialContainer(fileUrl); + + messageDialog.title = catalog.i18nc("@title:window", "Import Material"); + messageDialog.text = catalog.i18nc("@info:status Don't translate the XML tags or !", "Could not import material %1: %2").arg(fileUrl).arg(result.message); + if (result.status == "success") { + messageDialog.icon = StandardIcon.Information; + messageDialog.text = catalog.i18nc("@info:status Don't translate the XML tag !", "Successfully imported material %1").arg(fileUrl); + } + else if (result.status == "duplicate") { + messageDialog.icon = StandardIcon.Warning; + } + else { + messageDialog.icon = StandardIcon.Critical; + } + messageDialog.open(); + CuraApplication.setDefaultPath("dialog_material_path", folder); + } + } + + FileDialog + { + id: exportMaterialDialog + title: catalog.i18nc("@title:window", "Export Material") + selectExisting: false + nameFilters: Cura.ContainerManager.getContainerNameFilters("material") + folder: CuraApplication.getDefaultPath("dialog_material_path") + onAccepted: + { + var result = Cura.ContainerManager.exportContainer(base.currentItem.root_material_id, selectedNameFilter, fileUrl); + + messageDialog.title = catalog.i18nc("@title:window", "Export Material"); + if (result.status == "error") { + messageDialog.icon = StandardIcon.Critical; + messageDialog.text = catalog.i18nc("@info:status Don't translate the XML tags and !", "Failed to export material to %1: %2").arg(fileUrl).arg(result.message); + messageDialog.open(); + } + else if (result.status == "success") { + messageDialog.icon = StandardIcon.Information; + messageDialog.text = catalog.i18nc("@info:status Don't translate the XML tag !", "Successfully exported material to %1").arg(result.path); + messageDialog.open(); + } + CuraApplication.setDefaultPath("dialog_material_path", folder); + } + } + + MessageDialog + { + id: messageDialog + } - ] Item { - visible: base.currentItem != null - anchors.fill: parent + id: contentsItem + + anchors { + top: titleLabel.bottom + left: parent.left + right: parent.right + bottom: parent.bottom + margins: 5 * screenScaleFactor + bottomMargin: 0 + } + + clip: true + } + + Item + { + anchors { + top: buttonRow.bottom + topMargin: UM.Theme.getSize("default_margin").height + left: parent.left + right: parent.right + bottom: parent.bottom + } + + SystemPalette { id: palette } + + Label + { + id: captionLabel + anchors { + top: parent.top + left: parent.left + } + visible: text != "" + text: { + var caption = catalog.i18nc("@action:label", "Printer") + ": " + Cura.MachineManager.activeMachineName; + if (Cura.MachineManager.hasVariants) + { + caption += ", " + Cura.MachineManager.activeDefinitionVariantsName + ": " + Cura.MachineManager.activeVariantName; + } + return caption; + } + width: materialScrollView.width + elide: Text.ElideRight + } + + ScrollView + { + id: materialScrollView + anchors { + top: captionLabel.visible ? captionLabel.bottom : parent.top + topMargin: captionLabel.visible ? UM.Theme.getSize("default_margin").height : 0 + bottom: parent.bottom + left: parent.left + } + + Rectangle { + parent: viewport + anchors.fill: parent + color: palette.light + } + + width: true ? (parent.width * 0.4) | 0 : parent.width + + ListView + { + id: materialListView + + model: materialsModel + + section.property: "brand" + section.criteria: ViewSection.FullString + section.delegate: Rectangle + { + width: materialScrollView.width + height: childrenRect.height + color: palette.light + + Label + { + anchors.left: parent.left + anchors.leftMargin: UM.Theme.getSize("default_lining").width + text: section + font.bold: true + color: palette.text + } + } + + delegate: Rectangle + { + width: materialScrollView.width + height: childrenRect.height + color: ListView.isCurrentItem ? palette.highlight : (model.index % 2) ? palette.base : palette.alternateBase + + Row + { + id: materialRow + spacing: (UM.Theme.getSize("default_margin").width / 2) | 0 + anchors.left: parent.left + anchors.leftMargin: UM.Theme.getSize("default_margin").width + anchors.right: parent.right + + property bool isItemActivated: + { + const extruder_position = Cura.ExtruderManager.activeExtruderIndex; + const root_material_id = Cura.MachineManager.currentRootMaterialId[extruder_position]; + return model.root_material_id == root_material_id; + } + + Rectangle + { + width: Math.floor(parent.height * 0.8) + height: Math.floor(parent.height * 0.8) + color: model.color_code + border.color: parent.ListView.isCurrentItem ? palette.highlightedText : palette.text; + anchors.verticalCenter: parent.verticalCenter + } + Label + { + width: Math.floor((parent.width * 0.3)) + text: model.material + elide: Text.ElideRight + font.italic: materialRow.isItemActivated + color: parent.ListView.isCurrentItem ? palette.highlightedText : palette.text; + } + Label + { + text: (model.name != model.material) ? model.name : "" + elide: Text.ElideRight + font.italic: materialRow.isItemActivated + color: parent.ListView.isCurrentItem ? palette.highlightedText : palette.text; + } + } + + MouseArea + { + anchors.fill: parent + onClicked: { + parent.ListView.view.currentIndex = model.index; + } + } + } + + function activateDetailsWithIndex(index) { + var model = materialsModel.getItem(index); + base.currentItem = model; + materialDetailsView.containerId = model.container_id; + materialDetailsView.currentMaterialNode = model.container_node; + + detailsPanel.updateMaterialPropertiesObject(); + } + + onCurrentIndexChanged: + { + forceActiveFocus(); // causes the changed fields to be saved + activateDetailsWithIndex(currentIndex); + } + } + } + Item { - id: profileName + id: detailsPanel - width: parent.width; - height: childrenRect.height - - Label { text: materialProperties.name; font: UM.Theme.getFont("large"); } - } - - MaterialView - { - anchors - { - left: parent.left - right: parent.right - top: profileName.bottom - topMargin: UM.Theme.getSize("default_margin").height + anchors { + left: materialScrollView.right + leftMargin: UM.Theme.getSize("default_margin").width + top: parent.top bottom: parent.bottom + right: parent.right } - editingEnabled: base.currentItem != null && !base.currentItem.readOnly - - properties: materialProperties - containerId: base.currentItem != null ? base.currentItem.id : "" - - property alias pane: base - } - - QtObject - { - id: materialProperties - - property string guid: "00000000-0000-0000-0000-000000000000" - property string name: "Unknown"; - property string profile_type: "Unknown"; - property string supplier: "Unknown"; - property string material_type: "Unknown"; - - property string color_name: "Yellow"; - property color color_code: "yellow"; - - property real density: 0.0; - property real diameter: 0.0; - property string approximate_diameter: "0"; - - property real spool_cost: 0.0; - property real spool_weight: 0.0; - property real spool_length: 0.0; - property real cost_per_meter: 0.0; - - property string description: ""; - property string adhesion_info: ""; - } - - UM.ConfirmRemoveDialog - { - id: confirmDialog - object: base.currentItem != null ? base.currentItem.name : "" - onYes: + function updateMaterialPropertiesObject() { - // A material container can actually be multiple items, so we need to find (and remove) all of them. - var base_file = Cura.ContainerManager.getContainerMetaDataEntry(base.currentItem.id, "base_file") - if(base_file == "") - { - base_file = base.currentItem.id - } - var guid = Cura.ContainerManager.getContainerMetaDataEntry(base.currentItem.id, "GUID") - // remove base container first, it otherwise triggers loading the base file while removing other containers - var base_containers = Cura.ContainerManager.findInstanceContainers({"GUID": guid, "id": base_file, "base_file": base_file, "type": "material"}) - for(var i in base_containers) - { - Cura.ContainerManager.removeContainer(base_containers[i]); - } - var containers = Cura.ContainerManager.findInstanceContainers({"GUID": guid, "base_file": base_file, "type": "material"}) - for(var i in containers) - { - Cura.ContainerManager.removeContainer(containers[i]); - } - if(base.objectList.currentIndex > 0) - { - base.objectList.currentIndex--; - } - currentItem = base.model.getItem(base.objectList.currentIndex) // Refresh the current item. - } - } + var currentItem = materialsModel.getItem(materialListView.currentIndex); - FileDialog - { - id: importDialog; - title: catalog.i18nc("@title:window", "Import Material"); - selectExisting: true; - nameFilters: Cura.ContainerManager.getContainerNameFilters("material") - folder: CuraApplication.getDefaultPath("dialog_material_path") - onAccepted: + materialProperties.name = currentItem.name; + materialProperties.guid = currentItem.guid; + + materialProperties.brand = currentItem.brand ? currentItem.brand : "Unknown"; + materialProperties.material = currentItem.material ? currentItem.material : "Unknown"; + materialProperties.color_name = currentItem.color_name ? currentItem.color_name : "Yellow"; + materialProperties.color_code = currentItem.color_code ? currentItem.color_code : "yellow"; + + materialProperties.description = currentItem.description ? currentItem.description : ""; + materialProperties.adhesion_info = currentItem.adhesion_info ? currentItem.adhesion_info : ""; + + materialProperties.density = currentItem.density ? currentItem.density : 0.0; + materialProperties.diameter = currentItem.diameter ? currentItem.diameter : 0.0; + materialProperties.approximate_diameter = currentItem.approximate_diameter ? currentItem.approximate_diameter : "0"; + } + + Item { - var result = Cura.ContainerManager.importMaterialContainer(fileUrl) + anchors.fill: parent - messageDialog.title = catalog.i18nc("@title:window", "Import Material") - messageDialog.text = catalog.i18nc("@info:status Don't translate the XML tags or !", "Could not import material %1: %2").arg(fileUrl).arg(result.message) - if(result.status == "success") + Item // Material title Label { - messageDialog.icon = StandardIcon.Information - messageDialog.text = catalog.i18nc("@info:status Don't translate the XML tag !", "Successfully imported material %1").arg(fileUrl) + id: profileName + + width: parent.width + height: childrenRect.height + + Label { + text: materialProperties.name + font: UM.Theme.getFont("large") + } } - else if(result.status == "duplicate") + + MaterialView // Material detailed information view below the title Label { - messageDialog.icon = StandardIcon.Warning + id: materialDetailsView + anchors + { + left: parent.left + right: parent.right + top: profileName.bottom + topMargin: UM.Theme.getSize("default_margin").height + bottom: parent.bottom + } + + editingEnabled: base.currentItem != null && !base.currentItem.is_read_only + + properties: materialProperties + containerId: base.currentItem != null ? base.currentItem.container_id : "" + currentMaterialNode: base.currentItem.container_node + + property alias pane: base } - else + + QtObject { - messageDialog.icon = StandardIcon.Critical + id: materialProperties + + property string guid: "00000000-0000-0000-0000-000000000000" + property string name: "Unknown"; + property string profile_type: "Unknown"; + property string brand: "Unknown"; + property string material: "Unknown"; // This needs to be named as "material" to be consistent with + // the material container's metadata entry + + property string color_name: "Yellow"; + property color color_code: "yellow"; + + property real density: 0.0; + property real diameter: 0.0; + property string approximate_diameter: "0"; + + property real spool_cost: 0.0; + property real spool_weight: 0.0; + property real spool_length: 0.0; + property real cost_per_meter: 0.0; + + property string description: ""; + property string adhesion_info: ""; } - messageDialog.open() - CuraApplication.setDefaultPath("dialog_material_path", folder) } } - - FileDialog - { - id: exportDialog; - title: catalog.i18nc("@title:window", "Export Material"); - selectExisting: false; - nameFilters: Cura.ContainerManager.getContainerNameFilters("material") - folder: CuraApplication.getDefaultPath("dialog_material_path") - onAccepted: - { - if(base.currentItem.metadata.base_file) - { - var result = Cura.ContainerManager.exportContainer(base.currentItem.metadata.base_file, selectedNameFilter, fileUrl) - } - else - { - var result = Cura.ContainerManager.exportContainer(base.currentItem.id, selectedNameFilter, fileUrl) - } - - messageDialog.title = catalog.i18nc("@title:window", "Export Material") - if(result.status == "error") - { - messageDialog.icon = StandardIcon.Critical - messageDialog.text = catalog.i18nc("@info:status Don't translate the XML tags and !", "Failed to export material to %1: %2").arg(fileUrl).arg(result.message) - messageDialog.open() - } - else if(result.status == "success") - { - messageDialog.icon = StandardIcon.Information - messageDialog.text = catalog.i18nc("@info:status Don't translate the XML tag !", "Successfully exported material to %1").arg(result.path) - messageDialog.open() - } - CuraApplication.setDefaultPath("dialog_material_path", folder) - } - } - - MessageDialog - { - id: messageDialog - } - - UM.SettingPropertyProvider - { - id: materialDiameterProvider - - containerStackId: Cura.ExtruderManager.activeExtruderStackId - key: "material_diameter" - watchedProperties: [ "value" ] - storeIndex: 5 - } - - UM.I18nCatalog { id: catalog; name: "cura"; } - SystemPalette { id: palette } - } - - onCurrentItemChanged: - { - if(currentItem == null) - { - return - } - materialProperties.name = currentItem.name; - materialProperties.guid = Cura.ContainerManager.getContainerMetaDataEntry(base.currentItem.id, "GUID"); - - if(currentItem.metadata != undefined && currentItem.metadata != null) - { - materialProperties.supplier = currentItem.metadata.brand ? currentItem.metadata.brand : "Unknown"; - materialProperties.material_type = currentItem.metadata.material ? currentItem.metadata.material : "Unknown"; - materialProperties.color_name = currentItem.metadata.color_name ? currentItem.metadata.color_name : "Yellow"; - materialProperties.color_code = currentItem.metadata.color_code ? currentItem.metadata.color_code : "yellow"; - - materialProperties.description = currentItem.metadata.description ? currentItem.metadata.description : ""; - materialProperties.adhesion_info = currentItem.metadata.adhesion_info ? currentItem.metadata.adhesion_info : ""; - - if(currentItem.metadata.properties != undefined && currentItem.metadata.properties != null) - { - materialProperties.density = currentItem.metadata.properties.density ? currentItem.metadata.properties.density : 0.0; - materialProperties.diameter = currentItem.metadata.properties.diameter ? currentItem.metadata.properties.diameter : 0.0; - materialProperties.approximate_diameter = currentItem.metadata.approximate_diameter ? currentItem.metadata.approximate_diameter : "0"; - } - else - { - materialProperties.density = 0.0; - materialProperties.diameter = 0.0; - materialProperties.approximate_diameter = "0"; - } - - } } } diff --git a/resources/qml/Preferences/ProfileTab.qml b/resources/qml/Preferences/ProfileTab.qml index acebea3500..dcabf012b7 100644 --- a/resources/qml/Preferences/ProfileTab.qml +++ b/resources/qml/Preferences/ProfileTab.qml @@ -1,8 +1,8 @@ -// Copyright (c) 2016 Ultimaker B.V. +// Copyright (c) 2018 Ultimaker B.V. // Cura is released under the terms of the LGPLv3 or higher. -import QtQuick 2.1 -import QtQuick.Controls 1.1 +import QtQuick 2.8 +import QtQuick.Controls 1.4 import UM 1.2 as UM import Cura 1.0 as Cura @@ -11,10 +11,8 @@ Tab { id: base - property string extruderId: ""; - property string extruderDefinition: ""; - property string quality: ""; - property string material: ""; + property string extruderPosition: "" + property var qualityItem: null TableView { @@ -38,8 +36,8 @@ Tab anchors.leftMargin: UM.Theme.getSize("default_margin").width anchors.right: parent.right text: (styleData.value.substr(0,1) == "=") ? catalog.i18nc("@info:status", "Calculated") : styleData.value - font.strikeout: styleData.column == 1 && quality == Cura.MachineManager.globalQualityId && setting.user_value != "" - font.italic: setting.profile_value_source == "quality_changes" || (quality == Cura.MachineManager.globalQualityId && setting.user_value != "") + font.strikeout: styleData.column == 1 && setting.user_value != "" && qualityItem.name == Cura.MachineManager.activeQualityOrQualityChangesName + font.italic: setting.profile_value_source == "quality_changes" || (setting.user_value != "" && qualityItem.name == Cura.MachineManager.activeQualityOrQualityChangesName) opacity: font.strikeout ? 0.5 : 1 color: styleData.textColor elide: Text.ElideRight @@ -65,7 +63,7 @@ Tab { role: "user_value" title: catalog.i18nc("@title:column", "Current"); - visible: quality == Cura.MachineManager.globalQualityId + visible: qualityItem.name == Cura.MachineManager.activeQualityOrQualityChangesName width: (parent.width * 0.18) | 0 delegate: itemDelegate } @@ -87,10 +85,8 @@ Tab model: Cura.QualitySettingsModel { id: qualitySettings - extruderId: base.extruderId - extruderDefinition: base.extruderDefinition - quality: base.quality != null ? base.quality : "" - material: base.material != null ? base.material : "" + selectedPosition: base.extruderPosition + selectedQualityItem: base.qualityItem } SystemPalette { id: palette } diff --git a/resources/qml/Preferences/ProfilesPage.qml b/resources/qml/Preferences/ProfilesPage.qml index e3ba9b23a4..e9bbb4bc66 100644 --- a/resources/qml/Preferences/ProfilesPage.qml +++ b/resources/qml/Preferences/ProfilesPage.qml @@ -1,355 +1,532 @@ -// Copyright (c) 2016 Ultimaker B.V. -// Cura is released under the terms of the LGPLv3 or higher. +// Copyright (c) 2018 Ultimaker B.V. +// Uranium is released under the terms of the LGPLv3 or higher. -import QtQuick 2.1 -import QtQuick.Controls 1.1 +import QtQuick 2.8 +import QtQuick.Controls 1.4 +import QtQuick.Layouts 1.3 import QtQuick.Dialogs 1.2 import UM 1.2 as UM import Cura 1.0 as Cura -UM.ManagementPage + +Item { - id: base; + id: base - title: catalog.i18nc("@title:tab", "Profiles"); - property var extrudersModel: Cura.ExtrudersModel{} + property QtObject qualityManager: CuraApplication.getQualityManager() + property var resetEnabled: false // Keep PreferencesDialog happy + property var extrudersModel: Cura.ExtrudersModel {} - model: Cura.QualityAndUserProfilesModel { } + UM.I18nCatalog { id: catalog; name: "cura"; } - section.property: "readOnly" - section.delegate: Rectangle + Cura.QualityManagementModel { + id: qualitiesModel + } + + Label { + id: titleLabel + anchors { + top: parent.top + left: parent.left + right: parent.right + margins: 5 * screenScaleFactor + } + font.pointSize: 18 + text: catalog.i18nc("@title:tab", "Profiles") + } + + property var hasCurrentItem: qualityListView.currentItem != null + + property var currentItem: { + var current_index = qualityListView.currentIndex; + return qualitiesModel.getItem(current_index); + } + + property var isCurrentItemActivated: { + if (!base.currentItem) { + return false; + } + return base.currentItem.name == Cura.MachineManager.activeQualityOrQualityChangesName; + } + + property var canCreateProfile: { + return isCurrentItemActivated && Cura.MachineManager.hasUserSettings; + } + + Row // Button Row { - height: childrenRect.height; - - Label - { - anchors.left: parent.left; - anchors.leftMargin: UM.Theme.getSize("default_lining").width; - text: section == "true" ? catalog.i18nc("@label", "Protected profiles") : catalog.i18nc("@label", "Custom profiles") - font.bold: true + id: buttonRow + anchors { + left: parent.left + right: parent.right + top: titleLabel.bottom } - } + height: childrenRect.height - activeId: Cura.MachineManager.activeQualityId - activeIndex: { - for(var i = 0; i < model.rowCount(); i++) { - if (model.getItem(i).id == Cura.MachineManager.activeQualityId) { - return i; - } - } - return -1; - } - - function canCreateProfile() { - return base.currentItem && (base.currentItem.id == Cura.MachineManager.activeQualityId) && Cura.MachineManager.hasUserSettings; - } - - buttons: [ + // Activate button Button { - text: catalog.i18nc("@action:button", "Activate"); - iconName: "list-activate"; - enabled: base.currentItem != null ? base.currentItem.id != Cura.MachineManager.activeQualityId : false; - onClicked: - { - Cura.MachineManager.setActiveQuality(base.currentItem.id) - currentItem = base.model.getItem(base.objectList.currentIndex) // Refresh the current item. + text: catalog.i18nc("@action:button", "Activate") + iconName: "list-activate" + enabled: !isCurrentItemActivated + onClicked: { + if (base.currentItem.is_read_only) { + Cura.MachineManager.setQualityGroup(base.currentItem.quality_group); + } else { + Cura.MachineManager.setQualityChangesGroup(base.currentItem.quality_changes_group); + } } - }, + } // Create button Button { text: catalog.i18nc("@label", "Create") - enabled: base.canCreateProfile() && !Cura.MachineManager.stacksHaveErrors - visible: base.canCreateProfile() - iconName: "list-add"; + iconName: "list-add" + enabled: base.canCreateProfile && !Cura.MachineManager.stacksHaveErrors + visible: base.canCreateProfile - onClicked: - { - newNameDialog.object = base.currentItem != null ? Cura.ContainerManager.makeUniqueName(base.currentItem.name) : ""; - newNameDialog.open(); - newNameDialog.selectText(); + onClicked: { + createQualityDialog.object = Cura.ContainerManager.makeUniqueName(base.currentItem.name); + createQualityDialog.open(); + createQualityDialog.selectText(); } - }, + } // Duplicate button Button { text: catalog.i18nc("@label", "Duplicate") - enabled: ! base.canCreateProfile() - visible: ! base.canCreateProfile() - iconName: "list-add"; + iconName: "list-add" + enabled: !base.canCreateProfile + visible: !base.canCreateProfile - onClicked: - { - newDuplicateNameDialog.object = Cura.ContainerManager.makeUniqueName(base.currentItem.name); - newDuplicateNameDialog.open(); - newDuplicateNameDialog.selectText(); + onClicked: { + duplicateQualityDialog.object = Cura.ContainerManager.makeUniqueName(base.currentItem.name); + duplicateQualityDialog.open(); + duplicateQualityDialog.selectText(); } - }, + } + // Remove button Button { - text: catalog.i18nc("@action:button", "Remove"); - iconName: "list-remove"; - enabled: base.currentItem != null ? !base.currentItem.readOnly && !Cura.ContainerManager.isContainerUsed(base.currentItem.id) : false; - onClicked: confirmDialog.open(); - }, - Button - { - text: catalog.i18nc("@action:button", "Rename"); - iconName: "edit-rename"; - enabled: base.currentItem != null ? !base.currentItem.readOnly : false; - onClicked: - { - renameDialog.open(); - renameDialog.selectText(); + text: catalog.i18nc("@action:button", "Remove") + iconName: "list-remove" + enabled: base.hasCurrentItem && !base.currentItem.is_read_only && !base.isCurrentItemActivated + onClicked: { + forceActiveFocus(); + confirmRemoveQualityDialog.open(); } - }, + } + + // Rename button Button { - text: catalog.i18nc("@action:button", "Import"); - iconName: "document-import"; - onClicked: importDialog.open(); - }, + text: catalog.i18nc("@action:button", "Rename") + iconName: "edit-rename" + enabled: base.hasCurrentItem && !base.currentItem.is_read_only + onClicked: { + renameQualityDialog.object = base.currentItem.name; + renameQualityDialog.open(); + renameQualityDialog.selectText(); + } + } + + // Import button + Button + { + text: catalog.i18nc("@action:button", "Import") + iconName: "document-import" + onClicked: { + importDialog.open(); + } + } + + // Export button Button { text: catalog.i18nc("@action:button", "Export") iconName: "document-export" - onClicked: exportDialog.open() - enabled: currentItem != null && !base.currentItem.readOnly + enabled: base.hasCurrentItem && !base.currentItem.is_read_only + onClicked: { + exportDialog.open(); + } } - ] - - scrollviewCaption: catalog.i18nc("@label %1 is printer name","Printer: %1").arg(Cura.MachineManager.activeMachineName) + } + // Click create profile from ... in Profile context menu signal createProfile() onCreateProfile: { - newNameDialog.object = base.currentItem != null ? Cura.ContainerManager.makeUniqueName(base.currentItem.name) : ""; - newNameDialog.open(); - newNameDialog.selectText(); + createQualityDialog.object = Cura.ContainerManager.makeUniqueName(Cura.MachineManager.activeQualityOrQualityChangesName); + createQualityDialog.open(); + createQualityDialog.selectText(); } - signal selectContainer(string name) - onSelectContainer: + // Dialog to request a name when creating a new profile + UM.RenameDialog { - objectList.currentIndex = objectList.model.find("name", name); + id: createQualityDialog + title: catalog.i18nc("@title:window", "Create Profile") + object: "" + onAccepted: + { + base.newQualityNameToSelect = newName; // We want to switch to the new profile once it's created + base.toActivateNewQuality = true; + Cura.ContainerManager.createQualityChanges(newName); + } + } + + property string newQualityNameToSelect: "" + property bool toActivateNewQuality: false + + // This connection makes sure that we will switch to the correct quality after the model gets updated + Connections + { + target: qualitiesModel + onItemsChanged: { + var toSelectItemName = base.currentItem == null ? "" : base.currentItem.name; + if (newQualityNameToSelect != "") { + toSelectItemName = newQualityNameToSelect; + } + + var newIdx = -1; // Default to nothing if nothing can be found + if (toSelectItemName != "") { + // Select the required quality name if given + for (var idx = 0; idx < qualitiesModel.rowCount(); ++idx) { + var item = qualitiesModel.getItem(idx); + if (item.name == toSelectItemName) { + // Switch to the newly created profile if needed + newIdx = idx; + if (base.toActivateNewQuality) { + // Activate this custom quality if required + Cura.MachineManager.setQualityChangesGroup(item.quality_changes_group); + } + break; + } + } + } + qualityListView.currentIndex = newIdx; + + // Reset states + base.newQualityNameToSelect = ""; + base.toActivateNewQuality = false; + } + } + + // Dialog to request a name when duplicating a new profile + UM.RenameDialog + { + id: duplicateQualityDialog + title: catalog.i18nc("@title:window", "Duplicate Profile") + object: "" + onAccepted: + { + base.qualityManager.duplicateQualityChanges(newName, base.currentItem); + } + } + + // Confirmation dialog for removing a profile + MessageDialog + { + id: confirmRemoveQualityDialog + + icon: StandardIcon.Question; + title: catalog.i18nc("@title:window", "Confirm Remove") + text: catalog.i18nc("@label (%1 is object name)", "Are you sure you wish to remove %1? This cannot be undone!").arg(base.currentItem.name) + standardButtons: StandardButton.Yes | StandardButton.No + modality: Qt.ApplicationModal + + onYes: + { + base.qualityManager.removeQualityChangesGroup(base.currentItem.quality_changes_group); + // reset current item to the first if available + qualityListView.currentIndex = -1; // Reset selection. + } + } + + // Dialog to rename a quality profile + UM.RenameDialog + { + id: renameQualityDialog + title: catalog.i18nc("@title:window", "Rename Profile") + object: "" + onAccepted: + { + var actualNewName = base.qualityManager.renameQualityChangesGroup(base.currentItem.quality_changes_group, newName); + base.newQualityNameToSelect = actualNewName; // Select the new name after the model gets updated + } + } + + // Dialog for importing a quality profile + FileDialog + { + id: importDialog + title: catalog.i18nc("@title:window", "Import Profile") + selectExisting: true + nameFilters: qualitiesModel.getFileNameFilters("profile_reader") + folder: CuraApplication.getDefaultPath("dialog_profile_path") + onAccepted: + { + var result = Cura.ContainerManager.importProfile(fileUrl); + messageDialog.text = result.message; + if (result.status == "ok") { + messageDialog.icon = StandardIcon.Information; + } + else if (result.status == "duplicate") { + messageDialog.icon = StandardIcon.Warning; + } + else { + messageDialog.icon = StandardIcon.Critical; + } + messageDialog.open(); + CuraApplication.setDefaultPath("dialog_profile_path", folder); + } + } + + // Dialog for exporting a quality profile + FileDialog + { + id: exportDialog + title: catalog.i18nc("@title:window", "Export Profile") + selectExisting: false + nameFilters: qualitiesModel.getFileNameFilters("profile_writer") + folder: CuraApplication.getDefaultPath("dialog_profile_path") + onAccepted: + { + var result = Cura.ContainerManager.exportQualityChangesGroup(base.currentItem.quality_changes_group, + fileUrl, selectedNameFilter); + + if (result && result.status == "error") { + messageDialog.icon = StandardIcon.Critical; + messageDialog.text = result.message; + messageDialog.open(); + } + + // else pop-up Message thing from python code + CuraApplication.setDefaultPath("dialog_profile_path", folder); + } } Item { - visible: base.currentItem != null - anchors.fill: parent + id: contentsItem - Label { - id: profileName - text: base.currentItem ? base.currentItem.name: "" - font: UM.Theme.getFont("large") - width: parent.width - elide: Text.ElideRight + anchors { + top: titleLabel.bottom + left: parent.left + right: parent.right + bottom: parent.bottom + margins: 5 * screenScaleFactor + bottomMargin: 0 } - Flow { - id: currentSettingsActions - visible: currentItem && currentItem.id == Cura.MachineManager.activeQualityId - anchors.left: parent.left - anchors.right: parent.right - anchors.top: profileName.bottom - anchors.topMargin: UM.Theme.getSize("default_margin").height - - Button - { - text: { - return catalog.i18nc("@action:button", "Update profile with current settings/overrides"); - } - enabled: Cura.MachineManager.hasUserSettings && !Cura.MachineManager.isReadOnly(Cura.MachineManager.activeQualityId) - onClicked: Cura.ContainerManager.updateQualityChanges() - } - - Button - { - text: catalog.i18nc("@action:button", "Discard current changes"); - enabled: Cura.MachineManager.hasUserSettings - onClicked: Cura.ContainerManager.clearUserContainers(); - } - } - - Column { - id: profileNotices - anchors.top: currentSettingsActions.visible ? currentSettingsActions.bottom : currentSettingsActions.anchors.top - anchors.topMargin: UM.Theme.getSize("default_margin").height - anchors.left: parent.left - anchors.right: parent.right - spacing: UM.Theme.getSize("default_margin").height - - Label { - id: defaultsMessage - visible: false - text: catalog.i18nc("@action:label", "This profile uses the defaults specified by the printer, so it has no settings/overrides in the list below.") - wrapMode: Text.WordWrap - width: parent.width - } - Label { - id: noCurrentSettingsMessage - visible: currentItem && currentItem.id == Cura.MachineManager.activeQualityId && !Cura.MachineManager.hasUserSettings - text: catalog.i18nc("@action:label", "Your current settings match the selected profile.") - wrapMode: Text.WordWrap - width: parent.width - } - } - - TabView - { - anchors.left: parent.left - anchors.top: profileNotices.visible ? profileNotices.bottom : profileNotices.anchors.top - anchors.topMargin: UM.Theme.getSize("default_margin").height - anchors.right: parent.right - anchors.bottom: parent.bottom - - currentIndex: Cura.ExtruderManager.extruderCount > 0 ? Cura.ExtruderManager.activeExtruderIndex + 1 : 0 - - ProfileTab - { - title: catalog.i18nc("@title:tab", "Global Settings"); - quality: base.currentItem != null ? base.currentItem.id : ""; - material: Cura.MachineManager.allActiveMaterialIds[Cura.MachineManager.activeMachineId] - } - - Repeater - { - model: base.extrudersModel - - ProfileTab - { - title: model.name; - extruderId: model.id; - extruderDefinition: model.definition; - quality: base.currentItem != null ? base.currentItem.id : ""; - material: Cura.MachineManager.allActiveMaterialIds[model.id] - } - } - } + clip: true } Item { - UM.I18nCatalog { id: catalog; name: "cura"; } + anchors { + top: buttonRow.bottom + topMargin: UM.Theme.getSize("default_margin").height + left: parent.left + right: parent.right + bottom: parent.bottom + } - UM.ConfirmRemoveDialog + SystemPalette { id: palette } + + Label { - id: confirmDialog - object: base.currentItem != null ? base.currentItem.name : "" - onYes: + id: captionLabel + anchors { + top: parent.top + left: parent.left + } + visible: text != "" + text: catalog.i18nc("@label %1 is printer name", "Printer: %1").arg(Cura.MachineManager.activeMachineName) + width: profileScrollView.width + elide: Text.ElideRight + } + + ScrollView + { + id: profileScrollView + anchors { + top: captionLabel.visible ? captionLabel.bottom : parent.top + topMargin: captionLabel.visible ? UM.Theme.getSize("default_margin").height : 0 + bottom: parent.bottom + left: parent.left + } + + Rectangle { + parent: viewport + anchors.fill: parent + color: palette.light + } + + width: true ? (parent.width * 0.4) | 0 : parent.width + + ListView { - var name = base.currentItem.name; - Cura.ContainerManager.removeQualityChanges(name) - if(Cura.MachineManager.activeQualityName == name) + id: qualityListView + + model: qualitiesModel + + section.property: "is_read_only" + section.delegate: Rectangle { - Cura.MachineManager.setActiveQuality(base.model.getItem(0).name) + height: childrenRect.height + + Label + { + anchors.left: parent.left + anchors.leftMargin: UM.Theme.getSize("default_lining").width + text: section == "true" ? catalog.i18nc("@label", "Protected profiles") : catalog.i18nc("@label", "Custom profiles") + font.bold: true + } + } + + delegate: Rectangle + { + width: profileScrollView.width + height: childrenRect.height + color: ListView.isCurrentItem ? palette.highlight : (model.index % 2) ? palette.base : palette.alternateBase + + Row + { + spacing: (UM.Theme.getSize("default_margin").width / 2) | 0 + anchors.left: parent.left + anchors.leftMargin: UM.Theme.getSize("default_margin").width + anchors.right: parent.right + Label + { + width: Math.floor((parent.width * 0.8)) + text: model.name + elide: Text.ElideRight + font.italic: model.name == Cura.MachineManager.activeQualityOrQualityChangesName + color: parent.ListView.isCurrentItem ? palette.highlightedText : palette.text + } + } + + MouseArea + { + anchors.fill: parent + onClicked: { + parent.ListView.view.currentIndex = model.index; + } + } } - objectList.currentIndex = -1 //Reset selection. } } - UM.RenameDialog + // details panel on the right + Item { - title: catalog.i18nc("@title:window", "Rename Profile") - id: renameDialog; - object: base.currentItem != null ? base.currentItem.name : "" - onAccepted: - { - Cura.ContainerManager.renameQualityChanges(base.currentItem.name, newName) - objectList.currentIndex = -1 //Reset selection. + id: detailsPanel + + anchors { + left: profileScrollView.right + leftMargin: UM.Theme.getSize("default_margin").width + top: parent.top + bottom: parent.bottom + right: parent.right } - } - // Dialog to request a name when creating a new profile - UM.RenameDialog - { - title: catalog.i18nc("@title:window", "Create Profile") - id: newNameDialog; - object: ""; - onAccepted: + Item { - var selectedContainer = Cura.ContainerManager.createQualityChanges(newName); - base.selectContainer(selectedContainer); - objectList.currentIndex = -1 //Reset selection. - } - } + anchors.fill: parent - // Dialog to request a name when duplicating a new profile - UM.RenameDialog - { - title: catalog.i18nc("@title:window", "Duplicate Profile") - id: newDuplicateNameDialog; - object: ""; - onAccepted: - { - var selectedContainer = Cura.ContainerManager.duplicateQualityOrQualityChanges(base.currentItem.name, newName); - base.selectContainer(selectedContainer); - objectList.currentIndex = -1 //Reset selection. - } - } - - MessageDialog - { - id: messageDialog - title: catalog.i18nc("@window:title", "Import Profile"); - standardButtons: StandardButton.Ok - modality: Qt.ApplicationModal - } - - FileDialog - { - id: importDialog; - title: catalog.i18nc("@title:window", "Import Profile"); - selectExisting: true; - nameFilters: base.model.getFileNameFilters("profile_reader") - folder: CuraApplication.getDefaultPath("dialog_profile_path") - onAccepted: - { - var result = Cura.ContainerManager.importProfile(fileUrl); - messageDialog.text = result.message - if(result.status == "ok") + Item // Profile title Label { - messageDialog.icon = StandardIcon.Information - } - else if(result.status == "duplicate") - { - messageDialog.icon = StandardIcon.Warning - } - else - { - messageDialog.icon = StandardIcon.Critical - } - messageDialog.open() - CuraApplication.setDefaultPath("dialog_profile_path", folder) - } - } + id: profileName - FileDialog - { - id: exportDialog; - title: catalog.i18nc("@title:window", "Export Profile"); - selectExisting: false; - nameFilters: base.model.getFileNameFilters("profile_writer") - folder: CuraApplication.getDefaultPath("dialog_profile_path") - onAccepted: - { - var containers = Cura.ContainerManager.findInstanceContainers({"type": "quality_changes", "name": base.currentItem.name}) - var result = Cura.ContainerManager.exportProfile(containers, fileUrl, selectedNameFilter) + width: parent.width + height: childrenRect.height - if(result && result.status == "error") - { - messageDialog.icon = StandardIcon.Critical - messageDialog.text = result.message - messageDialog.open() + Label { + text: base.currentItem.name + font: UM.Theme.getFont("large") + } } - // else pop-up Message thing from python code - CuraApplication.setDefaultPath("dialog_profile_path", folder) + Flow { + id: currentSettingsActions + visible: base.hasCurrentItem && base.currentItem.name == Cura.MachineManager.activeQualityOrQualityChangesName + anchors.left: parent.left + anchors.right: parent.right + anchors.top: profileName.bottom + anchors.topMargin: UM.Theme.getSize("default_margin").height + + Button + { + text: catalog.i18nc("@action:button", "Update profile with current settings/overrides") + enabled: Cura.MachineManager.hasUserSettings && !base.currentItem.is_read_only + onClicked: Cura.ContainerManager.updateQualityChanges() + } + + Button + { + text: catalog.i18nc("@action:button", "Discard current changes"); + enabled: Cura.MachineManager.hasUserSettings + onClicked: Cura.ContainerManager.clearUserContainers(); + } + } + + Column { + id: profileNotices + anchors.top: currentSettingsActions.visible ? currentSettingsActions.bottom : currentSettingsActions.anchors.top + anchors.topMargin: UM.Theme.getSize("default_margin").height + anchors.left: parent.left + anchors.right: parent.right + spacing: UM.Theme.getSize("default_margin").height + + Label { + id: defaultsMessage + visible: false + text: catalog.i18nc("@action:label", "This profile uses the defaults specified by the printer, so it has no settings/overrides in the list below.") + wrapMode: Text.WordWrap + width: parent.width + } + Label { + id: noCurrentSettingsMessage + visible: base.isCurrentItemActivated && !Cura.MachineManager.hasUserSettings + text: catalog.i18nc("@action:label", "Your current settings match the selected profile.") + wrapMode: Text.WordWrap + width: parent.width + } + } + + + TabView + { + anchors.left: parent.left + anchors.top: profileNotices.visible ? profileNotices.bottom : profileNotices.anchors.top + anchors.topMargin: UM.Theme.getSize("default_margin").height + anchors.right: parent.right + anchors.bottom: parent.bottom + + currentIndex: 0 + + ProfileTab + { + title: catalog.i18nc("@title:tab", "Global Settings") + qualityItem: base.currentItem + } + + Repeater + { + model: base.extrudersModel + + ProfileTab + { + title: model.name + extruderPosition: model.index + qualityItem: base.currentItem + } + } + } } } } diff --git a/resources/qml/Settings/SettingView.qml b/resources/qml/Settings/SettingView.qml index 46842baa98..615e66277b 100644 --- a/resources/qml/Settings/SettingView.qml +++ b/resources/qml/Settings/SettingView.qml @@ -57,13 +57,13 @@ Item height: UM.Theme.getSize("setting_control").height anchors.left: globalProfileLabel.right anchors.right: parent.right - tooltip: Cura.MachineManager.activeQualityName + tooltip: Cura.MachineManager.activeQualityOrQualityChangesName style: UM.Theme.styles.sidebar_header_button activeFocusOnPress: true menu: ProfileMenu { } function generateActiveQualityText () { - var result = Cura.MachineManager.activeQualityName; + var result = Cura.MachineManager.activeQualityOrQualityChangesName; if (Cura.MachineManager.isActiveQualitySupported) { if (Cura.MachineManager.activeQualityLayerHeight > 0) { @@ -544,4 +544,4 @@ Item } } } -} \ No newline at end of file +} diff --git a/resources/qml/SidebarAdvanced.qml b/resources/qml/SidebarAdvanced.qml index ff5f545c80..ae77bc8d1b 100644 --- a/resources/qml/SidebarAdvanced.qml +++ b/resources/qml/SidebarAdvanced.qml @@ -1,7 +1,7 @@ // Copyright (c) 2015 Ultimaker B.V. // Cura is released under the terms of the LGPLv3 or higher. -import QtQuick 2.7 +import QtQuick 2.8 import QtQuick.Controls 2.0 import "Settings" diff --git a/resources/qml/SidebarHeader.qml b/resources/qml/SidebarHeader.qml index d43b8d3752..5d9cbe2ad1 100644 --- a/resources/qml/SidebarHeader.qml +++ b/resources/qml/SidebarHeader.qml @@ -252,10 +252,20 @@ Column { id: materialSelection - text: Cura.MachineManager.activeMaterialName - tooltip: Cura.MachineManager.activeMaterialName + property var currentRootMaterialName: + { + var materials = Cura.MachineManager.currentRootMaterialName; + var materialName = ""; + if (base.currentExtruderIndex in materials) { + materialName = materials[base.currentExtruderIndex]; + } + return materialName; + } + + text: currentRootMaterialName + tooltip: currentRootMaterialName visible: Cura.MachineManager.hasMaterials - enabled: !extrudersList.visible || base.currentExtruderIndex > -1 + enabled: !extrudersList.visible || base.currentExtruderIndex > -1 height: UM.Theme.getSize("setting_control").height width: Math.round(parent.width * 0.7) + UM.Theme.getSize("sidebar_margin").width anchors.right: parent.right diff --git a/resources/qml/SidebarSimple.qml b/resources/qml/SidebarSimple.qml index dc8549f282..1991a9fa57 100644 --- a/resources/qml/SidebarSimple.qml +++ b/resources/qml/SidebarSimple.qml @@ -1,13 +1,13 @@ -// Copyright (c) 2017 Ultimaker B.V. +// Copyright (c) 2018 Ultimaker B.V. // Cura is released under the terms of the LGPLv3 or higher. -import QtQuick 2.7 +import QtQuick 2.8 import QtQuick.Controls 1.4 import QtQuick.Controls.Styles 1.4 import QtQuick.Layouts 1.3 import UM 1.2 as UM -import Cura 1.2 as Cura +import Cura 1.0 as Cura Item { @@ -57,7 +57,10 @@ Item interval: 50 running: false repeat: false - onTriggered: Cura.MachineManager.setActiveQuality(Cura.ProfilesModel.getItem(qualitySlider.value).id) + onTriggered: { + var item = Cura.QualityProfilesDropDownMenuModel.getItem(qualitySlider.value); + Cura.MachineManager.activeQualityGroup = item.quality_group; + } } Component.onCompleted: qualityModel.update() @@ -102,14 +105,14 @@ Item var availableMin = -1 var availableMax = -1 - for (var i = 0; i < Cura.ProfilesModel.rowCount(); i++) { - var qualityItem = Cura.ProfilesModel.getItem(i) + for (var i = 0; i < Cura.QualityProfilesDropDownMenuModel.rowCount(); i++) { + var qualityItem = Cura.QualityProfilesDropDownMenuModel.getItem(i) // Add each quality item to the UI quality model qualityModel.append(qualityItem) // Set selected value - if (Cura.MachineManager.activeQualityType == qualityItem.metadata.quality_type) { + if (Cura.MachineManager.activeQualityType == qualityItem.quality_type) { // set to -1 when switching to user created profile so all ticks are clickable if (Cura.SimpleModeSettingsManager.isProfileUserCreated) { @@ -134,7 +137,7 @@ Item // Set total available ticks for active slider part if (availableMin != -1) { - qualityModel.availableTotalTicks = availableMax - availableMin + qualityModel.availableTotalTicks = availableMax - availableMin + 1 } // Calculate slider values @@ -161,11 +164,11 @@ Item function reset () { qualityModel.clear() - qualityModel.availableTotalTicks = -1 + qualityModel.availableTotalTicks = 0 qualityModel.existingQualityProfile = 0 // check, the ticks count cannot be less than zero - qualityModel.totalTicks = Math.max(0, Cura.ProfilesModel.rowCount() - 1) + qualityModel.totalTicks = Math.max(0, Cura.QualityProfilesDropDownMenuModel.rowCount() - 1) } } @@ -191,13 +194,13 @@ Item anchors.verticalCenter: parent.verticalCenter anchors.top: parent.top anchors.topMargin: Math.round(UM.Theme.getSize("sidebar_margin").height / 2) - color: (Cura.MachineManager.activeMachine != null && Cura.ProfilesModel.getItem(index).available) ? UM.Theme.getColor("quality_slider_available") : UM.Theme.getColor("quality_slider_unavailable") + color: (Cura.MachineManager.activeMachine != null && Cura.QualityProfilesDropDownMenuModel.getItem(index).available) ? UM.Theme.getColor("quality_slider_available") : UM.Theme.getColor("quality_slider_unavailable") text: { var result = "" if(Cura.MachineManager.activeMachine != null) { - result = Cura.ProfilesModel.getItem(index).layer_height_without_unit + result = Cura.QualityProfilesDropDownMenuModel.getItem(index).layer_height if(result == undefined) { @@ -262,7 +265,7 @@ Item Rectangle { anchors.verticalCenter: parent.verticalCenter - color: Cura.ProfilesModel.getItem(index).available ? UM.Theme.getColor("quality_slider_available") : UM.Theme.getColor("quality_slider_unavailable") + color: Cura.QualityProfilesDropDownMenuModel.getItem(index).available ? UM.Theme.getColor("quality_slider_available") : UM.Theme.getColor("quality_slider_unavailable") width: 1 * screenScaleFactor height: 6 * screenScaleFactor y: 0 @@ -270,32 +273,24 @@ Item } } - Rectangle { - id: disabledHandleButton - visible: !qualitySlider.visible - anchors.centerIn: parent - color: UM.Theme.getColor("quality_slider_unavailable") - implicitWidth: 10 * screenScaleFactor - implicitHeight: implicitWidth - radius: Math.round(width / 2) - } - Slider { id: qualitySlider height: UM.Theme.getSize("sidebar_margin").height anchors.bottom: speedSlider.bottom - enabled: qualityModel.availableTotalTicks > 0 && !Cura.SimpleModeSettingsManager.isProfileCustomized - visible: qualityModel.totalTicks > 0 + enabled: qualityModel.totalTicks > 0 && !Cura.SimpleModeSettingsManager.isProfileCustomized + visible: qualityModel.availableTotalTicks > 0 updateValueWhileDragging : false minimumValue: qualityModel.qualitySliderAvailableMin >= 0 ? qualityModel.qualitySliderAvailableMin : 0 - maximumValue: qualityModel.qualitySliderAvailableMax >= 0 ? qualityModel.qualitySliderAvailableMax : 0 + // maximumValue must be greater than minimumValue to be able to see the handle. While the value is strictly + // speaking not always correct, it seems to have the correct behavior (switching from 0 available to 1 available) + maximumValue: qualityModel.qualitySliderAvailableMax >= 1 ? qualityModel.qualitySliderAvailableMax : 1 stepSize: 1 value: qualityModel.qualitySliderActiveIndex - width: qualityModel.qualitySliderStepWidth * qualityModel.availableTotalTicks + width: qualityModel.qualitySliderStepWidth * (qualityModel.availableTotalTicks - 1) anchors.right: parent.right anchors.rightMargin: qualityModel.qualitySliderMarginRight @@ -373,7 +368,7 @@ Item text: catalog.i18nc("@label", "Slower") font: UM.Theme.getFont("default") - color: (qualityModel.availableTotalTicks > 0) ? UM.Theme.getColor("quality_slider_available") : UM.Theme.getColor("quality_slider_unavailable") + color: (qualityModel.availableTotalTicks > 1) ? UM.Theme.getColor("quality_slider_available") : UM.Theme.getColor("quality_slider_unavailable") horizontalAlignment: Text.AlignLeft } @@ -384,7 +379,7 @@ Item text: catalog.i18nc("@label", "Faster") font: UM.Theme.getFont("default") - color: (qualityModel.availableTotalTicks > 0) ? UM.Theme.getColor("quality_slider_available") : UM.Theme.getColor("quality_slider_unavailable") + color: (qualityModel.availableTotalTicks > 1) ? UM.Theme.getColor("quality_slider_available") : UM.Theme.getColor("quality_slider_unavailable") horizontalAlignment: Text.AlignRight } @@ -408,9 +403,10 @@ Item // if the current profile is user-created, switch to a built-in quality if (Cura.SimpleModeSettingsManager.isProfileUserCreated) { - if (Cura.ProfilesModel.rowCount() > 0) + if (Cura.QualityProfilesDropDownMenuModel.rowCount() > 0) { - Cura.MachineManager.setActiveQuality(Cura.ProfilesModel.getItem(0).id) + var item = Cura.QualityProfilesDropDownMenuModel.getItem(0); + Cura.MachineManager.activeQualityGroup = item.quality_group; } } if (Cura.SimpleModeSettingsManager.isProfileCustomized) diff --git a/resources/qml/WorkspaceSummaryDialog.qml b/resources/qml/WorkspaceSummaryDialog.qml index a05dee5a9a..1cfe36d14b 100644 --- a/resources/qml/WorkspaceSummaryDialog.qml +++ b/resources/qml/WorkspaceSummaryDialog.qml @@ -101,7 +101,7 @@ UM.Dialog } Label { - text: Cura.MachineManager.activeDefinitionName + text: Cura.MachineManager.activeMachine.definition.name width: (parent.width / 3) | 0 } } @@ -148,7 +148,7 @@ UM.Dialog Repeater { - model: Cura.MachineManager.activeMaterialNames + model: Cura.MachineManager.currentExtruderPositions delegate: Column { Item // Spacer @@ -158,7 +158,7 @@ UM.Dialog } Label { - text: catalog.i18nc("@action:label", "Extruder %1").arg(index+1) + text: catalog.i18nc("@action:label", "Extruder %1").arg(modelData) } height: childrenRect.height width: parent.width @@ -173,7 +173,7 @@ UM.Dialog } Label { - text: Cura.MachineManager.activeVariantNames[index] + ", " + modelData + text: Cura.MachineManager.activeVariantNames[modelData] + ", " + Cura.MachineManager.currentRootMaterialName[modelData] width: (parent.width / 3) | 0 } } @@ -217,7 +217,7 @@ UM.Dialog } Label { - text: Cura.MachineManager.activeQualityName + text: Cura.MachineManager.activeQualityOrQualityChangesName width: (parent.width / 3) | 0 } @@ -294,4 +294,4 @@ UM.Dialog } } } -} \ No newline at end of file +} diff --git a/resources/quality/abax_pri3/apri3_pla_fast.inst.cfg b/resources/quality/abax_pri3/apri3_pla_fast.inst.cfg index 32550d86a5..7d1c1bf588 100644 --- a/resources/quality/abax_pri3/apri3_pla_fast.inst.cfg +++ b/resources/quality/abax_pri3/apri3_pla_fast.inst.cfg @@ -4,11 +4,11 @@ name = Fine definition = abax_pri3 [metadata] -type = quality -material = generic_pla -weight = -1 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = -1 +material = generic_pla [values] layer_height = 0.2 @@ -19,4 +19,4 @@ speed_print = 80 speed_layer_0 = =round(speed_print * 30 / 50) speed_topbottom = 20 cool_min_layer_time = 5 -cool_min_speed = 10 \ No newline at end of file +cool_min_speed = 10 diff --git a/resources/quality/abax_pri3/apri3_pla_high.inst.cfg b/resources/quality/abax_pri3/apri3_pla_high.inst.cfg index 2007785719..46a4178dd9 100644 --- a/resources/quality/abax_pri3/apri3_pla_high.inst.cfg +++ b/resources/quality/abax_pri3/apri3_pla_high.inst.cfg @@ -4,11 +4,11 @@ name = Extra Fine definition = abax_pri3 [metadata] -type = quality -material = generic_pla -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_pla [values] layer_height = 0.1 @@ -19,4 +19,4 @@ speed_print = 50 speed_layer_0 = =round(speed_print * 30 / 50) speed_topbottom = 20 cool_min_layer_time = 5 -cool_min_speed = 10 \ No newline at end of file +cool_min_speed = 10 diff --git a/resources/quality/abax_pri3/apri3_pla_normal.inst.cfg b/resources/quality/abax_pri3/apri3_pla_normal.inst.cfg index dba0a0460f..3f6f36cfe6 100644 --- a/resources/quality/abax_pri3/apri3_pla_normal.inst.cfg +++ b/resources/quality/abax_pri3/apri3_pla_normal.inst.cfg @@ -4,11 +4,11 @@ name = Fine definition = abax_pri3 [metadata] -type = quality -material = generic_pla -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_pla [values] layer_height = 0.2 @@ -19,4 +19,4 @@ speed_print = 50 speed_layer_0 = =round(speed_print * 30 / 50) speed_topbottom = 20 cool_min_layer_time = 5 -cool_min_speed = 10 \ No newline at end of file +cool_min_speed = 10 diff --git a/resources/quality/abax_pri5/apri5_pla_fast.inst.cfg b/resources/quality/abax_pri5/apri5_pla_fast.inst.cfg index 11892a6223..517c767ac5 100644 --- a/resources/quality/abax_pri5/apri5_pla_fast.inst.cfg +++ b/resources/quality/abax_pri5/apri5_pla_fast.inst.cfg @@ -4,11 +4,11 @@ name = Fine definition = abax_pri5 [metadata] -type = quality -material = generic_pla -weight = -1 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = -1 +material = generic_pla [values] layer_height = 0.2 @@ -19,4 +19,4 @@ speed_print = 80 speed_layer_0 = =round(speed_print * 30 / 50) speed_topbottom = 20 cool_min_layer_time = 5 -cool_min_speed = 10 \ No newline at end of file +cool_min_speed = 10 diff --git a/resources/quality/abax_pri5/apri5_pla_high.inst.cfg b/resources/quality/abax_pri5/apri5_pla_high.inst.cfg index 852efe699e..01699e39f6 100644 --- a/resources/quality/abax_pri5/apri5_pla_high.inst.cfg +++ b/resources/quality/abax_pri5/apri5_pla_high.inst.cfg @@ -4,11 +4,11 @@ name = Extra Fine definition = abax_pri5 [metadata] -type = quality -material = generic_pla -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_pla [values] layer_height = 0.1 @@ -19,4 +19,4 @@ speed_print = 50 speed_layer_0 = =round(speed_print * 30 / 50) speed_topbottom = 20 cool_min_layer_time = 5 -cool_min_speed = 10 \ No newline at end of file +cool_min_speed = 10 diff --git a/resources/quality/abax_pri5/apri5_pla_normal.inst.cfg b/resources/quality/abax_pri5/apri5_pla_normal.inst.cfg index 244d544c80..ea1023dc43 100644 --- a/resources/quality/abax_pri5/apri5_pla_normal.inst.cfg +++ b/resources/quality/abax_pri5/apri5_pla_normal.inst.cfg @@ -4,11 +4,11 @@ name = Fine definition = abax_pri5 [metadata] -type = quality -material = generic_pla -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_pla [values] layer_height = 0.2 @@ -19,4 +19,4 @@ speed_print = 50 speed_layer_0 = =round(speed_print * 30 / 50) speed_topbottom = 20 cool_min_layer_time = 5 -cool_min_speed = 10 \ No newline at end of file +cool_min_speed = 10 diff --git a/resources/quality/abax_titan/atitan_pla_fast.inst.cfg b/resources/quality/abax_titan/atitan_pla_fast.inst.cfg index a2d802a3ba..ae489c3792 100644 --- a/resources/quality/abax_titan/atitan_pla_fast.inst.cfg +++ b/resources/quality/abax_titan/atitan_pla_fast.inst.cfg @@ -4,11 +4,11 @@ name = Fine definition = abax_titan [metadata] -type = quality -material = generic_pla -weight = -1 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = -1 +material = generic_pla [values] layer_height = 0.2 @@ -19,4 +19,4 @@ speed_print = 80 speed_layer_0 = =round(speed_print * 30 / 50) speed_topbottom = 20 cool_min_layer_time = 5 -cool_min_speed = 10 \ No newline at end of file +cool_min_speed = 10 diff --git a/resources/quality/abax_titan/atitan_pla_high.inst.cfg b/resources/quality/abax_titan/atitan_pla_high.inst.cfg index 7ee8c35133..f9bf350814 100644 --- a/resources/quality/abax_titan/atitan_pla_high.inst.cfg +++ b/resources/quality/abax_titan/atitan_pla_high.inst.cfg @@ -2,12 +2,13 @@ version = 2 name = Extra Fine definition = abax_titan + [metadata] -type = quality -material = generic_pla -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_pla [values] layer_height = 0.1 @@ -18,4 +19,4 @@ speed_print = 50 speed_layer_0 = =round(speed_print * 30 / 50) speed_topbottom = 20 cool_min_layer_time = 5 -cool_min_speed = 10 \ No newline at end of file +cool_min_speed = 10 diff --git a/resources/quality/abax_titan/atitan_pla_normal.inst.cfg b/resources/quality/abax_titan/atitan_pla_normal.inst.cfg index 6c40914566..c73d6901fb 100644 --- a/resources/quality/abax_titan/atitan_pla_normal.inst.cfg +++ b/resources/quality/abax_titan/atitan_pla_normal.inst.cfg @@ -4,11 +4,11 @@ name = Fine definition = abax_titan [metadata] -type = quality -material = generic_pla -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_pla [values] layer_height = 0.2 @@ -19,4 +19,4 @@ speed_print = 50 speed_layer_0 = =round(speed_print * 30 / 50) speed_topbottom = 20 cool_min_layer_time = 5 -cool_min_speed = 10 \ No newline at end of file +cool_min_speed = 10 diff --git a/resources/quality/anycubic_i3_mega/anycubic_i3_mega_draft.inst.cfg b/resources/quality/anycubic_i3_mega/anycubic_i3_mega_draft.inst.cfg index c6281767f9..caa6d8edb6 100644 --- a/resources/quality/anycubic_i3_mega/anycubic_i3_mega_draft.inst.cfg +++ b/resources/quality/anycubic_i3_mega/anycubic_i3_mega_draft.inst.cfg @@ -4,10 +4,10 @@ name = Draft definition = anycubic_i3_mega [metadata] +setting_version = 4 type = quality quality_type = draft weight = 0 -setting_version = 4 [values] acceleration_enabled = True @@ -57,4 +57,4 @@ support_type = everywhere support_use_towers = False support_xy_distance = 0.7 top_bottom_thickness = 1.2 -wall_thickness = 1.2 \ No newline at end of file +wall_thickness = 1.2 diff --git a/resources/quality/anycubic_i3_mega/anycubic_i3_mega_high.inst.cfg b/resources/quality/anycubic_i3_mega/anycubic_i3_mega_high.inst.cfg index 839054a4df..5d6f8d9013 100644 --- a/resources/quality/anycubic_i3_mega/anycubic_i3_mega_high.inst.cfg +++ b/resources/quality/anycubic_i3_mega/anycubic_i3_mega_high.inst.cfg @@ -4,10 +4,10 @@ name = High definition = anycubic_i3_mega [metadata] +setting_version = 4 type = quality quality_type = high weight = 2 -setting_version = 4 [values] acceleration_enabled = True @@ -57,4 +57,4 @@ support_type = everywhere support_use_towers = False support_xy_distance = 0.7 top_bottom_thickness = 1.2 -wall_thickness = 1.2 \ No newline at end of file +wall_thickness = 1.2 diff --git a/resources/quality/anycubic_i3_mega/anycubic_i3_mega_normal.inst.cfg b/resources/quality/anycubic_i3_mega/anycubic_i3_mega_normal.inst.cfg index 241a8b2e2c..ca25afa424 100644 --- a/resources/quality/anycubic_i3_mega/anycubic_i3_mega_normal.inst.cfg +++ b/resources/quality/anycubic_i3_mega/anycubic_i3_mega_normal.inst.cfg @@ -4,10 +4,10 @@ name = Normal definition = anycubic_i3_mega [metadata] +setting_version = 4 type = quality quality_type = normal weight = 1 -setting_version = 4 [values] acceleration_enabled = True @@ -57,4 +57,4 @@ support_type = everywhere support_use_towers = False support_xy_distance = 0.7 top_bottom_thickness = 1.2 -wall_thickness = 1.2 \ No newline at end of file +wall_thickness = 1.2 diff --git a/resources/quality/builder_premium/bp_BVOH_Coarse_Quality.inst.cfg b/resources/quality/builder_premium/bp_BVOH_Coarse_Quality.inst.cfg index 92f899bdeb..d83f2a1ccd 100644 --- a/resources/quality/builder_premium/bp_BVOH_Coarse_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_BVOH_Coarse_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Coarse definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = coarse -material = verbatim_bvoh_175 -setting_version = 4 weight = -1 +material = verbatim_bvoh_175 [values] material_print_temperature = =default_material_print_temperature + 5 @@ -21,4 +21,3 @@ layer_height = 0.3 top_thickness = =layer_height * 5 bottom_thickness = =layer_height * 3 speed_print = 40 - diff --git a/resources/quality/builder_premium/bp_BVOH_High_Quality.inst.cfg b/resources/quality/builder_premium/bp_BVOH_High_Quality.inst.cfg index cd8947aa80..f029a0206f 100644 --- a/resources/quality/builder_premium/bp_BVOH_High_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_BVOH_High_Quality.inst.cfg @@ -4,11 +4,11 @@ name = High Quality definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = high -material = verbatim_bvoh_175 -setting_version = 4 weight = 1 +material = verbatim_bvoh_175 [values] acceleration_print = 2000 @@ -22,4 +22,4 @@ layer_height = 0.1 top_thickness = =layer_height * 7 bottom_thickness = =layer_height * 5 speed_print = 40 -layer_height_0 = 0.2 \ No newline at end of file +layer_height_0 = 0.2 diff --git a/resources/quality/builder_premium/bp_BVOH_Normal_Quality.inst.cfg b/resources/quality/builder_premium/bp_BVOH_Normal_Quality.inst.cfg index d59f768470..640812b37d 100644 --- a/resources/quality/builder_premium/bp_BVOH_Normal_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_BVOH_Normal_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = normal -material = verbatim_bvoh_175 -setting_version = 4 weight = 0 +material = verbatim_bvoh_175 [values] material_print_temperature = =default_material_print_temperature + 5 @@ -20,4 +20,4 @@ material_bed_temperature_layer_0= =material_bed_temperature layer_height = 0.2 top_thickness = =layer_height * 5 bottom_thickness = =layer_height * 3 -speed_print = 40 \ No newline at end of file +speed_print = 40 diff --git a/resources/quality/builder_premium/bp_Innoflex60_Coarse_Quality.inst.cfg b/resources/quality/builder_premium/bp_Innoflex60_Coarse_Quality.inst.cfg index 41d882ee1d..905cf50518 100644 --- a/resources/quality/builder_premium/bp_Innoflex60_Coarse_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_Innoflex60_Coarse_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Coarse definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = coarse -material = innofill_innoflex60_175 -setting_version = 4 weight = -1 +material = innofill_innoflex60_175 [values] material_print_temperature = =default_material_print_temperature @@ -21,4 +21,3 @@ layer_height = 0.3 top_thickness = =layer_height * 5 bottom_thickness = =layer_height * 3 speed_print = 30 - diff --git a/resources/quality/builder_premium/bp_Innoflex60_High_Quality.inst.cfg b/resources/quality/builder_premium/bp_Innoflex60_High_Quality.inst.cfg index 147e1f4db8..835ce04d61 100644 --- a/resources/quality/builder_premium/bp_Innoflex60_High_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_Innoflex60_High_Quality.inst.cfg @@ -4,11 +4,11 @@ name = High Quality definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = high -material = innofill_innoflex60_175 -setting_version = 4 weight = 1 +material = innofill_innoflex60_175 [values] acceleration_print = 2000 @@ -22,4 +22,4 @@ layer_height = 0.1 top_thickness = =layer_height * 7 bottom_thickness = =layer_height * 5 speed_print = 30 -layer_height_0 = 0.2 \ No newline at end of file +layer_height_0 = 0.2 diff --git a/resources/quality/builder_premium/bp_Innoflex60_Normal_Quality.inst.cfg b/resources/quality/builder_premium/bp_Innoflex60_Normal_Quality.inst.cfg index fb43c8de19..ba176dbc5c 100644 --- a/resources/quality/builder_premium/bp_Innoflex60_Normal_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_Innoflex60_Normal_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = normal -material = innofill_innoflex60_175 -setting_version = 4 weight = 0 +material = innofill_innoflex60_175 [values] material_print_temperature = =default_material_print_temperature @@ -20,4 +20,4 @@ material_bed_temperature_layer_0= =material_bed_temperature layer_height = 0.2 top_thickness = =layer_height * 5 bottom_thickness = =layer_height * 3 -speed_print = 30 \ No newline at end of file +speed_print = 30 diff --git a/resources/quality/builder_premium/bp_PET_Coarse_Quality.inst.cfg b/resources/quality/builder_premium/bp_PET_Coarse_Quality.inst.cfg index f887600585..736defd5c6 100644 --- a/resources/quality/builder_premium/bp_PET_Coarse_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_PET_Coarse_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Coarse definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = coarse -material = generic_petg_175 -setting_version = 4 weight = -1 +material = generic_petg [values] material_print_temperature = =default_material_print_temperature - 5 @@ -21,4 +21,3 @@ layer_height = 0.3 top_thickness = =layer_height * 5 bottom_thickness = =layer_height * 3 speed_print = 60 - diff --git a/resources/quality/builder_premium/bp_PET_High_Quality.inst.cfg b/resources/quality/builder_premium/bp_PET_High_Quality.inst.cfg index 4258f2f708..82c7fa7baf 100644 --- a/resources/quality/builder_premium/bp_PET_High_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_PET_High_Quality.inst.cfg @@ -4,11 +4,11 @@ name = High Quality definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_petg_175 -setting_version = 4 weight = 1 +material = generic_petg [values] acceleration_print = 2000 @@ -22,4 +22,4 @@ layer_height = 0.1 top_thickness = =layer_height * 7 bottom_thickness = =layer_height * 5 speed_print = 40 -layer_height_0 = 0.2 \ No newline at end of file +layer_height_0 = 0.2 diff --git a/resources/quality/builder_premium/bp_PET_Normal_Quality.inst.cfg b/resources/quality/builder_premium/bp_PET_Normal_Quality.inst.cfg index b732073795..b1e9ff91df 100644 --- a/resources/quality/builder_premium/bp_PET_Normal_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_PET_Normal_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_petg_175 -setting_version = 4 weight = 0 +material = generic_petg [values] material_print_temperature = =default_material_print_temperature - 5 @@ -20,4 +20,4 @@ material_bed_temperature_layer_0= =material_bed_temperature layer_height = 0.2 top_thickness = =layer_height * 5 bottom_thickness = =layer_height * 3 -speed_print = 50 \ No newline at end of file +speed_print = 50 diff --git a/resources/quality/builder_premium/bp_PLA_Coarse_Quality.inst.cfg b/resources/quality/builder_premium/bp_PLA_Coarse_Quality.inst.cfg index 4f0c26dd7d..9b8078e266 100644 --- a/resources/quality/builder_premium/bp_PLA_Coarse_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_PLA_Coarse_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Coarse definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = coarse -material = generic_pla_175 -setting_version = 4 weight = -1 +material = generic_pla [values] material_print_temperature = =default_material_print_temperature + 15 @@ -21,4 +21,3 @@ layer_height = 0.3 top_thickness = =layer_height * 5 bottom_thickness = =layer_height * 3 speed_print = 60 - diff --git a/resources/quality/builder_premium/bp_PLA_High_Quality.inst.cfg b/resources/quality/builder_premium/bp_PLA_High_Quality.inst.cfg index 4a9bcb90bf..2bbfb02e0d 100644 --- a/resources/quality/builder_premium/bp_PLA_High_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_PLA_High_Quality.inst.cfg @@ -4,11 +4,11 @@ name = High Quality definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pla_175 -setting_version = 4 weight = 1 +material = generic_pla [values] acceleration_print = 2000 @@ -22,4 +22,4 @@ layer_height = 0.1 top_thickness = =layer_height * 7 bottom_thickness = =layer_height * 5 speed_print = 40 -layer_height_0 = 0.2 \ No newline at end of file +layer_height_0 = 0.2 diff --git a/resources/quality/builder_premium/bp_PLA_Normal_Quality.inst.cfg b/resources/quality/builder_premium/bp_PLA_Normal_Quality.inst.cfg index 6af5601fd6..b77ac747a8 100644 --- a/resources/quality/builder_premium/bp_PLA_Normal_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_PLA_Normal_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pla_175 -setting_version = 4 weight = 0 +material = generic_pla [values] material_print_temperature = =default_material_print_temperature + 15 @@ -20,4 +20,4 @@ material_bed_temperature_layer_0= =material_bed_temperature layer_height = 0.2 top_thickness = =layer_height * 5 bottom_thickness = =layer_height * 3 -speed_print = 50 \ No newline at end of file +speed_print = 50 diff --git a/resources/quality/builder_premium/bp_PVA_Coarse_Quality.inst.cfg b/resources/quality/builder_premium/bp_PVA_Coarse_Quality.inst.cfg index 12a4c9d883..f626604f70 100644 --- a/resources/quality/builder_premium/bp_PVA_Coarse_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_PVA_Coarse_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Coarse definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = coarse -material = generic_pva_175 -setting_version = 4 weight = -1 +material = generic_pva [values] material_print_temperature = =default_material_print_temperature + 10 @@ -21,4 +21,3 @@ layer_height = 0.3 top_thickness = =layer_height * 5 bottom_thickness = =layer_height * 3 speed_print = 40 - diff --git a/resources/quality/builder_premium/bp_PVA_High_Quality.inst.cfg b/resources/quality/builder_premium/bp_PVA_High_Quality.inst.cfg index d32017c5f2..caf0bd4bd7 100644 --- a/resources/quality/builder_premium/bp_PVA_High_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_PVA_High_Quality.inst.cfg @@ -4,11 +4,11 @@ name = High Quality definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pva_175 -setting_version = 4 weight = 1 +material = generic_pva [values] acceleration_print = 2000 @@ -22,4 +22,4 @@ layer_height = 0.1 top_thickness = =layer_height * 7 bottom_thickness = =layer_height * 5 speed_print = 40 -layer_height_0 = 0.2 \ No newline at end of file +layer_height_0 = 0.2 diff --git a/resources/quality/builder_premium/bp_PVA_Normal_Quality.inst.cfg b/resources/quality/builder_premium/bp_PVA_Normal_Quality.inst.cfg index 2acc354822..4f08010a6f 100644 --- a/resources/quality/builder_premium/bp_PVA_Normal_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_PVA_Normal_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pva_175 -setting_version = 4 weight = 0 +material = generic_pva [values] material_print_temperature = =default_material_print_temperature + 10 @@ -20,4 +20,4 @@ material_bed_temperature_layer_0= =material_bed_temperature layer_height = 0.2 top_thickness = =layer_height * 5 bottom_thickness = =layer_height * 3 -speed_print = 40 \ No newline at end of file +speed_print = 40 diff --git a/resources/quality/builder_premium/bp_global_Coarse_Quality.inst.cfg b/resources/quality/builder_premium/bp_global_Coarse_Quality.inst.cfg index 4b66293d04..c9b2b3a654 100644 --- a/resources/quality/builder_premium/bp_global_Coarse_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_global_Coarse_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Coarse definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = coarse -setting_version = 4 weight = -1 global_quality = True [values] -layer_height = 0.3 \ No newline at end of file +layer_height = 0.3 diff --git a/resources/quality/builder_premium/bp_global_High_Quality.inst.cfg b/resources/quality/builder_premium/bp_global_High_Quality.inst.cfg index 4a97dda084..efad0f96e5 100644 --- a/resources/quality/builder_premium/bp_global_High_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_global_High_Quality.inst.cfg @@ -4,11 +4,11 @@ name = High Quality definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = high -setting_version = 4 weight = 1 global_quality = True [values] -layer_height = 0.1 \ No newline at end of file +layer_height = 0.1 diff --git a/resources/quality/builder_premium/bp_global_Normal_Quality.inst.cfg b/resources/quality/builder_premium/bp_global_Normal_Quality.inst.cfg index 15ea66879f..69c6214aa8 100644 --- a/resources/quality/builder_premium/bp_global_Normal_Quality.inst.cfg +++ b/resources/quality/builder_premium/bp_global_Normal_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = builder_premium_small [metadata] +setting_version = 4 type = quality quality_type = normal -setting_version = 4 weight = 0 global_quality = True [values] -layer_height = 0.2 \ No newline at end of file +layer_height = 0.2 diff --git a/resources/quality/cartesio/abs/cartesio_0.25_abs_high.inst.cfg b/resources/quality/cartesio/abs/cartesio_0.25_abs_high.inst.cfg index f541fd9654..82cbed79e3 100644 --- a/resources/quality/cartesio/abs/cartesio_0.25_abs_high.inst.cfg +++ b/resources/quality/cartesio/abs/cartesio_0.25_abs_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_abs_175_cartesio_0.25_mm weight = 1 -setting_version = 4 +material = generic_abs +variant = 0.25 mm [values] infill_line_width = 0.3 diff --git a/resources/quality/cartesio/abs/cartesio_0.25_abs_normal.inst.cfg b/resources/quality/cartesio/abs/cartesio_0.25_abs_normal.inst.cfg index a3c1d1ac14..4c8da554d3 100644 --- a/resources/quality/cartesio/abs/cartesio_0.25_abs_normal.inst.cfg +++ b/resources/quality/cartesio/abs/cartesio_0.25_abs_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_abs_175_cartesio_0.25_mm weight = 2 -setting_version = 4 +material = generic_abs +variant = 0.25 mm [values] infill_line_width = 0.3 diff --git a/resources/quality/cartesio/abs/cartesio_0.4_abs_high.inst.cfg b/resources/quality/cartesio/abs/cartesio_0.4_abs_high.inst.cfg index e299ccd2b2..1e068c97c7 100644 --- a/resources/quality/cartesio/abs/cartesio_0.4_abs_high.inst.cfg +++ b/resources/quality/cartesio/abs/cartesio_0.4_abs_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_abs_175_cartesio_0.4_mm weight = 1 -setting_version = 4 +material = generic_abs +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/abs/cartesio_0.4_abs_normal.inst.cfg b/resources/quality/cartesio/abs/cartesio_0.4_abs_normal.inst.cfg index ea92f0bd34..7019eb7a5b 100644 --- a/resources/quality/cartesio/abs/cartesio_0.4_abs_normal.inst.cfg +++ b/resources/quality/cartesio/abs/cartesio_0.4_abs_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_abs_175_cartesio_0.4_mm weight = 2 -setting_version = 4 +material = generic_abs +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/abs/cartesio_0.8_abs_coarse.inst.cfg b/resources/quality/cartesio/abs/cartesio_0.8_abs_coarse.inst.cfg index 3887e9dfe2..7b12575e69 100644 --- a/resources/quality/cartesio/abs/cartesio_0.8_abs_coarse.inst.cfg +++ b/resources/quality/cartesio/abs/cartesio_0.8_abs_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = coarse -material = generic_abs_175_cartesio_0.8_mm weight = 3 -setting_version = 4 +material = generic_abs +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/abs/cartesio_0.8_abs_extra_coarse.inst.cfg b/resources/quality/cartesio/abs/cartesio_0.8_abs_extra_coarse.inst.cfg index c9f430ac9a..bc25bf8d00 100644 --- a/resources/quality/cartesio/abs/cartesio_0.8_abs_extra_coarse.inst.cfg +++ b/resources/quality/cartesio/abs/cartesio_0.8_abs_extra_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Extra Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = extra coarse -material = generic_abs_175_cartesio_0.8_mm weight = 4 -setting_version = 4 +material = generic_abs +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/abs/cartesio_0.8_abs_high.inst.cfg b/resources/quality/cartesio/abs/cartesio_0.8_abs_high.inst.cfg index 983d199533..b8ca55fa6e 100644 --- a/resources/quality/cartesio/abs/cartesio_0.8_abs_high.inst.cfg +++ b/resources/quality/cartesio/abs/cartesio_0.8_abs_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_abs_175_cartesio_0.8_mm weight = 1 -setting_version = 4 +material = generic_abs +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/abs/cartesio_0.8_abs_normal.inst.cfg b/resources/quality/cartesio/abs/cartesio_0.8_abs_normal.inst.cfg index 06570a7153..409e0f9adf 100644 --- a/resources/quality/cartesio/abs/cartesio_0.8_abs_normal.inst.cfg +++ b/resources/quality/cartesio/abs/cartesio_0.8_abs_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_abs_175_cartesio_0.8_mm weight = 2 -setting_version = 4 +material = generic_abs +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/arnitel/cartesio_0.4_arnitel2045_high.inst.cfg b/resources/quality/cartesio/arnitel/cartesio_0.4_arnitel2045_high.inst.cfg index 8afe86164e..11d541831d 100644 --- a/resources/quality/cartesio/arnitel/cartesio_0.4_arnitel2045_high.inst.cfg +++ b/resources/quality/cartesio/arnitel/cartesio_0.4_arnitel2045_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = dsm_arnitel2045_175_cartesio_0.4_mm weight = 1 -setting_version = 4 +material = dsm_arnitel2045_175 +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/arnitel/cartesio_0.4_arnitel2045_normal.inst.cfg b/resources/quality/cartesio/arnitel/cartesio_0.4_arnitel2045_normal.inst.cfg index 27c659ea0a..d6a972b1cd 100644 --- a/resources/quality/cartesio/arnitel/cartesio_0.4_arnitel2045_normal.inst.cfg +++ b/resources/quality/cartesio/arnitel/cartesio_0.4_arnitel2045_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = dsm_arnitel2045_175_cartesio_0.4_mm weight = 2 -setting_version = 4 +material = dsm_arnitel2045_175 +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/cartesio_global_Coarse_Quality.inst.cfg b/resources/quality/cartesio/cartesio_global_Coarse_Quality.inst.cfg index 11760b139f..53cbb6bf06 100644 --- a/resources/quality/cartesio/cartesio_global_Coarse_Quality.inst.cfg +++ b/resources/quality/cartesio/cartesio_global_Coarse_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = coarse -global_quality = True weight = -3 -setting_version = 4 +global_quality = True [values] layer_height = 0.4 diff --git a/resources/quality/cartesio/cartesio_global_Extra_Coarse_Quality.inst.cfg b/resources/quality/cartesio/cartesio_global_Extra_Coarse_Quality.inst.cfg index c654dba598..4d612db89f 100644 --- a/resources/quality/cartesio/cartesio_global_Extra_Coarse_Quality.inst.cfg +++ b/resources/quality/cartesio/cartesio_global_Extra_Coarse_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Extra Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = extra coarse -global_quality = True weight = -4 -setting_version = 4 +global_quality = True [values] layer_height = 0.6 diff --git a/resources/quality/cartesio/cartesio_global_High_Quality.inst.cfg b/resources/quality/cartesio/cartesio_global_High_Quality.inst.cfg index 393a5f3b39..b9e4f287a1 100644 --- a/resources/quality/cartesio/cartesio_global_High_Quality.inst.cfg +++ b/resources/quality/cartesio/cartesio_global_High_Quality.inst.cfg @@ -4,11 +4,11 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -global_quality = True weight = 1 -setting_version = 4 +global_quality = True [values] layer_height = 0.1 diff --git a/resources/quality/cartesio/cartesio_global_Normal_Quality.inst.cfg b/resources/quality/cartesio/cartesio_global_Normal_Quality.inst.cfg index c09493ba10..1b3af7c9ce 100644 --- a/resources/quality/cartesio/cartesio_global_Normal_Quality.inst.cfg +++ b/resources/quality/cartesio/cartesio_global_Normal_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -global_quality = True weight = 0 -setting_version = 4 +global_quality = True [values] layer_height = 0.2 diff --git a/resources/quality/cartesio/hips/cartesio_0.25_hips_high.inst.cfg b/resources/quality/cartesio/hips/cartesio_0.25_hips_high.inst.cfg index 670b9012c7..df6ca1d0a0 100644 --- a/resources/quality/cartesio/hips/cartesio_0.25_hips_high.inst.cfg +++ b/resources/quality/cartesio/hips/cartesio_0.25_hips_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_hips_175_cartesio_0.25_mm weight = 1 -setting_version = 4 +material = generic_hips +variant = 0.25 mm [values] infill_line_width = 0.3 diff --git a/resources/quality/cartesio/hips/cartesio_0.25_hips_normal.inst.cfg b/resources/quality/cartesio/hips/cartesio_0.25_hips_normal.inst.cfg index c2a5bbff08..663276681f 100644 --- a/resources/quality/cartesio/hips/cartesio_0.25_hips_normal.inst.cfg +++ b/resources/quality/cartesio/hips/cartesio_0.25_hips_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_hips_175_cartesio_0.25_mm weight = 2 -setting_version = 4 +material = generic_hips +variant = 0.25 mm [values] infill_line_width = 0.3 diff --git a/resources/quality/cartesio/hips/cartesio_0.4_hips_high.inst.cfg b/resources/quality/cartesio/hips/cartesio_0.4_hips_high.inst.cfg index fd3efddd07..54b6edc507 100644 --- a/resources/quality/cartesio/hips/cartesio_0.4_hips_high.inst.cfg +++ b/resources/quality/cartesio/hips/cartesio_0.4_hips_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_hips_175_cartesio_0.4_mm weight = 1 -setting_version = 4 +material = generic_hips +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/hips/cartesio_0.4_hips_normal.inst.cfg b/resources/quality/cartesio/hips/cartesio_0.4_hips_normal.inst.cfg index 1b0acd573e..c843f1653d 100644 --- a/resources/quality/cartesio/hips/cartesio_0.4_hips_normal.inst.cfg +++ b/resources/quality/cartesio/hips/cartesio_0.4_hips_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_hips_175_cartesio_0.4_mm weight = 2 -setting_version = 4 +material = generic_hips +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/hips/cartesio_0.8_hips_coarse.inst.cfg b/resources/quality/cartesio/hips/cartesio_0.8_hips_coarse.inst.cfg index ca9907923f..d848e3ee3b 100644 --- a/resources/quality/cartesio/hips/cartesio_0.8_hips_coarse.inst.cfg +++ b/resources/quality/cartesio/hips/cartesio_0.8_hips_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = coarse -material = generic_hips_175_cartesio_0.8_mm weight = 3 -setting_version = 4 +material = generic_hips +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/hips/cartesio_0.8_hips_extra_coarse.inst.cfg b/resources/quality/cartesio/hips/cartesio_0.8_hips_extra_coarse.inst.cfg index 8f79fa6d37..7f2d436f32 100644 --- a/resources/quality/cartesio/hips/cartesio_0.8_hips_extra_coarse.inst.cfg +++ b/resources/quality/cartesio/hips/cartesio_0.8_hips_extra_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Extra Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = extra coarse -material = generic_hips_175_cartesio_0.8_mm weight = 4 -setting_version = 4 +material = generic_hips +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/hips/cartesio_0.8_hips_high.inst.cfg b/resources/quality/cartesio/hips/cartesio_0.8_hips_high.inst.cfg index 1b7dac5eaf..0e529a97e9 100644 --- a/resources/quality/cartesio/hips/cartesio_0.8_hips_high.inst.cfg +++ b/resources/quality/cartesio/hips/cartesio_0.8_hips_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_hips_175_cartesio_0.8_mm weight = 1 -setting_version = 4 +material = generic_hips +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/hips/cartesio_0.8_hips_normal.inst.cfg b/resources/quality/cartesio/hips/cartesio_0.8_hips_normal.inst.cfg index 843f14ea43..7c4fcbcfdd 100644 --- a/resources/quality/cartesio/hips/cartesio_0.8_hips_normal.inst.cfg +++ b/resources/quality/cartesio/hips/cartesio_0.8_hips_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_hips_175_cartesio_0.8_mm weight = 2 -setting_version = 4 +material = generic_hips +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/nylon/cartesio_0.25_nylon_high.inst.cfg b/resources/quality/cartesio/nylon/cartesio_0.25_nylon_high.inst.cfg index f8a1d2df33..7690040f8c 100644 --- a/resources/quality/cartesio/nylon/cartesio_0.25_nylon_high.inst.cfg +++ b/resources/quality/cartesio/nylon/cartesio_0.25_nylon_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_nylon_175_cartesio_0.25_mm weight = 1 -setting_version = 4 +material = generic_nylon +variant = 0.25 mm [values] infill_line_width = 0.3 diff --git a/resources/quality/cartesio/nylon/cartesio_0.25_nylon_normal.inst.cfg b/resources/quality/cartesio/nylon/cartesio_0.25_nylon_normal.inst.cfg index 6c6f608390..fcff2b6e4b 100644 --- a/resources/quality/cartesio/nylon/cartesio_0.25_nylon_normal.inst.cfg +++ b/resources/quality/cartesio/nylon/cartesio_0.25_nylon_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_nylon_175_cartesio_0.25_mm weight = 2 -setting_version = 4 +material = generic_nylon +variant = 0.25 mm [values] infill_line_width = 0.3 diff --git a/resources/quality/cartesio/nylon/cartesio_0.4_nylon_high.inst.cfg b/resources/quality/cartesio/nylon/cartesio_0.4_nylon_high.inst.cfg index 53abdcad1f..0cca726dcc 100644 --- a/resources/quality/cartesio/nylon/cartesio_0.4_nylon_high.inst.cfg +++ b/resources/quality/cartesio/nylon/cartesio_0.4_nylon_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_nylon_175_cartesio_0.4_mm weight = 1 -setting_version = 4 +material = generic_nylon +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/nylon/cartesio_0.4_nylon_normal.inst.cfg b/resources/quality/cartesio/nylon/cartesio_0.4_nylon_normal.inst.cfg index 9ff9dbf5e9..d231b7c296 100644 --- a/resources/quality/cartesio/nylon/cartesio_0.4_nylon_normal.inst.cfg +++ b/resources/quality/cartesio/nylon/cartesio_0.4_nylon_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_nylon_175_cartesio_0.4_mm weight = 2 -setting_version = 4 +material = generic_nylon +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/nylon/cartesio_0.8_nylon_coarse.inst.cfg b/resources/quality/cartesio/nylon/cartesio_0.8_nylon_coarse.inst.cfg index 4add038914..22eb78ec00 100644 --- a/resources/quality/cartesio/nylon/cartesio_0.8_nylon_coarse.inst.cfg +++ b/resources/quality/cartesio/nylon/cartesio_0.8_nylon_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = coarse -material = generic_nylon_175_cartesio_0.8_mm weight = 3 -setting_version = 4 +material = generic_nylon +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/nylon/cartesio_0.8_nylon_extra_coarse.inst.cfg b/resources/quality/cartesio/nylon/cartesio_0.8_nylon_extra_coarse.inst.cfg index 0020950cd5..31f5d45a88 100644 --- a/resources/quality/cartesio/nylon/cartesio_0.8_nylon_extra_coarse.inst.cfg +++ b/resources/quality/cartesio/nylon/cartesio_0.8_nylon_extra_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Extra Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = extra coarse -material = generic_nylon_175_cartesio_0.8_mm weight = 4 -setting_version = 4 +material = generic_nylon +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/nylon/cartesio_0.8_nylon_high.inst.cfg b/resources/quality/cartesio/nylon/cartesio_0.8_nylon_high.inst.cfg index b74faaec40..9287ec9a4c 100644 --- a/resources/quality/cartesio/nylon/cartesio_0.8_nylon_high.inst.cfg +++ b/resources/quality/cartesio/nylon/cartesio_0.8_nylon_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_nylon_175_cartesio_0.8_mm weight = 1 -setting_version = 4 +material = generic_nylon +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/nylon/cartesio_0.8_nylon_normal.inst.cfg b/resources/quality/cartesio/nylon/cartesio_0.8_nylon_normal.inst.cfg index cb59f1803c..ecf83c29bd 100644 --- a/resources/quality/cartesio/nylon/cartesio_0.8_nylon_normal.inst.cfg +++ b/resources/quality/cartesio/nylon/cartesio_0.8_nylon_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_nylon_175_cartesio_0.8_mm weight = 2 -setting_version = 4 +material = generic_nylon +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/pc/cartesio_0.25_pc_high.inst.cfg b/resources/quality/cartesio/pc/cartesio_0.25_pc_high.inst.cfg index a1bee46782..23df3d0451 100644 --- a/resources/quality/cartesio/pc/cartesio_0.25_pc_high.inst.cfg +++ b/resources/quality/cartesio/pc/cartesio_0.25_pc_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pc_175_cartesio_0.25_mm weight = 1 -setting_version = 4 +material = generic_pc +variant = 0.25 mm [values] infill_line_width = 0.3 diff --git a/resources/quality/cartesio/pc/cartesio_0.25_pc_normal.inst.cfg b/resources/quality/cartesio/pc/cartesio_0.25_pc_normal.inst.cfg index dc5b88f84b..0ac876a538 100644 --- a/resources/quality/cartesio/pc/cartesio_0.25_pc_normal.inst.cfg +++ b/resources/quality/cartesio/pc/cartesio_0.25_pc_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pc_175_cartesio_0.25_mm weight = 2 -setting_version = 4 +material = generic_pc +variant = 0.25 mm [values] infill_line_width = 0.3 diff --git a/resources/quality/cartesio/pc/cartesio_0.4_pc_high.inst.cfg b/resources/quality/cartesio/pc/cartesio_0.4_pc_high.inst.cfg index 49ddf1bc98..0c92dc32fc 100644 --- a/resources/quality/cartesio/pc/cartesio_0.4_pc_high.inst.cfg +++ b/resources/quality/cartesio/pc/cartesio_0.4_pc_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pc_175_cartesio_0.4_mm weight = 1 -setting_version = 4 +material = generic_pc +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/pc/cartesio_0.4_pc_normal.inst.cfg b/resources/quality/cartesio/pc/cartesio_0.4_pc_normal.inst.cfg index 47fe5d9a40..2d53790fe7 100644 --- a/resources/quality/cartesio/pc/cartesio_0.4_pc_normal.inst.cfg +++ b/resources/quality/cartesio/pc/cartesio_0.4_pc_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pc_175_cartesio_0.4_mm weight = 2 -setting_version = 4 +material = generic_pc +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/pc/cartesio_0.8_pc_coarse.inst.cfg b/resources/quality/cartesio/pc/cartesio_0.8_pc_coarse.inst.cfg index c4313f2718..5d807c5d65 100644 --- a/resources/quality/cartesio/pc/cartesio_0.8_pc_coarse.inst.cfg +++ b/resources/quality/cartesio/pc/cartesio_0.8_pc_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = coarse -material = generic_pc_175_cartesio_0.8_mm weight = 3 -setting_version = 4 +material = generic_pc +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/pc/cartesio_0.8_pc_extra_coarse.inst.cfg b/resources/quality/cartesio/pc/cartesio_0.8_pc_extra_coarse.inst.cfg index 5e093a8f32..75c72a1f56 100644 --- a/resources/quality/cartesio/pc/cartesio_0.8_pc_extra_coarse.inst.cfg +++ b/resources/quality/cartesio/pc/cartesio_0.8_pc_extra_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Extra Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = extra coarse -material = generic_pc_175_cartesio_0.8_mm weight = 4 -setting_version = 4 +material = generic_pc +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/pc/cartesio_0.8_pc_high.inst.cfg b/resources/quality/cartesio/pc/cartesio_0.8_pc_high.inst.cfg index fa1bebc645..0b1469fde4 100644 --- a/resources/quality/cartesio/pc/cartesio_0.8_pc_high.inst.cfg +++ b/resources/quality/cartesio/pc/cartesio_0.8_pc_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pc_175_cartesio_0.8_mm weight = 1 -setting_version = 4 +material = generic_pc +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/pc/cartesio_0.8_pc_normal.inst.cfg b/resources/quality/cartesio/pc/cartesio_0.8_pc_normal.inst.cfg index 12cb3a5abd..7842a91f61 100644 --- a/resources/quality/cartesio/pc/cartesio_0.8_pc_normal.inst.cfg +++ b/resources/quality/cartesio/pc/cartesio_0.8_pc_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pc_175_cartesio_0.8_mm weight = 2 -setting_version = 4 +material = generic_pc +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/petg/cartesio_0.25_petg_high.inst.cfg b/resources/quality/cartesio/petg/cartesio_0.25_petg_high.inst.cfg index f926688cc7..5688828343 100644 --- a/resources/quality/cartesio/petg/cartesio_0.25_petg_high.inst.cfg +++ b/resources/quality/cartesio/petg/cartesio_0.25_petg_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_petg_175_cartesio_0.25_mm weight = 1 -setting_version = 4 +material = generic_petg +variant = 0.25 mm [values] infill_line_width = 0.3 diff --git a/resources/quality/cartesio/petg/cartesio_0.25_petg_normal.inst.cfg b/resources/quality/cartesio/petg/cartesio_0.25_petg_normal.inst.cfg index fbea40e500..e47b9849ad 100644 --- a/resources/quality/cartesio/petg/cartesio_0.25_petg_normal.inst.cfg +++ b/resources/quality/cartesio/petg/cartesio_0.25_petg_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_petg_175_cartesio_0.25_mm weight = 2 -setting_version = 4 +material = generic_petg +variant = 0.25 mm [values] infill_line_width = 0.3 diff --git a/resources/quality/cartesio/petg/cartesio_0.4_petg_high.inst.cfg b/resources/quality/cartesio/petg/cartesio_0.4_petg_high.inst.cfg index 30f0d2d926..eb0cc83a63 100644 --- a/resources/quality/cartesio/petg/cartesio_0.4_petg_high.inst.cfg +++ b/resources/quality/cartesio/petg/cartesio_0.4_petg_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_petg_175_cartesio_0.4_mm weight = 1 -setting_version = 4 +material = generic_petg +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/petg/cartesio_0.4_petg_normal.inst.cfg b/resources/quality/cartesio/petg/cartesio_0.4_petg_normal.inst.cfg index 688373bf94..5b2e8bb687 100644 --- a/resources/quality/cartesio/petg/cartesio_0.4_petg_normal.inst.cfg +++ b/resources/quality/cartesio/petg/cartesio_0.4_petg_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_petg_175_cartesio_0.4_mm weight = 2 -setting_version = 4 +material = generic_petg +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/petg/cartesio_0.8_petg_coarse.inst.cfg b/resources/quality/cartesio/petg/cartesio_0.8_petg_coarse.inst.cfg index 2516cd17e8..c65551c56c 100644 --- a/resources/quality/cartesio/petg/cartesio_0.8_petg_coarse.inst.cfg +++ b/resources/quality/cartesio/petg/cartesio_0.8_petg_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = coarse -material = generic_petg_175_cartesio_0.8_mm weight = 3 -setting_version = 4 +material = generic_petg +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/petg/cartesio_0.8_petg_extra_coarse.inst.cfg b/resources/quality/cartesio/petg/cartesio_0.8_petg_extra_coarse.inst.cfg index 5c1995f5bc..52099fc789 100644 --- a/resources/quality/cartesio/petg/cartesio_0.8_petg_extra_coarse.inst.cfg +++ b/resources/quality/cartesio/petg/cartesio_0.8_petg_extra_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Extra Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = extra coarse -material = generic_petg_175_cartesio_0.8_mm weight = 4 -setting_version = 4 +material = generic_petg +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/petg/cartesio_0.8_petg_high.inst.cfg b/resources/quality/cartesio/petg/cartesio_0.8_petg_high.inst.cfg index eb0afde18f..d6932f9c07 100644 --- a/resources/quality/cartesio/petg/cartesio_0.8_petg_high.inst.cfg +++ b/resources/quality/cartesio/petg/cartesio_0.8_petg_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_petg_175_cartesio_0.8_mm weight = 1 -setting_version = 4 +material = generic_petg +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/petg/cartesio_0.8_petg_normal.inst.cfg b/resources/quality/cartesio/petg/cartesio_0.8_petg_normal.inst.cfg index 27c7b894b5..6289073085 100644 --- a/resources/quality/cartesio/petg/cartesio_0.8_petg_normal.inst.cfg +++ b/resources/quality/cartesio/petg/cartesio_0.8_petg_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_petg_175_cartesio_0.8_mm weight = 2 -setting_version = 4 +material = generic_petg +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/pla/cartesio_0.25_pla_high.inst.cfg b/resources/quality/cartesio/pla/cartesio_0.25_pla_high.inst.cfg index 90572b988f..8b614f5bef 100644 --- a/resources/quality/cartesio/pla/cartesio_0.25_pla_high.inst.cfg +++ b/resources/quality/cartesio/pla/cartesio_0.25_pla_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pla_175_cartesio_0.25_mm weight = 1 -setting_version = 4 +material = generic_pla +variant = 0.25 mm [values] infill_line_width = 0.3 diff --git a/resources/quality/cartesio/pla/cartesio_0.25_pla_normal.inst.cfg b/resources/quality/cartesio/pla/cartesio_0.25_pla_normal.inst.cfg index 51faec512e..56ea324826 100644 --- a/resources/quality/cartesio/pla/cartesio_0.25_pla_normal.inst.cfg +++ b/resources/quality/cartesio/pla/cartesio_0.25_pla_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pla_175_cartesio_0.25_mm weight = 0 -setting_version = 4 +material = generic_pla +variant = 0.25 mm [values] infill_line_width = 0.3 diff --git a/resources/quality/cartesio/pla/cartesio_0.4_pla_high.inst.cfg b/resources/quality/cartesio/pla/cartesio_0.4_pla_high.inst.cfg index 54e59d2e44..e83d26581d 100644 --- a/resources/quality/cartesio/pla/cartesio_0.4_pla_high.inst.cfg +++ b/resources/quality/cartesio/pla/cartesio_0.4_pla_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pla_175_cartesio_0.4_mm weight = 1 -setting_version = 4 +material = generic_pla +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/pla/cartesio_0.4_pla_normal.inst.cfg b/resources/quality/cartesio/pla/cartesio_0.4_pla_normal.inst.cfg index a8526458b1..1c0b440904 100644 --- a/resources/quality/cartesio/pla/cartesio_0.4_pla_normal.inst.cfg +++ b/resources/quality/cartesio/pla/cartesio_0.4_pla_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pla_175_cartesio_0.4_mm weight = 0 -setting_version = 4 +material = generic_pla +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/pla/cartesio_0.8_pla_coarse.inst.cfg b/resources/quality/cartesio/pla/cartesio_0.8_pla_coarse.inst.cfg index 02e86f00f5..9a6a517a93 100644 --- a/resources/quality/cartesio/pla/cartesio_0.8_pla_coarse.inst.cfg +++ b/resources/quality/cartesio/pla/cartesio_0.8_pla_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = coarse -material = generic_pla_175_cartesio_0.8_mm weight = -3 -setting_version = 4 +material = generic_pla +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/pla/cartesio_0.8_pla_extra_coarse.inst.cfg b/resources/quality/cartesio/pla/cartesio_0.8_pla_extra_coarse.inst.cfg index aff51dc552..17ef04e0c0 100644 --- a/resources/quality/cartesio/pla/cartesio_0.8_pla_extra_coarse.inst.cfg +++ b/resources/quality/cartesio/pla/cartesio_0.8_pla_extra_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Extra Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = extra coarse -material = generic_pla_175_cartesio_0.8_mm weight = -4 -setting_version = 4 +material = generic_pla +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/pla/cartesio_0.8_pla_high.inst.cfg b/resources/quality/cartesio/pla/cartesio_0.8_pla_high.inst.cfg index 2e000b9ce4..6a4b88788a 100644 --- a/resources/quality/cartesio/pla/cartesio_0.8_pla_high.inst.cfg +++ b/resources/quality/cartesio/pla/cartesio_0.8_pla_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pla_175_cartesio_0.8_mm weight = 1 -setting_version = 4 +material = generic_pla +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/pla/cartesio_0.8_pla_normal.inst.cfg b/resources/quality/cartesio/pla/cartesio_0.8_pla_normal.inst.cfg index 240b0d497f..515e473bb0 100644 --- a/resources/quality/cartesio/pla/cartesio_0.8_pla_normal.inst.cfg +++ b/resources/quality/cartesio/pla/cartesio_0.8_pla_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pla_175_cartesio_0.8_mm weight = 0 -setting_version = 4 +material = generic_pla +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/pva/cartesio_0.25_pva_high.inst.cfg b/resources/quality/cartesio/pva/cartesio_0.25_pva_high.inst.cfg index 9330a977b7..dfbde35b9c 100644 --- a/resources/quality/cartesio/pva/cartesio_0.25_pva_high.inst.cfg +++ b/resources/quality/cartesio/pva/cartesio_0.25_pva_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pva_175_cartesio_0.25_mm weight = 1 -setting_version = 4 +material = generic_pva +variant = 0.25 mm [values] infill_line_width = 0.3 diff --git a/resources/quality/cartesio/pva/cartesio_0.25_pva_normal.inst.cfg b/resources/quality/cartesio/pva/cartesio_0.25_pva_normal.inst.cfg index 204ca68174..ed1fa07207 100644 --- a/resources/quality/cartesio/pva/cartesio_0.25_pva_normal.inst.cfg +++ b/resources/quality/cartesio/pva/cartesio_0.25_pva_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pva_175_cartesio_0.25_mm weight = 2 -setting_version = 4 +material = generic_pva +variant = 0.25 mm [values] infill_line_width = 0.3 diff --git a/resources/quality/cartesio/pva/cartesio_0.4_pva_high.inst.cfg b/resources/quality/cartesio/pva/cartesio_0.4_pva_high.inst.cfg index 7a484180d4..a2c4a21674 100644 --- a/resources/quality/cartesio/pva/cartesio_0.4_pva_high.inst.cfg +++ b/resources/quality/cartesio/pva/cartesio_0.4_pva_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pva_175_cartesio_0.4_mm weight = 1 -setting_version = 4 +material = generic_pva +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/pva/cartesio_0.4_pva_normal.inst.cfg b/resources/quality/cartesio/pva/cartesio_0.4_pva_normal.inst.cfg index 6e12288510..91164306fb 100644 --- a/resources/quality/cartesio/pva/cartesio_0.4_pva_normal.inst.cfg +++ b/resources/quality/cartesio/pva/cartesio_0.4_pva_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pva_175_cartesio_0.4_mm weight = 2 -setting_version = 4 +material = generic_pva +variant = 0.4 mm [values] infill_line_width = 0.5 diff --git a/resources/quality/cartesio/pva/cartesio_0.8_pva_coarse.inst.cfg b/resources/quality/cartesio/pva/cartesio_0.8_pva_coarse.inst.cfg index eefb7fe8a3..003f980901 100644 --- a/resources/quality/cartesio/pva/cartesio_0.8_pva_coarse.inst.cfg +++ b/resources/quality/cartesio/pva/cartesio_0.8_pva_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = coarse -material = generic_pva_175_cartesio_0.8_mm weight = 3 -setting_version = 4 +material = generic_pva +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/pva/cartesio_0.8_pva_extra_coarse.inst.cfg b/resources/quality/cartesio/pva/cartesio_0.8_pva_extra_coarse.inst.cfg index cd7fe200bf..c328442ee8 100644 --- a/resources/quality/cartesio/pva/cartesio_0.8_pva_extra_coarse.inst.cfg +++ b/resources/quality/cartesio/pva/cartesio_0.8_pva_extra_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Extra Coarse definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = extra coarse -material = generic_pva_175_cartesio_0.8_mm weight = 4 -setting_version = 4 +material = generic_pva +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/pva/cartesio_0.8_pva_high.inst.cfg b/resources/quality/cartesio/pva/cartesio_0.8_pva_high.inst.cfg index 602575b93c..4830d5bcc9 100644 --- a/resources/quality/cartesio/pva/cartesio_0.8_pva_high.inst.cfg +++ b/resources/quality/cartesio/pva/cartesio_0.8_pva_high.inst.cfg @@ -4,11 +4,12 @@ name = High definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pva_175_cartesio_0.8_mm weight = 1 -setting_version = 4 +material = generic_pva +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/cartesio/pva/cartesio_0.8_pva_normal.inst.cfg b/resources/quality/cartesio/pva/cartesio_0.8_pva_normal.inst.cfg index 4201c8e37d..f739f1668b 100644 --- a/resources/quality/cartesio/pva/cartesio_0.8_pva_normal.inst.cfg +++ b/resources/quality/cartesio/pva/cartesio_0.8_pva_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = cartesio [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pva_175_cartesio_0.8_mm weight = 2 -setting_version = 4 +material = generic_pva +variant = 0.8 mm [values] infill_line_width = 0.9 diff --git a/resources/quality/coarse.inst.cfg b/resources/quality/coarse.inst.cfg index 133ffc8951..1accd77807 100644 --- a/resources/quality/coarse.inst.cfg +++ b/resources/quality/coarse.inst.cfg @@ -4,11 +4,11 @@ name = Coarse Quality definition = fdmprinter [metadata] +setting_version = 4 type = quality quality_type = coarse -global_quality = True weight = -3 -setting_version = 4 +global_quality = True [values] layer_height = 0.4 diff --git a/resources/quality/deltacomb/deltacomb_abs_fast.inst.cfg b/resources/quality/deltacomb/deltacomb_abs_fast.inst.cfg index 43643b6b92..75774fc000 100644 --- a/resources/quality/deltacomb/deltacomb_abs_fast.inst.cfg +++ b/resources/quality/deltacomb/deltacomb_abs_fast.inst.cfg @@ -4,11 +4,11 @@ definition = deltacomb name = Fast Quality (beta) [metadata] -type = quality setting_version = 4 -material = generic_abs_175 +type = quality quality_type = fast weight = -1 +material = generic_abs [values] adhesion_type = raft @@ -22,4 +22,3 @@ cool_fan_speed_min = 50 cool_min_layer_time = 3 cool_min_speed = 20 material_bed_temperature = 80 - diff --git a/resources/quality/deltacomb/deltacomb_abs_high.inst.cfg b/resources/quality/deltacomb/deltacomb_abs_high.inst.cfg index 99e47bc9cb..65542f114a 100644 --- a/resources/quality/deltacomb/deltacomb_abs_high.inst.cfg +++ b/resources/quality/deltacomb/deltacomb_abs_high.inst.cfg @@ -4,11 +4,11 @@ definition = deltacomb name = High Quality (beta) [metadata] -type = quality setting_version = 4 -material = generic_abs_175 +type = quality quality_type = high weight = 1 +material = generic_abs [values] adhesion_type = raft @@ -22,4 +22,3 @@ cool_fan_speed_min = 50 cool_min_layer_time = 3 cool_min_speed = 20 material_bed_temperature = 80 - diff --git a/resources/quality/deltacomb/deltacomb_abs_normal.inst.cfg b/resources/quality/deltacomb/deltacomb_abs_normal.inst.cfg index a2aa2be769..55248345fa 100644 --- a/resources/quality/deltacomb/deltacomb_abs_normal.inst.cfg +++ b/resources/quality/deltacomb/deltacomb_abs_normal.inst.cfg @@ -4,11 +4,11 @@ definition = deltacomb name = Normal Quality (beta) [metadata] -type = quality setting_version = 4 -material = generic_abs_175 +type = quality quality_type = normal weight = 0 +material = generic_abs [values] adhesion_type = raft diff --git a/resources/quality/deltacomb/deltacomb_nylon_fast.inst.cfg b/resources/quality/deltacomb/deltacomb_nylon_fast.inst.cfg index fac23939cf..5986c65872 100644 --- a/resources/quality/deltacomb/deltacomb_nylon_fast.inst.cfg +++ b/resources/quality/deltacomb/deltacomb_nylon_fast.inst.cfg @@ -4,11 +4,11 @@ name = Fast Quality (beta) definition = deltacomb [metadata] +setting_version = 4 type = quality -material = generic_nylon_175 quality_type = fast weight = -1 -setting_version = 4 +material = generic_nylon [values] adhesion_type = raft diff --git a/resources/quality/deltacomb/deltacomb_nylon_high.inst.cfg b/resources/quality/deltacomb/deltacomb_nylon_high.inst.cfg index d594126474..158f903bab 100644 --- a/resources/quality/deltacomb/deltacomb_nylon_high.inst.cfg +++ b/resources/quality/deltacomb/deltacomb_nylon_high.inst.cfg @@ -4,11 +4,11 @@ name = High Quality (beta) definition = deltacomb [metadata] +setting_version = 4 type = quality -material = generic_nylon_175 quality_type = high weight = 1 -setting_version = 4 +material = generic_nylon [values] adhesion_type = raft diff --git a/resources/quality/deltacomb/deltacomb_nylon_normal.inst.cfg b/resources/quality/deltacomb/deltacomb_nylon_normal.inst.cfg index 76716fc16d..89024f30b7 100644 --- a/resources/quality/deltacomb/deltacomb_nylon_normal.inst.cfg +++ b/resources/quality/deltacomb/deltacomb_nylon_normal.inst.cfg @@ -4,11 +4,11 @@ name = Normal Quality (beta) definition = deltacomb [metadata] +setting_version = 4 type = quality -material = generic_nylon_175 quality_type = normal weight = 0 -setting_version = 4 +material = generic_nylon [values] adhesion_type = raft @@ -55,4 +55,3 @@ support_z_distance = 0.15 top_bottom_thickness = 0.8 wall_thickness = 0.8 z_seam_type = random - diff --git a/resources/quality/deltacomb/deltacomb_pla_fast.inst.cfg b/resources/quality/deltacomb/deltacomb_pla_fast.inst.cfg index 9783cb11cc..98a5578d89 100644 --- a/resources/quality/deltacomb/deltacomb_pla_fast.inst.cfg +++ b/resources/quality/deltacomb/deltacomb_pla_fast.inst.cfg @@ -4,11 +4,11 @@ definition = deltacomb name = Fast Quality [metadata] -type = quality setting_version = 4 -material = generic_pla_175 +type = quality quality_type = fast weight = -1 +material = generic_pla [values] adhesion_type = skirt @@ -21,4 +21,3 @@ cool_fan_speed_max = 100 cool_fan_speed_min = 100 cool_min_layer_time = 5 cool_min_speed = 20 - diff --git a/resources/quality/deltacomb/deltacomb_pla_high.inst.cfg b/resources/quality/deltacomb/deltacomb_pla_high.inst.cfg index 9513e98b6a..554312ce7b 100644 --- a/resources/quality/deltacomb/deltacomb_pla_high.inst.cfg +++ b/resources/quality/deltacomb/deltacomb_pla_high.inst.cfg @@ -4,11 +4,11 @@ definition = deltacomb name = High Quality [metadata] -type = quality setting_version = 4 -material = generic_pla_175 +type = quality quality_type = high weight = 1 +material = generic_pla [values] adhesion_type = skirt @@ -22,4 +22,3 @@ cool_fan_speed_min = 100 cool_min_layer_time = 5 cool_min_speed = 20 material_print_temperature_layer_0 = =default_material_print_temperature + 5 - diff --git a/resources/quality/deltacomb/deltacomb_pla_normal.inst.cfg b/resources/quality/deltacomb/deltacomb_pla_normal.inst.cfg index d88f5909f0..3f22aa1200 100644 --- a/resources/quality/deltacomb/deltacomb_pla_normal.inst.cfg +++ b/resources/quality/deltacomb/deltacomb_pla_normal.inst.cfg @@ -4,11 +4,11 @@ definition = deltacomb name = Normal Quality [metadata] -type = quality setting_version = 4 -material = generic_pla_175 +type = quality quality_type = normal weight = 0 +material = generic_pla [values] adhesion_type = skirt diff --git a/resources/quality/draft.inst.cfg b/resources/quality/draft.inst.cfg index a155c8f2e1..2b375878b6 100644 --- a/resources/quality/draft.inst.cfg +++ b/resources/quality/draft.inst.cfg @@ -1,15 +1,14 @@ - [general] version = 2 name = Draft Quality definition = fdmprinter [metadata] +setting_version = 4 type = quality quality_type = draft -global_quality = True weight = -2 -setting_version = 4 +global_quality = True [values] layer_height = 0.2 diff --git a/resources/quality/extra_coarse.inst.cfg b/resources/quality/extra_coarse.inst.cfg index ce28e54721..bc8257a97f 100644 --- a/resources/quality/extra_coarse.inst.cfg +++ b/resources/quality/extra_coarse.inst.cfg @@ -4,11 +4,11 @@ name = Extra Coarse Quality definition = fdmprinter [metadata] -type = quality -quality_type = Extra coarse -global_quality = True -weight = -4 setting_version = 4 +type = quality +quality_type = extra coarse +weight = -4 +global_quality = True [values] layer_height = 0.6 diff --git a/resources/quality/fabtotum/fabtotum_abs_fast.inst.cfg b/resources/quality/fabtotum/fabtotum_abs_fast.inst.cfg index fe68b4a76e..54ad42537e 100644 --- a/resources/quality/fabtotum/fabtotum_abs_fast.inst.cfg +++ b/resources/quality/fabtotum/fabtotum_abs_fast.inst.cfg @@ -4,11 +4,11 @@ definition = fabtotum name = Fast Quality [metadata] -type = quality setting_version = 4 -material = fabtotum_abs +type = quality quality_type = fast weight = -1 +material = fabtotum_abs [values] adhesion_type = raft @@ -22,4 +22,3 @@ cool_fan_speed_max = 50 cool_fan_speed_min = 50 cool_min_layer_time = 3 cool_min_speed = 20 - diff --git a/resources/quality/fabtotum/fabtotum_abs_high.inst.cfg b/resources/quality/fabtotum/fabtotum_abs_high.inst.cfg index dd1f58a59a..a7a4e71709 100644 --- a/resources/quality/fabtotum/fabtotum_abs_high.inst.cfg +++ b/resources/quality/fabtotum/fabtotum_abs_high.inst.cfg @@ -4,11 +4,11 @@ definition = fabtotum name = High Quality [metadata] -type = quality setting_version = 4 -material = fabtotum_abs +type = quality quality_type = high weight = 1 +material = fabtotum_abs [values] adhesion_type = raft @@ -22,4 +22,3 @@ cool_fan_speed_max = 50 cool_fan_speed_min = 50 cool_min_layer_time = 3 cool_min_speed = 20 - diff --git a/resources/quality/fabtotum/fabtotum_abs_normal.inst.cfg b/resources/quality/fabtotum/fabtotum_abs_normal.inst.cfg index 31c588c498..19d6062dfa 100644 --- a/resources/quality/fabtotum/fabtotum_abs_normal.inst.cfg +++ b/resources/quality/fabtotum/fabtotum_abs_normal.inst.cfg @@ -4,11 +4,11 @@ definition = fabtotum name = Normal Quality [metadata] -type = quality setting_version = 4 -material = fabtotum_abs +type = quality quality_type = normal weight = 0 +material = fabtotum_abs [values] adhesion_type = raft @@ -22,4 +22,3 @@ cool_fan_speed_max = 50 cool_fan_speed_min = 50 cool_min_layer_time = 3 cool_min_speed = 20 - diff --git a/resources/quality/fabtotum/fabtotum_nylon_fast.inst.cfg b/resources/quality/fabtotum/fabtotum_nylon_fast.inst.cfg index 86eb5326e0..1983191e90 100644 --- a/resources/quality/fabtotum/fabtotum_nylon_fast.inst.cfg +++ b/resources/quality/fabtotum/fabtotum_nylon_fast.inst.cfg @@ -4,11 +4,11 @@ name = Fast Quality definition = fabtotum [metadata] +setting_version = 4 type = quality -material = fabtotum_nylon quality_type = fast weight = -1 -setting_version = 4 +material = fabtotum_nylon [values] adhesion_type = raft @@ -54,4 +54,4 @@ support_type = buildplate support_z_distance = 0.15 top_bottom_thickness = 0.8 wall_thickness = 0.8 -z_seam_type = random \ No newline at end of file +z_seam_type = random diff --git a/resources/quality/fabtotum/fabtotum_nylon_high.inst.cfg b/resources/quality/fabtotum/fabtotum_nylon_high.inst.cfg index 8585323537..5f81c12f22 100644 --- a/resources/quality/fabtotum/fabtotum_nylon_high.inst.cfg +++ b/resources/quality/fabtotum/fabtotum_nylon_high.inst.cfg @@ -4,11 +4,11 @@ name = High Quality definition = fabtotum [metadata] +setting_version = 4 type = quality -material = fabtotum_nylon quality_type = high weight = 1 -setting_version = 4 +material = fabtotum_nylon [values] adhesion_type = raft @@ -54,4 +54,4 @@ support_type = buildplate support_z_distance = 0.15 top_bottom_thickness = 0.8 wall_thickness = 0.8 -z_seam_type = random \ No newline at end of file +z_seam_type = random diff --git a/resources/quality/fabtotum/fabtotum_nylon_normal.inst.cfg b/resources/quality/fabtotum/fabtotum_nylon_normal.inst.cfg index 99ab0e10cb..834d9b8006 100644 --- a/resources/quality/fabtotum/fabtotum_nylon_normal.inst.cfg +++ b/resources/quality/fabtotum/fabtotum_nylon_normal.inst.cfg @@ -4,11 +4,11 @@ name = Normal Quality definition = fabtotum [metadata] +setting_version = 4 type = quality -material = fabtotum_nylon quality_type = normal weight = 0 -setting_version = 4 +material = fabtotum_nylon [values] adhesion_type = raft @@ -55,4 +55,3 @@ support_z_distance = 0.15 top_bottom_thickness = 0.8 wall_thickness = 0.8 z_seam_type = random - diff --git a/resources/quality/fabtotum/fabtotum_pla_fast.inst.cfg b/resources/quality/fabtotum/fabtotum_pla_fast.inst.cfg index 5b4cb737ff..2f123bc05b 100644 --- a/resources/quality/fabtotum/fabtotum_pla_fast.inst.cfg +++ b/resources/quality/fabtotum/fabtotum_pla_fast.inst.cfg @@ -4,11 +4,11 @@ definition = fabtotum name = Fast Quality [metadata] -type = quality setting_version = 4 -material = fabtotum_pla +type = quality quality_type = fast weight = -1 +material = fabtotum_pla [values] adhesion_type = skirt @@ -22,4 +22,3 @@ cool_fan_speed_max = 100 cool_fan_speed_min = 100 cool_min_layer_time = 5 cool_min_speed = 20 - diff --git a/resources/quality/fabtotum/fabtotum_pla_high.inst.cfg b/resources/quality/fabtotum/fabtotum_pla_high.inst.cfg index e427372010..4b3aff15d9 100644 --- a/resources/quality/fabtotum/fabtotum_pla_high.inst.cfg +++ b/resources/quality/fabtotum/fabtotum_pla_high.inst.cfg @@ -4,11 +4,11 @@ definition = fabtotum name = High Quality [metadata] -type = quality setting_version = 4 -material = fabtotum_pla +type = quality quality_type = high weight = 1 +material = fabtotum_pla [values] adhesion_type = skirt @@ -22,4 +22,3 @@ cool_fan_speed_max = 100 cool_fan_speed_min = 100 cool_min_layer_time = 5 cool_min_speed = 20 - diff --git a/resources/quality/fabtotum/fabtotum_pla_normal.inst.cfg b/resources/quality/fabtotum/fabtotum_pla_normal.inst.cfg index ee22d8fa9a..44ddbcb085 100644 --- a/resources/quality/fabtotum/fabtotum_pla_normal.inst.cfg +++ b/resources/quality/fabtotum/fabtotum_pla_normal.inst.cfg @@ -4,11 +4,11 @@ definition = fabtotum name = Normal Quality [metadata] -type = quality setting_version = 4 -material = fabtotum_pla +type = quality quality_type = normal weight = 0 +material = fabtotum_pla [values] adhesion_type = skirt @@ -22,4 +22,3 @@ cool_fan_speed_max = 100 cool_fan_speed_min = 100 cool_min_layer_time = 5 cool_min_speed = 20 - diff --git a/resources/quality/low.inst.cfg b/resources/quality/fast.inst.cfg similarity index 94% rename from resources/quality/low.inst.cfg rename to resources/quality/fast.inst.cfg index e92490722d..4b78cfcd75 100644 --- a/resources/quality/low.inst.cfg +++ b/resources/quality/fast.inst.cfg @@ -4,11 +4,11 @@ name = Low Quality definition = fdmprinter [metadata] -type = quality -quality_type = low -global_quality = True -weight = -1 setting_version = 4 +type = quality +quality_type = fast +weight = -1 +global_quality = True [values] infill_sparse_density = 10 diff --git a/resources/quality/gmax15plus/gmax15plus_pla_dual_normal.inst.cfg b/resources/quality/gmax15plus/gmax15plus_pla_dual_normal.inst.cfg index 74d3d1c134..e08a6ff421 100644 --- a/resources/quality/gmax15plus/gmax15plus_pla_dual_normal.inst.cfg +++ b/resources/quality/gmax15plus/gmax15plus_pla_dual_normal.inst.cfg @@ -4,11 +4,10 @@ name = gMax 1.5+ Dual Normal Layers definition = gmax15plus_dual [metadata] +setting_version = 4 type = quality quality_type = normal weight = -1 -setting_version = 4 -global_quality = True [values] layer_height = 0.2 diff --git a/resources/quality/gmax15plus/gmax15plus_pla_dual_thick.inst.cfg b/resources/quality/gmax15plus/gmax15plus_pla_dual_thick.inst.cfg index 32191f36d8..86bfe2af6c 100644 --- a/resources/quality/gmax15plus/gmax15plus_pla_dual_thick.inst.cfg +++ b/resources/quality/gmax15plus/gmax15plus_pla_dual_thick.inst.cfg @@ -4,11 +4,10 @@ name = gMax 1.5+ Dual Thick Layers definition = gmax15plus_dual [metadata] +setting_version = 4 type = quality quality_type = course weight = -2 -setting_version = 4 -global_quality = True [values] layer_height = 0.28 diff --git a/resources/quality/gmax15plus/gmax15plus_pla_dual_thin.inst.cfg b/resources/quality/gmax15plus/gmax15plus_pla_dual_thin.inst.cfg index 5906875a3a..0d19c6c9f0 100644 --- a/resources/quality/gmax15plus/gmax15plus_pla_dual_thin.inst.cfg +++ b/resources/quality/gmax15plus/gmax15plus_pla_dual_thin.inst.cfg @@ -4,11 +4,10 @@ name = gMax 1.5+ Dual Thin Layers definition = gmax15plus_dual [metadata] +setting_version = 4 type = quality quality_type = high weight = 0 -setting_version = 4 -global_quality = True [values] layer_height = 0.16 diff --git a/resources/quality/gmax15plus/gmax15plus_pla_dual_very_thick.inst.cfg b/resources/quality/gmax15plus/gmax15plus_pla_dual_very_thick.inst.cfg index a94a621a88..2b58120762 100644 --- a/resources/quality/gmax15plus/gmax15plus_pla_dual_very_thick.inst.cfg +++ b/resources/quality/gmax15plus/gmax15plus_pla_dual_very_thick.inst.cfg @@ -4,11 +4,10 @@ name = gMax 1.5+ Dual Very Thick Layers definition = gmax15plus_dual [metadata] +setting_version = 4 type = quality quality_type = extra_course weight = -3 -setting_version = 4 -global_quality = True [values] layer_height = 0.32 diff --git a/resources/quality/gmax15plus/gmax15plus_pla_normal.inst.cfg b/resources/quality/gmax15plus/gmax15plus_pla_normal.inst.cfg index a6513cba80..70920b6f6a 100644 --- a/resources/quality/gmax15plus/gmax15plus_pla_normal.inst.cfg +++ b/resources/quality/gmax15plus/gmax15plus_pla_normal.inst.cfg @@ -4,11 +4,10 @@ name = gMax 1.5+ Normal Layers definition = gmax15plus [metadata] +setting_version = 4 type = quality quality_type = normal weight = -1 -setting_version = 4 -global_quality = True [values] layer_height = 0.2 @@ -58,5 +57,3 @@ top_thickness = 1 bottom_layers = 2 wall_line_count = 2 z_seam_corner = z_seam_corner_none - - diff --git a/resources/quality/gmax15plus/gmax15plus_pla_thick.inst.cfg b/resources/quality/gmax15plus/gmax15plus_pla_thick.inst.cfg index be0d99a413..0f1e8a3802 100644 --- a/resources/quality/gmax15plus/gmax15plus_pla_thick.inst.cfg +++ b/resources/quality/gmax15plus/gmax15plus_pla_thick.inst.cfg @@ -4,11 +4,10 @@ name = gMax 1.5+ Thick Layers definition = gmax15plus [metadata] +setting_version = 4 type = quality quality_type = course weight = -2 -setting_version = 4 -global_quality = True [values] layer_height = 0.28 @@ -57,4 +56,4 @@ top_layers = 3 top_thickness = 1 bottom_layers = 2 wall_line_count = 2 -z_seam_corner = z_seam_corner_none \ No newline at end of file +z_seam_corner = z_seam_corner_none diff --git a/resources/quality/gmax15plus/gmax15plus_pla_thin.inst.cfg b/resources/quality/gmax15plus/gmax15plus_pla_thin.inst.cfg index 7069db6dd6..f548affc2c 100644 --- a/resources/quality/gmax15plus/gmax15plus_pla_thin.inst.cfg +++ b/resources/quality/gmax15plus/gmax15plus_pla_thin.inst.cfg @@ -4,11 +4,10 @@ name = gMax 1.5+ Thin Layers definition = gmax15plus [metadata] +setting_version = 4 type = quality quality_type = high weight = 0 -setting_version = 4 -global_quality = True [values] layer_height = 0.16 @@ -57,4 +56,4 @@ top_layers = 5 top_thickness = 1 bottom_layers = 3 wall_line_count = 2 -z_seam_corner = z_seam_corner_none \ No newline at end of file +z_seam_corner = z_seam_corner_none diff --git a/resources/quality/gmax15plus/gmax15plus_pla_very_thick.inst.cfg b/resources/quality/gmax15plus/gmax15plus_pla_very_thick.inst.cfg index 88d03ee77f..5db77a70ea 100644 --- a/resources/quality/gmax15plus/gmax15plus_pla_very_thick.inst.cfg +++ b/resources/quality/gmax15plus/gmax15plus_pla_very_thick.inst.cfg @@ -4,11 +4,10 @@ name = gMax 1.5+ Very Thick Layers definition = gmax15plus [metadata] +setting_version = 4 type = quality quality_type = extra_course weight = -3 -setting_version = 4 -global_quality = True [values] layer_height = 0.32 @@ -56,4 +55,4 @@ top_layers = 3 top_thickness = 1 bottom_layers = 2 wall_line_count = 2 -z_seam_corner = z_seam_corner_none \ No newline at end of file +z_seam_corner = z_seam_corner_none diff --git a/resources/quality/high.inst.cfg b/resources/quality/high.inst.cfg index d4333c90da..9ef90181a3 100644 --- a/resources/quality/high.inst.cfg +++ b/resources/quality/high.inst.cfg @@ -4,11 +4,11 @@ name = Extra Fine definition = fdmprinter [metadata] +setting_version = 4 type = quality quality_type = high -global_quality = True weight = 1 -setting_version = 4 +global_quality = True [values] layer_height = 0.06 diff --git a/resources/quality/imade3d_jellybox/generic_petg_0.4_coarse.inst.cfg b/resources/quality/imade3d_jellybox/generic_petg_0.4_coarse.inst.cfg index e36286c6ae..4d0493ae8b 100644 --- a/resources/quality/imade3d_jellybox/generic_petg_0.4_coarse.inst.cfg +++ b/resources/quality/imade3d_jellybox/generic_petg_0.4_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Coarse definition = imade3d_jellybox [metadata] -type = quality -material = generic_petg_imade3d_jellybox_0.4_mm -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_petg +variant = 0.4 mm [values] adhesion_type = skirt @@ -26,8 +27,6 @@ infill_line_width = 0.6 infill_overlap = 15 infill_pattern = zigzag infill_sparse_density = 20 -layer_height = 0.3 -layer_height_0 = 0.3 line_width = 0.4 material_bed_temperature = 50 material_bed_temperature_layer_0 = 55 diff --git a/resources/quality/imade3d_jellybox/generic_petg_0.4_coarse_2-fans.inst.cfg b/resources/quality/imade3d_jellybox/generic_petg_0.4_coarse_2-fans.inst.cfg index 3240bad98b..9251ae43b4 100644 --- a/resources/quality/imade3d_jellybox/generic_petg_0.4_coarse_2-fans.inst.cfg +++ b/resources/quality/imade3d_jellybox/generic_petg_0.4_coarse_2-fans.inst.cfg @@ -4,11 +4,12 @@ name = Coarse definition = imade3d_jellybox [metadata] -type = quality -material = generic_petg_imade3d_jellybox_0.4_mm_2-fans -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_petg +variant = 0.4 mm 2-fans [values] adhesion_type = skirt @@ -26,8 +27,6 @@ infill_line_width = 0.6 infill_overlap = 15 infill_pattern = zigzag infill_sparse_density = 20 -layer_height = 0.3 -layer_height_0 = 0.3 line_width = 0.4 material_bed_temperature = 50 material_bed_temperature_layer_0 = 55 diff --git a/resources/quality/imade3d_jellybox/generic_petg_0.4_medium.inst.cfg b/resources/quality/imade3d_jellybox/generic_petg_0.4_medium.inst.cfg index 2790a5a742..a10a3bcf0a 100644 --- a/resources/quality/imade3d_jellybox/generic_petg_0.4_medium.inst.cfg +++ b/resources/quality/imade3d_jellybox/generic_petg_0.4_medium.inst.cfg @@ -4,11 +4,12 @@ name = Medium definition = imade3d_jellybox [metadata] -type = quality -material = generic_petg_imade3d_jellybox_0.4_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_petg +variant = 0.4 mm [values] adhesion_type = skirt @@ -26,8 +27,6 @@ infill_line_width = 0.6 infill_overlap = 15 infill_pattern = zigzag infill_sparse_density = 20 -layer_height = 0.2 -layer_height_0 = 0.3 line_width = 0.4 material_bed_temperature = 50 material_bed_temperature_layer_0 = 55 diff --git a/resources/quality/imade3d_jellybox/generic_petg_0.4_medium_2-fans.inst.cfg b/resources/quality/imade3d_jellybox/generic_petg_0.4_medium_2-fans.inst.cfg index 14f141f0bf..b851c2e17c 100644 --- a/resources/quality/imade3d_jellybox/generic_petg_0.4_medium_2-fans.inst.cfg +++ b/resources/quality/imade3d_jellybox/generic_petg_0.4_medium_2-fans.inst.cfg @@ -4,11 +4,12 @@ name = Medium definition = imade3d_jellybox [metadata] -type = quality -material = generic_petg_imade3d_jellybox_0.4_mm_2-fans -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_petg +variant = 0.4 mm 2-fans [values] adhesion_type = skirt @@ -26,8 +27,6 @@ infill_line_width = 0.6 infill_overlap = 15 infill_pattern = zigzag infill_sparse_density = 20 -layer_height = 0.2 -layer_height_0 = 0.3 line_width = 0.4 material_bed_temperature = 50 material_bed_temperature_layer_0 = 55 diff --git a/resources/quality/imade3d_jellybox/generic_pla_0.4_coarse.inst.cfg b/resources/quality/imade3d_jellybox/generic_pla_0.4_coarse.inst.cfg index 842ec618e0..bc86119eb8 100644 --- a/resources/quality/imade3d_jellybox/generic_pla_0.4_coarse.inst.cfg +++ b/resources/quality/imade3d_jellybox/generic_pla_0.4_coarse.inst.cfg @@ -4,11 +4,12 @@ name = Coarse definition = imade3d_jellybox [metadata] -type = quality -material = generic_pla_imade3d_jellybox_0.4_mm -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_pla +variant = 0.4 mm [values] adhesion_type = skirt @@ -26,8 +27,6 @@ infill_line_width = 0.6 infill_overlap = 15 infill_pattern = zigzag infill_sparse_density = 20 -layer_height = 0.3 -layer_height_0 = 0.3 line_width = 0.4 material_flow = 90 meshfix_union_all = False diff --git a/resources/quality/imade3d_jellybox/generic_pla_0.4_coarse_2-fans.inst.cfg b/resources/quality/imade3d_jellybox/generic_pla_0.4_coarse_2-fans.inst.cfg index 17e085d84d..c05927fad5 100644 --- a/resources/quality/imade3d_jellybox/generic_pla_0.4_coarse_2-fans.inst.cfg +++ b/resources/quality/imade3d_jellybox/generic_pla_0.4_coarse_2-fans.inst.cfg @@ -4,11 +4,12 @@ name = Coarse definition = imade3d_jellybox [metadata] -type = quality -material = generic_pla_imade3d_jellybox_0.4_mm_2-fans -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_pla +variant = 0.4 mm 2-fans [values] adhesion_type = skirt @@ -26,8 +27,6 @@ infill_line_width = 0.6 infill_overlap = 15 infill_pattern = zigzag infill_sparse_density = 20 -layer_height = 0.3 -layer_height_0 = 0.3 line_width = 0.4 material_flow = 90 meshfix_union_all = False diff --git a/resources/quality/imade3d_jellybox/generic_pla_0.4_fine.inst.cfg b/resources/quality/imade3d_jellybox/generic_pla_0.4_fine.inst.cfg index a4b44f47f6..1bec96f05c 100644 --- a/resources/quality/imade3d_jellybox/generic_pla_0.4_fine.inst.cfg +++ b/resources/quality/imade3d_jellybox/generic_pla_0.4_fine.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = imade3d_jellybox [metadata] -type = quality -material = generic_pla_imade3d_jellybox_0.4_mm -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_pla +variant = 0.4 mm [values] adhesion_type = skirt @@ -26,8 +27,6 @@ infill_line_width = 0.6 infill_overlap = 15 infill_pattern = zigzag infill_sparse_density = 20 -layer_height = 0.1 -layer_height_0 = 0.3 line_width = 0.4 material_flow = 90 material_print_temperature = 205 diff --git a/resources/quality/imade3d_jellybox/generic_pla_0.4_fine_2-fans.inst.cfg b/resources/quality/imade3d_jellybox/generic_pla_0.4_fine_2-fans.inst.cfg index 962b3c9ad4..609662a149 100644 --- a/resources/quality/imade3d_jellybox/generic_pla_0.4_fine_2-fans.inst.cfg +++ b/resources/quality/imade3d_jellybox/generic_pla_0.4_fine_2-fans.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = imade3d_jellybox [metadata] -type = quality -material = generic_pla_imade3d_jellybox_0.4_mm_2-fans -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_pla +variant = 0.4 mm 2-fans [values] adhesion_type = skirt @@ -26,8 +27,6 @@ infill_line_width = 0.6 infill_overlap = 15 infill_pattern = zigzag infill_sparse_density = 20 -layer_height = 0.1 -layer_height_0 = 0.3 line_width = 0.4 material_flow = 90 material_print_temperature = 205 diff --git a/resources/quality/imade3d_jellybox/generic_pla_0.4_medium.inst.cfg b/resources/quality/imade3d_jellybox/generic_pla_0.4_medium.inst.cfg index 952b16ecf8..5249f2dc2b 100644 --- a/resources/quality/imade3d_jellybox/generic_pla_0.4_medium.inst.cfg +++ b/resources/quality/imade3d_jellybox/generic_pla_0.4_medium.inst.cfg @@ -4,11 +4,12 @@ name = Medium definition = imade3d_jellybox [metadata] -type = quality -material = generic_pla_imade3d_jellybox_0.4_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_pla +variant = 0.4 mm [values] adhesion_type = skirt @@ -26,8 +27,6 @@ infill_line_width = 0.6 infill_overlap = 15 infill_pattern = zigzag infill_sparse_density = 20 -layer_height = 0.2 -layer_height_0 = 0.3 line_width = 0.4 material_flow = 90 meshfix_union_all = False diff --git a/resources/quality/imade3d_jellybox/generic_pla_0.4_medium_2-fans.inst.cfg b/resources/quality/imade3d_jellybox/generic_pla_0.4_medium_2-fans.inst.cfg index bd70d105a4..1534d3a6fb 100644 --- a/resources/quality/imade3d_jellybox/generic_pla_0.4_medium_2-fans.inst.cfg +++ b/resources/quality/imade3d_jellybox/generic_pla_0.4_medium_2-fans.inst.cfg @@ -4,11 +4,12 @@ name = Medium definition = imade3d_jellybox [metadata] -type = quality -material = generic_pla_imade3d_jellybox_0.4_mm_2-fans -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_pla +variant = 0.4 mm 2-fans [values] adhesion_type = skirt @@ -26,8 +27,6 @@ infill_line_width = 0.6 infill_overlap = 15 infill_pattern = zigzag infill_sparse_density = 20 -layer_height = 0.2 -layer_height_0 = 0.3 line_width = 0.4 material_flow = 90 meshfix_union_all = False diff --git a/resources/quality/imade3d_jellybox/generic_pla_0.4_ultrafine.inst.cfg b/resources/quality/imade3d_jellybox/generic_pla_0.4_ultrafine.inst.cfg index a9d0679612..1166bd70c9 100644 --- a/resources/quality/imade3d_jellybox/generic_pla_0.4_ultrafine.inst.cfg +++ b/resources/quality/imade3d_jellybox/generic_pla_0.4_ultrafine.inst.cfg @@ -4,11 +4,12 @@ name = UltraFine definition = imade3d_jellybox [metadata] -type = quality -material = generic_pla_imade3d_jellybox_0.4_mm -weight = 2 -quality_type = ultrahigh setting_version = 4 +type = quality +quality_type = ultrahigh +weight = 2 +material = generic_pla +variant = 0.4 mm [values] adhesion_type = skirt @@ -26,8 +27,6 @@ infill_line_width = 0.6 infill_overlap = 15 infill_pattern = zigzag infill_sparse_density = 20 -layer_height = 0.05 -layer_height_0 = 0.3 line_width = 0.4 material_flow = 90 material_print_temperature = 202 diff --git a/resources/quality/imade3d_jellybox/generic_pla_0.4_ultrafine_2-fans.inst.cfg b/resources/quality/imade3d_jellybox/generic_pla_0.4_ultrafine_2-fans.inst.cfg index 097e1fc76a..5b05c10604 100644 --- a/resources/quality/imade3d_jellybox/generic_pla_0.4_ultrafine_2-fans.inst.cfg +++ b/resources/quality/imade3d_jellybox/generic_pla_0.4_ultrafine_2-fans.inst.cfg @@ -4,11 +4,12 @@ name = UltraFine definition = imade3d_jellybox [metadata] -type = quality -material = generic_pla_imade3d_jellybox_0.4_mm_2-fans -weight = 2 -quality_type = ultrahigh setting_version = 4 +type = quality +quality_type = ultrahigh +weight = 2 +material = generic_pla +variant = 0.4 mm 2-fans [values] adhesion_type = skirt @@ -26,8 +27,6 @@ infill_line_width = 0.6 infill_overlap = 15 infill_pattern = zigzag infill_sparse_density = 20 -layer_height = 0.05 -layer_height_0 = 0.3 line_width = 0.4 material_flow = 90 material_print_temperature = 202 diff --git a/resources/quality/imade3d_jellybox/imade3d_jellybox_coarse.inst.cfg b/resources/quality/imade3d_jellybox/imade3d_jellybox_coarse.inst.cfg new file mode 100644 index 0000000000..2e940ea646 --- /dev/null +++ b/resources/quality/imade3d_jellybox/imade3d_jellybox_coarse.inst.cfg @@ -0,0 +1,16 @@ +[general] +version = 2 +name = Coarse +definition = imade3d_jellybox + +[metadata] +setting_version = 4 +type = quality +quality_type = fast +weight = -1 +global_quality = True + +[values] +adhesion_type = skirt +layer_height = 0.3 +layer_height_0 = 0.3 diff --git a/resources/quality/imade3d_jellybox/imade3d_jellybox_fine.inst.cfg b/resources/quality/imade3d_jellybox/imade3d_jellybox_fine.inst.cfg new file mode 100644 index 0000000000..9979558963 --- /dev/null +++ b/resources/quality/imade3d_jellybox/imade3d_jellybox_fine.inst.cfg @@ -0,0 +1,16 @@ +[general] +version = 2 +name = Fine +definition = imade3d_jellybox + +[metadata] +setting_version = 4 +type = quality +quality_type = high +weight = 1 +global_quality = True + +[values] +adhesion_type = skirt +layer_height = 0.1 +layer_height_0 = 0.3 diff --git a/resources/quality/imade3d_jellybox/imade3d_jellybox_normal.inst.cfg b/resources/quality/imade3d_jellybox/imade3d_jellybox_normal.inst.cfg new file mode 100644 index 0000000000..0574099b63 --- /dev/null +++ b/resources/quality/imade3d_jellybox/imade3d_jellybox_normal.inst.cfg @@ -0,0 +1,16 @@ +[general] +version = 2 +name = Medium +definition = imade3d_jellybox + +[metadata] +setting_version = 4 +type = quality +quality_type = normal +weight = 0 +global_quality = True + +[values] +adhesion_type = skirt +layer_height = 0.2 +layer_height_0 = 0.3 diff --git a/resources/quality/imade3d_jellybox/imade3d_jellybox_ultrafine.inst.cfg b/resources/quality/imade3d_jellybox/imade3d_jellybox_ultrafine.inst.cfg new file mode 100644 index 0000000000..39344ce7f4 --- /dev/null +++ b/resources/quality/imade3d_jellybox/imade3d_jellybox_ultrafine.inst.cfg @@ -0,0 +1,16 @@ +[general] +version = 2 +name = UltraFine +definition = imade3d_jellybox + +[metadata] +setting_version = 4 +type = quality +quality_type = ultrahigh +weight = 2 +global_quality = True + +[values] +adhesion_type = skirt +layer_height = 0.05 +layer_height_0 = 0.3 diff --git a/resources/quality/kemiq_q2/kemiq_q2_beta_abs_draft.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_beta_abs_draft.inst.cfg index 5401ec7bd6..add07c797a 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_beta_abs_draft.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_beta_abs_draft.inst.cfg @@ -4,11 +4,11 @@ name = Draft definition = kemiq_q2_beta [metadata] +setting_version = 4 type = quality +quality_type = coarse weight = -3 material = generic_abs -quality_type = coarse -setting_version = 4 [values] layer_height = 0.35 diff --git a/resources/quality/kemiq_q2/kemiq_q2_beta_abs_extra_fine.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_beta_abs_extra_fine.inst.cfg index aea8fc9535..8d31e439e1 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_beta_abs_extra_fine.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_beta_abs_extra_fine.inst.cfg @@ -4,11 +4,11 @@ name = Extra Fine definition = kemiq_q2_beta [metadata] +setting_version = 4 type = quality +quality_type = high weight = 1 material = generic_abs -quality_type = high -setting_version = 4 [values] layer_height = 0.06 diff --git a/resources/quality/kemiq_q2/kemiq_q2_beta_abs_fine.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_beta_abs_fine.inst.cfg index 24adbd9f6c..936e9f8cd8 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_beta_abs_fine.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_beta_abs_fine.inst.cfg @@ -4,11 +4,11 @@ name = Fine definition = kemiq_q2_beta [metadata] +setting_version = 4 type = quality +quality_type = normal weight = 0 material = generic_abs -quality_type = normal -setting_version = 4 [values] layer_height = 0.1 diff --git a/resources/quality/kemiq_q2/kemiq_q2_beta_abs_low.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_beta_abs_low.inst.cfg index 98d2475633..8f48616dbf 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_beta_abs_low.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_beta_abs_low.inst.cfg @@ -4,11 +4,11 @@ name = Low definition = kemiq_q2_beta [metadata] +setting_version = 4 type = quality +quality_type = draft weight = -2 material = generic_abs -quality_type = draft -setting_version = 4 [values] layer_height = 0.2 diff --git a/resources/quality/kemiq_q2/kemiq_q2_beta_abs_normal.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_beta_abs_normal.inst.cfg index ab2e9dabbc..947fd0774d 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_beta_abs_normal.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_beta_abs_normal.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = kemiq_q2_beta [metadata] +setting_version = 4 type = quality +quality_type = fast weight = -1 material = generic_abs -quality_type = low -setting_version = 4 [values] layer_height = 0.15 diff --git a/resources/quality/kemiq_q2/kemiq_q2_beta_pla_draft.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_beta_pla_draft.inst.cfg index f868ab40fc..d9ea0e6850 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_beta_pla_draft.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_beta_pla_draft.inst.cfg @@ -4,11 +4,11 @@ name = Draft definition = kemiq_q2_beta [metadata] +setting_version = 4 type = quality +quality_type = coarse weight = -3 material = generic_pla -quality_type = coarse -setting_version = 4 [values] layer_height = 0.35 diff --git a/resources/quality/kemiq_q2/kemiq_q2_beta_pla_extra_fine.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_beta_pla_extra_fine.inst.cfg index e907f7ccaf..b1775b994f 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_beta_pla_extra_fine.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_beta_pla_extra_fine.inst.cfg @@ -4,11 +4,11 @@ name = Extra Fine definition = kemiq_q2_beta [metadata] -type = quality -material = generic_pla -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_pla [values] layer_height = 0.06 diff --git a/resources/quality/kemiq_q2/kemiq_q2_beta_pla_fine.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_beta_pla_fine.inst.cfg index 841023d532..cf7e070cb8 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_beta_pla_fine.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_beta_pla_fine.inst.cfg @@ -4,11 +4,11 @@ name = Fine definition = kemiq_q2_beta [metadata] +setting_version = 4 type = quality +quality_type = normal weight = 0 material = generic_pla -quality_type = normal -setting_version = 4 [values] layer_height = 0.1 diff --git a/resources/quality/kemiq_q2/kemiq_q2_beta_pla_low.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_beta_pla_low.inst.cfg index ca874c6bce..8b40fabb7b 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_beta_pla_low.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_beta_pla_low.inst.cfg @@ -4,11 +4,11 @@ name = Low definition = kemiq_q2_beta [metadata] +setting_version = 4 type = quality +quality_type = draft weight = -2 material = generic_pla -quality_type = draft -setting_version = 4 [values] layer_height = 0.2 diff --git a/resources/quality/kemiq_q2/kemiq_q2_beta_pla_normal.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_beta_pla_normal.inst.cfg index fcfbe72b24..cc7d877c70 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_beta_pla_normal.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_beta_pla_normal.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = kemiq_q2_beta [metadata] +setting_version = 4 type = quality +quality_type = fast weight = -1 material = generic_pla -quality_type = low -setting_version = 4 [values] layer_height = 0.15 diff --git a/resources/quality/kemiq_q2/kemiq_q2_gama_pla_draft.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_gama_pla_draft.inst.cfg index 009af9b87b..fcda1b081e 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_gama_pla_draft.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_gama_pla_draft.inst.cfg @@ -4,11 +4,11 @@ name = Draft definition = kemiq_q2_gama [metadata] +setting_version = 4 type = quality +quality_type = coarse weight = -3 material = generic_pla -quality_type = coarse -setting_version = 4 [values] layer_height = 0.35 diff --git a/resources/quality/kemiq_q2/kemiq_q2_gama_pla_extra_fine.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_gama_pla_extra_fine.inst.cfg index 447e3b012d..52e5e8df98 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_gama_pla_extra_fine.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_gama_pla_extra_fine.inst.cfg @@ -4,11 +4,11 @@ name = Extra Fine definition = kemiq_q2_gama [metadata] -type = quality -material = generic_pla -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_pla [values] layer_height = 0.06 diff --git a/resources/quality/kemiq_q2/kemiq_q2_gama_pla_fine.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_gama_pla_fine.inst.cfg index 80b2375108..b3ea5b8967 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_gama_pla_fine.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_gama_pla_fine.inst.cfg @@ -4,11 +4,11 @@ name = Fine definition = kemiq_q2_gama [metadata] +setting_version = 4 type = quality +quality_type = normal weight = 0 material = generic_pla -quality_type = normal -setting_version = 4 [values] layer_height = 0.1 diff --git a/resources/quality/kemiq_q2/kemiq_q2_gama_pla_low.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_gama_pla_low.inst.cfg index e30c52f4e6..08a3db0b1f 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_gama_pla_low.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_gama_pla_low.inst.cfg @@ -4,11 +4,11 @@ name = Low definition = kemiq_q2_gama [metadata] +setting_version = 4 type = quality +quality_type = draft weight = -2 material = generic_pla -quality_type = draft -setting_version = 4 [values] layer_height = 0.2 diff --git a/resources/quality/kemiq_q2/kemiq_q2_gama_pla_normal.inst.cfg b/resources/quality/kemiq_q2/kemiq_q2_gama_pla_normal.inst.cfg index 31bdaa51bc..a71c3c731b 100644 --- a/resources/quality/kemiq_q2/kemiq_q2_gama_pla_normal.inst.cfg +++ b/resources/quality/kemiq_q2/kemiq_q2_gama_pla_normal.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = kemiq_q2_gama [metadata] +setting_version = 4 type = quality +quality_type = fast weight = -1 material = generic_pla -quality_type = low -setting_version = 4 [values] layer_height = 0.15 diff --git a/resources/quality/malyan_m200/abs/malyan_m200_abs_draft.inst.cfg b/resources/quality/malyan_m200/abs/malyan_m200_abs_draft.inst.cfg index 19cc9fd00d..c02e789dfe 100644 --- a/resources/quality/malyan_m200/abs/malyan_m200_abs_draft.inst.cfg +++ b/resources/quality/malyan_m200/abs/malyan_m200_abs_draft.inst.cfg @@ -4,12 +4,12 @@ name = Fast definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_abs_175 weight = -2 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/malyan_m200/abs/malyan_m200_abs_fast.inst.cfg b/resources/quality/malyan_m200/abs/malyan_m200_abs_fast.inst.cfg index 5677a0d58d..7f4f368e06 100644 --- a/resources/quality/malyan_m200/abs/malyan_m200_abs_fast.inst.cfg +++ b/resources/quality/malyan_m200/abs/malyan_m200_abs_fast.inst.cfg @@ -4,12 +4,12 @@ name = Normal definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_abs_175 weight = -1 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/malyan_m200/abs/malyan_m200_abs_high.inst.cfg b/resources/quality/malyan_m200/abs/malyan_m200_abs_high.inst.cfg index 7798b3f545..37335b61ee 100644 --- a/resources/quality/malyan_m200/abs/malyan_m200_abs_high.inst.cfg +++ b/resources/quality/malyan_m200/abs/malyan_m200_abs_high.inst.cfg @@ -4,12 +4,12 @@ name = Finer definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_abs_175 weight = 1 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/malyan_m200/abs/malyan_m200_abs_normal.inst.cfg b/resources/quality/malyan_m200/abs/malyan_m200_abs_normal.inst.cfg index c87c66c813..138c31ab14 100644 --- a/resources/quality/malyan_m200/abs/malyan_m200_abs_normal.inst.cfg +++ b/resources/quality/malyan_m200/abs/malyan_m200_abs_normal.inst.cfg @@ -4,12 +4,12 @@ name = Fine definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_abs_175 weight = 0 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/malyan_m200/abs/malyan_m200_abs_superdraft.inst.cfg b/resources/quality/malyan_m200/abs/malyan_m200_abs_superdraft.inst.cfg index e6e3cfcd6c..2d748bd698 100644 --- a/resources/quality/malyan_m200/abs/malyan_m200_abs_superdraft.inst.cfg +++ b/resources/quality/malyan_m200/abs/malyan_m200_abs_superdraft.inst.cfg @@ -4,12 +4,12 @@ name = Lowest Quality Draft definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_abs_175 weight = -5 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/malyan_m200/abs/malyan_m200_abs_thickerdraft.inst.cfg b/resources/quality/malyan_m200/abs/malyan_m200_abs_thickerdraft.inst.cfg index fb08013809..ebf7798733 100644 --- a/resources/quality/malyan_m200/abs/malyan_m200_abs_thickerdraft.inst.cfg +++ b/resources/quality/malyan_m200/abs/malyan_m200_abs_thickerdraft.inst.cfg @@ -4,12 +4,12 @@ name = Draft definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = thickerdraft -material = generic_abs_175 weight = -3 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/malyan_m200/abs/malyan_m200_abs_ultra.inst.cfg b/resources/quality/malyan_m200/abs/malyan_m200_abs_ultra.inst.cfg index 385d852688..5be92914be 100644 --- a/resources/quality/malyan_m200/abs/malyan_m200_abs_ultra.inst.cfg +++ b/resources/quality/malyan_m200/abs/malyan_m200_abs_ultra.inst.cfg @@ -4,12 +4,12 @@ name = Ultra Fine definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = ultra -material = generic_abs_175 weight = 2 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/malyan_m200/abs/malyan_m200_abs_verydraft.inst.cfg b/resources/quality/malyan_m200/abs/malyan_m200_abs_verydraft.inst.cfg index 7026391fb6..bfe92a98e1 100644 --- a/resources/quality/malyan_m200/abs/malyan_m200_abs_verydraft.inst.cfg +++ b/resources/quality/malyan_m200/abs/malyan_m200_abs_verydraft.inst.cfg @@ -4,12 +4,12 @@ name = Low Detail Draft definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_abs_175 weight = -4 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/malyan_m200/malyan_m200_0.04375.inst.cfg b/resources/quality/malyan_m200/malyan_m200_0.04375.inst.cfg index 54be6ecbcc..89d7f2f2ec 100644 --- a/resources/quality/malyan_m200/malyan_m200_0.04375.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_0.04375.inst.cfg @@ -4,10 +4,10 @@ name = M1 Quality definition = malyan_m200 [metadata] -type = quality -weight = 2 -quality_type = fine setting_version = 4 +type = quality +quality_type = fine +weight = 2 [values] layer_height = 0.04375 diff --git a/resources/quality/malyan_m200/malyan_m200_0.0875.inst.cfg b/resources/quality/malyan_m200/malyan_m200_0.0875.inst.cfg index 568dd796f3..555b280c1c 100644 --- a/resources/quality/malyan_m200/malyan_m200_0.0875.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_0.0875.inst.cfg @@ -4,10 +4,10 @@ name = M2 Quality definition = malyan_m200 [metadata] -type = quality -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 [values] layer_height = 0.0875 diff --git a/resources/quality/malyan_m200/malyan_m200_0.13125.inst.cfg b/resources/quality/malyan_m200/malyan_m200_0.13125.inst.cfg index 1dc436502b..7829f33086 100644 --- a/resources/quality/malyan_m200/malyan_m200_0.13125.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_0.13125.inst.cfg @@ -4,10 +4,10 @@ name = M3 Quality definition = malyan_m200 [metadata] -type = quality -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 [values] layer_height = 0.13125 diff --git a/resources/quality/malyan_m200/malyan_m200_0.175.inst.cfg b/resources/quality/malyan_m200/malyan_m200_0.175.inst.cfg index 314a8acd83..e6fd4c9368 100644 --- a/resources/quality/malyan_m200/malyan_m200_0.175.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_0.175.inst.cfg @@ -4,11 +4,11 @@ name = M4 Quality definition = malyan_m200 [metadata] -type = quality -weight = -1 -quality_type = fast -global_quality = true setting_version = 4 +type = quality +quality_type = fast +weight = -1 +global_quality = true [values] layer_height = 0.175 diff --git a/resources/quality/malyan_m200/malyan_m200_0.21875.inst.cfg b/resources/quality/malyan_m200/malyan_m200_0.21875.inst.cfg index a7fedb7e04..143693dbc4 100644 --- a/resources/quality/malyan_m200/malyan_m200_0.21875.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_0.21875.inst.cfg @@ -4,10 +4,10 @@ name = M5 Quality definition = malyan_m200 [metadata] -type = quality -weight = -2 -quality_type = faster setting_version = 4 +type = quality +quality_type = faster +weight = -2 [values] layer_height = 0.21875 diff --git a/resources/quality/malyan_m200/malyan_m200_0.2625.inst.cfg b/resources/quality/malyan_m200/malyan_m200_0.2625.inst.cfg index 441abc3070..3dc33a81a0 100644 --- a/resources/quality/malyan_m200/malyan_m200_0.2625.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_0.2625.inst.cfg @@ -4,10 +4,10 @@ name = M6 Quality definition = malyan_m200 [metadata] -type = quality -weight = -3 -quality_type = draft setting_version = 4 +type = quality +quality_type = draft +weight = -3 [values] layer_height = 0.2625 diff --git a/resources/quality/malyan_m200/malyan_m200_0.30625.inst.cfg b/resources/quality/malyan_m200/malyan_m200_0.30625.inst.cfg index 2588838174..c7d6911a67 100644 --- a/resources/quality/malyan_m200/malyan_m200_0.30625.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_0.30625.inst.cfg @@ -4,10 +4,10 @@ name = M7 Quality definition = malyan_m200 [metadata] -type = quality -weight = -4 -quality_type = turbo setting_version = 4 +type = quality +quality_type = turbo +weight = -4 [values] layer_height = 0.30625 diff --git a/resources/quality/malyan_m200/malyan_m200_0.35.inst.cfg b/resources/quality/malyan_m200/malyan_m200_0.35.inst.cfg index 800b6104d9..5d14204a1e 100644 --- a/resources/quality/malyan_m200/malyan_m200_0.35.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_0.35.inst.cfg @@ -4,11 +4,11 @@ name = M8 Quality definition = malyan_m200 [metadata] -type = quality -weight = -5 -quality_type = hyper -global_quality = true setting_version = 4 +type = quality +quality_type = hyper +weight = -5 +global_quality = true [values] layer_height = 0.35 diff --git a/resources/quality/malyan_m200/malyan_m200_global_Draft_Quality.inst.cfg b/resources/quality/malyan_m200/malyan_m200_global_Draft_Quality.inst.cfg index d3104caa87..fd999cc6c7 100644 --- a/resources/quality/malyan_m200/malyan_m200_global_Draft_Quality.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_global_Draft_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Fast definition = malyan_m200 [metadata] -type = quality -weight = -2 -quality_type = draft -global_quality = True setting_version = 4 +type = quality +quality_type = draft +weight = -2 +global_quality = True [values] layer_height = 0.21875 diff --git a/resources/quality/malyan_m200/malyan_m200_global_Fast_Quality.inst.cfg b/resources/quality/malyan_m200/malyan_m200_global_Fast_Quality.inst.cfg index aec535bd71..8027a7b01a 100644 --- a/resources/quality/malyan_m200/malyan_m200_global_Fast_Quality.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_global_Fast_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = malyan_m200 [metadata] -type = quality -weight = -1 -quality_type = fast -global_quality = True setting_version = 4 +type = quality +quality_type = fast +weight = -1 +global_quality = True [values] layer_height = 0.175 diff --git a/resources/quality/malyan_m200/malyan_m200_global_High_Quality.inst.cfg b/resources/quality/malyan_m200/malyan_m200_global_High_Quality.inst.cfg index ca202862a2..01fea67382 100644 --- a/resources/quality/malyan_m200/malyan_m200_global_High_Quality.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_global_High_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Finer definition = malyan_m200 [metadata] -type = quality -weight = 1 -quality_type = high -global_quality = True setting_version = 4 +type = quality +quality_type = high +weight = 1 +global_quality = True [values] layer_height = 0.0875 diff --git a/resources/quality/malyan_m200/malyan_m200_global_Normal_Quality.inst.cfg b/resources/quality/malyan_m200/malyan_m200_global_Normal_Quality.inst.cfg index 7076718903..a705d187f1 100644 --- a/resources/quality/malyan_m200/malyan_m200_global_Normal_Quality.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_global_Normal_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Fine definition = malyan_m200 [metadata] -type = quality -weight = 0 -quality_type = normal -global_quality = True setting_version = 4 +type = quality +quality_type = normal +weight = 0 +global_quality = True [values] layer_height = 0.13125 diff --git a/resources/quality/malyan_m200/malyan_m200_global_SuperDraft_Quality.inst.cfg b/resources/quality/malyan_m200/malyan_m200_global_SuperDraft_Quality.inst.cfg index 7dfbdb5886..92f1eb2286 100644 --- a/resources/quality/malyan_m200/malyan_m200_global_SuperDraft_Quality.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_global_SuperDraft_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Lowest Quality Draft definition = malyan_m200 [metadata] -type = quality -weight = -5 -quality_type = superdraft -global_quality = True setting_version = 4 +type = quality +quality_type = superdraft +weight = -5 +global_quality = True [values] layer_height = 0.35 diff --git a/resources/quality/malyan_m200/malyan_m200_global_ThickerDraft_Quality.inst.cfg b/resources/quality/malyan_m200/malyan_m200_global_ThickerDraft_Quality.inst.cfg index 2fbf82b128..246443503e 100644 --- a/resources/quality/malyan_m200/malyan_m200_global_ThickerDraft_Quality.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_global_ThickerDraft_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Draft definition = malyan_m200 [metadata] -type = quality -weight = -3 -quality_type = thickerdraft -global_quality = True setting_version = 4 +type = quality +quality_type = thickerdraft +weight = -3 +global_quality = True [values] layer_height = 0.2625 diff --git a/resources/quality/malyan_m200/malyan_m200_global_Ultra_Quality.inst.cfg b/resources/quality/malyan_m200/malyan_m200_global_Ultra_Quality.inst.cfg index 90e589cca5..0bbe46be4e 100644 --- a/resources/quality/malyan_m200/malyan_m200_global_Ultra_Quality.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_global_Ultra_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Ultra Fine definition = malyan_m200 [metadata] -type = quality -weight = 2 -quality_type = ultra -global_quality = True setting_version = 4 +type = quality +quality_type = ultra +weight = 2 +global_quality = True [values] layer_height = 0.04375 diff --git a/resources/quality/malyan_m200/malyan_m200_global_VeryDraft_Quality.inst.cfg b/resources/quality/malyan_m200/malyan_m200_global_VeryDraft_Quality.inst.cfg index 1210ee214b..5cc85b9bc8 100644 --- a/resources/quality/malyan_m200/malyan_m200_global_VeryDraft_Quality.inst.cfg +++ b/resources/quality/malyan_m200/malyan_m200_global_VeryDraft_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Low Detail Draft definition = malyan_m200 [metadata] -type = quality -weight = -4 -quality_type = verydraft -global_quality = True setting_version = 4 +type = quality +quality_type = verydraft +weight = -4 +global_quality = True [values] layer_height = 0.30625 diff --git a/resources/quality/malyan_m200/petg/malyan_m200_petg_draft.inst.cfg b/resources/quality/malyan_m200/petg/malyan_m200_petg_draft.inst.cfg index aef83471ba..038af5eec0 100644 --- a/resources/quality/malyan_m200/petg/malyan_m200_petg_draft.inst.cfg +++ b/resources/quality/malyan_m200/petg/malyan_m200_petg_draft.inst.cfg @@ -4,8 +4,8 @@ name = Fast definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_petg_175 weight = -2 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/malyan_m200/petg/malyan_m200_petg_fast.inst.cfg b/resources/quality/malyan_m200/petg/malyan_m200_petg_fast.inst.cfg index 3c7fc2c239..df341d195c 100644 --- a/resources/quality/malyan_m200/petg/malyan_m200_petg_fast.inst.cfg +++ b/resources/quality/malyan_m200/petg/malyan_m200_petg_fast.inst.cfg @@ -4,8 +4,8 @@ name = Normal definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_petg_175 weight = -1 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/malyan_m200/petg/malyan_m200_petg_high.inst.cfg b/resources/quality/malyan_m200/petg/malyan_m200_petg_high.inst.cfg index eb1654eae3..ff9dbc8227 100644 --- a/resources/quality/malyan_m200/petg/malyan_m200_petg_high.inst.cfg +++ b/resources/quality/malyan_m200/petg/malyan_m200_petg_high.inst.cfg @@ -4,8 +4,8 @@ name = Finer definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_petg_175 weight = 1 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/malyan_m200/petg/malyan_m200_petg_normal.inst.cfg b/resources/quality/malyan_m200/petg/malyan_m200_petg_normal.inst.cfg index 53e60d2d62..8531bbf98b 100644 --- a/resources/quality/malyan_m200/petg/malyan_m200_petg_normal.inst.cfg +++ b/resources/quality/malyan_m200/petg/malyan_m200_petg_normal.inst.cfg @@ -4,8 +4,8 @@ name = Fine definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_petg_175 weight = 0 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/malyan_m200/petg/malyan_m200_petg_superdraft.inst.cfg b/resources/quality/malyan_m200/petg/malyan_m200_petg_superdraft.inst.cfg index d2a96386ae..8b065ecea8 100644 --- a/resources/quality/malyan_m200/petg/malyan_m200_petg_superdraft.inst.cfg +++ b/resources/quality/malyan_m200/petg/malyan_m200_petg_superdraft.inst.cfg @@ -4,8 +4,8 @@ name = Lowest Quality Draft definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_petg_175 weight = -5 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/malyan_m200/petg/malyan_m200_petg_thickerdraft.inst.cfg b/resources/quality/malyan_m200/petg/malyan_m200_petg_thickerdraft.inst.cfg index e2f37ae43b..97672ee1c7 100644 --- a/resources/quality/malyan_m200/petg/malyan_m200_petg_thickerdraft.inst.cfg +++ b/resources/quality/malyan_m200/petg/malyan_m200_petg_thickerdraft.inst.cfg @@ -4,8 +4,8 @@ name = Draft definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = thickerdraft -material = generic_petg_175 weight = -3 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/malyan_m200/petg/malyan_m200_petg_ultra.inst.cfg b/resources/quality/malyan_m200/petg/malyan_m200_petg_ultra.inst.cfg index 0fa89f2569..7b92f9d454 100644 --- a/resources/quality/malyan_m200/petg/malyan_m200_petg_ultra.inst.cfg +++ b/resources/quality/malyan_m200/petg/malyan_m200_petg_ultra.inst.cfg @@ -4,8 +4,8 @@ name = Ultra Fine definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = ultra -material = generic_petg_175 weight = 2 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/malyan_m200/petg/malyan_m200_petg_verydraft.inst.cfg b/resources/quality/malyan_m200/petg/malyan_m200_petg_verydraft.inst.cfg index 84bedf5c14..1a1b59d90f 100644 --- a/resources/quality/malyan_m200/petg/malyan_m200_petg_verydraft.inst.cfg +++ b/resources/quality/malyan_m200/petg/malyan_m200_petg_verydraft.inst.cfg @@ -4,8 +4,8 @@ name = Low Detail Draft definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_petg_175 weight = -4 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/malyan_m200/pla/malyan_m200_pla_draft.inst.cfg b/resources/quality/malyan_m200/pla/malyan_m200_pla_draft.inst.cfg index 4f221eceb7..f3ef39f009 100644 --- a/resources/quality/malyan_m200/pla/malyan_m200_pla_draft.inst.cfg +++ b/resources/quality/malyan_m200/pla/malyan_m200_pla_draft.inst.cfg @@ -4,12 +4,12 @@ name = Fast definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_pla_175 weight = -2 -setting_version = 4 +material = generic_pla [values] material_bed_temperature = 60 -material_bed_temperature_layer_0 = 60 \ No newline at end of file +material_bed_temperature_layer_0 = 60 diff --git a/resources/quality/malyan_m200/pla/malyan_m200_pla_fast.inst.cfg b/resources/quality/malyan_m200/pla/malyan_m200_pla_fast.inst.cfg index 3097fe055a..0e047b140e 100644 --- a/resources/quality/malyan_m200/pla/malyan_m200_pla_fast.inst.cfg +++ b/resources/quality/malyan_m200/pla/malyan_m200_pla_fast.inst.cfg @@ -4,12 +4,12 @@ name = Normal definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_pla_175 weight = -1 -setting_version = 4 +material = generic_pla [values] material_bed_temperature = 60 -material_bed_temperature_layer_0 = 60 \ No newline at end of file +material_bed_temperature_layer_0 = 60 diff --git a/resources/quality/malyan_m200/pla/malyan_m200_pla_high.inst.cfg b/resources/quality/malyan_m200/pla/malyan_m200_pla_high.inst.cfg index 062c120ad0..e68ad90c6c 100644 --- a/resources/quality/malyan_m200/pla/malyan_m200_pla_high.inst.cfg +++ b/resources/quality/malyan_m200/pla/malyan_m200_pla_high.inst.cfg @@ -4,12 +4,12 @@ name = Finer definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pla_175 weight = 1 -setting_version = 4 +material = generic_pla [values] material_bed_temperature = 60 -material_bed_temperature_layer_0 = 60 \ No newline at end of file +material_bed_temperature_layer_0 = 60 diff --git a/resources/quality/malyan_m200/pla/malyan_m200_pla_normal.inst.cfg b/resources/quality/malyan_m200/pla/malyan_m200_pla_normal.inst.cfg index e01141ed9e..78bdc826ba 100644 --- a/resources/quality/malyan_m200/pla/malyan_m200_pla_normal.inst.cfg +++ b/resources/quality/malyan_m200/pla/malyan_m200_pla_normal.inst.cfg @@ -4,12 +4,12 @@ name = Fine definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pla_175 weight = 0 -setting_version = 4 +material = generic_pla [values] material_bed_temperature = 60 -material_bed_temperature_layer_0 = 60 \ No newline at end of file +material_bed_temperature_layer_0 = 60 diff --git a/resources/quality/malyan_m200/pla/malyan_m200_pla_superdraft.inst.cfg b/resources/quality/malyan_m200/pla/malyan_m200_pla_superdraft.inst.cfg index 53eb4380eb..cc24c4a0b2 100644 --- a/resources/quality/malyan_m200/pla/malyan_m200_pla_superdraft.inst.cfg +++ b/resources/quality/malyan_m200/pla/malyan_m200_pla_superdraft.inst.cfg @@ -4,12 +4,12 @@ name = Lowest Quality Draft definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_pla_175 weight = -5 -setting_version = 4 +material = generic_pla [values] material_bed_temperature = 60 -material_bed_temperature_layer_0 = 60 \ No newline at end of file +material_bed_temperature_layer_0 = 60 diff --git a/resources/quality/malyan_m200/pla/malyan_m200_pla_thickerdraft.inst.cfg b/resources/quality/malyan_m200/pla/malyan_m200_pla_thickerdraft.inst.cfg index 32d2b419bc..5bfb82ee90 100644 --- a/resources/quality/malyan_m200/pla/malyan_m200_pla_thickerdraft.inst.cfg +++ b/resources/quality/malyan_m200/pla/malyan_m200_pla_thickerdraft.inst.cfg @@ -4,12 +4,12 @@ name = Draft definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = thickerdraft -material = generic_pla_175 weight = -3 -setting_version = 4 +material = generic_pla [values] material_bed_temperature = 60 -material_bed_temperature_layer_0 = 60 \ No newline at end of file +material_bed_temperature_layer_0 = 60 diff --git a/resources/quality/malyan_m200/pla/malyan_m200_pla_ultra.inst.cfg b/resources/quality/malyan_m200/pla/malyan_m200_pla_ultra.inst.cfg index 3865059254..d042fc7978 100644 --- a/resources/quality/malyan_m200/pla/malyan_m200_pla_ultra.inst.cfg +++ b/resources/quality/malyan_m200/pla/malyan_m200_pla_ultra.inst.cfg @@ -4,12 +4,12 @@ name = Ultra Fine definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = ultra -material = generic_pla_175 weight = 2 -setting_version = 4 +material = generic_pla [values] material_bed_temperature = 60 -material_bed_temperature_layer_0 = 60 \ No newline at end of file +material_bed_temperature_layer_0 = 60 diff --git a/resources/quality/malyan_m200/pla/malyan_m200_pla_verydraft.inst.cfg b/resources/quality/malyan_m200/pla/malyan_m200_pla_verydraft.inst.cfg index a624c056be..8e79071db4 100644 --- a/resources/quality/malyan_m200/pla/malyan_m200_pla_verydraft.inst.cfg +++ b/resources/quality/malyan_m200/pla/malyan_m200_pla_verydraft.inst.cfg @@ -4,12 +4,12 @@ name = Low Detail Draft definition = malyan_m200 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_pla_175 weight = -4 -setting_version = 4 +material = generic_pla [values] material_bed_temperature = 60 -material_bed_temperature_layer_0 = 60 \ No newline at end of file +material_bed_temperature_layer_0 = 60 diff --git a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_draft.inst.cfg b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_draft.inst.cfg index a63256573a..3387b51d7d 100644 --- a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_draft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_draft.inst.cfg @@ -4,12 +4,12 @@ name = Fast definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_abs_175 weight = -2 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_fast.inst.cfg b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_fast.inst.cfg index 49f4486596..da187c85ea 100644 --- a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_fast.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_fast.inst.cfg @@ -4,12 +4,12 @@ name = Normal definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_abs_175 weight = -1 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_high.inst.cfg b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_high.inst.cfg index eab16a8e2b..a2efa54353 100644 --- a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_high.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_high.inst.cfg @@ -4,12 +4,12 @@ name = Finer definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_abs_175 weight = 1 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_normal.inst.cfg b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_normal.inst.cfg index 03aeb4067b..a331a63aaf 100644 --- a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_normal.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_normal.inst.cfg @@ -4,12 +4,12 @@ name = Fine definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_abs_175 weight = 0 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_superdraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_superdraft.inst.cfg index 148f53ba73..d328e353ac 100644 --- a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_superdraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_superdraft.inst.cfg @@ -4,12 +4,12 @@ name = Lowest Quality Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_abs_175 weight = -5 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_thickerdraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_thickerdraft.inst.cfg index e2ad71a360..8e64dae5aa 100644 --- a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_thickerdraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_thickerdraft.inst.cfg @@ -4,12 +4,12 @@ name = Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = thickerdraft -material = generic_abs_175 weight = -3 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_ultra.inst.cfg b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_ultra.inst.cfg index 7ebdf80baf..5757e57a3b 100644 --- a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_ultra.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_ultra.inst.cfg @@ -4,12 +4,12 @@ name = Ultra Fine definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = thickerdraft -material = generic_abs_175 weight = 2 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_verydraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_verydraft.inst.cfg index 9965ae8bcf..77810c8809 100644 --- a/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_verydraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/abs/monoprice_select_mini_v2_abs_verydraft.inst.cfg @@ -4,12 +4,12 @@ name = Low Detail Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_abs_175 weight = -4 -setting_version = 4 +material = generic_abs [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Draft_Quality.inst.cfg b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Draft_Quality.inst.cfg index b7d0faa2c7..d8aa07b779 100644 --- a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Draft_Quality.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Draft_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Fast definition = monoprice_select_mini_v2 [metadata] -type = quality -weight = -2 -quality_type = draft -global_quality = True setting_version = 4 +type = quality +quality_type = draft +weight = -2 +global_quality = True [values] layer_height = 0.21875 diff --git a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Fast_Quality.inst.cfg b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Fast_Quality.inst.cfg index f7f338e4c9..a0620d532a 100644 --- a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Fast_Quality.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Fast_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = monoprice_select_mini_v2 [metadata] -type = quality -weight = -1 -quality_type = fast -global_quality = True setting_version = 4 +type = quality +quality_type = fast +weight = -1 +global_quality = True [values] layer_height = 0.175 diff --git a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_High_Quality.inst.cfg b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_High_Quality.inst.cfg index 4a37a1afd8..7237dbc42a 100644 --- a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_High_Quality.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_High_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Finer definition = monoprice_select_mini_v2 [metadata] -type = quality -weight = 1 -quality_type = high -global_quality = True setting_version = 4 +type = quality +quality_type = high +weight = 1 +global_quality = True [values] layer_height = 0.0875 diff --git a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Normal_Quality.inst.cfg b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Normal_Quality.inst.cfg index b8e545adcf..bcb360d310 100644 --- a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Normal_Quality.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Normal_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Fine definition = monoprice_select_mini_v2 [metadata] -type = quality -weight = 0 -quality_type = normal -global_quality = True setting_version = 4 +type = quality +quality_type = normal +weight = 0 +global_quality = True [values] layer_height = 0.13125 diff --git a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_SuperDraft_Quality.inst.cfg b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_SuperDraft_Quality.inst.cfg index 0ef9db5875..81954f86e7 100644 --- a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_SuperDraft_Quality.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_SuperDraft_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Lowest Quality Draft definition = monoprice_select_mini_v2 [metadata] -type = quality -weight = -5 -quality_type = superdraft -global_quality = True setting_version = 4 +type = quality +quality_type = superdraft +weight = -5 +global_quality = True [values] layer_height = 0.35 diff --git a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_ThickerDraft_Quality.inst.cfg b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_ThickerDraft_Quality.inst.cfg index 4dd3a7aafe..1fe7ee22ab 100644 --- a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_ThickerDraft_Quality.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_ThickerDraft_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Draft definition = monoprice_select_mini_v2 [metadata] -type = quality -weight = -3 -quality_type = thickerdraft -global_quality = True setting_version = 4 +type = quality +quality_type = thickerdraft +weight = -3 +global_quality = True [values] layer_height = 0.2625 diff --git a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Ultra_Quality.inst.cfg b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Ultra_Quality.inst.cfg index 337f0d06bc..89e2f43dad 100644 --- a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Ultra_Quality.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_Ultra_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Ultra Fine definition = monoprice_select_mini_v2 [metadata] -type = quality -weight = 2 -quality_type = ultra -global_quality = True setting_version = 4 +type = quality +quality_type = ultra +weight = 2 +global_quality = True [values] layer_height = 0.04375 diff --git a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_VeryDraft_Quality.inst.cfg b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_VeryDraft_Quality.inst.cfg index e884077069..c7fc09d9e8 100644 --- a/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_VeryDraft_Quality.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/monoprice_select_mini_v2_global_VeryDraft_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Low Detail Draft definition = monoprice_select_mini_v2 [metadata] -type = quality -weight = -4 -quality_type = verydraft -global_quality = True setting_version = 4 +type = quality +quality_type = verydraft +weight = -4 +global_quality = True [values] layer_height = 0.30625 diff --git a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_draft.inst.cfg b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_draft.inst.cfg index 4a03c17a63..80905c64f7 100644 --- a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_draft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_draft.inst.cfg @@ -4,8 +4,8 @@ name = Fast definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_nylon_175 weight = -2 -setting_version = 4 \ No newline at end of file +material = generic_nylon diff --git a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_fast.inst.cfg b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_fast.inst.cfg index 1c04f77b8b..eab42b728e 100644 --- a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_fast.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_fast.inst.cfg @@ -4,8 +4,8 @@ name = Normal definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_nylon_175 weight = -1 -setting_version = 4 \ No newline at end of file +material = generic_nylon diff --git a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_high.inst.cfg b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_high.inst.cfg index d57516598a..1261eff697 100644 --- a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_high.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_high.inst.cfg @@ -4,8 +4,8 @@ name = Finer definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_nylon_175 weight = 1 -setting_version = 4 \ No newline at end of file +material = generic_nylon diff --git a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_normal.inst.cfg b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_normal.inst.cfg index 308ea86311..6cf8709bf6 100644 --- a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_normal.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_normal.inst.cfg @@ -4,8 +4,8 @@ name = Fine definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_nylon_175 weight = 0 -setting_version = 4 \ No newline at end of file +material = generic_nylon diff --git a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_superdraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_superdraft.inst.cfg index db4f3ca907..3cf4efb73b 100644 --- a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_superdraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_superdraft.inst.cfg @@ -4,8 +4,8 @@ name = Lowest Quality Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_nylon_175 weight = -5 -setting_version = 4 \ No newline at end of file +material = generic_nylon diff --git a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_thickerdraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_thickerdraft.inst.cfg index 9a1afc0e48..22f27ab084 100644 --- a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_thickerdraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_thickerdraft.inst.cfg @@ -4,8 +4,8 @@ name = Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = thickerdraft -material = generic_nylon_175 weight = -3 -setting_version = 4 \ No newline at end of file +material = generic_nylon diff --git a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_ultra.inst.cfg b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_ultra.inst.cfg index 3453671a72..b3b80d651f 100644 --- a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_ultra.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_ultra.inst.cfg @@ -4,8 +4,8 @@ name = Ultra Fine definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = ultra -material = generic_nylon_175 weight = 2 -setting_version = 4 \ No newline at end of file +material = generic_nylon diff --git a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_verydraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_verydraft.inst.cfg index ee2531fc4e..efd93a5381 100644 --- a/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_verydraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/nylon/monoprice_select_mini_v2_nylon_verydraft.inst.cfg @@ -4,8 +4,8 @@ name = Low Detail Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_nylon_175 weight = -4 -setting_version = 4 \ No newline at end of file +material = generic_nylon diff --git a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_draft.inst.cfg b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_draft.inst.cfg index aa5fc7844d..05283042c2 100644 --- a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_draft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_draft.inst.cfg @@ -4,12 +4,12 @@ name = Fast definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_pc_175 weight = -2 -setting_version = 4 +material = generic_pc [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_fast.inst.cfg b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_fast.inst.cfg index 232c4ab6f3..07319fe4db 100644 --- a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_fast.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_fast.inst.cfg @@ -4,12 +4,12 @@ name = Normal definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_pc_175 weight = -1 -setting_version = 4 +material = generic_pc [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_high.inst.cfg b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_high.inst.cfg index aa9da322fb..668040c851 100644 --- a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_high.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_high.inst.cfg @@ -4,12 +4,12 @@ name = Finer definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pc_175 weight = 1 -setting_version = 4 +material = generic_pc [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_normal.inst.cfg b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_normal.inst.cfg index 145b21221b..e9d907fabd 100644 --- a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_normal.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_normal.inst.cfg @@ -4,12 +4,12 @@ name = Fine definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pc_175 weight = 0 -setting_version = 4 +material = generic_pc [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_superdraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_superdraft.inst.cfg index b6e53bda62..5d1af5a430 100644 --- a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_superdraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_superdraft.inst.cfg @@ -4,12 +4,12 @@ name = Lowest Quality Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_pc_175 weight = -5 -setting_version = 4 +material = generic_pc [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_thickerdraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_thickerdraft.inst.cfg index 055228ab13..06c4b4f405 100644 --- a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_thickerdraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_thickerdraft.inst.cfg @@ -4,12 +4,12 @@ name = Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = thickerdraft -material = generic_pc_175 weight = -3 -setting_version = 4 +material = generic_pc [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_ultra.inst.cfg b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_ultra.inst.cfg index a3e99b998e..821658554d 100644 --- a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_ultra.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_ultra.inst.cfg @@ -4,12 +4,12 @@ name = Ultra Fine definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = ultra -material = generic_pc_175 weight = 2 -setting_version = 4 +material = generic_pc [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_verydraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_verydraft.inst.cfg index 73f5a2f2c9..93dc04e13c 100644 --- a/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_verydraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pc/monoprice_select_mini_v2_pc_verydraft.inst.cfg @@ -4,12 +4,12 @@ name = Low Detail Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_pc_175 weight = -4 -setting_version = 4 +material = generic_pc [values] material_bed_temperature = 70 -material_bed_temperature_layer_0 = 70 \ No newline at end of file +material_bed_temperature_layer_0 = 70 diff --git a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_draft.inst.cfg b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_draft.inst.cfg index 8a33e03310..917e8b98a3 100644 --- a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_draft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_draft.inst.cfg @@ -4,8 +4,8 @@ name = Fast definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_petg_175 weight = -2 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_fast.inst.cfg b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_fast.inst.cfg index fb084fa08e..aa98ea4de0 100644 --- a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_fast.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_fast.inst.cfg @@ -4,8 +4,8 @@ name = Normal definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_petg_175 weight = -1 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_high.inst.cfg b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_high.inst.cfg index 16891f6f43..3db3af0db2 100644 --- a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_high.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_high.inst.cfg @@ -4,8 +4,8 @@ name = Finer definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_petg_175 weight = 1 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_normal.inst.cfg b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_normal.inst.cfg index bb2f0b47a8..e39fd54550 100644 --- a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_normal.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_normal.inst.cfg @@ -4,8 +4,8 @@ name = Fine definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_petg_175 weight = 0 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_superdraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_superdraft.inst.cfg index 78ca1b6b7a..6d9e99d365 100644 --- a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_superdraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_superdraft.inst.cfg @@ -4,8 +4,8 @@ name = Lowest Quality Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_petg_175 weight = -5 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_thickerdraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_thickerdraft.inst.cfg index 69606ff913..5227aac686 100644 --- a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_thickerdraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_thickerdraft.inst.cfg @@ -4,8 +4,8 @@ name = Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = thickerdraft -material = generic_petg_175 weight = -3 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_ultra.inst.cfg b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_ultra.inst.cfg index 7c5ac599c8..a58c05b004 100644 --- a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_ultra.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_ultra.inst.cfg @@ -4,8 +4,8 @@ name = Ultra Fine definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = ultra -material = generic_petg_175 weight = 2 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_verydraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_verydraft.inst.cfg index ed0c2510f5..0fe38fb5df 100644 --- a/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_verydraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/petg/monoprice_select_mini_v2_petg_verydraft.inst.cfg @@ -4,8 +4,8 @@ name = Low Detail Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_petg_175 weight = -4 -setting_version = 4 \ No newline at end of file +material = generic_petg diff --git a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_draft.inst.cfg b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_draft.inst.cfg index 04a955cf6c..0b9f10a790 100644 --- a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_draft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_draft.inst.cfg @@ -4,8 +4,8 @@ name = Fast definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_pla_175 weight = -2 -setting_version = 4 \ No newline at end of file +material = generic_pla diff --git a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_fast.inst.cfg b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_fast.inst.cfg index 6efc0935e2..d831890413 100644 --- a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_fast.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_fast.inst.cfg @@ -4,8 +4,8 @@ name = Normal definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_pla_175 weight = 0 -setting_version = 4 \ No newline at end of file +material = generic_pla diff --git a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_high.inst.cfg b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_high.inst.cfg index 8fe2371e5d..f5049308f3 100644 --- a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_high.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_high.inst.cfg @@ -4,8 +4,8 @@ name = Finer definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pla_175 weight = 0 -setting_version = 4 \ No newline at end of file +material = generic_pla diff --git a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_normal.inst.cfg b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_normal.inst.cfg index 01351154c4..f63c87a52c 100644 --- a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_normal.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_normal.inst.cfg @@ -4,8 +4,8 @@ name = Fine definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pla_175 weight = 0 -setting_version = 4 \ No newline at end of file +material = generic_pla diff --git a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_superdraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_superdraft.inst.cfg index adfced9787..a8bd9a5179 100644 --- a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_superdraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_superdraft.inst.cfg @@ -4,8 +4,8 @@ name = Lowest Quality Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_pla_175 weight = -5 -setting_version = 4 \ No newline at end of file +material = generic_pla diff --git a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_thickerdraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_thickerdraft.inst.cfg index f4522c9778..df1ae97a16 100644 --- a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_thickerdraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_thickerdraft.inst.cfg @@ -4,8 +4,8 @@ name = Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = thickerdraft -material = generic_pla_175 weight = -3 -setting_version = 4 \ No newline at end of file +material = generic_pla diff --git a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_ultra.inst.cfg b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_ultra.inst.cfg index 2fa8eb7f81..3b3ec79692 100644 --- a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_ultra.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_ultra.inst.cfg @@ -4,8 +4,8 @@ name = Ultra Fine definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality quality_type = ultra -material = generic_pla_175 weight = 2 -setting_version = 4 \ No newline at end of file +material = generic_pla diff --git a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_verydraft.inst.cfg b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_verydraft.inst.cfg index e59cf4a490..5e63de3952 100644 --- a/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_verydraft.inst.cfg +++ b/resources/quality/monoprice_select_mini_v2/pla/monoprice_select_mini_v2_pla_verydraft.inst.cfg @@ -4,8 +4,8 @@ name = Low Detail Draft definition = monoprice_select_mini_v2 [metadata] +setting_version = 4 type = quality -quality_type = verydraft -material = generic_pla_175 +material = generic_pla weight = 0 -setting_version = 4 \ No newline at end of file +quality_type = verydraft diff --git a/resources/quality/normal.inst.cfg b/resources/quality/normal.inst.cfg index 9fb7b238cd..2eeb91324f 100644 --- a/resources/quality/normal.inst.cfg +++ b/resources/quality/normal.inst.cfg @@ -4,10 +4,10 @@ name = Fine definition = fdmprinter [metadata] +setting_version = 4 type = quality quality_type = normal -global_quality = True weight = 0 -setting_version = 4 +global_quality = True [values] diff --git a/resources/quality/peopoly_moai/peopoly_moai_high.inst.cfg b/resources/quality/peopoly_moai/peopoly_moai_high.inst.cfg index ae8a377116..208fa453fe 100644 --- a/resources/quality/peopoly_moai/peopoly_moai_high.inst.cfg +++ b/resources/quality/peopoly_moai/peopoly_moai_high.inst.cfg @@ -4,10 +4,10 @@ name = Extra Fine definition = peopoly_moai [metadata] -type = quality -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 [values] infill_sparse_density = 70 diff --git a/resources/quality/peopoly_moai/peopoly_moai_max.inst.cfg b/resources/quality/peopoly_moai/peopoly_moai_max.inst.cfg index 07ab7e364b..cc764009a9 100644 --- a/resources/quality/peopoly_moai/peopoly_moai_max.inst.cfg +++ b/resources/quality/peopoly_moai/peopoly_moai_max.inst.cfg @@ -4,10 +4,10 @@ name = Maximum Quality definition = peopoly_moai [metadata] -type = quality -weight = 2 -quality_type = extra_high setting_version = 4 +type = quality +quality_type = extra_high +weight = 2 [values] infill_sparse_density = 70 diff --git a/resources/quality/peopoly_moai/peopoly_moai_normal.inst.cfg b/resources/quality/peopoly_moai/peopoly_moai_normal.inst.cfg index e0d2f7d818..2baa70be1e 100644 --- a/resources/quality/peopoly_moai/peopoly_moai_normal.inst.cfg +++ b/resources/quality/peopoly_moai/peopoly_moai_normal.inst.cfg @@ -4,10 +4,10 @@ name = Fine definition = peopoly_moai [metadata] -type = quality -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 [values] infill_sparse_density = 70 diff --git a/resources/quality/tevo_blackwidow/tevo_blackwidow_draft.inst.cfg b/resources/quality/tevo_blackwidow/tevo_blackwidow_draft.inst.cfg index 082b7dded7..2536cbba12 100644 --- a/resources/quality/tevo_blackwidow/tevo_blackwidow_draft.inst.cfg +++ b/resources/quality/tevo_blackwidow/tevo_blackwidow_draft.inst.cfg @@ -4,10 +4,10 @@ name = Draft definition = tevo_blackwidow [metadata] +setting_version = 4 type = quality quality_type = draft weight = -2 -setting_version = 4 [values] brim_width = 4.0 @@ -30,4 +30,4 @@ support_type = everywhere support_use_towers = False support_xy_distance = 0.7 top_bottom_thickness = 1.2 -wall_thickness = 1.2 \ No newline at end of file +wall_thickness = 1.2 diff --git a/resources/quality/tevo_blackwidow/tevo_blackwidow_high.inst.cfg b/resources/quality/tevo_blackwidow/tevo_blackwidow_high.inst.cfg index 79d020463f..29599eaebc 100644 --- a/resources/quality/tevo_blackwidow/tevo_blackwidow_high.inst.cfg +++ b/resources/quality/tevo_blackwidow/tevo_blackwidow_high.inst.cfg @@ -4,10 +4,10 @@ name = High definition = tevo_blackwidow [metadata] +setting_version = 4 type = quality quality_type = high weight = 1 -setting_version = 4 [values] brim_width = 4.0 @@ -30,4 +30,4 @@ support_type = everywhere support_use_towers = False support_xy_distance = 0.7 top_bottom_thickness = 1.2 -wall_thickness = 1.2 \ No newline at end of file +wall_thickness = 1.2 diff --git a/resources/quality/tevo_blackwidow/tevo_blackwidow_normal.inst.cfg b/resources/quality/tevo_blackwidow/tevo_blackwidow_normal.inst.cfg index 2982c44d3d..98dbf5a79a 100644 --- a/resources/quality/tevo_blackwidow/tevo_blackwidow_normal.inst.cfg +++ b/resources/quality/tevo_blackwidow/tevo_blackwidow_normal.inst.cfg @@ -4,10 +4,10 @@ name = Normal definition = tevo_blackwidow [metadata] +setting_version = 4 type = quality quality_type = normal weight = 0 -setting_version = 4 [values] brim_width = 4.0 @@ -30,4 +30,4 @@ support_type = everywhere support_use_towers = False support_xy_distance = 0.7 top_bottom_thickness = 1.2 -wall_thickness = 1.2 \ No newline at end of file +wall_thickness = 1.2 diff --git a/resources/quality/ultimaker2/um2_draft.inst.cfg b/resources/quality/ultimaker2/um2_draft.inst.cfg index 4fe3f51e20..88d3ed3520 100644 --- a/resources/quality/ultimaker2/um2_draft.inst.cfg +++ b/resources/quality/ultimaker2/um2_draft.inst.cfg @@ -4,10 +4,11 @@ name = Draft Quality definition = ultimaker2 [metadata] +setting_version = 4 type = quality quality_type = draft weight = -2 -setting_version = 4 +global_quality = True [values] layer_height = 0.2 diff --git a/resources/quality/ultimaker2/um2_low.inst.cfg b/resources/quality/ultimaker2/um2_fast.inst.cfg similarity index 87% rename from resources/quality/ultimaker2/um2_low.inst.cfg rename to resources/quality/ultimaker2/um2_fast.inst.cfg index 832962984c..36e4fe03c2 100644 --- a/resources/quality/ultimaker2/um2_low.inst.cfg +++ b/resources/quality/ultimaker2/um2_fast.inst.cfg @@ -4,10 +4,11 @@ name = Low Quality definition = ultimaker2 [metadata] -type = quality -quality_type = low -weight = -1 setting_version = 4 +type = quality +quality_type = fast +weight = -1 +global_quality = True [values] infill_sparse_density = 10 diff --git a/resources/quality/ultimaker2/um2_high.inst.cfg b/resources/quality/ultimaker2/um2_high.inst.cfg index 96941beed2..2fb7ead455 100644 --- a/resources/quality/ultimaker2/um2_high.inst.cfg +++ b/resources/quality/ultimaker2/um2_high.inst.cfg @@ -4,10 +4,11 @@ name = Extra Fine definition = ultimaker2 [metadata] +setting_version = 4 type = quality quality_type = high weight = 1 -setting_version = 4 +global_quality = True [values] layer_height = 0.06 diff --git a/resources/quality/ultimaker2/um2_normal.inst.cfg b/resources/quality/ultimaker2/um2_normal.inst.cfg index ea804feb80..51fe1f317c 100644 --- a/resources/quality/ultimaker2/um2_normal.inst.cfg +++ b/resources/quality/ultimaker2/um2_normal.inst.cfg @@ -4,9 +4,10 @@ name = Fine definition = ultimaker2 [metadata] +setting_version = 4 type = quality quality_type = normal weight = 0 -setting_version = 4 +global_quality = True [values] diff --git a/resources/quality/ultimaker2_plus/pla_0.25_normal.inst.cfg b/resources/quality/ultimaker2_plus/pla_0.25_normal.inst.cfg index 638a1a9384..07e3dcd7db 100644 --- a/resources/quality/ultimaker2_plus/pla_0.25_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/pla_0.25_normal.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_pla_ultimaker2_plus_0.25_mm -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_pla +variant = 0.25 mm [values] cool_min_layer_time = 5 @@ -19,4 +20,3 @@ speed_layer_0 = =round(speed_print * 30 / 30) speed_print = 30 top_bottom_thickness = 0.72 wall_thickness = 0.88 - diff --git a/resources/quality/ultimaker2_plus/pla_0.4_fast.inst.cfg b/resources/quality/ultimaker2_plus/pla_0.4_fast.inst.cfg index 9f4dfc0b5d..2a72e40d80 100644 --- a/resources/quality/ultimaker2_plus/pla_0.4_fast.inst.cfg +++ b/resources/quality/ultimaker2_plus/pla_0.4_fast.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker2_plus [metadata] -type = quality -material = generic_pla_ultimaker2_plus_0.4_mm -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_pla +variant = 0.4 mm [values] cool_min_layer_time = 5 @@ -22,4 +23,3 @@ speed_travel = 150 speed_wall = 50 top_bottom_thickness = 0.75 wall_thickness = 0.7 - diff --git a/resources/quality/ultimaker2_plus/pla_0.4_high.inst.cfg b/resources/quality/ultimaker2_plus/pla_0.4_high.inst.cfg index 7bf51b0211..ce41158378 100644 --- a/resources/quality/ultimaker2_plus/pla_0.4_high.inst.cfg +++ b/resources/quality/ultimaker2_plus/pla_0.4_high.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_pla_ultimaker2_plus_0.4_mm -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_pla +variant = 0.4 mm [values] cool_min_layer_time = 5 @@ -20,4 +21,3 @@ speed_print = 50 speed_topbottom = 20 top_bottom_thickness = 0.72 wall_thickness = 1.05 - diff --git a/resources/quality/ultimaker2_plus/pla_0.4_normal.inst.cfg b/resources/quality/ultimaker2_plus/pla_0.4_normal.inst.cfg index 3c6f40e0bc..edfe131ddf 100644 --- a/resources/quality/ultimaker2_plus/pla_0.4_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/pla_0.4_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_pla_ultimaker2_plus_0.4_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_pla +variant = 0.4 mm [values] cool_min_layer_time = 5 @@ -20,4 +21,3 @@ speed_print = 50 speed_topbottom = 20 top_bottom_thickness = 0.8 wall_thickness = 1.05 - diff --git a/resources/quality/ultimaker2_plus/pla_0.6_normal.inst.cfg b/resources/quality/ultimaker2_plus/pla_0.6_normal.inst.cfg index ef79e30b74..548c7478ba 100644 --- a/resources/quality/ultimaker2_plus/pla_0.6_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/pla_0.6_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -material = generic_pla_ultimaker2_plus_0.6_mm -type = quality -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_pla +variant = 0.6 mm [values] cool_min_layer_time = 5 @@ -22,4 +23,3 @@ speed_wall = 40 speed_wall_0 = 25 top_bottom_thickness = 1.2 wall_thickness = 1.59 - diff --git a/resources/quality/ultimaker2_plus/pla_0.8_normal.inst.cfg b/resources/quality/ultimaker2_plus/pla_0.8_normal.inst.cfg index 42418ea392..a257d3d6f8 100644 --- a/resources/quality/ultimaker2_plus/pla_0.8_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/pla_0.8_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker2_plus [metadata] -material = generic_pla_ultimaker2_plus_0.8_mm -type = quality -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_pla +variant = 0.8 mm [values] cool_min_layer_time = 5 @@ -20,4 +21,3 @@ speed_print = 40 speed_wall_0 = 25 top_bottom_thickness = 1.2 wall_thickness = 2.1 - diff --git a/resources/quality/ultimaker2_plus/um2p_abs_0.25_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_abs_0.25_normal.inst.cfg index 50a4076de2..e448b9d180 100644 --- a/resources/quality/ultimaker2_plus/um2p_abs_0.25_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_abs_0.25_normal.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_abs_ultimaker2_plus_0.25_mm -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_abs +variant = 0.25 mm [values] cool_fan_speed_min = =cool_fan_speed * 0.2 @@ -21,4 +22,3 @@ speed_layer_0 = =round(speed_print * 30 / 30) speed_print = 30 top_bottom_thickness = 0.72 wall_thickness = 0.88 - diff --git a/resources/quality/ultimaker2_plus/um2p_abs_0.4_fast.inst.cfg b/resources/quality/ultimaker2_plus/um2p_abs_0.4_fast.inst.cfg index 9d1bcf6ff5..3fd2de3a36 100644 --- a/resources/quality/ultimaker2_plus/um2p_abs_0.4_fast.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_abs_0.4_fast.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker2_plus [metadata] -type = quality -material = generic_abs_ultimaker2_plus_0.4_mm -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_abs +variant = 0.4 mm [values] cool_fan_speed_min = =cool_fan_speed * 0.2 @@ -24,4 +25,3 @@ speed_travel = 150 speed_wall = 40 top_bottom_thickness = 0.75 wall_thickness = 0.7 - diff --git a/resources/quality/ultimaker2_plus/um2p_abs_0.4_high.inst.cfg b/resources/quality/ultimaker2_plus/um2p_abs_0.4_high.inst.cfg index 84a5557434..2f119ae86b 100644 --- a/resources/quality/ultimaker2_plus/um2p_abs_0.4_high.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_abs_0.4_high.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_abs_ultimaker2_plus_0.4_mm -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_abs +variant = 0.4 mm [values] cool_fan_speed_min = =cool_fan_speed * 0.2 @@ -22,4 +23,3 @@ speed_print = 45 speed_wall = 30 top_bottom_thickness = 0.72 wall_thickness = 1.05 - diff --git a/resources/quality/ultimaker2_plus/um2p_abs_0.4_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_abs_0.4_normal.inst.cfg index efc749ad8c..8416e69dba 100644 --- a/resources/quality/ultimaker2_plus/um2p_abs_0.4_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_abs_0.4_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_abs_ultimaker2_plus_0.4_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_abs +variant = 0.4 mm [values] cool_fan_speed_min = =cool_fan_speed * 0.2 @@ -22,4 +23,3 @@ speed_print = 45 speed_wall = 30 top_bottom_thickness = 0.8 wall_thickness = 1.05 - diff --git a/resources/quality/ultimaker2_plus/um2p_abs_0.6_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_abs_0.6_normal.inst.cfg index eb706c5762..393e630299 100644 --- a/resources/quality/ultimaker2_plus/um2p_abs_0.6_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_abs_0.6_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_abs_ultimaker2_plus_0.6_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_abs +variant = 0.6 mm [values] cool_fan_speed_min = =cool_fan_speed * 0.5 @@ -22,4 +23,3 @@ speed_layer_0 = =round(speed_print * 30 / 40) speed_print = 40 top_bottom_thickness = 1.2 wall_thickness = 1.59 - diff --git a/resources/quality/ultimaker2_plus/um2p_abs_0.8_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_abs_0.8_normal.inst.cfg index 2dba5a9304..d0dcbb0908 100644 --- a/resources/quality/ultimaker2_plus/um2p_abs_0.8_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_abs_0.8_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker2_plus [metadata] -type = quality -material = generic_abs_ultimaker2_plus_0.8_mm -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_abs +variant = 0.8 mm [values] cool_fan_speed_min = =cool_fan_speed * 0.5 @@ -21,4 +22,3 @@ speed_layer_0 = =round(speed_print * 30 / 40) speed_print = 40 top_bottom_thickness = 1.2 wall_thickness = 2.1 - diff --git a/resources/quality/ultimaker2_plus/um2p_cpe_0.25_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_cpe_0.25_normal.inst.cfg index 8e87e0e7b6..1047b0ca39 100644 --- a/resources/quality/ultimaker2_plus/um2p_cpe_0.25_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_cpe_0.25_normal.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_cpe_ultimaker2_plus_0.25_mm -weight = -1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = -1 +material = generic_cpe +variant = 0.25 mm [values] cool_fan_speed_min = =cool_fan_speed * 0.2 @@ -21,4 +22,3 @@ speed_layer_0 = =round(speed_print * 30 / 30) speed_print = 30 top_bottom_thickness = 0.72 wall_thickness = 0.88 - diff --git a/resources/quality/ultimaker2_plus/um2p_cpe_0.4_fast.inst.cfg b/resources/quality/ultimaker2_plus/um2p_cpe_0.4_fast.inst.cfg index e311df00a8..7beaf2f229 100644 --- a/resources/quality/ultimaker2_plus/um2p_cpe_0.4_fast.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_cpe_0.4_fast.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker2_plus [metadata] -type = quality -material = generic_cpe_ultimaker2_plus_0.4_mm -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_cpe +variant = 0.4 mm [values] cool_fan_speed_min = =cool_fan_speed * 0.8 @@ -23,4 +24,3 @@ speed_travel = 150 speed_wall = 40 top_bottom_thickness = 0.75 wall_thickness = 0.7 - diff --git a/resources/quality/ultimaker2_plus/um2p_cpe_0.4_high.inst.cfg b/resources/quality/ultimaker2_plus/um2p_cpe_0.4_high.inst.cfg index 685b7798fc..efd73655b1 100644 --- a/resources/quality/ultimaker2_plus/um2p_cpe_0.4_high.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_cpe_0.4_high.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_cpe_ultimaker2_plus_0.4_mm -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_cpe +variant = 0.4 mm [values] cool_fan_speed_min = =cool_fan_speed * 0.8 @@ -22,4 +23,3 @@ speed_print = 45 speed_wall = 30 top_bottom_thickness = 0.72 wall_thickness = 1.05 - diff --git a/resources/quality/ultimaker2_plus/um2p_cpe_0.4_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_cpe_0.4_normal.inst.cfg index aadb4195f3..3badb3f191 100644 --- a/resources/quality/ultimaker2_plus/um2p_cpe_0.4_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_cpe_0.4_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_cpe_ultimaker2_plus_0.4_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_cpe +variant = 0.4 mm [values] cool_fan_speed_min = =cool_fan_speed * 0.8 @@ -22,4 +23,3 @@ speed_print = 45 speed_wall = 30 top_bottom_thickness = 0.8 wall_thickness = 1.05 - diff --git a/resources/quality/ultimaker2_plus/um2p_cpe_0.6_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_cpe_0.6_normal.inst.cfg index 332033368f..727d68eede 100644 --- a/resources/quality/ultimaker2_plus/um2p_cpe_0.6_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_cpe_0.6_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_cpe_ultimaker2_plus_0.6_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_cpe +variant = 0.6 mm [values] cool_fan_speed_min = =cool_fan_speed * 0.8 @@ -21,4 +22,3 @@ speed_layer_0 = =round(speed_print * 30 / 40) speed_print = 40 top_bottom_thickness = 1.2 wall_thickness = 1.59 - diff --git a/resources/quality/ultimaker2_plus/um2p_cpe_0.8_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_cpe_0.8_normal.inst.cfg index e4fcae8aa1..1460d69b7a 100644 --- a/resources/quality/ultimaker2_plus/um2p_cpe_0.8_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_cpe_0.8_normal.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker2_plus [metadata] -type = quality -material = generic_cpe_ultimaker2_plus_0.8_mm -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_cpe +variant = 0.8 mm [values] cool_fan_speed_min = =cool_fan_speed * 0.8 @@ -21,4 +22,3 @@ speed_layer_0 = =round(speed_print * 30 / 40) speed_print = 40 top_bottom_thickness = 1.2 wall_thickness = 2.1 - diff --git a/resources/quality/ultimaker2_plus/um2p_cpep_0.4_draft.inst.cfg b/resources/quality/ultimaker2_plus/um2p_cpep_0.4_draft.inst.cfg index 55af936a89..be33739e72 100644 --- a/resources/quality/ultimaker2_plus/um2p_cpep_0.4_draft.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_cpep_0.4_draft.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker2_plus [metadata] -type = quality -material = generic_cpe_plus_ultimaker2_plus_0.4_mm -weight = -2 -quality_type = draft setting_version = 4 +type = quality +quality_type = draft +weight = -2 +material = generic_cpe_plus +variant = 0.4 mm [values] adhesion_type = raft @@ -40,4 +41,3 @@ support_pattern = lines support_z_distance = 0.26 top_bottom_thickness = 1.5 wall_thickness = 1.14 - diff --git a/resources/quality/ultimaker2_plus/um2p_cpep_0.4_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_cpep_0.4_normal.inst.cfg index eb0ca5e81f..58cf4bd0e3 100644 --- a/resources/quality/ultimaker2_plus/um2p_cpep_0.4_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_cpep_0.4_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_cpe_plus_ultimaker2_plus_0.4_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_cpe_plus +variant = 0.4 mm [values] adhesion_type = raft @@ -40,4 +41,3 @@ support_pattern = lines support_z_distance = 0.26 top_bottom_thickness = 1.5 wall_thickness = 1.14 - diff --git a/resources/quality/ultimaker2_plus/um2p_cpep_0.6_draft.inst.cfg b/resources/quality/ultimaker2_plus/um2p_cpep_0.6_draft.inst.cfg index b324d867bc..fe4f895611 100644 --- a/resources/quality/ultimaker2_plus/um2p_cpep_0.6_draft.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_cpep_0.6_draft.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker2_plus [metadata] -type = quality -material = generic_cpe_plus_ultimaker2_plus_0.6_mm -weight = -2 -quality_type = draft setting_version = 4 +type = quality +quality_type = draft +weight = -2 +material = generic_cpe_plus +variant = 0.6 mm [values] adhesion_type = raft @@ -44,4 +45,3 @@ support_xy_distance = 0.6 support_z_distance = 0.22 top_bottom_thickness = 0.75 wall_thickness = 1.14 - diff --git a/resources/quality/ultimaker2_plus/um2p_cpep_0.6_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_cpep_0.6_normal.inst.cfg index c8c7576d30..bcc507a3d9 100644 --- a/resources/quality/ultimaker2_plus/um2p_cpep_0.6_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_cpep_0.6_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_cpe_plus_ultimaker2_plus_0.6_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_cpe_plus +variant = 0.6 mm [values] adhesion_type = raft @@ -44,4 +45,3 @@ support_xy_distance = 0.6 support_z_distance = 0.22 top_bottom_thickness = 0.75 wall_thickness = 1.14 - diff --git a/resources/quality/ultimaker2_plus/um2p_cpep_0.8_draft.inst.cfg b/resources/quality/ultimaker2_plus/um2p_cpep_0.8_draft.inst.cfg index 28353f729d..c27d90ead8 100644 --- a/resources/quality/ultimaker2_plus/um2p_cpep_0.8_draft.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_cpep_0.8_draft.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker2_plus [metadata] -type = quality -material = generic_cpe_plus_ultimaker2_plus_0.8_mm -weight = -2 -quality_type = draft setting_version = 4 +type = quality +quality_type = draft +weight = -2 +material = generic_cpe_plus +variant = 0.8 mm [values] adhesion_type = raft @@ -39,4 +40,3 @@ support_pattern = lines support_z_distance = 0.26 top_bottom_thickness = 1.2 wall_thickness = 2.1 - diff --git a/resources/quality/ultimaker2_plus/um2p_cpep_0.8_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_cpep_0.8_normal.inst.cfg index f74db21b91..7eb8b1fd72 100644 --- a/resources/quality/ultimaker2_plus/um2p_cpep_0.8_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_cpep_0.8_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_cpe_plus_ultimaker2_plus_0.8_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_cpe_plus +variant = 0.8 mm [values] adhesion_type = raft @@ -39,4 +40,3 @@ support_pattern = lines support_z_distance = 0.26 top_bottom_thickness = 1.2 wall_thickness = 2.1 - diff --git a/resources/quality/ultimaker2_plus/um2p_nylon_0.25_high.inst.cfg b/resources/quality/ultimaker2_plus/um2p_nylon_0.25_high.inst.cfg index b8924423e2..33041f89ae 100644 --- a/resources/quality/ultimaker2_plus/um2p_nylon_0.25_high.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_nylon_0.25_high.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_nylon_ultimaker2_plus_0.25_mm -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_nylon +variant = 0.25 mm [values] adhesion_type = raft @@ -41,4 +42,3 @@ support_xy_distance = 0.6 support_z_distance = =layer_height * 2 top_bottom_thickness = 1.2 wall_thickness = 1 - diff --git a/resources/quality/ultimaker2_plus/um2p_nylon_0.25_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_nylon_0.25_normal.inst.cfg index 323fa51a8d..88974491cb 100644 --- a/resources/quality/ultimaker2_plus/um2p_nylon_0.25_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_nylon_0.25_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_nylon_ultimaker2_plus_0.25_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_nylon +variant = 0.25 mm [values] adhesion_type = raft @@ -41,4 +42,3 @@ support_xy_distance = 0.6 support_z_distance = =layer_height * 2 top_bottom_thickness = 1.2 wall_thickness = 1 - diff --git a/resources/quality/ultimaker2_plus/um2p_nylon_0.4_fast.inst.cfg b/resources/quality/ultimaker2_plus/um2p_nylon_0.4_fast.inst.cfg index 7628cd0be1..832fa12bc9 100644 --- a/resources/quality/ultimaker2_plus/um2p_nylon_0.4_fast.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_nylon_0.4_fast.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker2_plus [metadata] -type = quality -material = generic_nylon_ultimaker2_plus_0.4_mm -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_nylon +variant = 0.4 mm [values] adhesion_type = raft @@ -40,4 +41,3 @@ support_xy_distance = 0.6 support_z_distance = =layer_height * 2 top_bottom_thickness = 0.75 wall_thickness = 1.06 - diff --git a/resources/quality/ultimaker2_plus/um2p_nylon_0.4_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_nylon_0.4_normal.inst.cfg index a97a4c4e8f..c12573691e 100644 --- a/resources/quality/ultimaker2_plus/um2p_nylon_0.4_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_nylon_0.4_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_nylon_ultimaker2_plus_0.4_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_nylon +variant = 0.4 mm [values] adhesion_type = raft @@ -39,4 +40,3 @@ support_xy_distance = 0.6 support_z_distance = =layer_height * 2 top_bottom_thickness = 0.75 wall_thickness = 1.06 - diff --git a/resources/quality/ultimaker2_plus/um2p_nylon_0.6_fast.inst.cfg b/resources/quality/ultimaker2_plus/um2p_nylon_0.6_fast.inst.cfg index 0cd7bbdbfd..eaa4f86e23 100644 --- a/resources/quality/ultimaker2_plus/um2p_nylon_0.6_fast.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_nylon_0.6_fast.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker2_plus [metadata] -type = quality -material = generic_nylon_ultimaker2_plus_0.6_mm -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_nylon +variant = 0.6 mm [values] adhesion_type = raft @@ -45,4 +46,3 @@ support_xy_distance = 0.7 support_z_distance = =layer_height * 2 top_bottom_thickness = 1.2 wall_thickness = 1.2 - diff --git a/resources/quality/ultimaker2_plus/um2p_nylon_0.6_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_nylon_0.6_normal.inst.cfg index d5e0025913..5e3db4db22 100644 --- a/resources/quality/ultimaker2_plus/um2p_nylon_0.6_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_nylon_0.6_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_nylon_ultimaker2_plus_0.6_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_nylon +variant = 0.6 mm [values] adhesion_type = raft @@ -43,4 +44,3 @@ support_xy_distance = 0.7 support_z_distance = =layer_height * 2 top_bottom_thickness = 1.2 wall_thickness = 1.2 - diff --git a/resources/quality/ultimaker2_plus/um2p_nylon_0.8_draft.inst.cfg b/resources/quality/ultimaker2_plus/um2p_nylon_0.8_draft.inst.cfg index f653a90f95..38a71c9109 100644 --- a/resources/quality/ultimaker2_plus/um2p_nylon_0.8_draft.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_nylon_0.8_draft.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker2_plus [metadata] -type = quality -material = generic_nylon_ultimaker2_plus_0.8_mm -weight = -2 -quality_type = draft setting_version = 4 +type = quality +quality_type = draft +weight = -2 +material = generic_nylon +variant = 0.8 mm [values] adhesion_type = raft @@ -44,4 +45,3 @@ support_xy_distance = 0.75 support_z_distance = =layer_height * 2 top_bottom_thickness = 1.2 wall_thickness = 2.4 - diff --git a/resources/quality/ultimaker2_plus/um2p_nylon_0.8_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_nylon_0.8_normal.inst.cfg index 144c8e74ac..9d20a6d91f 100644 --- a/resources/quality/ultimaker2_plus/um2p_nylon_0.8_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_nylon_0.8_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_nylon_ultimaker2_plus_0.8_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_nylon +variant = 0.8 mm [values] adhesion_type = raft @@ -44,4 +45,3 @@ support_xy_distance = 0.75 support_z_distance = =layer_height * 2 top_bottom_thickness = 1.2 wall_thickness = 2.4 - diff --git a/resources/quality/ultimaker2_plus/um2p_pc_0.25_high.inst.cfg b/resources/quality/ultimaker2_plus/um2p_pc_0.25_high.inst.cfg index d38f2af4d3..7829d7b7b9 100644 --- a/resources/quality/ultimaker2_plus/um2p_pc_0.25_high.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_pc_0.25_high.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_pc_ultimaker2_plus_0.25_mm -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_pc +variant = 0.25 mm [values] adhesion_type = raft @@ -35,4 +36,3 @@ support_infill_rate = 20 support_pattern = lines support_z_distance = 0.19 wall_thickness = 0.88 - diff --git a/resources/quality/ultimaker2_plus/um2p_pc_0.25_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_pc_0.25_normal.inst.cfg index aa176f67a2..168a308916 100644 --- a/resources/quality/ultimaker2_plus/um2p_pc_0.25_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_pc_0.25_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_pc_ultimaker2_plus_0.25_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_pc +variant = 0.25 mm [values] adhesion_type = raft @@ -35,4 +36,3 @@ support_infill_rate = 20 support_pattern = lines support_z_distance = 0.19 wall_thickness = 0.88 - diff --git a/resources/quality/ultimaker2_plus/um2p_pc_0.4_fast.inst.cfg b/resources/quality/ultimaker2_plus/um2p_pc_0.4_fast.inst.cfg index 0408ead05e..46a349d81f 100644 --- a/resources/quality/ultimaker2_plus/um2p_pc_0.4_fast.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_pc_0.4_fast.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker2_plus [metadata] -type = quality -material = generic_pc_ultimaker2_plus_0.4_mm -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_pc +variant = 0.4 mm [values] adhesion_type = raft @@ -36,4 +37,3 @@ support_infill_rate = 20 support_pattern = lines support_z_distance = 0.19 wall_thickness = 1.2 - diff --git a/resources/quality/ultimaker2_plus/um2p_pc_0.4_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_pc_0.4_normal.inst.cfg index ed430f10c0..0c2450f512 100644 --- a/resources/quality/ultimaker2_plus/um2p_pc_0.4_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_pc_0.4_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_pc_ultimaker2_plus_0.4_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_pc +variant = 0.4 mm [values] adhesion_type = raft @@ -36,4 +37,3 @@ support_infill_rate = 20 support_pattern = lines support_z_distance = 0.19 wall_thickness = 1.2 - diff --git a/resources/quality/ultimaker2_plus/um2p_pc_0.6_fast.inst.cfg b/resources/quality/ultimaker2_plus/um2p_pc_0.6_fast.inst.cfg index b6c3a66c0b..68528a0209 100644 --- a/resources/quality/ultimaker2_plus/um2p_pc_0.6_fast.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_pc_0.6_fast.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker2_plus [metadata] -type = quality -material = generic_pc_ultimaker2_plus_0.6_mm -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_pc +variant = 0.6 mm [values] adhesion_type = raft @@ -42,4 +43,3 @@ support_pattern = lines support_z_distance = 0.21 top_bottom_thickness = 0.75 wall_thickness = 1.06 - diff --git a/resources/quality/ultimaker2_plus/um2p_pc_0.6_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_pc_0.6_normal.inst.cfg index 0dfb533f56..a92110a149 100644 --- a/resources/quality/ultimaker2_plus/um2p_pc_0.6_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_pc_0.6_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_pc_ultimaker2_plus_0.6_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_pc +variant = 0.6 mm [values] adhesion_type = raft @@ -42,4 +43,3 @@ support_pattern = lines support_z_distance = 0.21 top_bottom_thickness = 0.75 wall_thickness = 1.06 - diff --git a/resources/quality/ultimaker2_plus/um2p_pc_0.8_draft.inst.cfg b/resources/quality/ultimaker2_plus/um2p_pc_0.8_draft.inst.cfg index 3eee23006f..8c8bff3846 100644 --- a/resources/quality/ultimaker2_plus/um2p_pc_0.8_draft.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_pc_0.8_draft.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker2_plus [metadata] -type = quality -material = generic_pc_ultimaker2_plus_0.8_mm -weight = -2 -quality_type = draft setting_version = 4 +type = quality +quality_type = draft +weight = -2 +material = generic_pc +variant = 0.8 mm [values] adhesion_type = raft @@ -36,4 +37,3 @@ support_pattern = lines support_z_distance = 0.26 top_bottom_thickness = 2.0 wall_thickness = 2.1 - diff --git a/resources/quality/ultimaker2_plus/um2p_pc_0.8_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_pc_0.8_normal.inst.cfg index 40da82e6bf..db83d5181f 100644 --- a/resources/quality/ultimaker2_plus/um2p_pc_0.8_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_pc_0.8_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_pc_ultimaker2_plus_0.8_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_pc +variant = 0.8 mm [values] adhesion_type = raft @@ -36,4 +37,3 @@ support_pattern = lines support_z_distance = 0.26 top_bottom_thickness = 1.2 wall_thickness = 2.1 - diff --git a/resources/quality/ultimaker2_plus/um2p_pp_0.4_fast.inst.cfg b/resources/quality/ultimaker2_plus/um2p_pp_0.4_fast.inst.cfg index 6f4e366209..b7474044f3 100644 --- a/resources/quality/ultimaker2_plus/um2p_pp_0.4_fast.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_pp_0.4_fast.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker2_plus [metadata] -type = quality -material = generic_pp_ultimaker2_plus_0.4_mm -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_pp +variant = 0.4 mm [values] acceleration_enabled = True @@ -68,4 +69,3 @@ travel_avoid_distance = 3 wall_0_inset = 0 wall_line_width_x = =round(line_width * 0.38 / 0.38, 2) wall_thickness = 0.76 - diff --git a/resources/quality/ultimaker2_plus/um2p_pp_0.4_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_pp_0.4_normal.inst.cfg index c7224f475f..f6d2c38161 100644 --- a/resources/quality/ultimaker2_plus/um2p_pp_0.4_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_pp_0.4_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_pp_ultimaker2_plus_0.4_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_pp +variant = 0.4 mm [values] acceleration_enabled = True @@ -67,4 +68,3 @@ travel_avoid_distance = 3 wall_0_inset = 0 wall_line_width_x = =round(line_width * 0.38 / 0.38, 2) wall_thickness = 0.76 - diff --git a/resources/quality/ultimaker2_plus/um2p_pp_0.6_draft.inst.cfg b/resources/quality/ultimaker2_plus/um2p_pp_0.6_draft.inst.cfg index ef808a81d0..99fdf8346c 100644 --- a/resources/quality/ultimaker2_plus/um2p_pp_0.6_draft.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_pp_0.6_draft.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker2_plus [metadata] -type = quality -material = generic_pp_ultimaker2_plus_0.6_mm -weight = -2 -quality_type = draft setting_version = 4 +type = quality +quality_type = draft +weight = -2 +material = generic_pp +variant = 0.6 mm [values] acceleration_enabled = True @@ -69,4 +70,3 @@ travel_avoid_distance = 3 wall_0_inset = 0 wall_line_width_x = =round(line_width * 0.57 / 0.57, 2) wall_thickness = 1.14 - diff --git a/resources/quality/ultimaker2_plus/um2p_pp_0.6_fast.inst.cfg b/resources/quality/ultimaker2_plus/um2p_pp_0.6_fast.inst.cfg index c3da178405..7a9ec8e4e3 100644 --- a/resources/quality/ultimaker2_plus/um2p_pp_0.6_fast.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_pp_0.6_fast.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker2_plus [metadata] -type = quality -material = generic_pp_ultimaker2_plus_0.6_mm -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_pp +variant = 0.6 mm [values] acceleration_enabled = True @@ -69,4 +70,3 @@ travel_avoid_distance = 3 wall_0_inset = 0 wall_line_width_x = =round(line_width * 0.57 / 0.57, 2) wall_thickness = 1.14 - diff --git a/resources/quality/ultimaker2_plus/um2p_pp_0.8_draft.inst.cfg b/resources/quality/ultimaker2_plus/um2p_pp_0.8_draft.inst.cfg index 063097845e..071c50c05b 100644 --- a/resources/quality/ultimaker2_plus/um2p_pp_0.8_draft.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_pp_0.8_draft.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker2_plus [metadata] -type = quality -material = generic_pp_ultimaker2_plus_0.8_mm -weight = -2 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -2 +material = generic_pp +variant = 0.8 mm [values] acceleration_enabled = True @@ -69,4 +70,3 @@ travel_avoid_distance = 3 wall_0_inset = 0 wall_line_width_x = =round(line_width * 0.76 / 0.76, 2) wall_thickness = 1.52 - diff --git a/resources/quality/ultimaker2_plus/um2p_pp_0.8_verydraft.inst.cfg b/resources/quality/ultimaker2_plus/um2p_pp_0.8_verydraft.inst.cfg index 5014f9d66d..cbea59a879 100644 --- a/resources/quality/ultimaker2_plus/um2p_pp_0.8_verydraft.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_pp_0.8_verydraft.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fast definition = ultimaker2_plus [metadata] -type = quality -material = generic_pp_ultimaker2_plus_0.8_mm -weight = -3 -quality_type = draft setting_version = 4 +type = quality +quality_type = draft +weight = -3 +material = generic_pp +variant = 0.8 mm [values] acceleration_enabled = True @@ -69,4 +70,3 @@ travel_avoid_distance = 3 wall_0_inset = 0 wall_line_width_x = =round(line_width * 0.76 / 0.76, 2) wall_thickness = 1.52 - diff --git a/resources/quality/ultimaker2_plus/um2p_tpu_0.25_high.inst.cfg b/resources/quality/ultimaker2_plus/um2p_tpu_0.25_high.inst.cfg index b1cb56a543..2ad062bd31 100644 --- a/resources/quality/ultimaker2_plus/um2p_tpu_0.25_high.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_tpu_0.25_high.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_tpu_ultimaker2_plus_0.25_mm -weight = 1 -quality_type = high setting_version = 4 +type = quality +quality_type = high +weight = 1 +material = generic_tpu +variant = 0.25 mm [values] adhesion_type = brim @@ -40,4 +41,3 @@ support_xy_distance = 0.6 support_z_distance = =layer_height * 2 top_bottom_thickness = 1.2 wall_thickness = 0.88 - diff --git a/resources/quality/ultimaker2_plus/um2p_tpu_0.4_normal.inst.cfg b/resources/quality/ultimaker2_plus/um2p_tpu_0.4_normal.inst.cfg index 80cc92fe64..56ce55ee96 100644 --- a/resources/quality/ultimaker2_plus/um2p_tpu_0.4_normal.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_tpu_0.4_normal.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker2_plus [metadata] -type = quality -material = generic_tpu_ultimaker2_plus_0.4_mm -weight = 0 -quality_type = normal setting_version = 4 +type = quality +quality_type = normal +weight = 0 +material = generic_tpu +variant = 0.4 mm [values] adhesion_type = brim @@ -37,4 +38,3 @@ support_xy_distance = 0.65 support_z_distance = =layer_height * 2 top_bottom_thickness = 1.2 wall_thickness = 1.05 - diff --git a/resources/quality/ultimaker2_plus/um2p_tpu_0.6_fast.inst.cfg b/resources/quality/ultimaker2_plus/um2p_tpu_0.6_fast.inst.cfg index 9796adada9..6bcc5fa31f 100644 --- a/resources/quality/ultimaker2_plus/um2p_tpu_0.6_fast.inst.cfg +++ b/resources/quality/ultimaker2_plus/um2p_tpu_0.6_fast.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker2_plus [metadata] -type = quality -material = generic_tpu_ultimaker2_plus_0.6_mm -weight = -1 -quality_type = fast setting_version = 4 +type = quality +quality_type = fast +weight = -1 +material = generic_tpu +variant = 0.6 mm [values] adhesion_type = brim @@ -42,4 +43,3 @@ support_xy_distance = 0.7 support_z_distance = =layer_height * 2 top_bottom_thickness = 1.2 wall_thickness = 1.14 - diff --git a/resources/quality/ultimaker3/um3_aa0.25_ABS_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.25_ABS_Normal_Quality.inst.cfg index fc7d4d12d2..0b100d8717 100644 --- a/resources/quality/ultimaker3/um3_aa0.25_ABS_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.25_ABS_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_abs_ultimaker3_AA_0.25 weight = 0 -setting_version = 4 +material = generic_abs +variant = AA 0.25 [values] cool_fan_speed = 40 @@ -20,4 +21,3 @@ prime_tower_wall_thickness = 0.9 retraction_prime_speed = 25 speed_topbottom = =math.ceil(speed_print * 30 / 55) wall_thickness = 0.92 - diff --git a/resources/quality/ultimaker3/um3_aa0.25_CPE_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.25_CPE_Normal_Quality.inst.cfg index 83e0c549c4..77494d6339 100644 --- a/resources/quality/ultimaker3/um3_aa0.25_CPE_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.25_CPE_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_cpe_ultimaker3_AA_0.25 weight = 0 -setting_version = 4 +material = generic_cpe +variant = AA 0.25 [values] prime_tower_size = 12 @@ -18,4 +19,3 @@ speed_infill = 40 speed_topbottom = =math.ceil(speed_print * 30 / 55) top_bottom_thickness = 0.8 wall_thickness = 0.92 - diff --git a/resources/quality/ultimaker3/um3_aa0.25_Nylon_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.25_Nylon_Normal_Quality.inst.cfg index 58ddc32101..0187084ff8 100644 --- a/resources/quality/ultimaker3/um3_aa0.25_Nylon_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.25_Nylon_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_nylon_ultimaker3_AA_0.25 weight = 0 -setting_version = 4 +material = generic_nylon +variant = AA 0.25 [values] cool_min_layer_time_fan_speed_max = 20 @@ -32,4 +33,3 @@ switch_extruder_prime_speed = 30 switch_extruder_retraction_amount = 30 switch_extruder_retraction_speeds = 40 wall_line_width_x = =wall_line_width - diff --git a/resources/quality/ultimaker3/um3_aa0.25_PC_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.25_PC_Normal_Quality.inst.cfg index 7c9fa32949..0070419a4e 100644 --- a/resources/quality/ultimaker3/um3_aa0.25_PC_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.25_PC_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine - Experimental definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pc_ultimaker3_AA_0.25 weight = 0 -setting_version = 4 +material = generic_pc +variant = AA 0.25 [values] acceleration_enabled = True @@ -53,4 +54,3 @@ switch_extruder_retraction_speeds = 35 wall_0_inset = 0 wall_line_width_x = =line_width wall_thickness = 1.2 - diff --git a/resources/quality/ultimaker3/um3_aa0.25_PLA_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.25_PLA_Normal_Quality.inst.cfg index 1bee4b8f18..b2347f1902 100644 --- a/resources/quality/ultimaker3/um3_aa0.25_PLA_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.25_PLA_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pla_ultimaker3_AA_0.25 weight = 0 -setting_version = 4 +material = generic_pla +variant = AA 0.25 [values] brim_width = 8 @@ -33,4 +34,3 @@ travel_avoid_distance = 0.4 wall_0_inset = 0.015 wall_0_wipe_dist = 0.25 wall_thickness = 0.7 - diff --git a/resources/quality/ultimaker3/um3_aa0.25_PP_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.25_PP_Normal_Quality.inst.cfg index ccc558530e..732289dedf 100644 --- a/resources/quality/ultimaker3/um3_aa0.25_PP_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.25_PP_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine - Experimental definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pp_ultimaker3_AA_0.25 weight = 0 -setting_version = 4 +material = generic_pp +variant = AA 0.25 [values] acceleration_enabled = True diff --git a/resources/quality/ultimaker3/um3_aa0.4_ABS_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_ABS_Draft_Print.inst.cfg index 13dca72c27..a5cc4aaa0c 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_ABS_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_ABS_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_abs_ultimaker3_AA_0.4 weight = -2 -setting_version = 4 +material = generic_abs +variant = AA 0.4 [values] machine_nozzle_cool_down_speed = 0.85 @@ -24,4 +25,3 @@ speed_topbottom = =math.ceil(speed_print * 35 / 60) speed_wall = =math.ceil(speed_print * 45 / 60) speed_wall_0 = =math.ceil(speed_wall * 35 / 45) wall_thickness = 1 - diff --git a/resources/quality/ultimaker3/um3_aa0.4_ABS_Fast_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_ABS_Fast_Print.inst.cfg index 10fa10c726..ba80ad588e 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_ABS_Fast_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_ABS_Fast_Print.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_abs_ultimaker3_AA_0.4 weight = -1 -setting_version = 4 +material = generic_abs +variant = AA 0.4 [values] cool_min_speed = 7 @@ -24,4 +25,3 @@ speed_layer_0 = 20 speed_topbottom = =math.ceil(speed_print * 30 / 60) speed_wall = =math.ceil(speed_print * 40 / 60) speed_wall_0 = =math.ceil(speed_wall * 30 / 40) - diff --git a/resources/quality/ultimaker3/um3_aa0.4_ABS_High_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_ABS_High_Quality.inst.cfg index 02f2327468..c84ef6dabe 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_ABS_High_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_ABS_High_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_abs_ultimaker3_AA_0.4 weight = 1 -setting_version = 4 +material = generic_abs +variant = AA 0.4 [values] cool_min_speed = 12 @@ -23,4 +24,3 @@ speed_print = 50 speed_layer_0 = 20 speed_topbottom = =math.ceil(speed_print * 30 / 50) speed_wall = =math.ceil(speed_print * 30 / 50) - diff --git a/resources/quality/ultimaker3/um3_aa0.4_ABS_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_ABS_Normal_Quality.inst.cfg index fccb6a35f5..f3c9f6a892 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_ABS_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_ABS_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_abs_ultimaker3_AA_0.4 weight = 0 -setting_version = 4 +material = generic_abs +variant = AA 0.4 [values] machine_nozzle_cool_down_speed = 0.85 @@ -21,4 +22,3 @@ speed_print = 55 speed_layer_0 = 20 speed_topbottom = =math.ceil(speed_print * 30 / 55) speed_wall = =math.ceil(speed_print * 30 / 55) - diff --git a/resources/quality/ultimaker3/um3_aa0.4_BAM_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_BAM_Draft_Print.inst.cfg index f3c6ae8387..fbc0c599ef 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_BAM_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_BAM_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_bam_ultimaker3_AA_0.4 weight = -2 -setting_version = 4 +material = generic_bam +variant = AA 0.4 [values] cool_fan_full_at_height = =layer_height_0 + 2 * layer_height diff --git a/resources/quality/ultimaker3/um3_aa0.4_BAM_Fast_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_BAM_Fast_Print.inst.cfg index e027477595..d6f64cb056 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_BAM_Fast_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_BAM_Fast_Print.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_bam_ultimaker3_AA_0.4 weight = -1 -setting_version = 4 +material = generic_bam +variant = AA 0.4 [values] cool_fan_full_at_height = =layer_height_0 + 2 * layer_height diff --git a/resources/quality/ultimaker3/um3_aa0.4_BAM_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_BAM_Normal_Quality.inst.cfg index 3ced3a0417..53fb52bff6 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_BAM_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_BAM_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_bam_ultimaker3_AA_0.4 weight = 0 -setting_version = 4 +material = generic_bam +variant = AA 0.4 [values] cool_fan_full_at_height = =layer_height_0 + 2 * layer_height diff --git a/resources/quality/ultimaker3/um3_aa0.4_CPEP_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_CPEP_Draft_Print.inst.cfg index dfdb1ca8a7..dd089294de 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_CPEP_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_CPEP_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_cpe_plus_ultimaker3_AA_0.4 weight = -2 -setting_version = 4 +material = generic_cpe_plus +variant = AA 0.4 [values] acceleration_enabled = True diff --git a/resources/quality/ultimaker3/um3_aa0.4_CPEP_Fast_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_CPEP_Fast_Print.inst.cfg index 93b371a627..373107d767 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_CPEP_Fast_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_CPEP_Fast_Print.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_cpe_plus_ultimaker3_AA_0.4 weight = -1 -setting_version = 4 +material = generic_cpe_plus +variant = AA 0.4 [values] acceleration_enabled = True diff --git a/resources/quality/ultimaker3/um3_aa0.4_CPEP_High_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_CPEP_High_Quality.inst.cfg index 93647f9f44..67544db97b 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_CPEP_High_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_CPEP_High_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_cpe_plus_ultimaker3_AA_0.4 weight = 1 -setting_version = 4 +material = generic_cpe_plus +variant = AA 0.4 [values] acceleration_enabled = True diff --git a/resources/quality/ultimaker3/um3_aa0.4_CPEP_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_CPEP_Normal_Quality.inst.cfg index 2886ef2229..183d05ce60 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_CPEP_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_CPEP_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_cpe_plus_ultimaker3_AA_0.4 weight = 0 -setting_version = 4 +material = generic_cpe_plus +variant = AA 0.4 [values] acceleration_enabled = True diff --git a/resources/quality/ultimaker3/um3_aa0.4_CPE_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_CPE_Draft_Print.inst.cfg index 5e3daf5a9e..74395628af 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_CPE_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_CPE_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_cpe_ultimaker3_AA_0.4 weight = -2 -setting_version = 4 +material = generic_cpe +variant = AA 0.4 [values] material_print_temperature = =default_material_print_temperature + 10 @@ -22,4 +23,3 @@ speed_topbottom = =math.ceil(speed_print * 35 / 60) speed_wall = =math.ceil(speed_print * 45 / 60) speed_wall_0 = =math.ceil(speed_wall * 35 / 45) wall_thickness = 1 - diff --git a/resources/quality/ultimaker3/um3_aa0.4_CPE_Fast_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_CPE_Fast_Print.inst.cfg index e48f83994d..dbcf7f3e42 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_CPE_Fast_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_CPE_Fast_Print.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_cpe_ultimaker3_AA_0.4 weight = -1 -setting_version = 4 +material = generic_cpe +variant = AA 0.4 [values] cool_min_speed = 7 @@ -21,4 +22,3 @@ speed_layer_0 = 20 speed_topbottom = =math.ceil(speed_print * 30 / 60) speed_wall = =math.ceil(speed_print * 40 / 60) speed_wall_0 = =math.ceil(speed_wall * 30 / 40) - diff --git a/resources/quality/ultimaker3/um3_aa0.4_CPE_High_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_CPE_High_Quality.inst.cfg index fd0a8cd18d..89b5210631 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_CPE_High_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_CPE_High_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_cpe_ultimaker3_AA_0.4 weight = 1 -setting_version = 4 +material = generic_cpe +variant = AA 0.4 [values] cool_min_speed = 12 @@ -22,4 +23,3 @@ speed_print = 50 speed_layer_0 = 20 speed_topbottom = =math.ceil(speed_print * 30 / 50) speed_wall = =math.ceil(speed_print * 30 / 50) - diff --git a/resources/quality/ultimaker3/um3_aa0.4_CPE_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_CPE_Normal_Quality.inst.cfg index 56c997eb15..12927714ec 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_CPE_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_CPE_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_cpe_ultimaker3_AA_0.4 weight = 0 -setting_version = 4 +material = generic_cpe +variant = AA 0.4 [values] machine_nozzle_cool_down_speed = 0.85 @@ -20,4 +21,3 @@ speed_print = 55 speed_layer_0 = 20 speed_topbottom = =math.ceil(speed_print * 30 / 55) speed_wall = =math.ceil(speed_print * 30 / 55) - diff --git a/resources/quality/ultimaker3/um3_aa0.4_Nylon_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_Nylon_Draft_Print.inst.cfg index 15283a3242..ff938df8f8 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_Nylon_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_Nylon_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_nylon_ultimaker3_AA_0.4 weight = -2 -setting_version = 4 +material = generic_nylon +variant = AA 0.4 [values] adhesion_type = brim @@ -33,4 +34,3 @@ switch_extruder_prime_speed = 30 switch_extruder_retraction_amount = 30 switch_extruder_retraction_speeds = 40 wall_line_width_x = =wall_line_width - diff --git a/resources/quality/ultimaker3/um3_aa0.4_Nylon_Fast_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_Nylon_Fast_Print.inst.cfg index c063725e82..e9fd6df1e2 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_Nylon_Fast_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_Nylon_Fast_Print.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_nylon_ultimaker3_AA_0.4 weight = -1 -setting_version = 4 +material = generic_nylon +variant = AA 0.4 [values] adhesion_type = brim @@ -33,4 +34,3 @@ switch_extruder_prime_speed = 30 switch_extruder_retraction_amount = 30 switch_extruder_retraction_speeds = 40 wall_line_width_x = =wall_line_width - diff --git a/resources/quality/ultimaker3/um3_aa0.4_Nylon_High_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_Nylon_High_Quality.inst.cfg index 218e1e50e1..635cc573ea 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_Nylon_High_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_Nylon_High_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_nylon_ultimaker3_AA_0.4 weight = 1 -setting_version = 4 +material = generic_nylon +variant = AA 0.4 [values] adhesion_type = brim @@ -32,4 +33,3 @@ switch_extruder_prime_speed = 30 switch_extruder_retraction_amount = 30 switch_extruder_retraction_speeds = 40 wall_line_width_x = =wall_line_width - diff --git a/resources/quality/ultimaker3/um3_aa0.4_Nylon_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_Nylon_Normal_Quality.inst.cfg index 3b96939ac9..778ace19e4 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_Nylon_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_Nylon_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_nylon_ultimaker3_AA_0.4 weight = 0 -setting_version = 4 +material = generic_nylon +variant = AA 0.4 [values] adhesion_type = brim @@ -32,4 +33,3 @@ switch_extruder_prime_speed = 30 switch_extruder_retraction_amount = 30 switch_extruder_retraction_speeds = 40 wall_line_width_x = =wall_line_width - diff --git a/resources/quality/ultimaker3/um3_aa0.4_PC_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_PC_Draft_Print.inst.cfg index f8b4dd067c..437e4676b3 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_PC_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_PC_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_pc_ultimaker3_AA_0.4 weight = -2 -setting_version = 4 +material = generic_pc +variant = AA 0.4 [values] acceleration_enabled = True diff --git a/resources/quality/ultimaker3/um3_aa0.4_PC_Fast_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_PC_Fast_Print.inst.cfg index 1db3935180..320cf0a96f 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_PC_Fast_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_PC_Fast_Print.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_pc_ultimaker3_AA_0.4 weight = -1 -setting_version = 4 +material = generic_pc +variant = AA 0.4 [values] acceleration_enabled = True diff --git a/resources/quality/ultimaker3/um3_aa0.4_PC_High_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_PC_High_Quality.inst.cfg index 0f9e9b15b0..6d7e8f7976 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_PC_High_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_PC_High_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pc_ultimaker3_AA_0.4 weight = 1 -setting_version = 4 +material = generic_pc +variant = AA 0.4 [values] acceleration_enabled = True diff --git a/resources/quality/ultimaker3/um3_aa0.4_PC_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_PC_Normal_Quality.inst.cfg index 26a3136069..c18e9dbbd5 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_PC_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_PC_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pc_ultimaker3_AA_0.4 weight = 0 -setting_version = 4 +material = generic_pc +variant = AA 0.4 [values] acceleration_enabled = True diff --git a/resources/quality/ultimaker3/um3_aa0.4_PLA_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_PLA_Draft_Print.inst.cfg index a32d9268d3..24b7c51fbc 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_PLA_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_PLA_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_pla_ultimaker3_AA_0.4 weight = -2 -setting_version = 4 +material = generic_pla +variant = AA 0.4 [values] cool_fan_full_at_height = =layer_height_0 + 2 * layer_height @@ -26,4 +27,3 @@ speed_wall = =math.ceil(speed_print * 55 / 70) speed_wall_0 = =math.ceil(speed_wall * 45 / 50) top_bottom_thickness = 1 wall_thickness = 1 - diff --git a/resources/quality/ultimaker3/um3_aa0.4_PLA_Fast_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_PLA_Fast_Print.inst.cfg index 30b7d44d4e..6b3d8642e0 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_PLA_Fast_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_PLA_Fast_Print.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_pla_ultimaker3_AA_0.4 weight = -1 -setting_version = 4 +material = generic_pla +variant = AA 0.4 [values] cool_fan_full_at_height = =layer_height_0 + 2 * layer_height @@ -25,4 +26,3 @@ speed_wall = =math.ceil(speed_print * 40 / 80) speed_wall_0 = =math.ceil(speed_wall * 30 / 40) top_bottom_thickness = 1 wall_thickness = 1 - diff --git a/resources/quality/ultimaker3/um3_aa0.4_PLA_High_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_PLA_High_Quality.inst.cfg index da62ce2e3f..6009031e0c 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_PLA_High_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_PLA_High_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = high -material = generic_pla_ultimaker3_AA_0.4 weight = 1 -setting_version = 4 +material = generic_pla +variant = AA 0.4 [values] cool_fan_full_at_height = =layer_height_0 + 2 * layer_height @@ -27,4 +28,3 @@ speed_topbottom = =math.ceil(speed_print * 30 / 60) speed_wall = =math.ceil(speed_print * 30 / 60) top_bottom_thickness = 1 wall_thickness = 1 - diff --git a/resources/quality/ultimaker3/um3_aa0.4_PLA_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_PLA_Normal_Quality.inst.cfg index 04707735f5..3722134df6 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_PLA_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_PLA_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pla_ultimaker3_AA_0.4 weight = 0 -setting_version = 4 +material = generic_pla +variant = AA 0.4 [values] cool_fan_full_at_height = =layer_height_0 + 2 * layer_height @@ -23,4 +24,3 @@ skin_overlap = 10 speed_layer_0 = 20 top_bottom_thickness = 1 wall_thickness = 1 - diff --git a/resources/quality/ultimaker3/um3_aa0.4_PP_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_PP_Draft_Print.inst.cfg index 3fe25e563a..265e068598 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_PP_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_PP_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_pp_ultimaker3_AA_0.4 weight = -2 -setting_version = 4 +material = generic_pp +variant = AA 0.4 [values] acceleration_enabled = True @@ -63,4 +64,4 @@ switch_extruder_retraction_speeds = 35 travel_avoid_distance = 3 wall_0_inset = 0 wall_line_width_x = =line_width -wall_thickness = =line_width * 3 \ No newline at end of file +wall_thickness = =line_width * 3 diff --git a/resources/quality/ultimaker3/um3_aa0.4_PP_Fast_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_PP_Fast_Print.inst.cfg index 4c92c7a14b..7698c0a273 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_PP_Fast_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_PP_Fast_Print.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_pp_ultimaker3_AA_0.4 weight = -1 -setting_version = 4 +material = generic_pp +variant = AA 0.4 [values] acceleration_enabled = True @@ -63,4 +64,4 @@ top_bottom_thickness = 1.1 travel_avoid_distance = 3 wall_0_inset = 0 wall_line_width_x = =line_width -wall_thickness = =line_width * 3 \ No newline at end of file +wall_thickness = =line_width * 3 diff --git a/resources/quality/ultimaker3/um3_aa0.4_PP_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_PP_Normal_Quality.inst.cfg index db55956497..897ec993e7 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_PP_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_PP_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_pp_ultimaker3_AA_0.4 weight = 0 -setting_version = 4 +material = generic_pp +variant = AA 0.4 [values] acceleration_enabled = True @@ -62,4 +63,4 @@ top_bottom_thickness = 1 travel_avoid_distance = 3 wall_0_inset = 0 wall_line_width_x = =line_width -wall_thickness = =line_width * 3 \ No newline at end of file +wall_thickness = =line_width * 3 diff --git a/resources/quality/ultimaker3/um3_aa0.4_TPU_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_TPU_Draft_Print.inst.cfg index e2751a13ac..d3654cb3e0 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_TPU_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_TPU_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_tpu_ultimaker3_AA_0.4 weight = -2 -setting_version = 4 +material = generic_tpu +variant = AA 0.4 [values] acceleration_enabled = True @@ -62,4 +63,4 @@ top_bottom_thickness = 0.7 travel_avoid_distance = 1.5 wall_0_inset = 0 wall_line_width_x = =line_width -wall_thickness = 0.76 \ No newline at end of file +wall_thickness = 0.76 diff --git a/resources/quality/ultimaker3/um3_aa0.4_TPU_Fast_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_TPU_Fast_Print.inst.cfg index 13ff46cef4..3686fefdff 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_TPU_Fast_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_TPU_Fast_Print.inst.cfg @@ -4,11 +4,12 @@ name = Normal definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = fast -material = generic_tpu_ultimaker3_AA_0.4 weight = -1 -setting_version = 4 +material = generic_tpu +variant = AA 0.4 [values] acceleration_enabled = True @@ -63,4 +64,4 @@ top_bottom_thickness = 0.7 travel_avoid_distance = 1.5 wall_0_inset = 0 wall_line_width_x = =line_width -wall_thickness = 0.76 \ No newline at end of file +wall_thickness = 0.76 diff --git a/resources/quality/ultimaker3/um3_aa0.4_TPU_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_aa0.4_TPU_Normal_Quality.inst.cfg index 04454a9ff3..18d7a5275a 100644 --- a/resources/quality/ultimaker3/um3_aa0.4_TPU_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.4_TPU_Normal_Quality.inst.cfg @@ -4,11 +4,12 @@ name = Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -material = generic_tpu_ultimaker3_AA_0.4 weight = 0 -setting_version = 4 +material = generic_tpu +variant = AA 0.4 [values] acceleration_enabled = True @@ -60,4 +61,4 @@ top_bottom_thickness = 0.7 travel_avoid_distance = 1.5 wall_0_inset = 0 wall_line_width_x = =line_width -wall_thickness = 0.76 \ No newline at end of file +wall_thickness = 0.76 diff --git a/resources/quality/ultimaker3/um3_aa0.8_ABS_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_ABS_Draft_Print.inst.cfg index 7c16e6e8ee..78930b84e2 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_ABS_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_ABS_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_abs_ultimaker3_AA_0.8 weight = -2 -setting_version = 4 +material = generic_abs +variant = AA 0.8 [values] line_width = =machine_nozzle_size * 0.875 diff --git a/resources/quality/ultimaker3/um3_aa0.8_ABS_Superdraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_ABS_Superdraft_Print.inst.cfg index 728b4c868f..9470779bd4 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_ABS_Superdraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_ABS_Superdraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Sprint definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_abs_ultimaker3_AA_0.8 weight = -4 -setting_version = 4 +material = generic_abs +variant = AA 0.8 [values] layer_height = 0.4 diff --git a/resources/quality/ultimaker3/um3_aa0.8_ABS_Verydraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_ABS_Verydraft_Print.inst.cfg index 98ae70c568..d28e9b75b6 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_ABS_Verydraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_ABS_Verydraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_abs_ultimaker3_AA_0.8 weight = -3 -setting_version = 4 +material = generic_abs +variant = AA 0.8 [values] layer_height = 0.3 diff --git a/resources/quality/ultimaker3/um3_aa0.8_CPEP_Fast_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_CPEP_Fast_Print.inst.cfg index 0a05e9aafd..6f84174c5a 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_CPEP_Fast_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_CPEP_Fast_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast - Experimental definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_cpe_plus_ultimaker3_AA_0.8 weight = -2 -setting_version = 4 +material = generic_cpe_plus +variant = AA 0.8 [values] brim_width = 14 @@ -35,4 +36,4 @@ support_bottom_distance = =support_z_distance support_line_width = =round(line_width * 0.6 / 0.7, 2) support_z_distance = =layer_height top_bottom_thickness = 1.2 -travel_avoid_distance = 1.5 \ No newline at end of file +travel_avoid_distance = 1.5 diff --git a/resources/quality/ultimaker3/um3_aa0.8_CPEP_Superdraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_CPEP_Superdraft_Print.inst.cfg index 82efb6a57b..09e59ee8ca 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_CPEP_Superdraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_CPEP_Superdraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Sprint - Experimental definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_cpe_plus_ultimaker3_AA_0.8 weight = -4 -setting_version = 4 +material = generic_cpe_plus +variant = AA 0.8 [values] brim_width = 14 @@ -36,4 +37,4 @@ support_bottom_distance = =support_z_distance support_line_width = =round(line_width * 0.6 / 0.7, 2) support_z_distance = =layer_height top_bottom_thickness = 1.2 -travel_avoid_distance = 1.5 \ No newline at end of file +travel_avoid_distance = 1.5 diff --git a/resources/quality/ultimaker3/um3_aa0.8_CPEP_Verydraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_CPEP_Verydraft_Print.inst.cfg index ff375b6e49..7b7d211c21 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_CPEP_Verydraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_CPEP_Verydraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fast - Experimental definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_cpe_plus_ultimaker3_AA_0.8 weight = -3 -setting_version = 4 +material = generic_cpe_plus +variant = AA 0.8 [values] brim_width = 14 @@ -36,4 +37,4 @@ support_bottom_distance = =support_z_distance support_line_width = =round(line_width * 0.6 / 0.7, 2) support_z_distance = =layer_height top_bottom_thickness = 1.2 -travel_avoid_distance = 1.5 \ No newline at end of file +travel_avoid_distance = 1.5 diff --git a/resources/quality/ultimaker3/um3_aa0.8_CPE_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_CPE_Draft_Print.inst.cfg index b4d7035b8d..ecce20d9a2 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_CPE_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_CPE_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_cpe_ultimaker3_AA_0.8 weight = -2 -setting_version = 4 +material = generic_cpe +variant = AA 0.8 [values] brim_width = 15 diff --git a/resources/quality/ultimaker3/um3_aa0.8_CPE_Superdraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_CPE_Superdraft_Print.inst.cfg index b5ccc38534..a14d4601ee 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_CPE_Superdraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_CPE_Superdraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Sprint definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_cpe_ultimaker3_AA_0.8 weight = -4 -setting_version = 4 +material = generic_cpe +variant = AA 0.8 [values] brim_width = 15 diff --git a/resources/quality/ultimaker3/um3_aa0.8_CPE_Verydraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_CPE_Verydraft_Print.inst.cfg index 33ae223526..7a6cbc7251 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_CPE_Verydraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_CPE_Verydraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_cpe_ultimaker3_AA_0.8 weight = -3 -setting_version = 4 +material = generic_cpe +variant = AA 0.8 [values] brim_width = 15 diff --git a/resources/quality/ultimaker3/um3_aa0.8_Nylon_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_Nylon_Draft_Print.inst.cfg index 43ec77453c..9254894df3 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_Nylon_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_Nylon_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_nylon_ultimaker3_AA_0.8 weight = -2 -setting_version = 4 +material = generic_nylon +variant = AA 0.8 [values] brim_width = 5.6 diff --git a/resources/quality/ultimaker3/um3_aa0.8_Nylon_Superdraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_Nylon_Superdraft_Print.inst.cfg index 5b8626e8c2..f6e2787e65 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_Nylon_Superdraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_Nylon_Superdraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Sprint definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_nylon_ultimaker3_AA_0.8 weight = -4 -setting_version = 4 +material = generic_nylon +variant = AA 0.8 [values] brim_width = 5.6 diff --git a/resources/quality/ultimaker3/um3_aa0.8_Nylon_Verydraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_Nylon_Verydraft_Print.inst.cfg index 0b115ada4b..794ccd006d 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_Nylon_Verydraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_Nylon_Verydraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_nylon_ultimaker3_AA_0.8 weight = -3 -setting_version = 4 +material = generic_nylon +variant = AA 0.8 [values] brim_width = 5.6 diff --git a/resources/quality/ultimaker3/um3_aa0.8_PC_Fast_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_PC_Fast_Print.inst.cfg index 0b666d2e0b..c0ae3852dc 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_PC_Fast_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_PC_Fast_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast - Experimental definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_pc_ultimaker3_AA_0.8 weight = 0 -setting_version = 4 +material = generic_pc +variant = AA 0.8 [values] brim_width = 14 @@ -28,4 +29,4 @@ speed_topbottom = =math.ceil(speed_print * 25 / 50) speed_wall = =math.ceil(speed_print * 40 / 50) speed_wall_0 = =math.ceil(speed_wall * 30 / 40) support_line_width = =round(line_width * 0.6 / 0.7, 2) -travel_avoid_distance = 3 \ No newline at end of file +travel_avoid_distance = 3 diff --git a/resources/quality/ultimaker3/um3_aa0.8_PC_Superdraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_PC_Superdraft_Print.inst.cfg index de212df4af..ca58342847 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_PC_Superdraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_PC_Superdraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Sprint - Experimental definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_pc_ultimaker3_AA_0.8 weight = -2 -setting_version = 4 +material = generic_pc +variant = AA 0.8 [values] brim_width = 14 @@ -28,4 +29,4 @@ speed_topbottom = =math.ceil(speed_print * 25 / 50) speed_wall = =math.ceil(speed_print * 40 / 50) speed_wall_0 = =math.ceil(speed_wall * 30 / 40) support_line_width = =round(line_width * 0.6 / 0.7, 2) -travel_avoid_distance = 3 \ No newline at end of file +travel_avoid_distance = 3 diff --git a/resources/quality/ultimaker3/um3_aa0.8_PC_Verydraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_PC_Verydraft_Print.inst.cfg index 3e0c669eeb..6c69aa8ff5 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_PC_Verydraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_PC_Verydraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fast - Experimental definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_pc_ultimaker3_AA_0.8 weight = -1 -setting_version = 4 +material = generic_pc +variant = AA 0.8 [values] brim_width = 14 @@ -29,4 +30,4 @@ speed_topbottom = =math.ceil(speed_print * 25 / 50) speed_wall = =math.ceil(speed_print * 40 / 50) speed_wall_0 = =math.ceil(speed_wall * 30 / 40) support_line_width = =round(line_width * 0.6 / 0.7, 2) -travel_avoid_distance = 3 \ No newline at end of file +travel_avoid_distance = 3 diff --git a/resources/quality/ultimaker3/um3_aa0.8_PLA_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_PLA_Draft_Print.inst.cfg index 8b3c3e56c6..c03cc1ad5f 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_PLA_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_PLA_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_pla_ultimaker3_AA_0.8 weight = -2 -setting_version = 4 +material = generic_pla +variant = AA 0.8 [values] cool_fan_full_at_height = =layer_height_0 + 2 * layer_height diff --git a/resources/quality/ultimaker3/um3_aa0.8_PLA_Superdraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_PLA_Superdraft_Print.inst.cfg index 2fe8f7c6f9..b1252a3662 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_PLA_Superdraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_PLA_Superdraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Sprint definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_pla_ultimaker3_AA_0.8 weight = -4 -setting_version = 4 +material = generic_pla +variant = AA 0.8 [values] cool_fan_full_at_height = =layer_height_0 + 2 * layer_height diff --git a/resources/quality/ultimaker3/um3_aa0.8_PLA_Verydraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_PLA_Verydraft_Print.inst.cfg index 9072e0c60f..191a7a4b1d 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_PLA_Verydraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_PLA_Verydraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_pla_ultimaker3_AA_0.8 weight = -3 -setting_version = 4 +material = generic_pla +variant = AA 0.8 [values] cool_fan_full_at_height = =layer_height_0 + 2 * layer_height diff --git a/resources/quality/ultimaker3/um3_aa0.8_PP_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_PP_Draft_Print.inst.cfg index f46c3cfb8f..fb67666dc7 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_PP_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_PP_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_pp_ultimaker3_AA_0.8 weight = -2 -setting_version = 4 +material = generic_pp +variant = AA 0.8 [values] brim_width = 25 @@ -48,4 +49,4 @@ top_bottom_thickness = 1.6 travel_compensate_overlapping_walls_0_enabled = False wall_0_wipe_dist = =line_width * 2 wall_line_width_x = =round(line_width * 0.8 / 0.8, 2) -wall_thickness = 1.6 \ No newline at end of file +wall_thickness = 1.6 diff --git a/resources/quality/ultimaker3/um3_aa0.8_PP_Superdraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_PP_Superdraft_Print.inst.cfg index ac8087d0c4..0fe9eb2bf9 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_PP_Superdraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_PP_Superdraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Sprint definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_pp_ultimaker3_AA_0.8 weight = -4 -setting_version = 4 +material = generic_pp +variant = AA 0.8 [values] brim_width = 25 @@ -48,4 +49,4 @@ top_bottom_thickness = 1.6 travel_compensate_overlapping_walls_0_enabled = False wall_0_wipe_dist = =line_width * 2 wall_line_width_x = =round(line_width * 0.8 / 0.8, 2) -wall_thickness = 1.6 \ No newline at end of file +wall_thickness = 1.6 diff --git a/resources/quality/ultimaker3/um3_aa0.8_PP_Verydraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_PP_Verydraft_Print.inst.cfg index daf60f24e6..5ec1311987 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_PP_Verydraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_PP_Verydraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_pp_ultimaker3_AA_0.8 weight = -3 -setting_version = 4 +material = generic_pp +variant = AA 0.8 [values] brim_width = 25 @@ -48,4 +49,4 @@ top_bottom_thickness = 1.6 travel_compensate_overlapping_walls_0_enabled = False wall_0_wipe_dist = =line_width * 2 wall_line_width_x = =round(line_width * 0.8 / 0.8, 2) -wall_thickness = 1.6 \ No newline at end of file +wall_thickness = 1.6 diff --git a/resources/quality/ultimaker3/um3_aa0.8_TPU_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_TPU_Draft_Print.inst.cfg index 8c11e1247a..be3ea7e06d 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_TPU_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_TPU_Draft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -material = generic_tpu_ultimaker3_AA_0.8 weight = -2 -setting_version = 4 +material = generic_tpu +variant = AA 0.8 [values] brim_width = 8.75 @@ -60,4 +61,4 @@ travel_avoid_distance = 1.5 travel_compensate_overlapping_walls_0_enabled = False wall_0_wipe_dist = =line_width * 2 wall_line_width_x = =round(line_width * 0.6 / 0.8, 2) -wall_thickness = 1.3 \ No newline at end of file +wall_thickness = 1.3 diff --git a/resources/quality/ultimaker3/um3_aa0.8_TPU_Superdraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_TPU_Superdraft_Print.inst.cfg index 6bd777f4b0..cc0e963a35 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_TPU_Superdraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_TPU_Superdraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Sprint definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = superdraft -material = generic_tpu_ultimaker3_AA_0.8 weight = -4 -setting_version = 4 +material = generic_tpu +variant = AA 0.8 [values] brim_width = 8.75 @@ -61,4 +62,4 @@ travel_avoid_distance = 1.5 travel_compensate_overlapping_walls_0_enabled = False wall_0_wipe_dist = =line_width * 2 wall_line_width_x = =round(line_width * 0.6 / 0.8, 2) -wall_thickness = 1.3 \ No newline at end of file +wall_thickness = 1.3 diff --git a/resources/quality/ultimaker3/um3_aa0.8_TPU_Verydraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_aa0.8_TPU_Verydraft_Print.inst.cfg index f43818d7d4..3310c09ba7 100644 --- a/resources/quality/ultimaker3/um3_aa0.8_TPU_Verydraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_aa0.8_TPU_Verydraft_Print.inst.cfg @@ -4,11 +4,12 @@ name = Extra Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = verydraft -material = generic_tpu_ultimaker3_AA_0.8 weight = -3 -setting_version = 4 +material = generic_tpu +variant = AA 0.8 [values] brim_width = 8.75 @@ -60,4 +61,4 @@ travel_avoid_distance = 1.5 travel_compensate_overlapping_walls_0_enabled = False wall_0_wipe_dist = =line_width * 2 wall_line_width_x = =round(line_width * 0.6 / 0.8, 2) -wall_thickness = 1.3 \ No newline at end of file +wall_thickness = 1.3 diff --git a/resources/quality/ultimaker3/um3_bb0.4_PVA_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_bb0.4_PVA_Draft_Print.inst.cfg index c87f744932..eacdaccffe 100644 --- a/resources/quality/ultimaker3/um3_bb0.4_PVA_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_bb0.4_PVA_Draft_Print.inst.cfg @@ -4,14 +4,15 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft weight = -2 -material = generic_pva_ultimaker3_BB_0.4 -setting_version = 4 +material = generic_pva +variant = BB 0.4 [values] material_print_temperature = =default_material_print_temperature + 10 material_standby_temperature = 100 prime_tower_enable = False -skin_overlap = 20 \ No newline at end of file +skin_overlap = 20 diff --git a/resources/quality/ultimaker3/um3_bb0.4_PVA_Fast_Print.inst.cfg b/resources/quality/ultimaker3/um3_bb0.4_PVA_Fast_Print.inst.cfg index 23fa6d61d8..c6ddd85181 100644 --- a/resources/quality/ultimaker3/um3_bb0.4_PVA_Fast_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_bb0.4_PVA_Fast_Print.inst.cfg @@ -4,15 +4,16 @@ name = Normal definition = ultimaker3 [metadata] -weight = -1 +setting_version = 4 type = quality quality_type = fast -material = generic_pva_ultimaker3_BB_0.4 -setting_version = 4 +weight = -1 +material = generic_pva +variant = BB 0.4 [values] material_print_temperature = =default_material_print_temperature + 5 material_standby_temperature = 100 prime_tower_enable = False skin_overlap = 15 -support_infill_sparse_thickness = 0.3 \ No newline at end of file +support_infill_sparse_thickness = 0.3 diff --git a/resources/quality/ultimaker3/um3_bb0.4_PVA_High_Quality.inst.cfg b/resources/quality/ultimaker3/um3_bb0.4_PVA_High_Quality.inst.cfg index 3ba82d65c6..0b1d0f9f8d 100644 --- a/resources/quality/ultimaker3/um3_bb0.4_PVA_High_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_bb0.4_PVA_High_Quality.inst.cfg @@ -4,13 +4,14 @@ name = Extra Fine definition = ultimaker3 [metadata] -weight = 1 +setting_version = 4 type = quality quality_type = high -material = generic_pva_ultimaker3_BB_0.4 -setting_version = 4 +weight = 1 +material = generic_pva +variant = BB 0.4 [values] material_standby_temperature = 100 prime_tower_enable = False -support_infill_sparse_thickness = 0.18 \ No newline at end of file +support_infill_sparse_thickness = 0.18 diff --git a/resources/quality/ultimaker3/um3_bb0.4_PVA_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_bb0.4_PVA_Normal_Quality.inst.cfg index a709d5613b..9980e2b31c 100644 --- a/resources/quality/ultimaker3/um3_bb0.4_PVA_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_bb0.4_PVA_Normal_Quality.inst.cfg @@ -4,12 +4,13 @@ name = Fine definition = ultimaker3 [metadata] -weight = 0 +setting_version = 4 type = quality quality_type = normal -material = generic_pva_ultimaker3_BB_0.4 -setting_version = 4 +weight = 0 +material = generic_pva +variant = BB 0.4 [values] material_standby_temperature = 100 -prime_tower_enable = False \ No newline at end of file +prime_tower_enable = False diff --git a/resources/quality/ultimaker3/um3_bb0.8_PVA_Draft_Print.inst.cfg b/resources/quality/ultimaker3/um3_bb0.8_PVA_Draft_Print.inst.cfg index 4cb296b4c7..edc960cc8c 100644 --- a/resources/quality/ultimaker3/um3_bb0.8_PVA_Draft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_bb0.8_PVA_Draft_Print.inst.cfg @@ -4,12 +4,13 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft weight = -2 -material = generic_pva_ultimaker3_BB_0.8 -setting_version = 4 +material = generic_pva +variant = BB 0.8 [values] material_print_temperature = =default_material_print_temperature + 5 -material_standby_temperature = 100 \ No newline at end of file +material_standby_temperature = 100 diff --git a/resources/quality/ultimaker3/um3_bb0.8_PVA_Superdraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_bb0.8_PVA_Superdraft_Print.inst.cfg index 5249517844..6fb66dab14 100644 --- a/resources/quality/ultimaker3/um3_bb0.8_PVA_Superdraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_bb0.8_PVA_Superdraft_Print.inst.cfg @@ -4,13 +4,14 @@ name = Sprint definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = superdraft weight = -4 -material = generic_pva_ultimaker3_BB_0.8 -setting_version = 4 +material = generic_pva +variant = BB 0.8 [values] layer_height = 0.4 material_standby_temperature = 100 -support_interface_height = 0.9 \ No newline at end of file +support_interface_height = 0.9 diff --git a/resources/quality/ultimaker3/um3_bb0.8_PVA_Verydraft_Print.inst.cfg b/resources/quality/ultimaker3/um3_bb0.8_PVA_Verydraft_Print.inst.cfg index c34e19b134..12288919fe 100644 --- a/resources/quality/ultimaker3/um3_bb0.8_PVA_Verydraft_Print.inst.cfg +++ b/resources/quality/ultimaker3/um3_bb0.8_PVA_Verydraft_Print.inst.cfg @@ -4,14 +4,15 @@ name = Extra Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = verydraft weight = -3 -material = generic_pva_ultimaker3_BB_0.8 -setting_version = 4 +material = generic_pva +variant = BB 0.8 [values] layer_height = 0.3 material_standby_temperature = 100 support_infill_sparse_thickness = 0.3 -support_interface_height = 1.2 \ No newline at end of file +support_interface_height = 1.2 diff --git a/resources/quality/ultimaker3/um3_global_Draft_Quality.inst.cfg b/resources/quality/ultimaker3/um3_global_Draft_Quality.inst.cfg index b56775a987..9f13bbd3c2 100644 --- a/resources/quality/ultimaker3/um3_global_Draft_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_global_Draft_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = draft -global_quality = True weight = -2 -setting_version = 4 +global_quality = True [values] layer_height = 0.2 diff --git a/resources/quality/ultimaker3/um3_global_Fast_Quality.inst.cfg b/resources/quality/ultimaker3/um3_global_Fast_Quality.inst.cfg index 12f1183364..073ae82a07 100644 --- a/resources/quality/ultimaker3/um3_global_Fast_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_global_Fast_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = fast -global_quality = True weight = -1 -setting_version = 4 +global_quality = True [values] layer_height = 0.15 diff --git a/resources/quality/ultimaker3/um3_global_High_Quality.inst.cfg b/resources/quality/ultimaker3/um3_global_High_Quality.inst.cfg index cf6e6c45e0..1daff86c49 100644 --- a/resources/quality/ultimaker3/um3_global_High_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_global_High_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Extra Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = high -global_quality = True weight = 0 -setting_version = 4 +global_quality = True [values] layer_height = 0.06 diff --git a/resources/quality/ultimaker3/um3_global_Normal_Quality.inst.cfg b/resources/quality/ultimaker3/um3_global_Normal_Quality.inst.cfg index fef2328923..91c5bab8b7 100644 --- a/resources/quality/ultimaker3/um3_global_Normal_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_global_Normal_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Fine definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = normal -global_quality = True weight = 0 -setting_version = 4 +global_quality = True [values] layer_height = 0.1 diff --git a/resources/quality/ultimaker3/um3_global_Superdraft_Quality.inst.cfg b/resources/quality/ultimaker3/um3_global_Superdraft_Quality.inst.cfg index be9acd4394..da39b065d5 100644 --- a/resources/quality/ultimaker3/um3_global_Superdraft_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_global_Superdraft_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Sprint definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = superdraft -global_quality = True weight = -4 -setting_version = 4 +global_quality = True [values] layer_height = 0.4 diff --git a/resources/quality/ultimaker3/um3_global_Verydraft_Quality.inst.cfg b/resources/quality/ultimaker3/um3_global_Verydraft_Quality.inst.cfg index e2c828fc2d..11e8315a7b 100644 --- a/resources/quality/ultimaker3/um3_global_Verydraft_Quality.inst.cfg +++ b/resources/quality/ultimaker3/um3_global_Verydraft_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Extra Fast definition = ultimaker3 [metadata] +setting_version = 4 type = quality quality_type = verydraft -global_quality = True weight = -3 -setting_version = 4 +global_quality = True [values] layer_height = 0.3 diff --git a/resources/quality/vertex_delta_k8800/k8800_ABS_Extreme_Quality.inst.cfg b/resources/quality/vertex_delta_k8800/k8800_ABS_Extreme_Quality.inst.cfg index 2c42bd82b6..50a1ef3415 100644 --- a/resources/quality/vertex_delta_k8800/k8800_ABS_Extreme_Quality.inst.cfg +++ b/resources/quality/vertex_delta_k8800/k8800_ABS_Extreme_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Extreme definition = vertex_delta_k8800 [metadata] +setting_version = 4 type = quality quality_type = extreme -material = Vertex_Delta_ABS weight = 2 -setting_version = 4 +material = Vertex_Delta_ABS [values] layer_height = 0.05 @@ -19,4 +19,4 @@ material_initial_print_temperature = 250 material_print_temperature = 250 retraction_amount = 3 material_standby_temperature = 225 -cool_fan_speed = 0 \ No newline at end of file +cool_fan_speed = 0 diff --git a/resources/quality/vertex_delta_k8800/k8800_ABS_High_Quality.inst.cfg b/resources/quality/vertex_delta_k8800/k8800_ABS_High_Quality.inst.cfg index a770131adb..e650f11afd 100644 --- a/resources/quality/vertex_delta_k8800/k8800_ABS_High_Quality.inst.cfg +++ b/resources/quality/vertex_delta_k8800/k8800_ABS_High_Quality.inst.cfg @@ -4,11 +4,11 @@ name = High definition = vertex_delta_k8800 [metadata] +setting_version = 4 type = quality quality_type = high -material = Vertex_Delta_ABS weight = 1 -setting_version = 4 +material = Vertex_Delta_ABS [values] layer_height = 0.1 @@ -19,4 +19,4 @@ material_initial_print_temperature = 250 material_print_temperature = 250 retraction_amount = 3 material_standby_temperature = 225 -cool_fan_speed = 0 \ No newline at end of file +cool_fan_speed = 0 diff --git a/resources/quality/vertex_delta_k8800/k8800_ABS_Normal_Quality.inst.cfg b/resources/quality/vertex_delta_k8800/k8800_ABS_Normal_Quality.inst.cfg index 7c7e635149..aa962190ce 100644 --- a/resources/quality/vertex_delta_k8800/k8800_ABS_Normal_Quality.inst.cfg +++ b/resources/quality/vertex_delta_k8800/k8800_ABS_Normal_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = vertex_delta_k8800 [metadata] +setting_version = 4 type = quality quality_type = normal -material = Vertex_Delta_ABS weight = 0 -setting_version = 4 +material = Vertex_Delta_ABS [values] layer_height = 0.2 @@ -19,4 +19,4 @@ material_initial_print_temperature = 250 material_print_temperature = 250 retraction_amount = 3 material_standby_temperature = 225 -cool_fan_speed = 00 \ No newline at end of file +cool_fan_speed = 00 diff --git a/resources/quality/vertex_delta_k8800/k8800_PET_Extreme_Quality.inst.cfg b/resources/quality/vertex_delta_k8800/k8800_PET_Extreme_Quality.inst.cfg index 836d900247..29a4170adf 100644 --- a/resources/quality/vertex_delta_k8800/k8800_PET_Extreme_Quality.inst.cfg +++ b/resources/quality/vertex_delta_k8800/k8800_PET_Extreme_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Extreme definition = vertex_delta_k8800 [metadata] +setting_version = 4 type = quality quality_type = extreme -material = Vertex_Delta_PET weight = 2 -setting_version = 4 +material = Vertex_Delta_PET [values] layer_height = 0.05 @@ -19,4 +19,4 @@ material_initial_print_temperature = 240 material_print_temperature = 240 retraction_amount = 3 material_standby_temperature = 215 -cool_fan_speed = 10 \ No newline at end of file +cool_fan_speed = 10 diff --git a/resources/quality/vertex_delta_k8800/k8800_PET_High_Quality.inst.cfg b/resources/quality/vertex_delta_k8800/k8800_PET_High_Quality.inst.cfg index b0cae312b2..fc92590da1 100644 --- a/resources/quality/vertex_delta_k8800/k8800_PET_High_Quality.inst.cfg +++ b/resources/quality/vertex_delta_k8800/k8800_PET_High_Quality.inst.cfg @@ -4,11 +4,11 @@ name = High definition = vertex_delta_k8800 [metadata] +setting_version = 4 type = quality quality_type = high -material = Vertex_Delta_PET weight = 1 -setting_version = 4 +material = Vertex_Delta_PET [values] layer_height = 0.1 @@ -19,4 +19,4 @@ material_initial_print_temperature = 240 material_print_temperature = 240 retraction_amount = 3 material_standby_temperature = 215 -cool_fan_speed = 10 \ No newline at end of file +cool_fan_speed = 10 diff --git a/resources/quality/vertex_delta_k8800/k8800_PET_Normal_Quality.inst.cfg b/resources/quality/vertex_delta_k8800/k8800_PET_Normal_Quality.inst.cfg index ebec26d04a..b02bfa5178 100644 --- a/resources/quality/vertex_delta_k8800/k8800_PET_Normal_Quality.inst.cfg +++ b/resources/quality/vertex_delta_k8800/k8800_PET_Normal_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = vertex_delta_k8800 [metadata] +setting_version = 4 type = quality quality_type = normal -material = Vertex_Delta_PET weight = 0 -setting_version = 4 +material = Vertex_Delta_PET [values] layer_height = 0.2 @@ -19,4 +19,4 @@ material_initial_print_temperature = 240 material_print_temperature = 240 retraction_amount = 3 material_standby_temperature = 215 -cool_fan_speed = 10 \ No newline at end of file +cool_fan_speed = 10 diff --git a/resources/quality/vertex_delta_k8800/k8800_PLA_Extreme_Quality.inst.cfg b/resources/quality/vertex_delta_k8800/k8800_PLA_Extreme_Quality.inst.cfg index 13ad6455c9..3cdad7a06f 100644 --- a/resources/quality/vertex_delta_k8800/k8800_PLA_Extreme_Quality.inst.cfg +++ b/resources/quality/vertex_delta_k8800/k8800_PLA_Extreme_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Extreme definition = vertex_delta_k8800 [metadata] +setting_version = 4 type = quality quality_type = extreme -material = Vertex_Delta_PLA weight = 2 -setting_version = 4 +material = Vertex_Delta_PLA [values] layer_height = 0.05 @@ -19,4 +19,4 @@ material_initial_print_temperature = 200 material_print_temperature = 200 retraction_amount = 3 material_standby_temperature = 175 -cool_fan_speed = 40 \ No newline at end of file +cool_fan_speed = 40 diff --git a/resources/quality/vertex_delta_k8800/k8800_PLA_High_Quality.inst.cfg b/resources/quality/vertex_delta_k8800/k8800_PLA_High_Quality.inst.cfg index e8c7e893cb..192750ef71 100644 --- a/resources/quality/vertex_delta_k8800/k8800_PLA_High_Quality.inst.cfg +++ b/resources/quality/vertex_delta_k8800/k8800_PLA_High_Quality.inst.cfg @@ -4,11 +4,11 @@ name = High definition = vertex_delta_k8800 [metadata] +setting_version = 4 type = quality quality_type = high -material = Vertex_Delta_PLA weight = 1 -setting_version = 4 +material = Vertex_Delta_PLA [values] layer_height = 0.1 @@ -19,4 +19,4 @@ material_initial_print_temperature = 200 material_print_temperature = 200 retraction_amount = 3 material_standby_temperature = 175 -cool_fan_speed = 40 \ No newline at end of file +cool_fan_speed = 40 diff --git a/resources/quality/vertex_delta_k8800/k8800_PLA_Normal_Quality.inst.cfg b/resources/quality/vertex_delta_k8800/k8800_PLA_Normal_Quality.inst.cfg index 27002caea2..1e519734bb 100644 --- a/resources/quality/vertex_delta_k8800/k8800_PLA_Normal_Quality.inst.cfg +++ b/resources/quality/vertex_delta_k8800/k8800_PLA_Normal_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = vertex_delta_k8800 [metadata] +setting_version = 4 type = quality quality_type = normal -material = Vertex_Delta_PLA weight = 0 -setting_version = 4 +material = Vertex_Delta_PLA [values] layer_height = 0.2 @@ -19,4 +19,4 @@ material_initial_print_temperature = 200 material_print_temperature = 200 retraction_amount = 3 material_standby_temperature = 175 -cool_fan_speed = 40 \ No newline at end of file +cool_fan_speed = 40 diff --git a/resources/quality/vertex_delta_k8800/k8800_TPU_Extreme_Quality.inst.cfg b/resources/quality/vertex_delta_k8800/k8800_TPU_Extreme_Quality.inst.cfg index 8a0a01fb0b..9da37f2148 100644 --- a/resources/quality/vertex_delta_k8800/k8800_TPU_Extreme_Quality.inst.cfg +++ b/resources/quality/vertex_delta_k8800/k8800_TPU_Extreme_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Extreme definition = vertex_delta_k8800 [metadata] +setting_version = 4 type = quality quality_type = extreme -material = Vertex_Delta_TPU weight = 2 -setting_version = 4 +material = Vertex_Delta_TPU [values] layer_height = 0.05 @@ -19,4 +19,4 @@ material_initial_print_temperature = 220 material_print_temperature = 220 retraction_amount = 3 material_standby_temperature = 195 -cool_fan_speed = 20 \ No newline at end of file +cool_fan_speed = 20 diff --git a/resources/quality/vertex_delta_k8800/k8800_TPU_High_Quality.inst.cfg b/resources/quality/vertex_delta_k8800/k8800_TPU_High_Quality.inst.cfg index 7e23947f39..f5583d32b9 100644 --- a/resources/quality/vertex_delta_k8800/k8800_TPU_High_Quality.inst.cfg +++ b/resources/quality/vertex_delta_k8800/k8800_TPU_High_Quality.inst.cfg @@ -4,11 +4,11 @@ name = High definition = vertex_delta_k8800 [metadata] +setting_version = 4 type = quality quality_type = high -material = Vertex_Delta_TPU weight = 1 -setting_version = 4 +material = Vertex_Delta_TPU [values] layer_height = 0.1 @@ -19,4 +19,4 @@ material_initial_print_temperature = 220 material_print_temperature = 220 retraction_amount = 3 material_standby_temperature = 195 -cool_fan_speed = 20 \ No newline at end of file +cool_fan_speed = 20 diff --git a/resources/quality/vertex_delta_k8800/k8800_TPU_Normal_Quality.inst.cfg b/resources/quality/vertex_delta_k8800/k8800_TPU_Normal_Quality.inst.cfg index 5fb46e1ea6..a520eb2473 100644 --- a/resources/quality/vertex_delta_k8800/k8800_TPU_Normal_Quality.inst.cfg +++ b/resources/quality/vertex_delta_k8800/k8800_TPU_Normal_Quality.inst.cfg @@ -4,11 +4,11 @@ name = Normal definition = vertex_delta_k8800 [metadata] +setting_version = 4 type = quality quality_type = normal -material = Vertex_Delta_TPU weight = 0 -setting_version = 4 +material = Vertex_Delta_TPU [values] layer_height = 0.2 diff --git a/resources/variants/cartesio_0.25.inst.cfg b/resources/variants/cartesio_0.25.inst.cfg index 0cc01093f2..014069451c 100644 --- a/resources/variants/cartesio_0.25.inst.cfg +++ b/resources/variants/cartesio_0.25.inst.cfg @@ -5,8 +5,8 @@ definition = cartesio [metadata] author = Cartesio -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/cartesio_0.4.inst.cfg b/resources/variants/cartesio_0.4.inst.cfg index 9920e699f5..7b5dccd980 100644 --- a/resources/variants/cartesio_0.4.inst.cfg +++ b/resources/variants/cartesio_0.4.inst.cfg @@ -5,8 +5,8 @@ definition = cartesio [metadata] author = Cartesio -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/cartesio_0.8.inst.cfg b/resources/variants/cartesio_0.8.inst.cfg index 8031a9fa31..70271dbf75 100644 --- a/resources/variants/cartesio_0.8.inst.cfg +++ b/resources/variants/cartesio_0.8.inst.cfg @@ -5,8 +5,8 @@ definition = cartesio [metadata] author = Cartesio -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/fabtotum_hyb35.inst.cfg b/resources/variants/fabtotum_hyb35.inst.cfg index e8fa13cc0d..e036b2e474 100644 --- a/resources/variants/fabtotum_hyb35.inst.cfg +++ b/resources/variants/fabtotum_hyb35.inst.cfg @@ -5,8 +5,8 @@ definition = fabtotum [metadata] author = FABtotum -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/fabtotum_lite04.inst.cfg b/resources/variants/fabtotum_lite04.inst.cfg index 7264abbdda..defa6692a8 100644 --- a/resources/variants/fabtotum_lite04.inst.cfg +++ b/resources/variants/fabtotum_lite04.inst.cfg @@ -5,8 +5,8 @@ definition = fabtotum [metadata] author = FABtotum -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/fabtotum_lite06.inst.cfg b/resources/variants/fabtotum_lite06.inst.cfg index 0ad33ca332..d269092b42 100644 --- a/resources/variants/fabtotum_lite06.inst.cfg +++ b/resources/variants/fabtotum_lite06.inst.cfg @@ -5,8 +5,8 @@ definition = fabtotum [metadata] author = FABtotum -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/fabtotum_pro02.inst.cfg b/resources/variants/fabtotum_pro02.inst.cfg index d83618b712..b705929c35 100644 --- a/resources/variants/fabtotum_pro02.inst.cfg +++ b/resources/variants/fabtotum_pro02.inst.cfg @@ -5,8 +5,8 @@ definition = fabtotum [metadata] author = FABtotum -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/fabtotum_pro04.inst.cfg b/resources/variants/fabtotum_pro04.inst.cfg index 4f2a622887..b835312324 100644 --- a/resources/variants/fabtotum_pro04.inst.cfg +++ b/resources/variants/fabtotum_pro04.inst.cfg @@ -5,8 +5,8 @@ definition = fabtotum [metadata] author = FABtotum -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/fabtotum_pro06.inst.cfg b/resources/variants/fabtotum_pro06.inst.cfg index aa44e762ba..140b6618cf 100644 --- a/resources/variants/fabtotum_pro06.inst.cfg +++ b/resources/variants/fabtotum_pro06.inst.cfg @@ -5,8 +5,8 @@ definition = fabtotum [metadata] author = FABtotum -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/fabtotum_pro08.inst.cfg b/resources/variants/fabtotum_pro08.inst.cfg index 597d23275e..421cd0b662 100644 --- a/resources/variants/fabtotum_pro08.inst.cfg +++ b/resources/variants/fabtotum_pro08.inst.cfg @@ -5,8 +5,8 @@ definition = fabtotum [metadata] author = FABtotum -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/gmax15plus_025_e3d.inst.cfg b/resources/variants/gmax15plus_025_e3d.inst.cfg index 0500a63638..3c7b2e4949 100644 --- a/resources/variants/gmax15plus_025_e3d.inst.cfg +++ b/resources/variants/gmax15plus_025_e3d.inst.cfg @@ -5,8 +5,9 @@ definition = gmax15plus [metadata] author = gcreate -type = variant setting_version = 4 +type = variant +hardware_type = nozzle [values] machine_nozzle_size = 0.25 diff --git a/resources/variants/gmax15plus_04_e3d.inst.cfg b/resources/variants/gmax15plus_04_e3d.inst.cfg index 514893a8a5..e9c0cf1b18 100644 --- a/resources/variants/gmax15plus_04_e3d.inst.cfg +++ b/resources/variants/gmax15plus_04_e3d.inst.cfg @@ -5,8 +5,9 @@ definition = gmax15plus [metadata] author = gcreate -type = variant setting_version = 4 +type = variant +hardware_type = nozzle [values] machine_nozzle_size = 0.4 diff --git a/resources/variants/gmax15plus_05_e3d.inst.cfg b/resources/variants/gmax15plus_05_e3d.inst.cfg index 2579409d5a..8575f3c539 100644 --- a/resources/variants/gmax15plus_05_e3d.inst.cfg +++ b/resources/variants/gmax15plus_05_e3d.inst.cfg @@ -5,8 +5,9 @@ definition = gmax15plus [metadata] author = gcreate -type = variant setting_version = 4 +type = variant +hardware_type = nozzle [values] machine_nozzle_size = 0.5 diff --git a/resources/variants/gmax15plus_05_jhead.inst.cfg b/resources/variants/gmax15plus_05_jhead.inst.cfg index ca107c9559..14d6ab5e9d 100644 --- a/resources/variants/gmax15plus_05_jhead.inst.cfg +++ b/resources/variants/gmax15plus_05_jhead.inst.cfg @@ -5,8 +5,9 @@ definition = gmax15plus [metadata] author = gcreate -type = variant setting_version = 4 +type = variant +hardware_type = nozzle [values] machine_nozzle_size = 0.5 diff --git a/resources/variants/gmax15plus_06_e3d.inst.cfg b/resources/variants/gmax15plus_06_e3d.inst.cfg index eb709f1487..5d3f5c63a9 100644 --- a/resources/variants/gmax15plus_06_e3d.inst.cfg +++ b/resources/variants/gmax15plus_06_e3d.inst.cfg @@ -5,8 +5,9 @@ definition = gmax15plus [metadata] author = gcreate -type = variant setting_version = 4 +type = variant +hardware_type = nozzle [values] machine_nozzle_size = 0.6 diff --git a/resources/variants/gmax15plus_08_e3d.inst.cfg b/resources/variants/gmax15plus_08_e3d.inst.cfg index 093bce99c0..af08cd2c7c 100644 --- a/resources/variants/gmax15plus_08_e3d.inst.cfg +++ b/resources/variants/gmax15plus_08_e3d.inst.cfg @@ -5,8 +5,9 @@ definition = gmax15plus [metadata] author = gcreate -type = variant setting_version = 4 +type = variant +hardware_type = nozzle [values] machine_nozzle_size = 0.8 diff --git a/resources/variants/gmax15plus_10_jhead.inst.cfg b/resources/variants/gmax15plus_10_jhead.inst.cfg index 977469e304..df61d9729f 100644 --- a/resources/variants/gmax15plus_10_jhead.inst.cfg +++ b/resources/variants/gmax15plus_10_jhead.inst.cfg @@ -5,8 +5,9 @@ definition = gmax15plus [metadata] author = gcreate -type = variant setting_version = 4 +type = variant +hardware_type = nozzle [values] machine_nozzle_size = 0.5 diff --git a/resources/variants/gmax15plus_dual_025_e3d.inst.cfg b/resources/variants/gmax15plus_dual_025_e3d.inst.cfg index b083174beb..07bdfca9b7 100644 --- a/resources/variants/gmax15plus_dual_025_e3d.inst.cfg +++ b/resources/variants/gmax15plus_dual_025_e3d.inst.cfg @@ -5,8 +5,9 @@ definition = gmax15plus_dual [metadata] author = gcreate -type = variant setting_version = 4 +type = variant +hardware_type = nozzle [values] machine_nozzle_size = 0.25 diff --git a/resources/variants/gmax15plus_dual_04_e3d.inst.cfg b/resources/variants/gmax15plus_dual_04_e3d.inst.cfg index f1a95f4f2a..966fe9f224 100644 --- a/resources/variants/gmax15plus_dual_04_e3d.inst.cfg +++ b/resources/variants/gmax15plus_dual_04_e3d.inst.cfg @@ -5,8 +5,9 @@ definition = gmax15plus_dual [metadata] author = gcreate -type = variant setting_version = 4 +type = variant +hardware_type = nozzle [values] machine_nozzle_size = 0.4 diff --git a/resources/variants/gmax15plus_dual_05_e3d.inst.cfg b/resources/variants/gmax15plus_dual_05_e3d.inst.cfg index dd148f8082..85464bd733 100644 --- a/resources/variants/gmax15plus_dual_05_e3d.inst.cfg +++ b/resources/variants/gmax15plus_dual_05_e3d.inst.cfg @@ -5,8 +5,9 @@ definition = gmax15plus_dual [metadata] author = gcreate -type = variant setting_version = 4 +type = variant +hardware_type = nozzle [values] machine_nozzle_size = 0.5 diff --git a/resources/variants/gmax15plus_dual_05_jhead.inst.cfg b/resources/variants/gmax15plus_dual_05_jhead.inst.cfg index 7e038a3980..689c76541a 100644 --- a/resources/variants/gmax15plus_dual_05_jhead.inst.cfg +++ b/resources/variants/gmax15plus_dual_05_jhead.inst.cfg @@ -5,8 +5,9 @@ definition = gmax15plus_dual [metadata] author = gcreate -type = variant setting_version = 4 +type = variant +hardware_type = nozzle [values] machine_nozzle_size = 0.5 diff --git a/resources/variants/gmax15plus_dual_06_e3d.inst.cfg b/resources/variants/gmax15plus_dual_06_e3d.inst.cfg index 93cf21780f..57641a4244 100644 --- a/resources/variants/gmax15plus_dual_06_e3d.inst.cfg +++ b/resources/variants/gmax15plus_dual_06_e3d.inst.cfg @@ -5,8 +5,9 @@ definition = gmax15plus_dual [metadata] author = gcreate -type = variant setting_version = 4 +type = variant +hardware_type = nozzle [values] machine_nozzle_size = 0.6 diff --git a/resources/variants/gmax15plus_dual_08_e3d.inst.cfg b/resources/variants/gmax15plus_dual_08_e3d.inst.cfg index 3088113f27..11523ccd67 100644 --- a/resources/variants/gmax15plus_dual_08_e3d.inst.cfg +++ b/resources/variants/gmax15plus_dual_08_e3d.inst.cfg @@ -5,8 +5,9 @@ definition = gmax15plus_dual [metadata] author = gcreate -type = variant setting_version = 4 +type = variant +hardware_type = nozzle [values] machine_nozzle_size = 0.8 diff --git a/resources/variants/gmax15plus_dual_10_jhead.inst.cfg b/resources/variants/gmax15plus_dual_10_jhead.inst.cfg index a526cc676e..26721d0169 100644 --- a/resources/variants/gmax15plus_dual_10_jhead.inst.cfg +++ b/resources/variants/gmax15plus_dual_10_jhead.inst.cfg @@ -5,8 +5,9 @@ definition = gmax15plus_dual [metadata] author = gcreate -type = variant setting_version = 4 +type = variant +hardware_type = nozzle [values] machine_nozzle_size = 0.5 diff --git a/resources/variants/imade3d_jellybox_0.4.inst.cfg b/resources/variants/imade3d_jellybox_0.4.inst.cfg index c37a2ecabf..5baa8123f2 100644 --- a/resources/variants/imade3d_jellybox_0.4.inst.cfg +++ b/resources/variants/imade3d_jellybox_0.4.inst.cfg @@ -5,8 +5,8 @@ definition = imade3d_jellybox [metadata] author = IMADE3D -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/imade3d_jellybox_0.4_2-fans.inst.cfg b/resources/variants/imade3d_jellybox_0.4_2-fans.inst.cfg index c3e63aab34..5d1a01c366 100644 --- a/resources/variants/imade3d_jellybox_0.4_2-fans.inst.cfg +++ b/resources/variants/imade3d_jellybox_0.4_2-fans.inst.cfg @@ -5,8 +5,8 @@ definition = imade3d_jellybox [metadata] author = IMADE3D -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_0.25.inst.cfg b/resources/variants/ultimaker2_0.25.inst.cfg index aee83e2483..2b1b04f123 100644 --- a/resources/variants/ultimaker2_0.25.inst.cfg +++ b/resources/variants/ultimaker2_0.25.inst.cfg @@ -4,12 +4,11 @@ version = 2 definition = ultimaker2 [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] machine_nozzle_size = 0.25 machine_nozzle_tip_outer_diameter = 0.8 -raft_airgap = 0.25 \ No newline at end of file +raft_airgap = 0.25 diff --git a/resources/variants/ultimaker2_0.4.inst.cfg b/resources/variants/ultimaker2_0.4.inst.cfg index fe128137d9..8886992f6f 100644 --- a/resources/variants/ultimaker2_0.4.inst.cfg +++ b/resources/variants/ultimaker2_0.4.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2 [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_0.6.inst.cfg b/resources/variants/ultimaker2_0.6.inst.cfg index 7fea2fbb22..42de9d3ee8 100644 --- a/resources/variants/ultimaker2_0.6.inst.cfg +++ b/resources/variants/ultimaker2_0.6.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2 [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_0.8.inst.cfg b/resources/variants/ultimaker2_0.8.inst.cfg index 5f1176b7ec..df2ca88ba2 100644 --- a/resources/variants/ultimaker2_0.8.inst.cfg +++ b/resources/variants/ultimaker2_0.8.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2 [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_extended_0.25.inst.cfg b/resources/variants/ultimaker2_extended_0.25.inst.cfg index e705327cf8..f04a28e5ba 100644 --- a/resources/variants/ultimaker2_extended_0.25.inst.cfg +++ b/resources/variants/ultimaker2_extended_0.25.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2_extended [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_extended_0.4.inst.cfg b/resources/variants/ultimaker2_extended_0.4.inst.cfg index d486ed4f4e..c54202750a 100644 --- a/resources/variants/ultimaker2_extended_0.4.inst.cfg +++ b/resources/variants/ultimaker2_extended_0.4.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2_extended [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_extended_0.6.inst.cfg b/resources/variants/ultimaker2_extended_0.6.inst.cfg index f9dd4d4e69..67176632aa 100644 --- a/resources/variants/ultimaker2_extended_0.6.inst.cfg +++ b/resources/variants/ultimaker2_extended_0.6.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2_extended [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_extended_0.8.inst.cfg b/resources/variants/ultimaker2_extended_0.8.inst.cfg index ee56b6d194..61917309ef 100644 --- a/resources/variants/ultimaker2_extended_0.8.inst.cfg +++ b/resources/variants/ultimaker2_extended_0.8.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2_extended [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_extended_plus_0.25.inst.cfg b/resources/variants/ultimaker2_extended_plus_0.25.inst.cfg index f23406fec3..6386d71f50 100644 --- a/resources/variants/ultimaker2_extended_plus_0.25.inst.cfg +++ b/resources/variants/ultimaker2_extended_plus_0.25.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2_extended_plus [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_extended_plus_0.4.inst.cfg b/resources/variants/ultimaker2_extended_plus_0.4.inst.cfg index c0b1c6ab79..1426f733cc 100644 --- a/resources/variants/ultimaker2_extended_plus_0.4.inst.cfg +++ b/resources/variants/ultimaker2_extended_plus_0.4.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2_extended_plus [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_extended_plus_0.6.inst.cfg b/resources/variants/ultimaker2_extended_plus_0.6.inst.cfg index 6ef64bed5f..5ea4072022 100644 --- a/resources/variants/ultimaker2_extended_plus_0.6.inst.cfg +++ b/resources/variants/ultimaker2_extended_plus_0.6.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2_extended_plus [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_extended_plus_0.8.inst.cfg b/resources/variants/ultimaker2_extended_plus_0.8.inst.cfg index 2f890d0827..69b2b9b0d0 100644 --- a/resources/variants/ultimaker2_extended_plus_0.8.inst.cfg +++ b/resources/variants/ultimaker2_extended_plus_0.8.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2_extended_plus [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_plus_0.25.inst.cfg b/resources/variants/ultimaker2_plus_0.25.inst.cfg index 1c4688568d..2b40656cf4 100644 --- a/resources/variants/ultimaker2_plus_0.25.inst.cfg +++ b/resources/variants/ultimaker2_plus_0.25.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2_plus [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_plus_0.4.inst.cfg b/resources/variants/ultimaker2_plus_0.4.inst.cfg index 00a4ef47dd..0aaf4f4e5a 100644 --- a/resources/variants/ultimaker2_plus_0.4.inst.cfg +++ b/resources/variants/ultimaker2_plus_0.4.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2_plus [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_plus_0.6.inst.cfg b/resources/variants/ultimaker2_plus_0.6.inst.cfg index 4dceab70d0..7988a949bc 100644 --- a/resources/variants/ultimaker2_plus_0.6.inst.cfg +++ b/resources/variants/ultimaker2_plus_0.6.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2_plus [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker2_plus_0.8.inst.cfg b/resources/variants/ultimaker2_plus_0.8.inst.cfg index e1bbddb823..1a7824b0b1 100644 --- a/resources/variants/ultimaker2_plus_0.8.inst.cfg +++ b/resources/variants/ultimaker2_plus_0.8.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker2_plus [metadata] -author = Ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker3_aa0.25.inst.cfg b/resources/variants/ultimaker3_aa0.25.inst.cfg index 2d2d893202..8f06e73f91 100644 --- a/resources/variants/ultimaker3_aa0.25.inst.cfg +++ b/resources/variants/ultimaker3_aa0.25.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker3 [metadata] -author = ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker3_aa0.8.inst.cfg b/resources/variants/ultimaker3_aa0.8.inst.cfg index 402190c357..218c1ea3bf 100644 --- a/resources/variants/ultimaker3_aa0.8.inst.cfg +++ b/resources/variants/ultimaker3_aa0.8.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker3 [metadata] -author = ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker3_aa04.inst.cfg b/resources/variants/ultimaker3_aa04.inst.cfg index 0163024fa4..2964ab74a0 100644 --- a/resources/variants/ultimaker3_aa04.inst.cfg +++ b/resources/variants/ultimaker3_aa04.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker3 [metadata] -author = ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] @@ -40,4 +39,3 @@ switch_extruder_prime_speed = =switch_extruder_retraction_speeds switch_extruder_retraction_amount = =machine_heat_zone_length top_bottom_thickness = 1.2 wall_thickness = 1.3 - diff --git a/resources/variants/ultimaker3_bb0.8.inst.cfg b/resources/variants/ultimaker3_bb0.8.inst.cfg index 017da649a0..03b38f225c 100644 --- a/resources/variants/ultimaker3_bb0.8.inst.cfg +++ b/resources/variants/ultimaker3_bb0.8.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker3 [metadata] -author = ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker3_bb04.inst.cfg b/resources/variants/ultimaker3_bb04.inst.cfg index 93b2025031..78d201318d 100644 --- a/resources/variants/ultimaker3_bb04.inst.cfg +++ b/resources/variants/ultimaker3_bb04.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker3 [metadata] -author = ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] @@ -47,4 +46,4 @@ support_line_width = =round(line_width * 0.4 / 0.35, 2) support_offset = 3 support_xy_distance = =round(wall_line_width_0 * 0.75, 2) support_xy_distance_overhang = =wall_line_width_0 / 2 -switch_extruder_retraction_amount = 12 \ No newline at end of file +switch_extruder_retraction_amount = 12 diff --git a/resources/variants/ultimaker3_extended_aa0.25.inst.cfg b/resources/variants/ultimaker3_extended_aa0.25.inst.cfg index 04d7a7990a..f45d90b762 100644 --- a/resources/variants/ultimaker3_extended_aa0.25.inst.cfg +++ b/resources/variants/ultimaker3_extended_aa0.25.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker3_extended [metadata] -author = ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] @@ -38,4 +37,3 @@ support_z_distance = =layer_height * 2 top_bottom_thickness = 1.2 wall_line_width_x = 0.23 wall_thickness = 1.3 - diff --git a/resources/variants/ultimaker3_extended_aa0.8.inst.cfg b/resources/variants/ultimaker3_extended_aa0.8.inst.cfg index 3e1b3ed3de..1f5709e504 100644 --- a/resources/variants/ultimaker3_extended_aa0.8.inst.cfg +++ b/resources/variants/ultimaker3_extended_aa0.8.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker3_extended [metadata] -author = ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker3_extended_aa04.inst.cfg b/resources/variants/ultimaker3_extended_aa04.inst.cfg index 94bee65b5d..4d9d2b4646 100644 --- a/resources/variants/ultimaker3_extended_aa04.inst.cfg +++ b/resources/variants/ultimaker3_extended_aa04.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker3_extended [metadata] -author = ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker3_extended_bb0.8.inst.cfg b/resources/variants/ultimaker3_extended_bb0.8.inst.cfg index e1086535ec..752083f42a 100644 --- a/resources/variants/ultimaker3_extended_bb0.8.inst.cfg +++ b/resources/variants/ultimaker3_extended_bb0.8.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker3_extended [metadata] -author = ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] diff --git a/resources/variants/ultimaker3_extended_bb04.inst.cfg b/resources/variants/ultimaker3_extended_bb04.inst.cfg index a995acf77c..1ceaf58c5b 100644 --- a/resources/variants/ultimaker3_extended_bb04.inst.cfg +++ b/resources/variants/ultimaker3_extended_bb04.inst.cfg @@ -4,9 +4,8 @@ version = 2 definition = ultimaker3_extended [metadata] -author = ultimaker -type = variant setting_version = 4 +type = variant hardware_type = nozzle [values] @@ -47,4 +46,4 @@ support_line_width = =round(line_width * 0.4 / 0.35, 2) support_offset = 3 support_xy_distance = =round(wall_line_width_0 * 0.75, 2) support_xy_distance_overhang = =wall_line_width_0 / 2 -switch_extruder_retraction_amount = 12 \ No newline at end of file +switch_extruder_retraction_amount = 12 diff --git a/tests/Settings/TestExtruderStack.py b/tests/Settings/TestExtruderStack.py index e1538cd3fc..ce829da4b3 100644 --- a/tests/Settings/TestExtruderStack.py +++ b/tests/Settings/TestExtruderStack.py @@ -325,30 +325,6 @@ def test_removeContainer(extruder_stack): with pytest.raises(InvalidOperationError): extruder_stack.removeContainer(unittest.mock.MagicMock()) -## Tests setting definitions by specifying an ID of a definition that exists. -def test_setDefinitionByIdExists(extruder_stack, container_registry): - container_registry.return_value = DefinitionContainer(container_id = "some_definition") - extruder_stack.setDefinitionById("some_definition") - assert extruder_stack.definition.getId() == "some_definition" - -## Tests setting definitions by specifying an ID of a definition that doesn't -# exist. -def test_setDefinitionByIdDoesntExist(extruder_stack): - with pytest.raises(InvalidContainerError): - extruder_stack.setDefinitionById("some_definition") #Container registry is empty now. - -## Tests setting materials by specifying an ID of a material that exists. -def test_setMaterialByIdExists(extruder_stack, container_registry): - container_registry.return_value = getInstanceContainer(container_type = "material") - extruder_stack.setMaterialById("InstanceContainer") - assert extruder_stack.material.getId() == "InstanceContainer" - -## Tests setting materials by specifying an ID of a material that doesn't -# exist. -def test_setMaterialByIdDoesntExist(extruder_stack): - with pytest.raises(InvalidContainerError): - extruder_stack.setMaterialById("some_material") #Container registry is empty now. - ## Tests setting properties directly on the extruder stack. @pytest.mark.parametrize("key, property, value", [ ("layer_height", "value", 0.1337), @@ -387,38 +363,3 @@ def test_setPropertyOtherContainers(target_container, stack_variable, extruder_s extruder_stack.setProperty(key, property, value, target_container = target_container) #The actual test. getattr(extruder_stack, stack_variable).setProperty.assert_called_once_with(key, property, value) #Make sure that the proper container gets a setProperty call. - -## Tests setting qualities by specifying an ID of a quality that exists. -def test_setQualityByIdExists(extruder_stack, container_registry): - container_registry.return_value = getInstanceContainer(container_type = "quality") - extruder_stack.setQualityById("InstanceContainer") - assert extruder_stack.quality.getId() == "InstanceContainer" - -## Tests setting qualities by specifying an ID of a quality that doesn't exist. -def test_setQualityByIdDoesntExist(extruder_stack): - with pytest.raises(InvalidContainerError): - extruder_stack.setQualityById("some_quality") #Container registry is empty now. - -## Tests setting quality changes by specifying an ID of a quality change that -# exists. -def test_setQualityChangesByIdExists(extruder_stack, container_registry): - container_registry.return_value = getInstanceContainer(container_type = "quality_changes") - extruder_stack.setQualityChangesById("InstanceContainer") - assert extruder_stack.qualityChanges.getId() == "InstanceContainer" - -## Tests setting quality changes by specifying an ID of a quality change that -# doesn't exist. -def test_setQualityChangesByIdDoesntExist(extruder_stack): - with pytest.raises(InvalidContainerError): - extruder_stack.setQualityChangesById("some_quality_changes") #Container registry is empty now. - -## Tests setting variants by specifying an ID of a variant that exists. -def test_setVariantByIdExists(extruder_stack, container_registry): - container_registry.return_value = getInstanceContainer(container_type = "variant") - extruder_stack.setVariantById("InstanceContainer") - assert extruder_stack.variant.getId() == "InstanceContainer" - -## Tests setting variants by specifying an ID of a variant that doesn't exist. -def test_setVariantByIdDoesntExist(extruder_stack): - with pytest.raises(InvalidContainerError): - extruder_stack.setVariantById("some_variant") #Container registry is empty now. diff --git a/tests/Settings/TestGlobalStack.py b/tests/Settings/TestGlobalStack.py index 9b0735c8f2..6bf10dd8c1 100755 --- a/tests/Settings/TestGlobalStack.py +++ b/tests/Settings/TestGlobalStack.py @@ -116,31 +116,6 @@ def test_addExtruder(global_stack): # global_stack.addExtruder(unittest.mock.MagicMock()) assert len(global_stack.extruders) == 2 #Didn't add the faulty extruder. -## Tests getting the approximate material diameter. -@pytest.mark.parametrize("diameter, approximate_diameter", [ - #Some real-life cases that are common in printers. - (2.85, 3), - (1.75, 2), - (3.0, 3), - (2.0, 2), - #Exceptional cases. - (0, 0), - (-10.1, -10), - (-1, -1), - (9000.1, 9000) -]) -def test_approximateMaterialDiameter(diameter, approximate_diameter, global_stack): - global_stack.definition = DefinitionContainer(container_id = "TestDefinition") - material_diameter = UM.Settings.SettingDefinition.SettingDefinition(key = "material_diameter", container = global_stack.definition) - material_diameter.addSupportedProperty("value", UM.Settings.SettingDefinition.DefinitionPropertyType.Any, default = diameter) - global_stack.definition.definitions.append(material_diameter) - assert float(global_stack.approximateMaterialDiameter) == approximate_diameter - -## Tests getting the material diameter when there is no material diameter. -def test_approximateMaterialDiameterNoDiameter(global_stack): - global_stack.definition = DefinitionContainer(container_id = "TestDefinition") - assert global_stack.approximateMaterialDiameter == "-1" - #Tests setting user changes profiles to invalid containers. @pytest.mark.parametrize("container", [ getInstanceContainer(container_type = "wrong container type"), @@ -486,43 +461,6 @@ def test_removeContainer(global_stack): with pytest.raises(InvalidOperationError): global_stack.removeContainer(unittest.mock.MagicMock()) -## Tests setting definitions by specifying an ID of a definition that exists. -def test_setDefinitionByIdExists(global_stack, container_registry): - container_registry.return_value = DefinitionContainer(container_id = "some_definition") - global_stack.setDefinitionById("some_definition") - assert global_stack.definition.getId() == "some_definition" - -## Tests setting definitions by specifying an ID of a definition that doesn't -# exist. -def test_setDefinitionByIdDoesntExist(global_stack): - with pytest.raises(InvalidContainerError): - global_stack.setDefinitionById("some_definition") #Container registry is empty now. - -## Tests setting definition changes by specifying an ID of a container that -# exists. -def test_setDefinitionChangesByIdExists(global_stack, container_registry): - container_registry.return_value = getInstanceContainer(container_type = "definition_changes") - global_stack.setDefinitionChangesById("InstanceContainer") - assert global_stack.definitionChanges.getId() == "InstanceContainer" - -## Tests setting definition changes by specifying an ID of a container that -# doesn't exist. -def test_setDefinitionChangesByIdDoesntExist(global_stack): - with pytest.raises(InvalidContainerError): - global_stack.setDefinitionChangesById("some_definition_changes") #Container registry is empty now. - -## Tests setting materials by specifying an ID of a material that exists. -def test_setMaterialByIdExists(global_stack, container_registry): - container_registry.return_value = getInstanceContainer(container_type = "material") - global_stack.setMaterialById("InstanceContainer") - assert global_stack.material.getId() == "InstanceContainer" - -## Tests setting materials by specifying an ID of a material that doesn't -# exist. -def test_setMaterialByIdDoesntExist(global_stack): - with pytest.raises(InvalidContainerError): - global_stack.setMaterialById("some_material") #Container registry is empty now. - ## Tests whether changing the next stack is properly forbidden. def test_setNextStack(global_stack): with pytest.raises(InvalidOperationError): @@ -567,50 +505,3 @@ def test_setPropertyOtherContainers(target_container, stack_variable, global_sta global_stack.setProperty(key, property, value, target_container = target_container) #The actual test. getattr(global_stack, stack_variable).setProperty.assert_called_once_with(key, property, value) #Make sure that the proper container gets a setProperty call. - -## Tests setting qualities by specifying an ID of a quality that exists. -def test_setQualityByIdExists(global_stack, container_registry): - container_registry.return_value = getInstanceContainer(container_type = "quality") - global_stack.setQualityById("InstanceContainer") - assert global_stack.quality.getId() == "InstanceContainer" - -## Tests setting qualities by specifying an ID of a quality that doesn't exist. -def test_setQualityByIdDoesntExist(global_stack): - with pytest.raises(InvalidContainerError): - global_stack.setQualityById("some_quality") #Container registry is empty now. - -## Tests setting quality changes by specifying an ID of a quality change that -# exists. -def test_setQualityChangesByIdExists(global_stack, container_registry): - container_registry.return_value = getInstanceContainer(container_type = "quality_changes") - global_stack.setQualityChangesById("InstanceContainer") - assert global_stack.qualityChanges.getId() == "InstanceContainer" - -## Tests setting quality changes by specifying an ID of a quality change that -# doesn't exist. -def test_setQualityChangesByIdDoesntExist(global_stack): - with pytest.raises(InvalidContainerError): - global_stack.setQualityChangesById("some_quality_changes") #Container registry is empty now. - -## Tests setting variants by specifying an ID of a variant that exists. -def test_setVariantByIdExists(global_stack, container_registry): - container_registry.return_value = getInstanceContainer(container_type = "variant") - global_stack.setVariantById("InstanceContainer") - assert global_stack.variant.getId() == "InstanceContainer" - -## Tests setting variants by specifying an ID of a variant that doesn't exist. -def test_setVariantByIdDoesntExist(global_stack): - with pytest.raises(InvalidContainerError): - global_stack.setVariantById("some_variant") #Container registry is empty now. - -## Smoke test for findDefaultVariant -def test_smoke_findDefaultVariant(global_stack): - global_stack.findDefaultVariant() - -## Smoke test for findDefaultMaterial -def test_smoke_findDefaultMaterial(global_stack): - global_stack.findDefaultMaterial() - -## Smoke test for findDefaultQuality -def test_smoke_findDefaultQuality(global_stack): - global_stack.findDefaultQuality()