Browse Source

Merge branch '4.6'

Ghostkeeper 4 years ago
parent
commit
e1308f0768

+ 1 - 0
cura/PreviewPass.py

@@ -61,6 +61,7 @@ class PreviewPass(RenderPass):
                 self._shader.setUniformValue("u_ambientColor", [0.1, 0.1, 0.1, 1.0])
                 self._shader.setUniformValue("u_specularColor", [0.6, 0.6, 0.6, 1.0])
                 self._shader.setUniformValue("u_shininess", 20.0)
+                self._shader.setUniformValue("u_renderError", 0.0)  # We don't want any error markers!.
                 self._shader.setUniformValue("u_faceId", -1)  # Don't render any selected faces in the preview.
 
         if not self._non_printing_shader:

+ 25 - 11
plugins/CuraEngineBackend/StartSliceJob.py

@@ -13,6 +13,8 @@ from UM.Job import Job
 from UM.Logger import Logger
 from UM.Scene.SceneNode import SceneNode
 from UM.Settings.ContainerStack import ContainerStack #For typing.
+from UM.Settings.InstanceContainer import InstanceContainer
+from UM.Settings.SettingDefinition import SettingDefinition
 from UM.Settings.SettingRelation import SettingRelation #For typing.
 
 from UM.Scene.Iterator.DepthFirstIterator import DepthFirstIterator
@@ -103,20 +105,33 @@ class StartSliceJob(Job):
     ##  Check if a stack has any errors.
     ##  returns true if it has errors, false otherwise.
     def _checkStackForErrors(self, stack: ContainerStack) -> bool:
-        if stack is None:
-            return False
 
-        # if there are no per-object settings we don't need to check the other settings here
-        stack_top = stack.getTop()
-        if stack_top is None or not stack_top.getAllKeys():
-            return False
+        top_of_stack = cast(InstanceContainer, stack.getTop())  # Cache for efficiency.
+        changed_setting_keys = top_of_stack.getAllKeys()
 
-        for key in stack.getAllKeys():
-            validation_state = stack.getProperty(key, "validationState")
-            if validation_state in (ValidatorState.Exception, ValidatorState.MaximumError, ValidatorState.MinimumError, ValidatorState.Invalid):
-                Logger.log("w", "Setting %s is not valid, but %s. Aborting slicing.", key, validation_state)
+        # Add all relations to changed settings as well.
+        for key in top_of_stack.getAllKeys():
+            instance = top_of_stack.getInstance(key)
+            if instance is None:
+                continue
+            self._addRelations(changed_setting_keys, instance.definition.relations)
+            Job.yieldThread()
+
+        for changed_setting_key in changed_setting_keys:
+            validation_state = stack.getProperty(changed_setting_key, "validationState")
+
+            if validation_state is None:
+                definition = cast(SettingDefinition, stack.getSettingDefinition(changed_setting_key))
+                validator_type = SettingDefinition.getValidatorForType(definition.type)
+                if validator_type:
+                    validator = validator_type(changed_setting_key)
+                    validation_state = validator(stack)
+            if validation_state in (
+            ValidatorState.Exception, ValidatorState.MaximumError, ValidatorState.MinimumError, ValidatorState.Invalid):
+                Logger.log("w", "Setting %s is not valid, but %s. Aborting slicing.", changed_setting_key, validation_state)
                 return True
             Job.yieldThread()
+
         return False
 
     ##  Runs the job that initiates the slicing.
@@ -511,4 +526,3 @@ class StartSliceJob(Job):
 
             relations_set.add(relation.target.key)
             self._addRelations(relations_set, relation.target.relations)
-

+ 1 - 1
plugins/PerObjectSettingsTool/PerObjectSettingsPanel.qml

@@ -54,7 +54,7 @@ Item
         UM.ActiveTool.setProperty("MeshType", type)
     }
 
