Add thumbnail to all 3MF files, and add relation and content-type metadata

This commit is contained in:
fieldOfView 2021-12-01 21:46:40 +01:00
parent 0813f27389
commit 0a906accec
2 changed files with 36 additions and 20 deletions

View file

@ -5,8 +5,6 @@ import configparser
from io import StringIO from io import StringIO
import zipfile import zipfile
from PyQt5.QtCore import QBuffer
from UM.Application import Application from UM.Application import Application
from UM.Logger import Logger from UM.Logger import Logger
from UM.Preferences import Preferences from UM.Preferences import Preferences
@ -16,7 +14,7 @@ from UM.i18n import i18nCatalog
catalog = i18nCatalog("cura") catalog = i18nCatalog("cura")
from cura.Utils.Threading import call_on_qt_thread from cura.Utils.Threading import call_on_qt_thread
from cura.Snapshot import Snapshot
class ThreeMFWorkspaceWriter(WorkspaceWriter): class ThreeMFWorkspaceWriter(WorkspaceWriter):
def __init__(self): def __init__(self):
@ -88,23 +86,7 @@ class ThreeMFWorkspaceWriter(WorkspaceWriter):
self._writePluginMetadataToArchive(archive) self._writePluginMetadataToArchive(archive)
# Attempt to add a thumbnail # Close the archive & reset states.
Logger.log("d", "Creating thumbnail image...")
try:
snapshot = Snapshot.snapshot(width = 300, height = 300)
except Exception:
snapshot = None
Logger.logException("w", "Failed to create snapshot image")
if snapshot:
thumbnail_file = zipfile.ZipInfo("Metadata/thumbnail.png")
thumbnail_buffer = QBuffer()
thumbnail_buffer.open(QBuffer.ReadWrite)
snapshot.save(thumbnail_buffer, "PNG")
archive.writestr(thumbnail_file, thumbnail_buffer.data())
# Close the archive & reset states
archive.close() archive.close()
except PermissionError: except PermissionError:
self.setInformation(catalog.i18nc("@error:zip", "No permission to write the workspace here.")) self.setInformation(catalog.i18nc("@error:zip", "No permission to write the workspace here."))

View file

@ -10,6 +10,10 @@ from UM.Application import Application
from UM.Scene.SceneNode import SceneNode from UM.Scene.SceneNode import SceneNode
from cura.CuraApplication import CuraApplication from cura.CuraApplication import CuraApplication
from cura.Utils.Threading import call_on_qt_thread
from cura.Snapshot import Snapshot
from PyQt5.QtCore import QBuffer
import Savitar import Savitar
@ -149,6 +153,22 @@ class ThreeMFWriter(MeshWriter):
relations_element = ET.Element("Relationships", xmlns = self._namespaces["relationships"]) relations_element = ET.Element("Relationships", xmlns = self._namespaces["relationships"])
model_relation_element = ET.SubElement(relations_element, "Relationship", Target = "/3D/3dmodel.model", Id = "rel0", Type = "http://schemas.microsoft.com/3dmanufacturing/2013/01/3dmodel") model_relation_element = ET.SubElement(relations_element, "Relationship", Target = "/3D/3dmodel.model", Id = "rel0", Type = "http://schemas.microsoft.com/3dmanufacturing/2013/01/3dmodel")
# Attempt to add a thumbnail
snapshot = self._createSnapshot()
if snapshot:
thumbnail_buffer = QBuffer()
thumbnail_buffer.open(QBuffer.ReadWrite)
snapshot.save(thumbnail_buffer, "PNG")
thumbnail_file = zipfile.ZipInfo("Metadata/thumbnail.png")
# Don't try to compress snapshot file, because the PNG is pretty much as compact as it will get
archive.writestr(thumbnail_file, thumbnail_buffer.data())
# Add PNG to content types file
thumbnail_type = ET.SubElement(content_types, "Default", Extension = "png", ContentType = "image/png")
# Add thumbnail relation to _rels/.rels file
thumbnail_relation_element = ET.SubElement(relations_element, "Relationship", Target = "/Metadata/thumbnail.png", Id = "rel1", Type = "http://schemas.openxmlformats.org/package/2006/relationships/metadata/thumbnail")
savitar_scene = Savitar.Scene() savitar_scene = Savitar.Scene()
metadata_to_store = CuraApplication.getInstance().getController().getScene().getMetaData() metadata_to_store = CuraApplication.getInstance().getController().getScene().getMetaData()
@ -212,3 +232,17 @@ class ThreeMFWriter(MeshWriter):
self._archive = archive self._archive = archive
return True return True
@call_on_qt_thread # must be called from the main thread because of OpenGL
def _createSnapshot(self) -> None:
Logger.log("d", "Creating thumbnail image...")
if not CuraApplication.getInstance().isVisible:
Logger.log("w", "Can't create snapshot when renderer not initialized.")
return None
try:
snapshot = Snapshot.snapshot(width = 300, height = 300)
except:
Logger.logException("w", "Failed to create snapshot image")
return None
return snapshot