Browse Source

Merge branch 'CURA-6706_intents_on_quality_mgr_page' of github.com:Ultimaker/Cura into feature_intent

Jaime van Kessel 5 years ago
parent
commit
cb526f0f31

+ 18 - 20
cura/Machines/Models/IntentModel.py

@@ -65,30 +65,28 @@ class IntentModel(ListModel):
 
         material_nodes = self._getActiveMaterials()
 
-        layer_heights_added = []  # type: List[float]
-
+        added_quality_type_set = set()  # type: Set[str]
         for material_node in material_nodes:
             intents = self._getIntentsForMaterial(material_node, quality_groups)
             for intent in intents:
-                if intent["layer_height"] not in layer_heights_added:
+                if intent["quality_type"] not in added_quality_type_set:
                     new_items.append(intent)
-                    layer_heights_added.append(intent["layer_height"])
+                    added_quality_type_set.add(intent["quality_type"])
 
         # Now that we added all intents that we found something for, ensure that we set add ticks (and layer_heights)
         # for all groups that we don't have anything for (and set it to not available)
-        for quality_tuple, quality_group in quality_groups.items():
+        for quality_type, quality_group in quality_groups.items():
             # Add the intents that are of the correct category
-            if quality_tuple[0] != self._intent_category:
+            if quality_type not in added_quality_type_set:
                 layer_height = fetchLayerHeight(quality_group)
-                if layer_height not in layer_heights_added:
-                    new_items.append({"name": "Unavailable",
-                                      "quality_type": "",
-                                      "layer_height": layer_height,
-                                      "intent_category": self._intent_category,
-                                      "available": False})
-                    layer_heights_added.append(layer_height)
-
-        new_items = sorted(new_items, key=lambda x: x["layer_height"])
+                new_items.append({"name": "Unavailable",
+                                  "quality_type": quality_type,
+                                  "layer_height": layer_height,
+                                  "intent_category": self._intent_category,
+                                  "available": False})
+                added_quality_type_set.add(quality_type)
+
+        new_items = sorted(new_items, key = lambda x: x["layer_height"])
         self.setItems(new_items)
 
     ##  Get the active materials for all extruders. No duplicates will be returned
@@ -122,11 +120,11 @@ class IntentModel(ListModel):
                 if intent_node.intent_category != self._intent_category:
                     continue
                 extruder_intents.append({"name": quality_group.name,
-                                  "quality_type": quality_group.quality_type,
-                                  "layer_height": layer_height,
-                                  "available": quality_group.is_available,
-                                  "intent_category": self._intent_category
-                                  })
+                                         "quality_type": quality_group.quality_type,
+                                         "layer_height": layer_height,
+                                         "available": quality_group.is_available,
+                                         "intent_category": self._intent_category
+                                         })
         return extruder_intents
 
     def __repr__(self):

+ 69 - 6
cura/Machines/Models/QualityManagementModel.py

@@ -12,6 +12,10 @@ import cura.CuraApplication  # Imported this way to prevent circular imports.
 from cura.Settings.ContainerManager import ContainerManager
 from cura.Machines.ContainerTree import ContainerTree
 from cura.Settings.cura_empty_instance_containers import empty_quality_changes_container
+from cura.Settings.IntentManager import IntentManager
+
+from UM.i18n import i18nCatalog
+catalog = i18nCatalog("cura")
 
 if TYPE_CHECKING:
     from UM.Settings.Interfaces import ContainerInterface
@@ -19,6 +23,7 @@ if TYPE_CHECKING:
     from cura.Settings.ExtruderStack import ExtruderStack
     from cura.Settings.GlobalStack import GlobalStack
 
+
 #
 # This the QML model for the quality management page.
 #
@@ -26,15 +31,21 @@ class QualityManagementModel(ListModel):
     NameRole = Qt.UserRole + 1
     IsReadOnlyRole = Qt.UserRole + 2
     QualityGroupRole = Qt.UserRole + 3