-    UM.I18nCatalog { id: catalog; name: "uranium"}
+    UM.I18nCatalog { id: catalog; name: "cura"}
 
     Column
     {

+ 0 - 19
plugins/SolidView/SolidView.py

@@ -286,25 +286,6 @@ class SolidView(View):
                 Logger.log("i", "X-Ray overlay found non-manifold pixels.")
 
     def event(self, event):
-        if event.type == Event.ViewActivateEvent:
-            # FIX: on Max OS X, somehow QOpenGLContext.currentContext() can become None during View switching.
-            # This can happen when you do the following steps:
-            #   1. Start Cura
-            #   2. Load a model
-            #   3. Switch to Custom mode
-            #   4. Select the model and click on the per-object tool icon
-            #   5. Switch view to Layer view or X-Ray
-            #   6. Cura will very likely crash
-            # It seems to be a timing issue that the currentContext can somehow be empty, but I have no clue why.
-            # This fix tries to reschedule the view changing event call on the Qt thread again if the current OpenGL
-            # context is None.
-            if Platform.isOSX():
-                if QOpenGLContext.currentContext() is None:
-                    Logger.log("d", "current context of OpenGL is empty on Mac OS X, will try to create shaders later")
-                    Application.getInstance().callLater(lambda e = event: self.event(e))
-                    return
-
-
         if event.type == Event.ViewDeactivateEvent:
             if self._composite_pass and 'xray' in self._composite_pass.getLayerBindings():
                 self.getRenderer().removeRenderPass(self._xray_pass)

+ 4 - 1
plugins/UM3NetworkPrinting/src/Models/Http/ClusterPrintJobStatus.py

@@ -1,4 +1,4 @@
-# Copyright (c) 2019 Ultimaker B.V.
+# Copyright (c) 2020 Ultimaker B.V.
 # Cura is released under the terms of the LGPLv3 or higher.
 from typing import List, Optional, Union, Dict, Any
 
@@ -44,6 +44,7 @@ class ClusterPrintJobStatus(BaseModel):
     #  \param compatible_machine_families: Family names of machines suitable for this print job
     #  \param impediments_to_printing: A list of reasons that prevent this job from being printed on the associated
     #       printer
+    #  \param preview_url: URL to the preview image (same as wou;d've been included in the ufp).
     def __init__(self, created_at: str, force: bool, machine_variant: str, name: str, started: bool, status: str,
                  time_total: int, uuid: str,
                  configuration: List[Union[Dict[str, Any], ClusterPrintCoreConfiguration]],
@@ -57,6 +58,7 @@ class ClusterPrintJobStatus(BaseModel):
                  build_plate: Union[Dict[str, Any], ClusterBuildPlate] = None,
                  compatible_machine_families: List[str] = None,
                  impediments_to_printing: List[Union[Dict[str, Any], ClusterPrintJobImpediment]] = None,
+                 preview_url: Optional[str] = None,
                  **kwargs) -> None:
         self.assigned_to = assigned_to
         self.configuration = self.parseModels(ClusterPrintCoreConfiguration, configuration)
@@ -76,6 +78,7 @@ class ClusterPrintJobStatus(BaseModel):
         self.uuid = uuid
         self.deleted_at = deleted_at
         self.printed_on_uuid = printed_on_uuid
+        self.preview_url = preview_url
 
         self.configuration_changes_required = self.parseModels(ClusterPrintJobConfigurationChange,
                                                                configuration_changes_required) \

+ 15 - 2
plugins/UM3NetworkPrinting/src/Models/UM3PrintJobOutputModel.py

@@ -1,10 +1,13 @@
-# Copyright (c) 2019 Ultimaker B.V.
+# Copyright (c) 2020 Ultimaker B.V.
 # Cura is released under the terms of the LGPLv3 or higher.
-from typing import List
+from typing import List, Optional
 
 from PyQt5.QtCore import pyqtProperty, pyqtSignal
 from PyQt5.QtGui import QImage
+from PyQt5.QtNetwork import QNetworkReply, QNetworkRequest
 
+from UM.Logger import Logger
+from UM.TaskManagement.HttpRequestManager import HttpRequestManager
 from cura.PrinterOutput.Models.PrintJobOutputModel import PrintJobOutputModel
 from cura.PrinterOutput.PrinterOutputController import PrinterOutputController
 
@@ -32,3 +35,13 @@ class UM3PrintJobOutputModel(PrintJobOutputModel):
         image = QImage()
         image.loadFromData(data)
         self.updatePreviewImage(image)
+
+    def loadPreviewImageFromUrl(self, url: str) -> None:
+        HttpRequestManager.getInstance().get(url=url, callback=self._onImageLoaded, error_callback=self._onImageLoaded)
+
+    def _onImageLoaded(self, reply: QNetworkReply, error: Optional["QNetworkReply.NetworkError"] = None) -> None:
+        if not HttpRequestManager.replyIndicatesSuccess(reply, error):
+            Logger.warning("Requesting preview image failed, response code {0} while trying to connect to {1}".format(
+                           reply.attribute(QNetworkRequest.HttpStatusCodeAttribute), reply.url()))
+            return
+        self.updatePreviewImageData(reply.readAll())

+ 3 - 1
plugins/UM3NetworkPrinting/src/UltimakerNetworkedPrinterOutputDevice.py

@@ -1,4 +1,4 @@
-# Copyright (c) 2019 Ultimaker B.V.
+# Copyright (c) 2020 Ultimaker B.V.
 # Cura is released under the terms of the LGPLv3 or higher.
 import os
 from time import time
@@ -330,6 +330,8 @@ class UltimakerNetworkedPrinterOutputDevice(NetworkedPrinterOutputDevice):
             self._updateAssignedPrinter(model, remote_job.printer_uuid)
         if remote_job.assigned_to:
             self._updateAssignedPrinter(model, remote_job.assigned_to)
+        if remote_job.preview_url:
+            model.loadPreviewImageFromUrl(remote_job.preview_url)
         return model
 
     ## Updates the printer assignment for the given print job model.

+ 45 - 38
resources/i18n/zh_TW/cura.po

@@ -8,7 +8,7 @@ msgstr ""
 "Project-Id-Version: Cura 4.6\n"
 "Report-Msgid-Bugs-To: r.dulek@ultimaker.com\n"
 "POT-Creation-Date: 2020-04-06 16:33+0200\n"
-"PO-Revision-Date: 2020-02-16 18:19+0800\n"
+"PO-Revision-Date: 2020-04-18 17:49+0800\n"
 "Last-Translator: Zhang Heh Ji <dinowchang@gmail.com>\n"
 "Language-Team: Zhang Heh Ji <dinowchang@gmail.com>\n"
 "Language: zh_TW\n"
@@ -347,7 +347,7 @@ msgstr "正在設定場景..."
 #: /home/trin/Gedeeld/Projects/Cura/cura/CuraApplication.py:868
 msgctxt "@info:progress"
 msgid "Loading interface..."
-msgstr "正在載入介面"
+msgstr "正在載入介面..."
 
 #: /home/trin/Gedeeld/Projects/Cura/cura/CuraApplication.py:873
 msgctxt "@info:progress"
@@ -730,13 +730,13 @@ msgstr "3MF 檔案"
 #: /home/trin/Gedeeld/Projects/Cura/plugins/3MFWriter/ThreeMFWorkspaceWriter.py:31
 msgctxt "@error:zip"
 msgid "3MF Writer plug-in is corrupt."
-msgstr ""
+msgstr "3MF 寫入器外掛已損壞。"
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/3MFWriter/ThreeMFWorkspaceWriter.py:59
 #: /home/trin/Gedeeld/Projects/Cura/plugins/3MFWriter/ThreeMFWorkspaceWriter.py:92
 msgctxt "@error:zip"
 msgid "No permission to write the workspace here."
-msgstr ""
+msgstr "沒有寫入此處工作區的權限。"
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/3MFWriter/ThreeMFWriter.py:181
 msgctxt "@error:zip"
@@ -771,12 +771,12 @@ msgstr "上傳你的備份時發生錯誤。"
 #: /home/trin/Gedeeld/Projects/Cura/plugins/CuraDrive/src/CreateBackupJob.py:47
 msgctxt "@info:backup_status"
 msgid "Creating your backup..."
-msgstr ""
+msgstr "正在建立備份..."
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/CuraDrive/src/CreateBackupJob.py:54
 msgctxt "@info:backup_status"
 msgid "There was an error while creating your backup."
-msgstr ""
+msgstr "建立備份時發生了錯誤。"
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/CuraDrive/src/CreateBackupJob.py:58
 msgctxt "@info:backup_status"
@@ -791,7 +791,7 @@ msgstr "你的備份上傳完成。"
 #: /home/trin/Gedeeld/Projects/Cura/plugins/CuraDrive/src/CreateBackupJob.py:107
 msgctxt "@error:file_size"
 msgid "The backup exceeds the maximum file size."
-msgstr ""
+msgstr "備份超過了最大檔案大小。"
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/CuraDrive/src/DriveApiService.py:82
 #: /home/trin/Gedeeld/Projects/Cura/plugins/CuraDrive/src/RestoreBackupJob.py:23
@@ -850,6 +850,10 @@ msgid ""
 "- Are assigned to an enabled extruder\n"
 "- Are not all set as modifier meshes"
 msgstr ""
+"請檢查設定並檢查你的模型是否:\n"
+"- 適合列印範圍\n"
+"- 分配了一個已啟用的擠出機\n"
+"- 沒有全部設定成修改網格"
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/CuraEngineBackend/ProcessSlicedLayersJob.py:50
 #: /home/trin/Gedeeld/Projects/Cura/plugins/CuraEngineBackend/ProcessSlicedLayersJob.py:256
@@ -1156,7 +1160,7 @@ msgstr "建立一塊不列印支撐的空間。"
 #: /home/trin/Gedeeld/Projects/Cura/plugins/Toolbox/src/CloudSync/CloudPackageChecker.py:101
 msgctxt "@info:generic"
 msgid "Do you want to sync material and software packages with your account?"
-msgstr ""
+msgstr "你要使用你的帳號同步耗材資料和軟體套件嗎?"
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/Toolbox/src/CloudSync/CloudPackageChecker.py:102
 #: /home/trin/Gedeeld/Projects/Cura/plugins/Toolbox/src/CloudSync/DownloadPresenter.py:91
@@ -1172,7 +1176,7 @@ msgstr "同步"
 #: /home/trin/Gedeeld/Projects/Cura/plugins/Toolbox/src/CloudSync/DownloadPresenter.py:87
 msgctxt "@info:generic"
 msgid "Syncing..."
-msgstr ""
+msgstr "同步中..."
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/Toolbox/src/CloudSync/LicenseModel.py:9
 msgctxt "@button"
@@ -2070,12 +2074,12 @@ msgstr "重疊處不建立支撐"
 #: /home/trin/Gedeeld/Projects/Cura/plugins/PerObjectSettingsTool/PerObjectSettingsPanel.qml:142
 msgctxt "@item:inlistbox"
 msgid "Infill mesh only"
-msgstr ""
+msgstr "只填充網格"
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/PerObjectSettingsTool/PerObjectSettingsPanel.qml:143
 msgctxt "@item:inlistbox"
 msgid "Cutting mesh"
-msgstr ""
+msgstr "切割網格"
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/PerObjectSettingsTool/PerObjectSettingsPanel.qml:373
 msgctxt "@action:button"
@@ -2091,7 +2095,7 @@ msgstr "選擇對此模型的自訂設定"
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Preferences/SettingVisibilityPage.qml:94
 msgctxt "@label:textbox"
 msgid "Filter..."
-msgstr "篩選"
+msgstr "篩選..."
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/PerObjectSettingsTool/SettingPickDialog.qml:70
 msgctxt "@label:checkbox"
@@ -2121,13 +2125,13 @@ msgstr "設定"
 #: /home/trin/Gedeeld/Projects/Cura/plugins/PostProcessingPlugin/PostProcessingPlugin.qml:499
 msgctxt "@info:tooltip"
 msgid "Change active post-processing scripts."
-msgstr ""
+msgstr "更改目前啟用的後處理腳本。"
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/PostProcessingPlugin/PostProcessingPlugin.qml:503
 msgctxt "@info:tooltip"
 msgid "The following script is active:"
 msgid_plural "The following scripts are active:"
-msgstr[0] ""
+msgstr[0] "下列為啟用中的腳本:"
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/SimulationView/SimulationViewMenuComponent.qml:20
 #: /home/trin/Gedeeld/Projects/Cura/plugins/SimulationView/SimulationViewMenuComponent.qml:49
@@ -2148,7 +2152,7 @@ msgstr "線條類型"
 #: /home/trin/Gedeeld/Projects/Cura/plugins/SimulationView/SimulationViewMenuComponent.qml:115
 msgctxt "@label:listbox"
 msgid "Speed"
-msgstr ""
+msgstr "速度"
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/SimulationView/SimulationViewMenuComponent.qml:119
 msgctxt "@label:listbox"
@@ -2354,7 +2358,7 @@ msgstr "需重新啟動 Cura,套件的更動才能生效。"
 #: /home/trin/Gedeeld/Projects/Cura/plugins/Toolbox/resources/qml/components/ToolboxFooter.qml:46
 msgctxt "@info:button, %1 is the application name"
 msgid "Quit %1"
-msgstr ""
+msgstr "結束 %1"
 
 #: /home/trin/Gedeeld/Projects/Cura/plugins/Toolbox/resources/qml/components/ToolboxHeader.qml:30
 #: /home/trin/Gedeeld/Projects/Cura/plugins/Toolbox/resources/qml/pages/ToolboxInstalledPage.qml:34
@@ -2960,7 +2964,7 @@ msgstr "登入"
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Account/GeneralOperations.qml:40
 msgctxt "@label"
 msgid "Your key to connected 3D printing"
-msgstr ""
+msgstr "連線 3D 列印的金鑰"
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Account/GeneralOperations.qml:51
 msgctxt "@text"
@@ -2969,6 +2973,9 @@ msgid ""
 "- Stay flexible by syncing your setup and loading it anywhere\n"
 "- Increase efficiency with a remote workflow on Ultimaker printers"
 msgstr ""
+"- 使用更多的列印參數設定和外掛訂做你的使用體驗\n"
+"- 通過同步設定可在任何地方將其載入以保持靈活性\n"
+"- 透過 Ultimaker 印表機上的遠端工作流程提高效率"
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Account/GeneralOperations.qml:78
 msgctxt "@button"
@@ -3113,12 +3120,12 @@ msgstr "右視圖"
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Actions.qml:167
 msgctxt "@action:inmenu"
 msgid "Configure Cura..."
-msgstr "設定 Cura"
+msgstr "設定 Cura..."
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Actions.qml:174
 msgctxt "@action:inmenu menubar:printer"
 msgid "&Add Printer..."
-msgstr "新增印表機(&A)"
+msgstr "新增印表機(&A)..."
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Actions.qml:180
 msgctxt "@action:inmenu menubar:printer"
@@ -3128,7 +3135,7 @@ msgstr "管理印表機(&I)..."
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Actions.qml:187
 msgctxt "@action:inmenu"
 msgid "Manage Materials..."
-msgstr "管理耗材"
+msgstr "管理耗材..."
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Actions.qml:195
 msgctxt "@action:inmenu"
@@ -3148,7 +3155,7 @@ msgstr "捨棄目前更改(&D)"
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Actions.qml:222
 msgctxt "@action:inmenu menubar:profile"
 msgid "&Create profile from current settings/overrides..."
-msgstr "從目前設定 / 覆寫值建立列印參數(&C)"
+msgstr "從目前設定 / 覆寫值建立列印參數(&C)..."
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Actions.qml:228
 msgctxt "@action:inmenu menubar:profile"
@@ -3173,7 +3180,7 @@ msgstr "新功能"
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Actions.qml:258
 msgctxt "@action:inmenu menubar:help"
 msgid "About..."
-msgstr "關於"
+msgstr "關於..."
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Actions.qml:265
 msgctxt "@action:inmenu menubar:edit"
@@ -3266,12 +3273,12 @@ msgstr "重置所有模型旋轉"
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Actions.qml:419
 msgctxt "@action:inmenu menubar:file"
 msgid "&Open File(s)..."
-msgstr "開啟檔案(&O)"
+msgstr "開啟檔案(&O)..."
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Actions.qml:427
 msgctxt "@action:inmenu menubar:file"
 msgid "&New Project..."
-msgstr "新建專案(&N)"
+msgstr "新建專案(&N)..."
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Actions.qml:434
 msgctxt "@action:inmenu menubar:help"
@@ -3320,13 +3327,13 @@ msgstr "列印參數"
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Cura.qml:563
 msgctxt "@title:window %1 is the application name"
 msgid "Closing %1"
-msgstr ""
+msgstr "關閉 %1 中"
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Cura.qml:564
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Cura.qml:576
 msgctxt "@label %1 is the application name"
 msgid "Are you sure you want to exit %1?"
-msgstr ""
+msgstr "是否確定要離開 %1 ?"
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Cura.qml:614
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Dialogs/OpenFilesIncludingProjectsDialog.qml:19
@@ -3362,7 +3369,7 @@ msgstr "新功能"
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Dialogs/AboutDialog.qml:15
 msgctxt "@title:window The argument is the application name."
 msgid "About %1"
-msgstr ""
+msgstr "關於 %1"
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Dialogs/AboutDialog.qml:57
 msgctxt "@label"
@@ -3782,7 +3789,7 @@ msgstr "匯出(&E)"
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Menus/FileMenu.qml:65
 msgctxt "@action:inmenu menubar:file"
 msgid "Export Selection..."
-msgstr "匯出選擇"
+msgstr "匯出選擇..."
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Menus/MaterialMenu.qml:13
 msgctxt "@label:category menu label"
@@ -4787,7 +4794,7 @@ msgstr "這個設定是所有擠出機共用的。修改它會同時更動到所
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Settings/SettingItem.qml:191
 msgctxt "@label"
 msgid "This setting is resolved from conflicting extruder-specific values:"
-msgstr ""
+msgstr "此設定是透過解決擠出機設定值衝突獲得:"
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/Settings/SettingItem.qml:230
 msgctxt "@label"
@@ -4940,7 +4947,7 @@ msgstr "無法連接到裝置。"
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/WelcomePages/AddPrinterByIpContent.qml:212
 msgctxt "@label"
 msgid "Can't connect to your Ultimaker printer?"
-msgstr ""
+msgstr "無法連接到 Ultimaker 印表機?"
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/WelcomePages/AddPrinterByIpContent.qml:211
 msgctxt "@label"
@@ -4965,27 +4972,27 @@ msgstr "連接"
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/WelcomePages/CloudContent.qml:36
 msgctxt "@label"
 msgid "Ultimaker Account"
-msgstr ""
+msgstr "Ultimaker 帳號"
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/WelcomePages/CloudContent.qml:77
 msgctxt "@text"
 msgid "Your key to connected 3D printing"
-msgstr ""
+msgstr "連線 3D 列印的金鑰"
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/WelcomePages/CloudContent.qml:94
 msgctxt "@text"
 msgid "- Customize your experience with more print profiles and plugins"
-msgstr ""
+msgstr "- 使用更多的列印參數設定和外掛訂做你的使用體驗"
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/WelcomePages/CloudContent.qml:97
 msgctxt "@text"
 msgid "- Stay flexible by syncing your setup and loading it anywhere"
-msgstr ""
+msgstr "- 通過同步設定可在任何地方將其載入以保持靈活性"
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/WelcomePages/CloudContent.qml:100
 msgctxt "@text"
 msgid "- Increase efficiency with a remote workflow on Ultimaker printers"
-msgstr ""
+msgstr "- 透過 Ultimaker 印表機上的遠端工作流程提高效率"
 
 #: /home/trin/Gedeeld/Projects/Cura/resources/qml/WelcomePages/CloudContent.qml:119
 msgctxt "@button"
@@ -5254,7 +5261,7 @@ msgstr "提供更改機器設定的方法(如列印範圍,噴頭大小等)
 #: MachineSettingsAction/plugin.json
 msgctxt "name"
 msgid "Machine Settings Action"
-msgstr ""
+msgstr "印表機設定操作"
 
 #: MonitorStage/plugin.json
 msgctxt "description"
@@ -5589,12 +5596,12 @@ msgstr "升級版本 4.4 到 4.5"
 #: VersionUpgrade/VersionUpgrade45to46/plugin.json
 msgctxt "description"
 msgid "Upgrades configurations from Cura 4.5 to Cura 4.6."
-msgstr ""
+msgstr "將設定從 Cura 4.5 版本升級至 4.6 版本。"
 
 #: VersionUpgrade/VersionUpgrade45to46/plugin.json
 msgctxt "name"
 msgid "Version Upgrade 4.5 to 4.6"
-msgstr ""
+msgstr "升級版本 4.5 到 4.6"
 
 #: X3DReader/plugin.json
 msgctxt "description"

+ 16 - 16
resources/i18n/zh_TW/fdmprinter.def.json.po

@@ -83,7 +83,7 @@ msgstr "耗材 GUID"
 #: fdmprinter.def.json
 msgctxt "material_guid description"
 msgid "GUID of the material. This is set automatically."
-msgstr ""
+msgstr "耗材的 GUID,此項為自動設定。"
 
 #: fdmprinter.def.json
 msgctxt "material_diameter label"
@@ -1253,12 +1253,12 @@ msgstr "套用到第一層所有多邊形的偏移量。負數值可以補償第
 #: fdmprinter.def.json
 msgctxt "hole_xy_offset label"
 msgid "Hole Horizontal Expansion"
-msgstr ""
+msgstr "孔洞水平擴展"
 
 #: fdmprinter.def.json
 msgctxt "hole_xy_offset description"
 msgid "Amount of offset applied to all holes in each layer. Positive values increase the size of the holes, negative values reduce the size of the holes."
-msgstr ""
+msgstr "套用到每一層孔洞的偏移量。正值增加孔洞的大小,負值減小孔洞的大小。"
 
 #: fdmprinter.def.json
 msgctxt "z_seam_type label"
@@ -2192,7 +2192,7 @@ msgstr "沖洗速度"
 #: fdmprinter.def.json
 msgctxt "material_flush_purge_speed description"
 msgid "How fast to prime the material after switching to a different material."
-msgstr ""
+msgstr "切換到另一耗材後,用多快的速度擠出耗材做沖洗。"
 
 #: fdmprinter.def.json
 msgctxt "material_flush_purge_length label"
@@ -2202,27 +2202,27 @@ msgstr "沖洗長度"
 #: fdmprinter.def.json
 msgctxt "material_flush_purge_length description"
 msgid "How much material to use to purge the previous material out of the nozzle (in length of filament) when switching to a different material."
-msgstr ""
+msgstr "切換到另一耗材時,要使用多少耗材(以耗材長度計算)將噴頭內先前的耗材沖洗出來。"
 
 #: fdmprinter.def.json
 msgctxt "material_end_of_filament_purge_speed label"
 msgid "End of Filament Purge Speed"
-msgstr ""
+msgstr "耗材更換沖洗速度"
 
 #: fdmprinter.def.json
 msgctxt "material_end_of_filament_purge_speed description"
 msgid "How fast to prime the material after replacing an empty spool with a fresh spool of the same material."
-msgstr ""
+msgstr "更換新的一捲相同耗材後,用多快的速度擠出耗材做沖洗。"
 
 #: fdmprinter.def.json
 msgctxt "material_end_of_filament_purge_length label"
 msgid "End of Filament Purge Length"
-msgstr ""
+msgstr "耗材更換沖洗長度"
 
 #: fdmprinter.def.json
 msgctxt "material_end_of_filament_purge_length description"
 msgid "How much material to use to purge the previous material out of the nozzle (in length of filament) when replacing an empty spool with a fresh spool of the same material."
-msgstr ""
+msgstr "更換新的一捲相同耗材時,要使用多少耗材(以耗材長度計算)將噴頭內先前的耗材沖洗出來。"
 
 #: fdmprinter.def.json
 msgctxt "material_maximum_park_duration label"
@@ -2232,7 +2232,7 @@ msgstr "最長停放時間"
 #: fdmprinter.def.json
 msgctxt "material_maximum_park_duration description"
 msgid "How long the material can be kept out of dry storage safely."
-msgstr ""
+msgstr "耗材可在乾燥箱外安全的存放多久。"
 
 #: fdmprinter.def.json
 msgctxt "material_no_load_move_factor label"
@@ -2242,7 +2242,7 @@ msgstr "空載移動係數"
 #: fdmprinter.def.json
 msgctxt "material_no_load_move_factor description"
 msgid "A factor indicating how much the filament gets compressed between the feeder and the nozzle chamber, used to determine how far to move the material for a filament switch."
-msgstr ""
+msgstr "一個用來表示耗材在進料器和噴頭腔室之間能被壓縮多少的係數,用來決定耗材切換時需要移動多長。"
 
 #: fdmprinter.def.json
 msgctxt "material_flow label"
@@ -3022,7 +3022,7 @@ msgstr "啟用回抽"
 #: fdmprinter.def.json
 msgctxt "retraction_enable description"
 msgid "Retract the filament when the nozzle is moving over a non-printed area."
-msgstr ""
+msgstr "當噴頭移動經過非列印區域時回抽耗材。"
 
 #: fdmprinter.def.json
 msgctxt "retract_at_layer_change label"
@@ -3717,7 +3717,7 @@ msgstr "最小支撐 X/Y 間距"
 #: fdmprinter.def.json
 msgctxt "support_xy_distance_overhang description"
 msgid "Distance of the support structure from the overhang in the X/Y directions."
-msgstr ""
+msgstr "支撐結構在 X/Y 方向與突出部分的間距。 "
 
 #: fdmprinter.def.json
 msgctxt "support_bottom_stair_step_height label"
@@ -4816,7 +4816,7 @@ msgstr "網格修復"
 #: fdmprinter.def.json
 msgctxt "meshfix description"
 msgid "Make the meshes more suited for 3D printing."
-msgstr ""
+msgstr "讓網格更適合 3D 列印。"
 
 #: fdmprinter.def.json
 msgctxt "meshfix_union_all label"
@@ -4936,7 +4936,7 @@ msgstr "特殊模式"
 #: fdmprinter.def.json
 msgctxt "blackmagic description"
 msgid "Non-traditional ways to print your models."
-msgstr ""
+msgstr "以非傳統的方式列印你的模型。"
 
 #: fdmprinter.def.json
 msgctxt "print_sequence label"
@@ -5111,7 +5111,7 @@ msgstr "實驗性"
 #: fdmprinter.def.json
 msgctxt "experimental description"
 msgid "Features that haven't completely been fleshed out yet."
-msgstr ""
+msgstr "尚未完全的功能。"
 
 #: fdmprinter.def.json
 msgctxt "support_tree_enable label"

+ 14 - 6
resources/shaders/overhang.shader

@@ -38,6 +38,8 @@ fragment =
     varying highp vec3 f_vertex;
     varying highp vec3 f_normal;
 
+    uniform lowp float u_renderError;
+
     float round(float f)
     {
         return sign(f) * floor(abs(f) + 0.5);
@@ -66,9 +68,11 @@ fragment =
 
         finalColor = (-normal.y > u_overhangAngle) ? u_overhangColor : finalColor;
 
-        vec3 grid = vec3(f_vertex.x - round(f_vertex.x), f_vertex.y - round(f_vertex.y), f_vertex.z - round(f_vertex.z));
-        finalColor.a = dot(grid, grid) < 0.245 ? 0.667 : 1.0;
-
+        if(u_renderError > 0.5)
+        {
+            vec3 grid = vec3(f_vertex.x - round(f_vertex.x), f_vertex.y - round(f_vertex.y), f_vertex.z - round(f_vertex.z));
+            finalColor.a = dot(grid, grid) < 0.245 ? 0.667 : 1.0;
+        }
         gl_FragColor = finalColor;
     }
 
@@ -104,6 +108,7 @@ fragment41core =
     uniform highp vec3 u_lightPosition;
     uniform mediump float u_shininess;
     uniform highp vec3 u_viewPosition;
+    uniform lowp float u_renderError;
 
     uniform lowp float u_overhangAngle;
     uniform lowp vec4 u_overhangColor;
@@ -139,9 +144,11 @@ fragment41core =
         finalColor = (u_faceId != gl_PrimitiveID) ? ((-normal.y > u_overhangAngle) ? u_overhangColor : finalColor) : u_faceColor;
 
         frag_color = finalColor;
-
-        vec3 grid = f_vertex - round(f_vertex);
-        frag_color.a = dot(grid, grid) < 0.245 ? 0.667 : 1.0;
+        if(u_renderError > 0.5)
+        {
+            vec3 grid = f_vertex - round(f_vertex);
+            frag_color.a = dot(grid, grid) < 0.245 ? 0.667 : 1.0;
+        }
     }
 
 [defaults]
@@ -151,6 +158,7 @@ u_specularColor = [0.4, 0.4, 0.4, 1.0]
 u_overhangColor = [1.0, 0.0, 0.0, 1.0]
 u_faceColor = [0.0, 0.0, 1.0, 1.0]
 u_shininess = 20.0
+u_renderError = 1.0
 
 [bindings]
 u_modelMatrix = model_matrix