mirror of
https://git.mirrors.martin98.com/https://github.com/Ultimaker/Cura
synced 2025-08-16 15:35:54 +08:00
Merge branch '2.3' of https://github.com/Ultimaker/Cura into 2.3
This commit is contained in:
commit
73d7e22efe
@ -58,9 +58,9 @@ class XmlMaterialProfile(UM.Settings.InstanceContainer):
|
|||||||
def setReadOnly(self, read_only):
|
def setReadOnly(self, read_only):
|
||||||
super().setReadOnly(read_only)
|
super().setReadOnly(read_only)
|
||||||
|
|
||||||
basefile = self.getMetaDataEntry("base_file", self._id) #if basefile is none, this is a basefile.
|
basefile = self.getMetaDataEntry("base_file", self._id) # if basefile is self.id, this is a basefile.
|
||||||
for container in UM.Settings.ContainerRegistry.getInstance().findInstanceContainers(base_file = basefile):
|
for container in UM.Settings.ContainerRegistry.getInstance().findInstanceContainers(base_file = basefile):
|
||||||
container._read_only = read_only
|
container._read_only = read_only # prevent loop instead of calling setReadOnly
|
||||||
|
|
||||||
## Overridden from InstanceContainer
|
## Overridden from InstanceContainer
|
||||||
def setMetaDataEntry(self, key, value):
|
def setMetaDataEntry(self, key, value):
|
||||||
@ -69,7 +69,7 @@ class XmlMaterialProfile(UM.Settings.InstanceContainer):
|
|||||||
|
|
||||||
super().setMetaDataEntry(key, value)
|
super().setMetaDataEntry(key, value)
|
||||||
|
|
||||||
basefile = self.getMetaDataEntry("base_file", self._id) #if basefile is none, this is a basefile.
|
basefile = self.getMetaDataEntry("base_file", self._id) #if basefile is self.id, this is a basefile.
|
||||||
# Update all containers that share GUID and basefile
|
# Update all containers that share GUID and basefile
|
||||||
for container in UM.Settings.ContainerRegistry.getInstance().findInstanceContainers(base_file = basefile):
|
for container in UM.Settings.ContainerRegistry.getInstance().findInstanceContainers(base_file = basefile):
|
||||||
container.setMetaData(copy.deepcopy(self._metadata))
|
container.setMetaData(copy.deepcopy(self._metadata))
|
||||||
@ -95,15 +95,15 @@ class XmlMaterialProfile(UM.Settings.InstanceContainer):
|
|||||||
container.setName(new_name)
|
container.setName(new_name)
|
||||||
|
|
||||||
## Overridden from InstanceContainer
|
## Overridden from InstanceContainer
|
||||||
def setProperty(self, key, property_name, property_value, container = None):
|
# def setProperty(self, key, property_name, property_value, container = None):
|
||||||
if self.isReadOnly():
|
# if self.isReadOnly():
|
||||||
return
|
# return
|
||||||
|
#
|
||||||
super().setProperty(key, property_name, property_value)
|
# super().setProperty(key, property_name, property_value)
|
||||||
|
#
|
||||||
basefile = self.getMetaDataEntry("base_file", self._id) #if basefile is none, this is a basefile.
|
# basefile = self.getMetaDataEntry("base_file", self._id) #if basefile is self.id, this is a basefile.
|
||||||
for container in UM.Settings.ContainerRegistry.getInstance().findInstanceContainers(base_file = basefile):
|
# for container in UM.Settings.ContainerRegistry.getInstance().findInstanceContainers(base_file = basefile):
|
||||||
container._dirty = True
|
# container._dirty = True
|
||||||
|
|
||||||
## Overridden from InstanceContainer
|
## Overridden from InstanceContainer
|
||||||
def serialize(self):
|
def serialize(self):
|
||||||
@ -272,29 +272,90 @@ class XmlMaterialProfile(UM.Settings.InstanceContainer):
|
|||||||
self._inherited_files.append(path)
|
self._inherited_files.append(path)
|
||||||
return ET.fromstring(contents)
|
return ET.fromstring(contents)
|
||||||
|
|
||||||
|
# The XML material profile can have specific settings for machines.
|
||||||
|
# Some machines share profiles, so they are only created once.
|
||||||
|
# This function duplicates those elements so that each machine tag only has one identifier.
|
||||||
|
def _flattenMachinesXML(self, element):
|
||||||
|
settings_element = element.find("./um:settings", self.__namespaces)
|
||||||
|
machines = settings_element.iterfind("./um:machine", self.__namespaces)
|
||||||
|
machines_to_add = []
|
||||||
|
machines_to_remove = []
|
||||||
|
for machine in machines:
|
||||||
|
identifiers = list(machine.iterfind("./um:machine_identifier", self.__namespaces))
|
||||||
|
has_multiple_identifiers = len(identifiers) > 1
|
||||||
|
if has_multiple_identifiers:
|
||||||
|
# Multiple identifiers found. We need to create a new machine element and copy all it's settings there.
|
||||||
|
for identifier in identifiers:
|
||||||
|
new_machine = copy.deepcopy(machine)
|
||||||
|
# Create list of identifiers that need to be removed from the copied element.
|
||||||
|
other_identifiers = [self._createKey(other_identifier) for other_identifier in identifiers if other_identifier is not identifier]
|
||||||
|
# As we can only remove by exact object reference, we need to look through the identifiers of copied machine.
|
||||||
|
new_machine_identifiers = list(new_machine.iterfind("./um:machine_identifier", self.__namespaces))
|
||||||
|
for new_machine_identifier in new_machine_identifiers:
|
||||||
|
key = self._createKey(new_machine_identifier)
|
||||||
|
# Key was in identifiers to remove, so this element needs to be purged
|
||||||
|
if key in other_identifiers:
|
||||||
|
new_machine.remove(new_machine_identifier)
|
||||||
|
machines_to_add.append(new_machine)
|
||||||
|
machines_to_remove.append(machine)
|
||||||
|
else:
|
||||||
|
pass # Machine only has one identifier. Nothing to do.
|
||||||
|
# Remove & add all required machines.
|
||||||
|
for machine_to_remove in machines_to_remove:
|
||||||
|
settings_element.remove(machine_to_remove)
|
||||||
|
for machine_to_add in machines_to_add:
|
||||||
|
settings_element.append(machine_to_add)
|
||||||
|
return element
|
||||||
|
|
||||||
def _mergeXML(self, first, second):
|
def _mergeXML(self, first, second):
|
||||||
result = copy.deepcopy(first)
|
result = copy.deepcopy(first)
|
||||||
self._combineElement(result, second)
|
self._combineElement(self._flattenMachinesXML(result), self._flattenMachinesXML(second))
|
||||||
return result
|
return result
|
||||||
|
|
||||||
|
def _createKey(self, element):
|
||||||
|
key = element.tag.split("}")[-1]
|
||||||
|
if "key" in element.attrib:
|
||||||
|
key += " key:" + element.attrib["key"]
|
||||||
|
if "manufacturer" in element.attrib:
|
||||||
|
key += " manufacturer:" + element.attrib["manufacturer"]
|
||||||
|
if "product" in element.attrib:
|
||||||
|
key += " product:" + element.attrib["product"]
|
||||||
|
if key == "machine":
|
||||||
|
for item in element:
|
||||||
|
if "machine_identifier" in item.tag:
|
||||||
|
key += " " + item.attrib["product"]
|
||||||
|
return key
|
||||||
|
|
||||||
# Recursively merges XML elements. Updates either the text or children if another element is found in first.
|
# Recursively merges XML elements. Updates either the text or children if another element is found in first.
|
||||||
# If it does not exist, copies it from second.
|
# If it does not exist, copies it from second.
|
||||||
def _combineElement(self, first, second):
|
def _combineElement(self, first, second):
|
||||||
# Create a mapping from tag name to element.
|
# Create a mapping from tag name to element.
|
||||||
mapping = {el.tag: el for el in first}
|
|
||||||
for el in second:
|
mapping = {}
|
||||||
if len(el): # Check if element has children.
|
for element in first:
|
||||||
|
key = self._createKey(element)
|
||||||
|
mapping[key] = element
|
||||||
|
for element in second:
|
||||||
|
key = self._createKey(element)
|
||||||
|
if len(element): # Check if element has children.
|
||||||
try:
|
try:
|
||||||
self._combineElement(mapping[el.tag], el) # Multiple elements, handle those.
|
if "setting " in key:
|
||||||
|
# Setting can have points in it. In that case, delete all values and override them.
|
||||||
|
for child in list(mapping[key]):
|
||||||
|
mapping[key].remove(child)
|
||||||
|
for child in element:
|
||||||
|
mapping[key].append(child)
|
||||||
|
else:
|
||||||
|
self._combineElement(mapping[key], element) # Multiple elements, handle those.
|
||||||
except KeyError:
|
except KeyError:
|
||||||
mapping[el.tag] = el
|
mapping[key] = element
|
||||||
first.append(el)
|
first.append(element)
|
||||||
else:
|
else:
|
||||||
try:
|
try:
|
||||||
mapping[el.tag].text = el.text
|
mapping[key].text = element.text
|
||||||
except KeyError: # Not in the mapping, so simply add it
|
except KeyError: # Not in the mapping, so simply add it
|
||||||
mapping[el.tag] = el
|
mapping[key] = element
|
||||||
first.append(el)
|
first.append(element)
|
||||||
|
|
||||||
## Overridden from InstanceContainer
|
## Overridden from InstanceContainer
|
||||||
def deserialize(self, serialized):
|
def deserialize(self, serialized):
|
||||||
@ -305,7 +366,7 @@ class XmlMaterialProfile(UM.Settings.InstanceContainer):
|
|||||||
|
|
||||||
# TODO: Add material verfication
|
# TODO: Add material verfication
|
||||||
self.addMetaDataEntry("status", "unknown")
|
self.addMetaDataEntry("status", "unknown")
|
||||||
|
|
||||||
inherits = data.find("./um:inherits", self.__namespaces)
|
inherits = data.find("./um:inherits", self.__namespaces)
|
||||||
if inherits is not None:
|
if inherits is not None:
|
||||||
inherited = self._resolveInheritance(inherits.text)
|
inherited = self._resolveInheritance(inherits.text)
|
||||||
|
@ -8,6 +8,7 @@
|
|||||||
"author": "Calvindog717",
|
"author": "Calvindog717",
|
||||||
"manufacturer": "PrintrBot",
|
"manufacturer": "PrintrBot",
|
||||||
"category": "Other",
|
"category": "Other",
|
||||||
|
"platform": "printrbot_simple_metal_platform.stl",
|
||||||
"file_formats": "text/x-gcode"
|
"file_formats": "text/x-gcode"
|
||||||
},
|
},
|
||||||
|
|
||||||
@ -17,7 +18,7 @@
|
|||||||
"machine_height": { "default_value": 150 },
|
"machine_height": { "default_value": 150 },
|
||||||
"machine_depth": { "default_value": 140 },
|
"machine_depth": { "default_value": 140 },
|
||||||
"machine_center_is_zero": { "default_value": false },
|
"machine_center_is_zero": { "default_value": false },
|
||||||
"machine_nozzle_size": { "default_value": 0.3 },
|
"machine_nozzle_size": { "default_value": 0.4 },
|
||||||
"material_diameter": { "default_value": 1.75 },
|
"material_diameter": { "default_value": 1.75 },
|
||||||
"machine_nozzle_heat_up_speed": { "default_value": 2 },
|
"machine_nozzle_heat_up_speed": { "default_value": 2 },
|
||||||
"machine_nozzle_cool_down_speed": { "default_value": 2 },
|
"machine_nozzle_cool_down_speed": { "default_value": 2 },
|
||||||
@ -33,10 +34,10 @@
|
|||||||
"machine_gcode_flavor": { "default_value": "RepRap (Marlin/Sprinter)" },
|
"machine_gcode_flavor": { "default_value": "RepRap (Marlin/Sprinter)" },
|
||||||
|
|
||||||
"machine_start_gcode": {
|
"machine_start_gcode": {
|
||||||
"default_value": "G21 ;metric values\nG90 ;absolute positioning\nM82 ;set extruder to absolute mode\nM107 ;start with the fan off\nG28 X0 Y0 ;move X/Y to min endstops\nG28 Z0 ;move Z to min endstops\nG29 ; auto bed-levelling\nG1 Z15.0 F9000 ;move the platform down 15mm\nG92 E0 ;zero the extruded length\nG1 F200 E3 ;extrude 3mm of feed stock\nG92 E0 ;zero the extruded length again\nG1 F9000\n;Put printing message on LCD screen\nM117 Printing..."
|
"default_value": "G21 ;metric values\nG90 ;absolute positioning\nM82 ;set extruder to absolute mode\nM107 ;start with the fan off\nG28 X0 Y0 ;home X/Y\nG28 Z0 ;home Z\nG92 E0 ;zero the extruded length\nG29 ;initiate auto bed leveling sequence\nG92 X132.4 Y20 ;correct bed origin (G29 changes it)"
|
||||||
},
|
},
|
||||||
"machine_end_gcode": {
|
"machine_end_gcode": {
|
||||||
"default_value": "M104 S0 ;extruder heater off\nM140 S0 ;heated bed heater off (if you have it)\nG91 ;relative positioning\nG1 E-1 F300 ;retract the filament a bit before lifting the nozzle, to release some of the pressure\nG1 Z+0.5 E-5 X-20 Y-20 F9000 ;move Z up a bit and retract filament even more\nG28 X0 Y0 ;move X/Y to min endstops, so the head is out of the way\nM84 ;steppers off\nG90 ;absolute positioning"
|
"default_value": "M104 S0 ;extruder heater off\nM140 S0 ;heated bed heater off (if you have it)\nM106 S0 ;fan off\nG91 ;relative positioning\nG1 E-1 F300 ;retract the filament a bit\nG1 Z+1 E-5 F9000 ;move Z up a bit and retract even more\nG28 X0 Y0 ;home X/Y, so the head is out of the way\nM84 ;steppers off\nG90 ;absolute positioning"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -3,6 +3,7 @@
|
|||||||
Automatically generated PLA profile. Data in this file may not be not correct.
|
Automatically generated PLA profile. Data in this file may not be not correct.
|
||||||
-->
|
-->
|
||||||
<fdmmaterial xmlns="http://www.ultimaker.com/material">
|
<fdmmaterial xmlns="http://www.ultimaker.com/material">
|
||||||
|
<inherits>generic_pla</inherits>
|
||||||
<metadata>
|
<metadata>
|
||||||
<name>
|
<name>
|
||||||
<brand>Ultimaker</brand>
|
<brand>Ultimaker</brand>
|
||||||
@ -36,16 +37,15 @@ Automatically generated PLA profile. Data in this file may not be not correct.
|
|||||||
<machine_identifier manufacturer="Ultimaker" product="Ultimaker 2"/>
|
<machine_identifier manufacturer="Ultimaker" product="Ultimaker 2"/>
|
||||||
<machine_identifier manufacturer="Ultimaker" product="Ultimaker 2 Go"/>
|
<machine_identifier manufacturer="Ultimaker" product="Ultimaker 2 Go"/>
|
||||||
<machine_identifier manufacturer="Ultimaker" product="Ultimaker 2 Extended"/>
|
<machine_identifier manufacturer="Ultimaker" product="Ultimaker 2 Extended"/>
|
||||||
<setting key="standby temperature">150</setting>
|
|
||||||
<setting key="processing temperature graph">
|
<setting key="processing temperature graph">
|
||||||
<point flow="2" temperature="180"/>
|
<point flow="2" temperature="20"/>
|
||||||
<point flow="10" temperature="230"/>
|
<point flow="10" temperature="20"/>
|
||||||
</setting>
|
</setting>
|
||||||
</machine>
|
</machine>
|
||||||
|
|
||||||
<machine>
|
<machine>
|
||||||
<machine_identifier manufacturer="Ultimaker" product="Ultimaker Original"/>
|
<machine_identifier manufacturer="Ultimaker" product="Ultimaker Original"/>
|
||||||
<setting key="standby temperature">150</setting>
|
<setting key="standby temperature">180</setting>
|
||||||
</machine>
|
</machine>
|
||||||
</settings>
|
</settings>
|
||||||
</fdmmaterial>
|
</fdmmaterial>
|
||||||
|
BIN
resources/meshes/printrbot_simple_metal_platform.stl
Normal file
BIN
resources/meshes/printrbot_simple_metal_platform.stl
Normal file
Binary file not shown.
@ -129,6 +129,7 @@ UM.ManagementPage
|
|||||||
enabled: base.currentItem != null && base.currentItem.id != Cura.MachineManager.activeMaterialId
|
enabled: base.currentItem != null && base.currentItem.id != Cura.MachineManager.activeMaterialId
|
||||||
onClicked: Cura.MachineManager.setActiveMaterial(base.currentItem.id)
|
onClicked: Cura.MachineManager.setActiveMaterial(base.currentItem.id)
|
||||||
},
|
},
|
||||||
|
/* // apparently visible does not work on OS X
|
||||||
Button
|
Button
|
||||||
{
|
{
|
||||||
text: catalog.i18nc("@action:button", "Duplicate");
|
text: catalog.i18nc("@action:button", "Duplicate");
|
||||||
@ -153,6 +154,7 @@ UM.ManagementPage
|
|||||||
}
|
}
|
||||||
visible: false;
|
visible: false;
|
||||||
},
|
},
|
||||||
|
*/
|
||||||
Button
|
Button
|
||||||
{
|
{
|
||||||
text: catalog.i18nc("@action:button", "Remove");
|
text: catalog.i18nc("@action:button", "Remove");
|
||||||
@ -160,6 +162,7 @@ UM.ManagementPage
|
|||||||
enabled: base.currentItem != null && !base.currentItem.readOnly && !Cura.ContainerManager.isContainerUsed(base.currentItem.id)
|
enabled: base.currentItem != null && !base.currentItem.readOnly && !Cura.ContainerManager.isContainerUsed(base.currentItem.id)
|
||||||
onClicked: confirmDialog.open()
|
onClicked: confirmDialog.open()
|
||||||
},
|
},
|
||||||
|
/* // apparently visible does not work on OS X
|
||||||
Button
|
Button
|
||||||
{
|
{
|
||||||
text: catalog.i18nc("@action:button", "Import");
|
text: catalog.i18nc("@action:button", "Import");
|
||||||
@ -167,6 +170,7 @@ UM.ManagementPage
|
|||||||
onClicked: importDialog.open();
|
onClicked: importDialog.open();
|
||||||
visible: false;
|
visible: false;
|
||||||
},
|
},
|
||||||
|
*/
|
||||||
Button
|
Button
|
||||||
{
|
{
|
||||||
text: catalog.i18nc("@action:button", "Export")
|
text: catalog.i18nc("@action:button", "Export")
|
||||||
|
@ -246,8 +246,8 @@ Item {
|
|||||||
// This ensures that the value in any of the deeper containers need not be removed, which is
|
// This ensures that the value in any of the deeper containers need not be removed, which is
|
||||||
// needed for the reset button (which deletes the top value) to correctly go back to profile
|
// needed for the reset button (which deletes the top value) to correctly go back to profile
|
||||||
// defaults.
|
// defaults.
|
||||||
propertyProvider.setPropertyValue("state", "InstanceState.Calculated")
|
|
||||||
propertyProvider.setPropertyValue("value", propertyProvider.getPropertyValue("value", last_entry))
|
propertyProvider.setPropertyValue("value", propertyProvider.getPropertyValue("value", last_entry))
|
||||||
|
propertyProvider.setPropertyValue("state", "InstanceState.Calculated")
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
x
Reference in New Issue
Block a user