-    QualityChangesGroupRole = Qt.UserRole + 4
+    QualityTypeRole = Qt.UserRole + 4
+    QualityChangesGroupRole = Qt.UserRole + 5
+    IntentCategoryRole = Qt.UserRole + 6
+    SectionNameRole = Qt.UserRole + 7
 
-    def __init__(self, parent = None):
+    def __init__(self, parent: Optional["QObject"] = None) -> 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.QualityTypeRole, "quality_type")
         self.addRoleName(self.QualityChangesGroupRole, "quality_changes_group")
+        self.addRoleName(self.IntentCategoryRole, "intent_category")
+        self.addRoleName(self.SectionNameRole, "section_name")
 
         application = cura.CuraApplication.CuraApplication.getInstance()
         container_registry = application.getContainerRegistry()
@@ -127,11 +138,13 @@ class QualityManagementModel(ListModel):
         container_registry = cura.CuraApplication.CuraApplication.getInstance().getContainerRegistry()
         new_name = container_registry.uniqueName(new_name)
 
+        intent_category = quality_model_item["intent_category"]
         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, None, new_name, global_stack, extruder_stack = None)
+            new_quality_changes = self._createQualityChanges(quality_group.quality_type, intent_category, new_name,
+                                                             global_stack, extruder_stack = None)
             container_registry.addContainer(new_quality_changes)
         else:
             for metadata in [quality_changes_group.metadata_for_global] + list(quality_changes_group.metadata_per_extruder.values()):
@@ -233,6 +246,30 @@ class QualityManagementModel(ListModel):
         if container.getMetaDataEntry("type") == "quality_changes":
             self._update()
 
+    @pyqtSlot("QVariantMap", result = str)
+    def getQualityItemDisplayName(self, quality_model_item: Dict[str, Any]) -> str:
+        quality_group = quality_model_item["quality_group"]
+        is_read_only = quality_model_item["is_read_only"]
+        intent_category = quality_model_item["intent_category"]
+
+        quality_level_name = "Not Supported"
+        if quality_group is not None:
+            quality_level_name = quality_group.name
+
+        display_name = quality_level_name
+
+        if intent_category != "default":
+            intent_display_name = catalog.i18nc("@label", intent_category.capitalize())
+            display_name = "{intent_name} - {the_rest}".format(intent_name = intent_display_name,
+                                                               the_rest = display_name)
+
+        # A custom quality
+        if not is_read_only:
+            display_name = "{custom_profile_name} - {the_rest}".format(custom_profile_name = quality_model_item["name"],
+                                                                       the_rest = display_name)
+
+        return display_name
+
     def _update(self):
         Logger.log("d", "Updating {model_class_name}.".format(model_class_name = self.__class__.__name__))
 
@@ -253,7 +290,7 @@ class QualityManagementModel(ListModel):
             return
 
         item_list = []
-        # Create quality group items
+        # Create quality group items (intent category = "default")
         for quality_group in quality_group_dict.values():
             if not quality_group.is_available:
                 continue
@@ -261,11 +298,33 @@ class QualityManagementModel(ListModel):
             item = {"name": quality_group.name,
                     "is_read_only": True,
                     "quality_group": quality_group,
-                    "quality_changes_group": None}
+                    "quality_type": quality_group.quality_type,
+                    "quality_changes_group": None,
+                    "intent_category": "default",
+                    "section_name": catalog.i18nc("@label", "Default"),
+                    }
             item_list.append(item)
         # Sort by quality names
         item_list = sorted(item_list, key = lambda x: x["name"].upper())
 
+        # Create intent items (non-default)
+        available_intent_list = IntentManager.getInstance().getCurrentAvailableIntents()
+        available_intent_list = [i for i in available_intent_list if i[0] != "default"]
+        result = []
+        for intent_category, quality_type in available_intent_list:
+            result.append({
+                "name": quality_group_dict[quality_type].name,  # Use the quality name as the display name
+                "is_read_only": True,
+                "quality_group": quality_group_dict[quality_type],
+                "quality_type": quality_type,
+                "quality_changes_group": None,
+                "intent_category": intent_category,
+                "section_name": catalog.i18nc("@label", intent_category.capitalize()),
+            })
+        # Sort by quality_type for each intent category
+        result = sorted(result, key = lambda x: (x["intent_category"], x["quality_type"]))
+        item_list += result
+
         # Create quality_changes group items
         quality_changes_item_list = []
         for quality_changes_group in quality_changes_group_list:
@@ -273,7 +332,11 @@ class QualityManagementModel(ListModel):
             item = {"name": quality_changes_group.name,
                     "is_read_only": False,
                     "quality_group": quality_group,
-                    "quality_changes_group": quality_changes_group}
+                    "quality_type": quality_group.quality_type,
+                    "quality_changes_group": quality_changes_group,
+                    "intent_category": quality_changes_group.intent_category,
+                    "section_name": catalog.i18nc("@label", "Custom profiles"),
+                    }
             quality_changes_item_list.append(item)
 
         # Sort quality_changes items by names and append to the item list

+ 2 - 2
cura/Settings/IntentManager.py

@@ -80,7 +80,7 @@ class IntentManager(QObject):
         for extruder_stack in global_stack.extruderList:
             nozzle_name = extruder_stack.variant.getMetaDataEntry("name")
             material_id = extruder_stack.material.getMetaDataEntry("base_file")
-            final_intent_ids |= {metadata["id"] for metadata in self.intentMetadatas(current_definition_id, nozzle_name, material_id) if metadata["quality_type"] in available_quality_types}
+            final_intent_ids |= {metadata["id"] for metadata in self.intentMetadatas(current_definition_id, nozzle_name, material_id) if metadata.get("quality_type") in available_quality_types}
 
         result = set()  # type: Set[Tuple[str, str]]
         for intent_id in final_intent_ids:
@@ -162,4 +162,4 @@ class IntentManager(QObject):
                 extruder_stack.intent = self.getDefaultIntent()
         application.getMachineManager().setQualityGroupByQualityType(quality_type)
         if old_intent_category != intent_category:
-            self.intentCategoryChanged.emit()
+            self.intentCategoryChanged.emit()

+ 2 - 0
cura/Settings/MachineManager.py

@@ -637,6 +637,7 @@ class MachineManager(QObject):
             category = extruder.intent.getMetaDataEntry("intent_category", "default")
             if category != "default" and category != intent_category:
                 intent_category = category
+
         return intent_category
 
     # Provies a list of extruder positions that have a different intent from the active one.
@@ -1626,6 +1627,7 @@ class MachineManager(QObject):
     #   Otherwise the intent profile will be left to the empty profile, which
     #   represents the "default" intent category.
     #   \param intent_category The intent category to change to.
+    @pyqtSlot(str)
     def setIntentByCategory(self, intent_category: str) -> None:
         global_stack = cura.CuraApplication.CuraApplication.getInstance().getGlobalContainerStack()
         if global_stack is None:

+ 28 - 9
resources/qml/Preferences/ProfilesPage.qml

@@ -7,7 +7,7 @@ import QtQuick.Layouts 1.3
 import QtQuick.Dialogs 1.2
 
 import UM 1.2 as UM
-import Cura 1.0 as Cura
+import Cura 1.6 as Cura
 
 
 Item
@@ -43,6 +43,7 @@ Item
     }
 
     property var currentItemName: hasCurrentItem ? base.currentItem.name : ""
+    property var currentItemDisplayName: hasCurrentItem ? base.qualityManagementModel.getQualityItemDisplayName(base.currentItem) : ""
 
     property var isCurrentItemActivated:
     {
@@ -50,7 +51,14 @@ Item
         {
             return false;
         }
-        return base.currentItem.name == Cura.MachineManager.activeQualityOrQualityChangesName;
+        if (base.currentItem.is_read_only)
+        {
+            return (base.currentItem.name == Cura.MachineManager.activeQualityOrQualityChangesName) && (base.currentItem.intent_category == Cura.MachineManager.activeIntentCategory);
+        }
+        else
+        {
+            return base.currentItem.name == Cura.MachineManager.activeQualityOrQualityChangesName;
+        }
     }
 
     property var canCreateProfile:
@@ -80,7 +88,7 @@ Item
             {
                 if (base.currentItem.is_read_only)
                 {
-                    Cura.MachineManager.setQualityGroup(base.currentItem.quality_group);
+                    Cura.IntentManager.selectIntent(base.currentItem.intent_category, base.currentItem.quality_type);
                 }
                 else
                 {
@@ -434,7 +442,7 @@ Item
                     }
                 }
 
-                section.property: "is_read_only"
+                section.property: "section_name"
                 section.delegate: Rectangle
                 {
                     height: childrenRect.height
@@ -443,7 +451,7 @@ Item
                     {
                         anchors.left: parent.left
                         anchors.leftMargin: UM.Theme.getSize("default_lining").width
-                        text: section == "true" ? catalog.i18nc("@label", "Default profiles") : catalog.i18nc("@label", "Custom profiles")
+                        text: section
                         font.bold: true
                     }
                 }
@@ -467,7 +475,19 @@ Item
                         width: Math.floor((parent.width * 0.8))
                         text: model.name
                         elide: Text.ElideRight
-                        font.italic: model.name == Cura.MachineManager.activeQualityOrQualityChangesName
+                        font.italic:
+                        {
+                            if (model.is_read_only)
+                            {
+                                // For built-in qualities, it needs to match both the intent category and the quality name
+                                return model.name == Cura.MachineManager.activeQualityOrQualityChangesName && model.intent_category == Cura.MachineManager.activeIntentCategory
+                            }
+                            else
+                            {
+                                // For custom qualities, it only needs to match the name
+                                return model.name == Cura.MachineManager.activeQualityOrQualityChangesName
+                            }
+                        }
                         color: parent.isCurrentItem ? palette.highlightedText : palette.text
                     }
 
@@ -511,7 +531,7 @@ Item
 
                     Label
                     {
-                        text: base.currentItemName
+                        text: base.currentItemDisplayName
                         font: UM.Theme.getFont("large_bold")
                     }
                 }
@@ -519,7 +539,7 @@ Item
                 Flow
                 {
                     id: currentSettingsActions
-                    visible: base.hasCurrentItem && base.currentItem.name == Cura.MachineManager.activeQualityOrQualityChangesName
+                    visible: base.hasCurrentItem && base.currentItem.name == Cura.MachineManager.activeQualityOrQualityChangesName && base.currentItem.intent_category == Cura.MachineManager.activeIntentCategory
                     anchors.left: parent.left
                     anchors.right: parent.right
                     anchors.top: profileName.bottom
@@ -567,7 +587,6 @@ Item
                     }
                 }
 
-
                 TabView
                 {
                     anchors.left: parent.left

+ 5 - 3
tests/TestQualityManager.py

@@ -118,10 +118,12 @@ def test_duplicateQualityChanges(quality_mocked_application):
     quality_group.getAllNodes = MagicMock(return_value = mocked_quality)
     quality_changes_group = MagicMock()
     mocked_quality_changes = MagicMock()
-    quality_changes_group.getAllNodes = MagicMock(return_value=[mocked_quality_changes])
+    quality_changes_group.getAllNodes = MagicMock(return_value = [mocked_quality_changes])
     mocked_quality_changes.duplicate = MagicMock(return_value = mocked_quality_changes)
 
     manager._container_registry.addContainer = MagicMock()  # Side effect we want to check.
 
-    manager.duplicateQualityChanges("zomg", {"quality_group": quality_group, "quality_changes_group": quality_changes_group})
-    assert manager._container_registry.addContainer.called_once_with(mocked_quality_changes)
+    manager.duplicateQualityChanges("zomg", {"intent_category": "default",
+                                             "quality_group": quality_group,
+                                             "quality_changes_group": quality_changes_group})
+    assert manager._container_registry.addContainer.called_once_with(mocked_quality_changes)