Merge branch 'fs_dir_per_glyph_SPE-1597' into fs_svg

This commit is contained in:
Filip Sykala - NTB T15p 2023-06-09 11:17:41 +02:00
commit 87517c5c68
51 changed files with 574 additions and 340 deletions

View File

@ -4,6 +4,7 @@ prusaslicer_add_cmake_project(OpenEXR
URL_HASH SHA256=0307a3d7e1fa1e77e9d84d7e9a8694583fbbbfd50bdc6884e2c96b8ef6b902de
DEPENDS ${ZLIB_PKG}
GIT_TAG v2.5.5
PATCH_COMMAND COMMAND ${PATCH_CMD} ${CMAKE_CURRENT_LIST_DIR}/OpenEXR.patch
CMAKE_ARGS
-DCMAKE_POSITION_INDEPENDENT_CODE=ON
-DBUILD_TESTING=OFF

30
deps/OpenEXR/OpenEXR.patch vendored Normal file
View File

@ -0,0 +1,30 @@
--- ../OpenEXR-orig/OpenEXR/IlmImf/ImfDwaCompressor.cpp 2021-02-12 17:56:19.000000000 +0100
+++ ./OpenEXR/IlmImf/ImfDwaCompressor.cpp 2023-06-01 13:21:32.666695400 +0200
@@ -159,6 +159,7 @@
#include <limits>
#include <cstddef>
+#include <cstdint>
// Windows specific addition to prevent the indirect import of the redefined min/max macros
--- ../OpenEXR-orig/OpenEXR/IlmImf/ImfHuf.cpp 2021-02-12 17:56:19.000000000 +0100
+++ ./OpenEXR/IlmImf/ImfHuf.cpp 2023-06-01 13:21:53.018583400 +0200
@@ -53,6 +53,7 @@
#include <cstring>
#include <cassert>
#include <algorithm>
+#include <cstdint>
using namespace std;
--- ../OpenEXR-orig/OpenEXR/IlmImf/ImfMisc.cpp 2021-02-12 17:56:19.000000000 +0100
+++ ./OpenEXR/IlmImf/ImfMisc.cpp 2023-06-01 13:22:15.777480000 +0200
@@ -40,6 +40,7 @@
//
//-----------------------------------------------------------------------------
+#include <cstdint>
#include <ImfMisc.h>
#include <ImfHeader.h>
#include <ImfAttribute.h>

View File

@ -13,8 +13,8 @@ if (UNIX AND NOT APPLE) # wxWidgets will not use char as the underlying type for
endif()
prusaslicer_add_cmake_project(wxWidgets
URL https://github.com/prusa3d/wxWidgets/archive/0b49beaacce17d90f0c370ecd73221abd089667a.zip
URL_HASH SHA256=8fa978a76d6bd811b30eecc5124186b9ad54290b820f3a354e85bfa9dae6a5ce
URL https://github.com/prusa3d/wxWidgets/archive/78aa2dc0ea7ce99dc19adc1140f74c3e2e3f3a26.zip
URL_HASH SHA256=94b7d972373503e380e5a8b0ca63b1ccb956da4006402298dd89a0c5c7041b1e
DEPENDS ${PNG_PKG} ${ZLIB_PKG} ${EXPAT_PKG} dep_TIFF dep_JPEG dep_NanoSVG
CMAKE_ARGS
-DwxBUILD_PRECOMP=ON

View File

@ -1512,7 +1512,7 @@ msgstr ""
#: src/slic3r/GUI/DoubleSlider.cpp:1465
msgid "Edit current color - Right click the colored slider segment"
msgstr ""
"Змяніць бягучы колер - <b>Правая кнопка мышы</b> по каляроваму адрэзку "
"Змяніць бягучы колер - Правая кнопка мышы по каляроваму адрэзку "
"паўзунка"
#: src/slic3r/GUI/DoubleSlider.cpp:1467
@ -1533,32 +1533,32 @@ msgstr "Рэжым друку"
#: src/slic3r/GUI/DoubleSlider.cpp:1495
msgid "Add extruder change - Left click"
msgstr "Дадаць змену экструдара - <b>Левая кнопка мышы</b>"
msgstr "Дадаць змену экструдара - Левая кнопка мышы"
#: src/slic3r/GUI/DoubleSlider.cpp:1497
msgid ""
"Add color change - Left click for predefined color or Shift + Left click for "
"custom color selection"
msgstr ""
"Дадаць змену колера - <b>Левая кнопка мышы</b> для колера з спіску "
"першапачатковых колераў ці <b>Shift + Левая кнопка мышы</b> для выбору "
"Дадаць змену колера - Левая кнопка мышы для колера з спіску "
"першапачатковых колераў ці Shift + Левая кнопка мышы для выбору "
"свайго колеру"
#: src/slic3r/GUI/DoubleSlider.cpp:1499
msgid "Add color change - Left click"
msgstr "Дадаць змену колера - <b>Левая кнопка мышы</b>"
msgstr "Дадаць змену колера - Левая кнопка мышы"
#: src/slic3r/GUI/DoubleSlider.cpp:1500
msgid "or press \"+\" key"
msgstr "альбо клавіша <b>+</b>"
msgstr "альбо клавіша \"+\""
#: src/slic3r/GUI/DoubleSlider.cpp:1502
msgid "Add another code - Ctrl + Left click"
msgstr "Дадаць іншы кода - <b>Ctrl + левая кнопка мышы</b>"
msgstr "Дадаць іншы кода - Ctrl + левая кнопка мышы"
#: src/slic3r/GUI/DoubleSlider.cpp:1503
msgid "Add another code - Right click"
msgstr "Дадаць іншы код - <b>Правая кнопка мышы</b>"
msgstr "Дадаць іншы код - Правая кнопка мышы"
#: src/slic3r/GUI/DoubleSlider.cpp:1509
msgid ""
@ -1639,15 +1639,15 @@ msgstr ""
#: src/slic3r/GUI/DoubleSlider.cpp:1565
msgid "Delete tick mark - Left click or press \"-\" key"
msgstr "Выдаліц птушку - <b>Левая кнопка мышы</b> альбо клавіша <b>-</b>"
msgstr "Выдаліц птушку - Левая кнопка мышы альбо клавіша \"-\""
#: src/slic3r/GUI/DoubleSlider.cpp:1567
msgid "Edit tick mark - Ctrl + Left click"
msgstr "Змяніць птушку - <b>Ctrl + левая кнопка мышы</b>"
msgstr "Змяніць птушку - Ctrl + левая кнопка мышы"
#: src/slic3r/GUI/DoubleSlider.cpp:1568
msgid "Edit tick mark - Right click"
msgstr "Змяніць птушку - <b>Правая кнопка мышы</b>"
msgstr "Змяніць птушку - Правая кнопка мышы"
#: src/slic3r/GUI/DoubleSlider.cpp:1671 src/slic3r/GUI/DoubleSlider.cpp:1702
#: src/slic3r/GUI/GUI_Factories.cpp:870
@ -2495,7 +2495,7 @@ msgstr "Пераменная вышыня пластоў"
#: src/slic3r/GUI/GLCanvas3D.cpp:191
msgid "Left mouse button:"
msgstr "<b>Левая кнопка мышы</b>:"
msgstr "Левая кнопка мышы:"
#: src/slic3r/GUI/GLCanvas3D.cpp:193
msgid "Add detail"
@ -2503,7 +2503,7 @@ msgstr "Павялічыць дэтальнасць"
#: src/slic3r/GUI/GLCanvas3D.cpp:195
msgid "Right mouse button:"
msgstr "<b>Правая кнопка мышы</b>:"
msgstr "Правая кнопка мышы:"
#: src/slic3r/GUI/GLCanvas3D.cpp:197
msgid "Remove detail"
@ -2511,7 +2511,7 @@ msgstr "Паменьшыць дэтальнасць"
#: src/slic3r/GUI/GLCanvas3D.cpp:199
msgid "Shift + Left mouse button:"
msgstr "<b>Shift + Левая кнопка мышы</b>:"
msgstr "Shift + Левая кнопка мышы:"
#: src/slic3r/GUI/GLCanvas3D.cpp:201
msgid "Reset to base"
@ -2519,7 +2519,7 @@ msgstr "Скід да звычайнай вышыні пласта"
#: src/slic3r/GUI/GLCanvas3D.cpp:203
msgid "Shift + Right mouse button:"
msgstr "<b>Shift + Правая кнопка мышы</b>:"
msgstr "Shift + Правая кнопка мышы:"
#: src/slic3r/GUI/GLCanvas3D.cpp:205
msgid "Smoothing"
@ -2527,7 +2527,7 @@ msgstr "Згладжванне"
#: src/slic3r/GUI/GLCanvas3D.cpp:207
msgid "Mouse wheel:"
msgstr "<b>Кола мышы</b>:"
msgstr "Кола мышы:"
#: src/slic3r/GUI/GLCanvas3D.cpp:209
msgid "Increase/decrease edit area"
@ -2676,7 +2676,7 @@ msgstr "Налады ўпарадкавання"
#: src/slic3r/GUI/GLCanvas3D.cpp:4845
#, boost-format
msgid "Press %1%left mouse button to enter the exact value"
msgstr "Націсніце %1% <b>левую кнопку мышы</b> для ўводу дакладнага значэння"
msgstr "Націсніце %1% левую кнопку мышы для ўводу дакладнага значэння"
#: src/slic3r/GUI/GLCanvas3D.cpp:4847
msgid "Spacing"
@ -2739,7 +2739,7 @@ msgstr "Упарадкаваць абраныя"
#: src/slic3r/GUI/GLCanvas3D.cpp:5325
msgid "Click right mouse button to show arrangement options"
msgstr ""
"Пстрыкніце <b>правую кнопку мышы</b>, каб адлюстраваць налады ўпарадкавання"
"Пстрыкніце правую кнопку мышы, каб адлюстраваць налады ўпарадкавання"
#: src/slic3r/GUI/GLCanvas3D.cpp:5345
msgid "Copy"
@ -2769,7 +2769,7 @@ msgstr "Падзяліць на часткі"
#: src/slic3r/GUI/GLCanvas3D.cpp:5506 src/slic3r/GUI/GLCanvas3D.cpp:5543
msgid "Click right mouse button to open/close History"
msgstr ""
"Псктрыкнуць <b>правую кнопку мышы</b>, каб адлюстраваць/схаваць Гісторы дзей"
"Псктрыкнуць правую кнопку мышы, каб адлюстраваць/схаваць Гісторы дзей"
#: src/slic3r/GUI/GLCanvas3D.cpp:5528
#, boost-format
@ -2942,7 +2942,7 @@ msgstr ""
#: src/slic3r/GUI/Gizmos/GLGizmoSlaSupports.cpp:1268
#: src/slic3r/GUI/Gizmos/GLGizmoSlaSupports.cpp:1269
msgid "Left click"
msgstr "<b>Левая кнопка мышы</b>"
msgstr "Левая кнопка мышы"
#: src/slic3r/GUI/Gizmos/GLGizmoCut.cpp:823
#: src/slic3r/GUI/Gizmos/GLGizmoCut.cpp:2821
@ -2952,7 +2952,7 @@ msgstr ""
#: src/slic3r/GUI/Gizmos/GLGizmoCut.cpp:824
#: src/slic3r/GUI/Gizmos/GLGizmoSlaSupports.cpp:1266
msgid "Right click"
msgstr "<b>Правая кнопка мышы</b>"
msgstr "Правая кнопка мышы"
#: src/slic3r/GUI/Gizmos/GLGizmoCut.cpp:824
msgid "Remove connector"
@ -3612,7 +3612,7 @@ msgstr "Форма пэндзаля"
#: src/slic3r/GUI/Gizmos/GLGizmoMmuSegmentation.cpp:110
#: src/slic3r/GUI/Gizmos/GLGizmoSeam.cpp:35
msgid "Left mouse button"
msgstr "<b>Левая кнопка мышы</b>"
msgstr "Левая кнопка мышы"
#: src/slic3r/GUI/Gizmos/GLGizmoFdmSupports.cpp:55
msgid "Enforce supports"
@ -3622,7 +3622,7 @@ msgstr "Прымусовая падтрымка"
#: src/slic3r/GUI/Gizmos/GLGizmoMmuSegmentation.cpp:112
#: src/slic3r/GUI/Gizmos/GLGizmoSeam.cpp:37
msgid "Right mouse button"
msgstr "<b>Правая кнопка мышы</b>"
msgstr "Правая кнопка мышы"
#: src/slic3r/GUI/Gizmos/GLGizmoFdmSupports.cpp:57
#: src/slic3r/GUI/Gizmos/GLGizmoFdmSupports.cpp:575
@ -3633,7 +3633,7 @@ msgstr "Блакаваць падтрымкі"
#: src/slic3r/GUI/Gizmos/GLGizmoMmuSegmentation.cpp:114
#: src/slic3r/GUI/Gizmos/GLGizmoSeam.cpp:39
msgid "Shift + Left mouse button"
msgstr "<b>Shift + Левая кнопка мышы</b>"
msgstr "Shift + Левая кнопка мышы"
#: src/slic3r/GUI/Gizmos/GLGizmoFdmSupports.cpp:59
#: src/slic3r/GUI/Gizmos/GLGizmoFdmSupports.cpp:570
@ -3747,7 +3747,7 @@ msgstr "Фарбуе толькі адну мяжу."
#: src/slic3r/GUI/Gizmos/GLGizmoMmuSegmentation.cpp:462
#: src/slic3r/GUI/Gizmos/GLGizmoSeam.cpp:129
msgid "Alt + Mouse wheel"
msgstr "<b>Alt + Кола мышы</b>"
msgstr "Alt + Кола мышы"
#: src/slic3r/GUI/Gizmos/GLGizmoFdmSupports.cpp:290
msgid "Splits bigger facets into smaller ones while the object is painted."
@ -3757,7 +3757,7 @@ msgstr "Падчас фарбоўкі мадэлі разбівае вялікі
#: src/slic3r/GUI/Gizmos/GLGizmoMmuSegmentation.cpp:483
#: src/slic3r/GUI/Gizmos/GLGizmoSeam.cpp:167
msgid "Ctrl + Mouse wheel"
msgstr "<b>Ctrl + Кола мышы</b>"
msgstr "Ctrl + Кола мышы"
#: src/slic3r/GUI/Gizmos/GLGizmoFdmSupports.cpp:328
#: src/slic3r/GUI/Gizmos/GLGizmoMmuSegmentation.cpp:488
@ -5566,28 +5566,28 @@ msgstr "Засталося памылак"
#: src/slic3r/GUI/GUI_ObjectList.cpp:480
msgid "Right button click the icon to fix STL through Netfabb"
msgstr ""
"Пстрыкніце <b>правай кнопкай мышы</b> на гузік, каб выправіць STL з "
"Пстрыкніце правай кнопкай мышы на гузік, каб выправіць STL з "
"дапамогай сервіса Netfabb"
#: src/slic3r/GUI/GUI_ObjectList.cpp:526
msgid "Right button click the icon to change the object settings"
msgstr ""
"Пстрыкніце <b>правай кнопкай мышы</b> на гузік, каб змяніць налады мадэлі"
"Пстрыкніце правай кнопкай мышы на гузік, каб змяніць налады мадэлі"
#: src/slic3r/GUI/GUI_ObjectList.cpp:528
msgid "Click the icon to change the object settings"
msgstr "Пстрыкніце <b>кнопкай мышы</b> на гузік, каб змяніць налады мадэлі"
msgstr "Пстрыкніце кнопкай мышы на гузік, каб змяніць налады мадэлі"
#: src/slic3r/GUI/GUI_ObjectList.cpp:532
msgid "Right button click the icon to change the object printable property"
msgstr ""
"Пстрыкніце <b>правай кнопкай мышы</b> на гузік, каб змяніць уласцівасці "
"Пстрыкніце правай кнопкай мышы на гузік, каб змяніць уласцівасці "
"друку мадэлі"
#: src/slic3r/GUI/GUI_ObjectList.cpp:534
msgid "Click the icon to change the object printable property"
msgstr ""
"Пстрыкніце <b>кнопкай мышы</b> на гузік, каб змяніць уласцівасці друку мадэлі"
"Пстрыкніце кнопкай мышы на гузік, каб змяніць уласцівасці друку мадэлі"
#: src/slic3r/GUI/GUI_ObjectList.cpp:660
msgid "Change Extruder"
@ -6515,7 +6515,7 @@ msgstr "Націсніце, каб актываваць прастакутнік
#: src/slic3r/GUI/KBShortcutsDialog.cpp:239
#: src/slic3r/GUI/KBShortcutsDialog.cpp:254
msgid "Arrow Up"
msgstr "<b>Стрэлка ўверх</b>"
msgstr "Стрэлка ўверх"
#: src/slic3r/GUI/KBShortcutsDialog.cpp:148
msgid "Move selection 10 mm in positive Y direction"
@ -6526,7 +6526,7 @@ msgstr "Рушыць абранае на 10 мм у станоўчым кіру
#: src/slic3r/GUI/KBShortcutsDialog.cpp:240
#: src/slic3r/GUI/KBShortcutsDialog.cpp:255
msgid "Arrow Down"
msgstr "<b>Стрэлка ўніз</b>"
msgstr "Стрэлка ўніз"
#: src/slic3r/GUI/KBShortcutsDialog.cpp:149
msgid "Move selection 10 mm in negative Y direction"
@ -6537,7 +6537,7 @@ msgstr "Рушыць абранае на 10 мм у адмоўным кірун
#: src/slic3r/GUI/KBShortcutsDialog.cpp:241
#: src/slic3r/GUI/KBShortcutsDialog.cpp:252
msgid "Arrow Left"
msgstr "<b>Стрэлка налева</b>"
msgstr "Стрэлка налева"
#: src/slic3r/GUI/KBShortcutsDialog.cpp:150
msgid "Move selection 10 mm in negative X direction"
@ -6548,7 +6548,7 @@ msgstr "Рушыць абранае на 10 мм у адмоўным кірун
#: src/slic3r/GUI/KBShortcutsDialog.cpp:242
#: src/slic3r/GUI/KBShortcutsDialog.cpp:253
msgid "Arrow Right"
msgstr "<b>Стрэлка направа</b>"
msgstr "Стрэлка направа"
#: src/slic3r/GUI/KBShortcutsDialog.cpp:151
msgid "Move selection 10 mm in positive X direction"
@ -6569,7 +6569,7 @@ msgstr "Рух абранага ў прасторы камеры"
#: src/slic3r/GUI/KBShortcutsDialog.cpp:154
msgid "Page Up"
msgstr "<b>Page Up</b>"
msgstr "Page Up"
#: src/slic3r/GUI/KBShortcutsDialog.cpp:154
msgid "Rotate selection 45 degrees CCW"
@ -6577,7 +6577,7 @@ msgstr "Вярчэнне абранага на 45° супраць гадзін
#: src/slic3r/GUI/KBShortcutsDialog.cpp:155
msgid "Page Down"
msgstr "<b>Page Down</b>"
msgstr "Page Down"
#: src/slic3r/GUI/KBShortcutsDialog.cpp:155
msgid "Rotate selection 45 degrees CW"
@ -6688,8 +6688,8 @@ msgstr "Стол"
#: src/slic3r/GUI/KBShortcutsDialog.cpp:190
msgid "All gizmos: Rotate - left mouse button; Pan - right mouse button"
msgstr ""
"Усе штуковіны: Вярчэнне камеры - <b>Левая кнопка мышы</b>; Рух камеры - "
"<b>Правая кнопка мышы</b>"
"Усе штуковіны: Вярчэнне камеры - Левая кнопка мышы; Рух камеры - "
"Правая кнопка мышы"
#: src/slic3r/GUI/KBShortcutsDialog.cpp:191
msgid "Gizmo move: Press to snap by 1mm"
@ -8216,7 +8216,7 @@ msgstr "Нарэзаць зараз"
#: src/slic3r/GUI/Plater.cpp:1124
msgid "Hold Shift to Slice & Export G-code"
msgstr "Утрымлівайце <b>Shift</b>, каб нарэзаць і экспартаваць у G-код"
msgstr "Утрымлівайце Shift, каб нарэзаць і экспартаваць у G-код"
#: src/slic3r/GUI/Plater.cpp:1321
#, boost-format
@ -11163,7 +11163,7 @@ msgstr ""
msgid ""
"Some fields are too long to fit. Right mouse click reveals the full text."
msgstr ""
"Некаторыя палі занадта доўгія. Пстрыкніце <b>правай кнопкай мышы</b>, каб "
"Некаторыя палі занадта доўгія. Пстрыкніце правай кнопкай мышы, каб "
"адлюстраваць поўны тэкст."
#: src/slic3r/GUI/UnsavedChangesDialog.cpp:969
@ -17761,7 +17761,7 @@ msgid ""
"size of the gap between objects and to allow automatic rotations?"
msgstr ""
"Налады ўпарадкавання\n"
"Ці ведаеце вы, што вы можаце пстрыкнуць <b>правай кнопкай мышы</b> на гузік "
"Ці ведаеце вы, што вы можаце пстрыкнуць правай кнопкай мышы на гузік "
"<a>Упарадкаваць гузікі</a>, каб наладзіць прагал паміж мадэлямя і дазволіць "
"аўтаматычнае вярчэнне?"
@ -17788,8 +17788,8 @@ msgid ""
msgstr ""
"Спрасціць сетку\n"
"Ці ведаеце вы, што вы можаце паменьшыць колкасць трыкутнікаў у паліганальнай "
"сетцы, калі ўжыць функцыю спрашчэння сеткі? Пстрыкніце <b>правай кнопкай "
"мышы</b> на мадэлі і абярыце <a>Спрасціць мадэль</a>. Больш падрабязна "
"сетцы, калі ўжыць функцыю спрашчэння сеткі? Пстрыкніце правай кнопкай "
"мышы на мадэлі і абярыце Спрасціць мадэль. Больш падрабязна "
"чытайце ў дакументацыі."
#: resources/data/hints.ini: [hint:Reload from disk]
@ -17801,9 +17801,9 @@ msgid ""
msgstr ""
"Перазагрузіць з дыску\n"
"Ці ведаеце вы, што калі вы стварылі больш новую версію сваёй мадэлі, вы "
"можаце проста перазагрузіць яе ў PrusaSlicer? Пстрыкніце <b>правай кнопкай "
"мышы</b> на мадэлі ў акне 3D-прагляду і абярыце <a>Перазагрузіць з дыска</"
"a>. Больш падрабязна чытайце ў дакументацыі."
"можаце проста перазагрузіць яе ў PrusaSlicer? Пстрыкніце правай кнопкай "
"мышы на мадэлі ў акне 3D-прагляду і абярыце Перазагрузіць з дыска"
". Больш падрабязна чытайце ў дакументацыі."
#: resources/data/hints.ini: [hint:Hiding sidebar]
msgid ""
@ -17833,7 +17833,7 @@ msgid ""
"between predefined camera angles?"
msgstr ""
"Выгляд з камеры\n"
"Ці ведаеце вы, што вы можаце ўжываць лічбавыя клавішы <b>0</b>-<b>6</b>, каб "
"Ці ведаеце вы, што вы можаце ўжываць лічбавыя клавішы <b>0-6</b>, каб "
"хутка пераключацца паміж папярэдне зададзенымі ракурсамі камеры?"
#: resources/data/hints.ini: [hint:Place on face]
@ -17855,7 +17855,7 @@ msgid ""
"instances instead of copy-pasting it several times?"
msgstr ""
"Ужыць колькасць асобнікаў\n"
"Ці ведаеце вы, што вы можаце пстрыкнуць <b>правай кнопкай мышы</b> на мадэлі "
"Ці ведаеце вы, што вы можаце пстрыкнуць правай кнопкай мышы на мадэлі "
"і задаць дакладную колькасць копіяў мадэлі замест таго, каб капіяваць і "
"ўстаўляць её некалькі разоў?"
@ -17890,7 +17890,7 @@ msgid ""
"history of changes and to undo or redo several actions at once?"
msgstr ""
"Гісторыя адкаціць/зрабіць нанова\n"
"Ці ведаеце вы, вы можаце пстрыкнуць <b>правай кнопкай мышы</b> на <a>стрэлкі "
"Ці ведаеце вы, вы можаце пстрыкнуць правай кнопкай мышы на <a>стрэлкі "
"адмены/паўтору</a>, каб праглядзець гісторыю змяненняў і адмяніць ці "
"паўтарыць некалькі дзеянняў адначасова?"
@ -17904,8 +17904,8 @@ msgid ""
msgstr ""
"Розная вышыня пластаў для кожнай мадэлі\n"
"Ці ведаеце вы, што вы можаце надрукаваць кожную мадэль на стале з рознай "
"вышынёй пластоў? Пстрыкніце <b>правай кнопкай мышы</b> на мадэлі ў акне 3D-"
"прагляду, абярыце <a>Пласты і перыметры</a>, наладзьце значэнні на правай "
"вышынёй пластоў? Пстрыкніце правай кнопкай мышы на мадэлі ў акне 3D-"
"прагляду, абярыце Пласты і перыметры, наладзьце значэнні на правай "
"панэлі. Больш падрабязна чытайце ў дакументацыі."
#: resources/data/hints.ini: [hint:Solid infill threshold area]
@ -17938,8 +17938,8 @@ msgid ""
"also box-deselect objects with <b>Alt+Mouse drag</b>."
msgstr ""
"Выдзяленне прастакутнікам\n"
"Ці ведаеце вы, што вы можаце вылучыць поле з дапамогай <b>Shift + "
"перацягванне мышшу</b>? Вы так сама можаце адмяніць вылучэнне мадэляў з "
"Ці ведаеце вы, што вы можаце вылучыць поле з дапамогай Shift + "
"перацягванне мышшу? Вы так сама можаце адмяніць вылучэнне мадэляў з "
"дапамогай спалучэння клавішаў <b>Alt + перацягванне мышшу</b>."
#: resources/data/hints.ini: [hint:Zoom on selected objects or all if none
@ -17965,8 +17965,8 @@ msgstr ""
"Перамыкач для друку\n"
"Ці ведаеце вы, што вы можаце адключыць стварэнне G-кода для абранай мадэлі, "
"без неабходнасці рухаць ці выдаляць яе? Пераключыце ўласцівасць мадэлі "
"<a>Для друку</a> з кантэкстнага меню, калі пстрыкнуць <b>правай кнопкай "
"мышы</b>."
"Для друку з кантэкстнага меню, калі пстрыкнуць правай кнопкай "
"мышы."
#: resources/data/hints.ini: [hint:Mirror]
msgid ""
@ -17976,8 +17976,8 @@ msgid ""
msgstr ""
"Люстраваць\n"
"Ці ведаеце вы, што вы можаце люстраваць абраную мадэль, каб стварыць яе "
"зваротную версію? Пстрыкніце <b>правай кнопкай мышы</b> на мадэль, абярыце "
"<a>Люстраваць</a> і абярыце вось."
"зваротную версію? Пстрыкніце правай кнопкай мышы на мадэль, абярыце "
"Люстраваць і абярыце вось."
#: resources/data/hints.ini: [hint:PageUp / PageDown quick rotation by 45
#: degrees]
@ -18056,7 +18056,7 @@ msgid ""
msgstr ""
"Уставіць прыпынак\n"
"Ці ведаеце вы, што вы можаце запланаваць прыпынак друку на поэным пласту? "
"Пстрыкніце <b>правай кнопкай мышы</b> на паўзунке пласта ў акне папярэдняга "
"Пстрыкніце правай кнопкай мышы на паўзунке пласта ў акне папярэдняга "
"прагляду і абярыце \"Дадаць прыпынак друку\" (M601). Можна ўжываць для "
"ўстаўкі ў ўстаўкі магнітаў, грузікаў ці гаек увашыя мадэлі. Больш падрабязна "
"чытайце ў дакументацыі."
@ -18071,9 +18071,9 @@ msgid ""
msgstr ""
"Карыстальніцкі G-код\n"
"Ці ведаеце вы, што вы можаце ўставіць карыстальніцкі G-код на пэўным пласту? "
"Пстрыкніце <b>левай кнопкай мышы</b> на пласт у акне папярэдняга прагляду, "
"пстрыкніце <b>правай кнопкай мышы</b> гузік плюсу і абярыце <a>Дадаць "
"карыстальніцкі G-код</a>. З дапамогай гэтай функцыі можна, напрыклад, "
"Пстрыкніце левай кнопкай мышы на пласт у акне папярэдняга прагляду, "
"пстрыкніце правай кнопкай мышы гузік плюсу і абярыце Дадаць "
"карыстальніцкі G-код. З дапамогай гэтай функцыі можна, напрыклад, "
"стварыць тэмпературную вежу. Больш падрабязна чытайце ў дакументацыі."
#: resources/data/hints.ini: [hint:Configuration snapshots]
@ -18111,8 +18111,8 @@ msgstr ""
"Налады ў асобным акне\n"
"Ці ведаеце вы, што вы можаце адчыніць налады ў новым немадальным акне? Гэта "
"значыць, што налады можна адчыніць на адным экране, а папярэдні прагляд G-"
"кода на іншчым. Перайдзіце ў <a>Перавагі</a> і абярыце <a>Налады будуць "
"адлюстроўвацца ў асобным акне</a>."
"кода на іншчым. Перайдзіце ў <a>Перавагі</a> і абярыце Налады будуць "
"адлюстроўвацца ў асобным акне."
#: resources/data/hints.ini: [hint:Adaptive infills]
msgid ""
@ -19531,7 +19531,7 @@ msgstr "Колер фону"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:52
msgid "Backspace"
msgstr "<b>Backspace</b>"
msgstr "Backspace"
#: ../src/common/fmapbase.cpp:160
msgid "Baltic (ISO-8859-13)"
@ -20904,7 +20904,7 @@ msgstr "Канец"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:55
msgid "Enter"
msgstr "<b>Enter</b>"
msgstr "Enter"
#: ../src/richtext/richtextstyledlg.cpp:934
msgid "Enter a box style name"
@ -20991,7 +20991,7 @@ msgstr "Памылка: "
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:69
msgid "Esc"
msgstr "<b>Esc</b>"
msgstr "Esc"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:70
@ -22180,7 +22180,7 @@ msgstr "Ініцыялізацыя не атрымалася ў post init, пе
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:54
msgid "Ins"
msgstr "<b>Ins</b>"
msgstr "Ins"
#. TRANSLATORS: Name of keyboard key
#: ../src/richtext/richtextsymboldlg.cpp:472 ../src/common/accelcmn.cpp:53
@ -22879,7 +22879,7 @@ msgstr "&Згарнуць"
#. TRANSLATORS: System cursor name
#: ../src/propgrid/advprops.cpp:1763
msgid "Middle Button"
msgstr "<b>Сярэдняя кнопка</b>"
msgstr "Сярэдняя кнопка"
#: ../src/richtext/richtextsizepage.cpp:409
msgid "Min height:"
@ -23111,117 +23111,117 @@ msgstr "Заўвага, 8 1/2 x 11 цалі"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:105
msgid "Num *"
msgstr "<b>Num *</b>"
msgstr "Num *"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:106
msgid "Num +"
msgstr "<b>Num +</b>"
msgstr "Num +"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:107
msgid "Num ,"
msgstr "<b>Num ,</b>"
msgstr "Num ,"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:108
msgid "Num -"
msgstr "<b>Num -</b>"
msgstr "Num -"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:109
msgid "Num ."
msgstr "<b>Num .</b>"
msgstr "Num ."
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:110
msgid "Num /"
msgstr "<b>Num /</b>"
msgstr "Num /"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:104
msgid "Num ="
msgstr "<b>Num =</b>"
msgstr "Num ="
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:101
msgid "Num Begin"
msgstr "<b>Num Begin</b>"
msgstr "Num Begin"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:103
msgid "Num Delete"
msgstr "<b>Num Delete</b>"
msgstr "Num Delete"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:95
msgid "Num Down"
msgstr "<b>Num Down</b>"
msgstr "Num Down"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:100
msgid "Num End"
msgstr "<b>Num End</b>"
msgstr "Num End"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:90
msgid "Num Enter"
msgstr "<b>Num Enter</b>"
msgstr "Num Enter"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:91
msgid "Num Home"
msgstr "<b>Num Home</b>"
msgstr "Num Home"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:102
msgid "Num Insert"
msgstr "<b>Num Insert</b>"
msgstr "Num Insert"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:86
msgid "Num Lock"
msgstr "<b>Num Lock</b>"
msgstr "Num Lock"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:97
msgid "Num Page Down"
msgstr "<b>Num Page Down</b>"
msgstr "Num Page Down"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:96
msgid "Num Page Up"
msgstr "<b>Num Page Up</b>"
msgstr "Num Page Up"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:94
msgid "Num Right"
msgstr "<b>Num Right</b>"
msgstr "Num Right"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:88
msgid "Num Space"
msgstr "<b>Num Space</b>"
msgstr "Num Space"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:89
msgid "Num Tab"
msgstr "<b>Num Tab</b>"
msgstr "Num Tab"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:93
msgid "Num Up"
msgstr "<b>Num Up</b>"
msgstr "Num Up"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:92
msgid "Num left"
msgstr "<b>Num left</b>"
msgstr "Num left"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:86
msgid "Num_lock"
msgstr "<b>Num_lock</b>"
msgstr "Num_lock"
#: ../src/richtext/richtextliststylepage.cpp:487
#: ../src/richtext/richtextbulletspage.cpp:279
@ -23490,12 +23490,12 @@ msgstr "Налады старонкі"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:58
msgid "PageDown"
msgstr "<b>PageDown</b>"
msgstr "PageDown"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:57
msgid "PageUp"
msgstr "<b>PageUp</b>"
msgstr "PageUp"
#: ../src/generic/prntdlgg.cpp:216
msgid "Pages"
@ -23545,12 +23545,12 @@ msgstr "Дазволы"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:60
msgid "PgDn"
msgstr "<b>PgDn</b>"
msgstr "PgDn"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:59
msgid "PgUp"
msgstr "<b>PgUp</b>"
msgstr "PgUp"
#: ../src/richtext/richtextbuffer.cpp:12868
msgid "Picture Properties"
@ -25636,17 +25636,17 @@ msgstr "Кірыліца Windows/DOS OEM (CP 866)"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:111
msgid "Windows_Left"
msgstr "<b>Windows_Left</b>"
msgstr "Windows_Left"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:113
msgid "Windows_Menu"
msgstr "<b>Windows_Menu</b>"
msgstr "Windows_Menu"
#. TRANSLATORS: Name of keyboard key
#: ../src/common/accelcmn.cpp:112
msgid "Windows_Right"
msgstr "<b>Windows_Right</b>"
msgstr "Windows_Right"
#: ../src/common/ffile.cpp:150
#, c-format
@ -25709,7 +25709,7 @@ msgstr "Вы не можаце дадаць новы каталог у гэту
#: ../src/propgrid/propgrid.cpp:3299
msgid "You have entered invalid value. Press ESC to cancel editing."
msgstr ""
"Вы ўвялі недапушчальнае значэнне. Націсніце <b>Esc</b>, каб адмяніць змены."
"Вы ўвялі недапушчальнае значэнне. Націсніце ESC, каб адмяніць змены."
#: ../src/common/stockitem.cpp:209
msgid "Zoom &In"

View File

@ -1,4 +1,5 @@
min_slic3r_version = 2.6.0-alpha4
min_slic3r_version = 2.6.0-beta1
0.2.5 Fixed output file format for MONO SE.
0.2.4 Enable pad for Anycubic SLA profiles
0.2.3 Added Photon Mono printer.
0.2.2 Added Photon Mono SE printer.

View File

@ -5,7 +5,7 @@
name = Anycubic
# Configuration version of this file. Config file will only be installed, if the config_version differs.
# This means, the server may force the PrusaSlicer configuration to be downgraded.
config_version = 0.2.1
config_version = 0.2.5
# Where to get the updates from?
config_update_url = https://files.prusa3d.com/wp-content/uploads/repository/PrusaSlicer-settings-master/live/Anycubic/
# changelog_url = https://files.prusa3d.com/?latest=slicer-profiles&lng=%1%
@ -2386,7 +2386,7 @@ output_filename_format = [input_filename_base].pwmx
[sla_print:0.05 Normal @ANYCUBIC MONO SE]
inherits = 0.05 Normal @ANYCUBIC ABSTRACT
compatible_printers_condition = printer_notes=~/.*PHOTONMONOSE\n.*/
output_filename_format = [input_filename_base].pwma
output_filename_format = [input_filename_base].pwms
## SLA materials
@ -2498,3 +2498,4 @@ printer_correction = 1,1,1
gamma_correction = 1
area_fill = 45
printer_notes = Don't remove the following keywords! These keywords are used in the "compatible printer" condition of the print and filament profiles to link the particular print and filament profiles to this printer profile.'\nPRINTER_VENDOR_ANYCUBIC\nPRINTER_MODEL_PHOTONMONOX\nPRINTER_TECHNOLOGY_SLA\n

View File

@ -1,4 +1,5 @@
min_slic3r_version = 2.6.0-beta2
1.9.0 Bumped up configuration version.
1.9.0-beta3 Updated start g-code for MK4 (modified purge line and nozzle cleaning).
1.9.0-beta2 Added profiles for Original Prusa MK4 Input Shaper (Alpha).
min_slic3r_version = 2.6.0-beta0

View File

@ -5,7 +5,7 @@
name = Prusa Research
# Configuration version of this file. Config file will only be installed, if the config_version differs.
# This means, the server may force the PrusaSlicer configuration to be downgraded.
config_version = 1.9.0-beta3
config_version = 1.9.0
# Where to get the updates from?
config_update_url = https://files.prusa3d.com/wp-content/uploads/repository/PrusaSlicer-settings-master/live/PrusaResearch/
changelog_url = https://files.prusa3d.com/?latest=slicer-profiles&lng=%1%

Binary file not shown.

Before

Width:  |  Height:  |  Size: 58 KiB

After

Width:  |  Height:  |  Size: 60 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 58 KiB

After

Width:  |  Height:  |  Size: 58 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 70 KiB

After

Width:  |  Height:  |  Size: 68 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 70 KiB

After

Width:  |  Height:  |  Size: 68 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 70 KiB

After

Width:  |  Height:  |  Size: 67 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 70 KiB

After

Width:  |  Height:  |  Size: 62 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 102 KiB

After

Width:  |  Height:  |  Size: 77 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 68 KiB

After

Width:  |  Height:  |  Size: 64 KiB

View File

@ -480,10 +480,8 @@ std::vector<Polygons> expand_expolygons(const ExPolygons &src, const ExPolygons
return out;
}
std::vector<ExPolygon> expand_merge_expolygons(ExPolygons &&src, const ExPolygons &boundary, const RegionExpansionParameters &params)
std::vector<ExPolygon> merge_expansions_into_expolygons(ExPolygons &&src, std::vector<RegionExpansion> &&expanded)
{
// expanded regions are sorted by boundary id and source id
std::vector<RegionExpansion> expanded = propagate_waves(src, boundary, params);
// expanded regions will be merged into source regions, thus they will be re-sorted by source id.
std::sort(expanded.begin(), expanded.end(), [](const auto &l, const auto &r) { return l.src_id < r.src_id; });
uint32_t last = 0;
@ -535,5 +533,12 @@ std::vector<ExPolygon> expand_merge_expolygons(ExPolygons &&src, const ExPolygon
return out;
}
std::vector<ExPolygon> expand_merge_expolygons(ExPolygons &&src, const ExPolygons &boundary, const RegionExpansionParameters &params)
{
// expanded regions are sorted by boundary id and source id
std::vector<RegionExpansion> expanded = propagate_waves(src, boundary, params);
return merge_expansions_into_expolygons(std::move(src), std::move(expanded));
}
} // Algorithm
} // Slic3r

View File

@ -72,6 +72,7 @@ struct RegionExpansion
};
std::vector<RegionExpansion> propagate_waves(const WaveSeeds &seeds, const ExPolygons &boundary, const RegionExpansionParameters &params);
std::vector<RegionExpansion> propagate_waves(const ExPolygons &src, const ExPolygons &boundary, const RegionExpansionParameters &params);
std::vector<RegionExpansion> propagate_waves(const ExPolygons &src, const ExPolygons &boundary,
// Scaled expansion value
@ -106,6 +107,9 @@ std::vector<Polygons> expand_expolygons(const ExPolygons &src, const ExPolygons
// Don't take more than max_nr_steps for small expansion_step.
size_t max_nr_steps);
// Merge src with expansions, return the merged expolygons.
std::vector<ExPolygon> merge_expansions_into_expolygons(ExPolygons &&src, std::vector<RegionExpansion> &&expanded);
std::vector<ExPolygon> expand_merge_expolygons(ExPolygons &&src, const ExPolygons &boundary, const RegionExpansionParameters &params);
} // Algorithm

View File

@ -755,5 +755,21 @@ void arrange(ArrangePolygons &items,
}
}
BoundingBox bounding_box(const InfiniteBed &bed)
{
BoundingBox ret;
using C = coord_t;
// It is important for Mx and My to be strictly less than half of the
// range of type C. width(), height() and area() will not overflow this way.
C Mx = C((std::numeric_limits<C>::lowest() + 2 * bed.center.x()) / 4.01);
C My = C((std::numeric_limits<C>::lowest() + 2 * bed.center.y()) / 4.01);
ret.max = bed.center - Point{Mx, My};
ret.min = bed.center + Point{Mx, My};
return ret;
}
} // namespace arr
} // namespace Slic3r

View File

@ -55,6 +55,25 @@ struct IrregularBed {
using ArrangeBed = boost::variant<InfiniteBed, RectangleBed, CircleBed, SegmentedRectangleBed, IrregularBed>;
BoundingBox bounding_box(const InfiniteBed &bed);
inline BoundingBox bounding_box(const RectangleBed &b) { return b.bb; }
inline BoundingBox bounding_box(const SegmentedRectangleBed &b) { return b.bb; }
inline BoundingBox bounding_box(const CircleBed &b)
{
auto r = static_cast<coord_t>(std::round(b.radius()));
Point R{r, r};
return {b.center() - R, b.center() + R};
}
inline BoundingBox bounding_box(const ArrangeBed &b)
{
BoundingBox ret;
auto visitor = [&ret](const auto &b) { ret = bounding_box(b); };
boost::apply_visitor(visitor, b);
return ret;
}
ArrangeBed to_arrange_bed(const Points &bedpts);
/// A logical bed representing an object not being arranged. Either the arrange

View File

@ -5,6 +5,7 @@
#include <string>
#include <string_view>
#include <cstdint>
namespace Slic3r {

View File

@ -1065,6 +1065,9 @@ void GCodeProcessor::process_file(const std::string& filename, std::function<voi
apply_config_superslicer(filename);
else if (m_producer == EProducer::KissSlicer)
apply_config_kissslicer(filename);
if (m_result.extruders_count == 0)
m_result.extruders_count = MIN_EXTRUDERS_COUNT;
}
}
@ -2352,28 +2355,58 @@ void GCodeProcessor::process_G0(const GCodeReader::GCodeLine& line)
}
void GCodeProcessor::process_G1(const GCodeReader::GCodeLine& line)
{
std::array<std::optional<double>, 4> g1_axes = { std::nullopt, std::nullopt, std::nullopt, std::nullopt };
if (line.has_x()) g1_axes[X] = (double)line.x();
if (line.has_y()) g1_axes[Y] = (double)line.y();
if (line.has_z()) g1_axes[Z] = (double)line.z();
if (line.has_e()) g1_axes[E] = (double)line.e();
std::optional<double> g1_feedrate = std::nullopt;
if (line.has_f()) g1_feedrate = (double)line.f();
std::optional<std::string> g1_cmt = std::nullopt;
if (!line.comment().empty()) g1_cmt = line.comment();
process_G1(g1_axes, g1_feedrate, g1_cmt);
}
void GCodeProcessor::process_G1(const std::array<std::optional<double>, 4>& axes, std::optional<double> feedrate, std::optional<std::string> cmt)
{
const float filament_diameter = (static_cast<size_t>(m_extruder_id) < m_result.filament_diameters.size()) ? m_result.filament_diameters[m_extruder_id] : m_result.filament_diameters.back();
const float filament_radius = 0.5f * filament_diameter;
const float area_filament_cross_section = static_cast<float>(M_PI) * sqr(filament_radius);
auto move_type = [this](const AxisCoords& delta_pos) {
EMoveType type = EMoveType::Noop;
if (m_wiping)
type = EMoveType::Wipe;
return EMoveType::Wipe;
else if (delta_pos[E] < 0.0f)
type = (delta_pos[X] != 0.0f || delta_pos[Y] != 0.0f || delta_pos[Z] != 0.0f) ? EMoveType::Travel : EMoveType::Retract;
return (delta_pos[X] != 0.0f || delta_pos[Y] != 0.0f || delta_pos[Z] != 0.0f) ? EMoveType::Travel : EMoveType::Retract;
else if (delta_pos[E] > 0.0f) {
if (delta_pos[X] == 0.0f && delta_pos[Y] == 0.0f)
type = (delta_pos[Z] == 0.0f) ? EMoveType::Unretract : EMoveType::Travel;
return (delta_pos[Z] == 0.0f) ? EMoveType::Unretract : EMoveType::Travel;
else if (delta_pos[X] != 0.0f || delta_pos[Y] != 0.0f)
type = EMoveType::Extrude;
return EMoveType::Extrude;
}
else if (delta_pos[X] != 0.0f || delta_pos[Y] != 0.0f || delta_pos[Z] != 0.0f)
type = EMoveType::Travel;
return EMoveType::Travel;
return type;
return EMoveType::Noop;
};
auto extract_absolute_position_on_axis = [&](Axis axis, std::optional<double> value, double area_filament_cross_section)
{
if (value.has_value()) {
bool is_relative = (m_global_positioning_type == EPositioningType::Relative);
if (axis == E)
is_relative |= (m_e_local_positioning_type == EPositioningType::Relative);
const double lengthsScaleFactor = (m_units == EUnits::Inches) ? double(INCHES_TO_MM) : 1.0;
double ret = *value * lengthsScaleFactor;
if (axis == E && m_use_volumetric_e)
ret /= area_filament_cross_section;
return is_relative ? m_start_position[axis] + ret : m_origin[axis] + ret;
}
else
return m_start_position[axis];
};
++m_g1_line_id;
@ -2383,12 +2416,12 @@ void GCodeProcessor::process_G1(const GCodeReader::GCodeLine& line)
// updates axes positions from line
for (unsigned char a = X; a <= E; ++a) {
m_end_position[a] = extract_absolute_position_on_axis((Axis)a, line, double(area_filament_cross_section));
m_end_position[a] = extract_absolute_position_on_axis((Axis)a, axes[a], double(area_filament_cross_section));
}
// updates feedrate from line, if present
if (line.has_f())
m_feedrate = m_feed_multiply.current * line.f() * MMMIN_TO_MMSEC;
if (feedrate.has_value())
m_feedrate = m_feed_multiply.current * (*feedrate) * MMMIN_TO_MMSEC;
// calculates movement deltas
AxisCoords delta_pos;
@ -2401,8 +2434,7 @@ void GCodeProcessor::process_G1(const GCodeReader::GCodeLine& line)
const float volume_extruded_filament = area_filament_cross_section * delta_pos[E];
if (volume_extruded_filament != 0.)
m_used_filaments.increase_caches(volume_extruded_filament,
m_extruder_id, area_filament_cross_section * m_parking_position,
m_used_filaments.increase_caches(volume_extruded_filament, m_extruder_id, area_filament_cross_section * m_parking_position,
area_filament_cross_section * m_extra_loading_move);
const EMoveType type = move_type(delta_pos);
@ -2420,7 +2452,7 @@ void GCodeProcessor::process_G1(const GCodeReader::GCodeLine& line)
m_height = m_forced_height;
else if (m_layer_id == 0)
m_height = m_first_layer_height + m_z_offset;
else if (line.comment() != INTERNAL_G2G3_TAG){
else if (!cmt.has_value() || *cmt != INTERNAL_G2G3_TAG) {
if (m_end_position[Z] > m_extruded_last_z + EPSILON && delta_pos[Z] == 0.0)
m_height = m_end_position[Z] - m_extruded_last_z;
}
@ -2431,7 +2463,7 @@ void GCodeProcessor::process_G1(const GCodeReader::GCodeLine& line)
if (m_end_position[Z] == 0.0f || (m_extrusion_role == GCodeExtrusionRole::Custom && m_layer_id == 0))
m_end_position[Z] = m_height;
if (line.comment() != INTERNAL_G2G3_TAG)
if (!cmt.has_value() || *cmt != INTERNAL_G2G3_TAG)
m_extruded_last_z = m_end_position[Z];
m_options_z_corrector.update(m_height);
@ -2464,7 +2496,7 @@ void GCodeProcessor::process_G1(const GCodeReader::GCodeLine& line)
// time estimate section
auto move_length = [](const AxisCoords& delta_pos) {
float sq_xyz_length = sqr(delta_pos[X]) + sqr(delta_pos[Y]) + sqr(delta_pos[Z]);
const float sq_xyz_length = sqr(delta_pos[X]) + sqr(delta_pos[Y]) + sqr(delta_pos[Z]);
return (sq_xyz_length > 0.0f) ? std::sqrt(sq_xyz_length) : std::abs(delta_pos[E]);
};
@ -2485,8 +2517,7 @@ void GCodeProcessor::process_G1(const GCodeReader::GCodeLine& line)
TimeMachine::State& prev = machine.prev;
std::vector<TimeBlock>& blocks = machine.blocks;
curr.feedrate = (delta_pos[E] == 0.0f) ?
minimum_travel_feedrate(static_cast<PrintEstimatedStatistics::ETimeMode>(i), m_feedrate) :
curr.feedrate = (delta_pos[E] == 0.0f) ? minimum_travel_feedrate(static_cast<PrintEstimatedStatistics::ETimeMode>(i), m_feedrate) :
minimum_feedrate(static_cast<PrintEstimatedStatistics::ETimeMode>(i), m_feedrate);
TimeBlock block;
@ -2521,10 +2552,8 @@ void GCodeProcessor::process_G1(const GCodeReader::GCodeLine& line)
}
// calculates block acceleration
float acceleration =
(type == EMoveType::Travel) ? get_travel_acceleration(static_cast<PrintEstimatedStatistics::ETimeMode>(i)) :
(is_extrusion_only_move(delta_pos) ?
get_retract_acceleration(static_cast<PrintEstimatedStatistics::ETimeMode>(i)) :
float acceleration = (type == EMoveType::Travel) ? get_travel_acceleration(static_cast<PrintEstimatedStatistics::ETimeMode>(i)) :
(is_extrusion_only_move(delta_pos) ? get_retract_acceleration(static_cast<PrintEstimatedStatistics::ETimeMode>(i)) :
get_acceleration(static_cast<PrintEstimatedStatistics::ETimeMode>(i)));
for (unsigned char a = X; a <= E; ++a) {
@ -2551,8 +2580,8 @@ void GCodeProcessor::process_G1(const GCodeReader::GCodeLine& line)
// calculates block entry feedrate
float vmax_junction = curr.safe_feedrate;
if (!blocks.empty() && prev.feedrate > PREVIOUS_FEEDRATE_THRESHOLD) {
bool prev_speed_larger = prev.feedrate > block.feedrate_profile.cruise;
float smaller_speed_factor = prev_speed_larger ? (block.feedrate_profile.cruise / prev.feedrate) : (prev.feedrate / block.feedrate_profile.cruise);
const bool prev_speed_larger = prev.feedrate > block.feedrate_profile.cruise;
const float smaller_speed_factor = prev_speed_larger ? (block.feedrate_profile.cruise / prev.feedrate) : (prev.feedrate / block.feedrate_profile.cruise);
// Pick the smaller of the nominal speeds. Higher speed shall not be achieved at the junction during coasting.
vmax_junction = prev_speed_larger ? block.feedrate_profile.cruise : prev.feedrate;
@ -2664,7 +2693,7 @@ void GCodeProcessor::process_G1(const GCodeReader::GCodeLine& line)
}
// store move
store_move_vertex(type, line.comment() == INTERNAL_G2G3_TAG);
store_move_vertex(type, cmt.has_value() && *cmt == INTERNAL_G2G3_TAG);
}
void GCodeProcessor::process_G2_G3(const GCodeReader::GCodeLine& line, bool clockwise)
@ -2693,7 +2722,7 @@ void GCodeProcessor::process_G2_G3(const GCodeReader::GCodeLine& line, bool cloc
double delta_z() const { return end.z() - start.z(); }
double length() const { return angle * start_radius(); }
double travel_length() const { return std::sqrt(sqr(length() + sqr(delta_z()))); }
double travel_length() const { return std::sqrt(sqr(length()) + sqr(delta_z())); }
double start_radius() const { return (start - center).norm(); }
double end_radius() const { return (end - center).norm(); }
@ -2778,18 +2807,18 @@ void GCodeProcessor::process_G2_G3(const GCodeReader::GCodeLine& line, bool cloc
return ret;
};
auto internal_only_g1_line = [](const AxisCoords& target, bool has_z, const std::optional<float>& feedrate, const std::optional<float>& extrusion) {
std::string ret = (boost::format("G1 X%1% Y%2%") % target[X] % target[Y]).str();
auto internal_only_g1_line = [this](const AxisCoords& target, bool has_z, const std::optional<float>& feedrate, const std::optional<float>& extrusion) {
std::array<std::optional<double>, 4> g1_axes = { target[X], target[Y], std::nullopt, std::nullopt };
std::optional<double> g1_feedrate = std::nullopt;
if (has_z)
ret += (boost::format(" Z%1%") % target[Z]).str();
g1_axes[Z] = target[Z];
if (feedrate.has_value())
ret += (boost::format(" F%1%") % *feedrate).str();
g1_feedrate = (double)*feedrate;
if (extrusion.has_value())
ret += (boost::format(" E%1%") % target[E]).str();
g1_axes[E] = target[E];
std::optional<std::string> g1_cmt = INTERNAL_G2G3_TAG;
ret += (boost::format(" ;%1%\n") % INTERNAL_G2G3_TAG).str();
return ret;
process_G1(g1_axes, g1_feedrate, g1_cmt);
};
// calculate arc segments
@ -2798,17 +2827,16 @@ void GCodeProcessor::process_G2_G3(const GCodeReader::GCodeLine& line, bool cloc
// https://github.com/prusa3d/Prusa-Firmware/blob/MK3/Firmware/motion_control.cpp
// segments count
static const double MM_PER_ARC_SEGMENT = 0.5;
const size_t segments = std::ceil(travel_length / MM_PER_ARC_SEGMENT);
assert(segments >= 1);
static const double MM_PER_ARC_SEGMENT = 1.0;
const size_t segments = std::max<size_t>(std::floor(travel_length / MM_PER_ARC_SEGMENT), 1);
const double theta_per_segment = arc.angle / double(segments);
const double z_per_segment = arc.delta_z() / double(segments);
const double extruder_per_segment = (extrusion.has_value()) ? *extrusion / double(segments) : 0.0;
const double inv_segment = 1.0 / double(segments);
const double theta_per_segment = arc.angle * inv_segment;
const double z_per_segment = arc.delta_z() * inv_segment;
const double extruder_per_segment = (extrusion.has_value()) ? *extrusion * inv_segment : 0.0;
const double sq_theta_per_segment = sqr(theta_per_segment);
const double cos_T = 1.0 - 0.5 * sq_theta_per_segment; // Small angle approximation
const double sin_T = theta_per_segment - sq_theta_per_segment * theta_per_segment / 6.0; // Small angle approximation
const double cos_T = 1.0 - 0.5 * sqr(theta_per_segment); // Small angle approximation
const double sin_T = theta_per_segment;
AxisCoords prev_target = m_start_position;
AxisCoords arc_target;
@ -2820,28 +2848,25 @@ void GCodeProcessor::process_G2_G3(const GCodeReader::GCodeLine& line, bool cloc
arc_target[E] = m_start_position[E];
static const size_t N_ARC_CORRECTION = 25;
Vec3d curr_rel_arc_start = arc.relative_start();
std::string gcode;
size_t n_arc_correction = N_ARC_CORRECTION;
size_t count = 0;
for (size_t i = 1; i < segments; ++i) {
if (n_arc_correction-- == 0) {
// Calculate the actual position for r_axis_x and r_axis_y
const double cos_Ti = ::cos((double)i * theta_per_segment);
const double sin_Ti = ::sin((double)i * theta_per_segment);
curr_rel_arc_start.x() = -double(rel_center.x()) * cos_Ti + double(rel_center.y()) * sin_Ti;
curr_rel_arc_start.y() = -double(rel_center.x()) * sin_Ti - double(rel_center.y()) * cos_Ti;
// reset n_arc_correction
n_arc_correction = N_ARC_CORRECTION;
}
else {
// Calculate X and Y using the small angle approximation
if (count < N_ARC_CORRECTION) {
// Apply vector rotation matrix
const float r_axisi = curr_rel_arc_start.x() * sin_T + curr_rel_arc_start.y() * cos_T;
curr_rel_arc_start.x() = curr_rel_arc_start.x() * cos_T - curr_rel_arc_start.y() * sin_T;
curr_rel_arc_start.y() = r_axisi;
++count;
}
else {
// Arc correction to radius vector. Computed only every N_ARC_CORRECTION increments.
// Compute exact location by applying transformation matrix from initial radius vector(=-offset).
const double cos_Ti = ::cos(i * theta_per_segment);
const double sin_Ti = ::sin(i * theta_per_segment);
curr_rel_arc_start.x() = -double(rel_center.x()) * cos_Ti + double(rel_center.y()) * sin_Ti;
curr_rel_arc_start.y() = -double(rel_center.x()) * sin_Ti - double(rel_center.y()) * cos_Ti;
count = 0;
}
// Update arc_target location
@ -2850,23 +2875,14 @@ void GCodeProcessor::process_G2_G3(const GCodeReader::GCodeLine& line, bool cloc
arc_target[Z] += z_per_segment;
arc_target[E] += extruder_per_segment;
gcode += internal_only_g1_line(adjust_target(arc_target, prev_target), z_per_segment != 0.0, feedrate, extrusion);
m_start_position = m_end_position; // this is required because we are skipping the call to process_gcode_line()
internal_only_g1_line(adjust_target(arc_target, prev_target), z_per_segment != 0.0, (i == 1) ? feedrate : std::nullopt, extrusion);
prev_target = arc_target;
// feedrate is constant, we do not need to repeat it
feedrate.reset();
}
// Ensure last segment arrives at target location.
gcode += internal_only_g1_line(adjust_target(end_position, prev_target), arc.delta_z() != 0.0, feedrate, extrusion);
// process fake gcode lines
GCodeReader parser;
parser.parse_buffer(gcode, [this](GCodeReader&, const GCodeReader::GCodeLine& line) {
// force all lines to share the same id
--m_line_id;
process_gcode_line(line, false);
});
m_start_position = m_end_position; // this is required because we are skipping the call to process_gcode_line()
internal_only_g1_line(adjust_target(end_position, prev_target), arc.delta_z() != 0.0, (segments == 1) ? feedrate : std::nullopt, extrusion);
}
void GCodeProcessor::process_G10(const GCodeReader::GCodeLine& line)

View File

@ -680,6 +680,8 @@ namespace Slic3r {
// Move
void process_G0(const GCodeReader::GCodeLine& line);
void process_G1(const GCodeReader::GCodeLine& line);
void process_G1(const std::array<std::optional<double>, 4>& axes = { std::nullopt, std::nullopt, std::nullopt, std::nullopt },
std::optional<double> feedrate = std::nullopt, std::optional<std::string> cmt = std::nullopt);
// Arc Move
void process_G2_G3(const GCodeReader::GCodeLine& line, bool clockwise);

View File

@ -170,7 +170,9 @@ static ExPolygons fill_surfaces_extract_expolygons(Surfaces &surfaces, std::init
Surfaces expand_bridges_detect_orientations(
Surfaces &surfaces,
ExPolygons &shells,
const Algorithm::RegionExpansionParameters &expansion_params,
const Algorithm::RegionExpansionParameters &expansion_params_into_solid_infill,
ExPolygons &sparse,
const Algorithm::RegionExpansionParameters &expansion_params_into_sparse_infill,
const float closing_radius)
{
using namespace Slic3r::Algorithm;
@ -181,8 +183,23 @@ Surfaces expand_bridges_detect_orientations(
return {};
// Calculate bridge anchors and their expansions in their respective shell region.
WaveSeeds bridge_anchors = wave_seeds(bridges_ex, shells, expansion_params.tiny_expansion, true);
std::vector<RegionExpansionEx> bridge_expansions = propagate_waves_ex(bridge_anchors, shells, expansion_params);
WaveSeeds bridge_anchors = wave_seeds(bridges_ex, shells, expansion_params_into_solid_infill.tiny_expansion, true);
std::vector<RegionExpansionEx> bridge_expansions = propagate_waves_ex(bridge_anchors, shells, expansion_params_into_solid_infill);
bool expanded_into_shells = ! bridge_expansions.empty();
bool expanded_into_sparse = false;
{
WaveSeeds bridge_anchors_sparse = wave_seeds(bridges_ex, sparse, expansion_params_into_sparse_infill.tiny_expansion, true);
std::vector<RegionExpansionEx> bridge_expansions_sparse = propagate_waves_ex(bridge_anchors_sparse, sparse, expansion_params_into_sparse_infill);
if (! bridge_expansions_sparse.empty()) {
expanded_into_sparse = true;
for (WaveSeed &seed : bridge_anchors_sparse)
seed.boundary += uint32_t(shells.size());
for (RegionExpansionEx &expansion : bridge_expansions_sparse)
expansion.boundary_id += uint32_t(shells.size());
append(bridge_anchors, std::move(bridge_anchors_sparse));
append(bridge_expansions, std::move(bridge_expansions_sparse));
}
}
// Cache for detecting bridge orientation and merging regions with overlapping expansions.
struct Bridge {
@ -259,7 +276,7 @@ Surfaces expand_bridges_detect_orientations(
for (; it_bridge_anchor != bridge_anchors.end() && it_bridge_anchor->src == bridge_id; ++ it_bridge_anchor) {
if (last_anchor_id != int(it_bridge_anchor->boundary)) {
last_anchor_id = int(it_bridge_anchor->boundary);
append(anchor_areas, to_polygons(shells[last_anchor_id]));
append(anchor_areas, to_polygons(last_anchor_id < int32_t(shells.size()) ? shells[last_anchor_id] : sparse[last_anchor_id - int32_t(shells.size())]));
}
// if (Points &polyline = it_bridge_anchor->path; polyline.size() >= 2) {
// reserve_more_power_of_2(lines, polyline.size() - 1);
@ -270,17 +287,18 @@ Surfaces expand_bridges_detect_orientations(
lines = to_lines(diff_pl(to_polylines(bridge.expolygon), expand(anchor_areas, float(SCALED_EPSILON))));
auto [bridging_dir, unsupported_dist] = detect_bridging_direction(lines, to_polygons(bridge.expolygon));
bridge.angle = M_PI + std::atan2(bridging_dir.y(), bridging_dir.x());
// #if 1
// coordf_t stroke_width = scale_(0.06);
// BoundingBox bbox = get_extents(initial);
// bbox.offset(scale_(1.));
// ::Slic3r::SVG
// svg(debug_out_path(("bridge"+std::to_string(bridges[idx_last].bridge_angle)+"_"+std::to_string(this->layer()->bottom_z())).c_str()),
// bbox);
// svg.draw(initial, "cyan");
// svg.draw(to_lines(lower_layer->lslices), "green", stroke_width);
// #endif
#if 0
coordf_t stroke_width = scale_(0.06);
BoundingBox bbox = get_extents(anchor_areas);
bbox.merge(get_extents(bridge.expolygon));
bbox.offset(scale_(1.));
::Slic3r::SVG
svg(debug_out_path(("bridge" + std::to_string(bridge.angle) + "_" /* + std::to_string(this->layer()->bottom_z())*/).c_str()),
bbox);
svg.draw(bridge.expolygon, "cyan");
svg.draw(lines, "green", stroke_width);
svg.draw(anchor_areas, "red");
#endif
}
}
@ -322,8 +340,11 @@ Surfaces expand_bridges_detect_orientations(
}
}
// Clip the shells by the expanded bridges.
// Clip by the expanded bridges.
if (expanded_into_shells)
shells = diff_ex(shells, out);
if (expanded_into_sparse)
sparse = diff_ex(sparse, out);
return out;
}
@ -333,22 +354,42 @@ static Surfaces expand_merge_surfaces(
Surfaces &surfaces,
SurfaceType surface_type,
ExPolygons &shells,
const Algorithm::RegionExpansionParameters &params,
const Algorithm::RegionExpansionParameters &expansion_params_into_solid_infill,
ExPolygons &sparse,
const Algorithm::RegionExpansionParameters &expansion_params_into_sparse_infill,
const float closing_radius,
const double bridge_angle = -1.)
{
using namespace Slic3r::Algorithm;
double thickness;
ExPolygons src = fill_surfaces_extract_expolygons(surfaces, {surface_type}, thickness);
if (src.empty())
return {};
std::vector<ExPolygon> expanded = expand_merge_expolygons(std::move(src), shells, params);
std::vector<RegionExpansion> expansions = propagate_waves(src, shells, expansion_params_into_solid_infill);
bool expanded_into_shells = !expansions.empty();
bool expanded_into_sparse = false;
{
std::vector<RegionExpansion> expansions2 = propagate_waves(src, sparse, expansion_params_into_sparse_infill);
if (! expansions2.empty()) {
expanded_into_sparse = true;
for (RegionExpansion &expansion : expansions2)
expansion.boundary_id += uint32_t(shells.size());
append(expansions, std::move(expansions2));
}
}
std::vector<ExPolygon> expanded = merge_expansions_into_expolygons(std::move(src), std::move(expansions));
//NOTE: The current regularization of the shells can create small unasigned regions in the object (E.G. benchy)
// without the following closing operation, those regions will stay unfilled and cause small holes in the expanded surface.
// look for narrow_ensure_vertical_wall_thickness_region_radius filter.
expanded = closing_ex(expanded, closing_radius);
// Trim the shells by the expanded expolygons.
if (expanded_into_shells)
shells = diff_ex(shells, expanded);
if (expanded_into_sparse)
sparse = diff_ex(sparse, expanded);
Surface templ{ surface_type, {} };
templ.bridge_angle = bridge_angle;
@ -361,20 +402,25 @@ static Surfaces expand_merge_surfaces(
void LayerRegion::process_external_surfaces(const Layer *lower_layer, const Polygons *lower_layer_covered)
{
using namespace Slic3r::Algorithm;
#ifdef SLIC3R_DEBUG_SLICE_PROCESSING
export_region_fill_surfaces_to_svg_debug("4_process_external_surfaces-initial");
#endif /* SLIC3R_DEBUG_SLICE_PROCESSING */
// Width of the perimeters.
float shell_width = 0;
float expansion_min = 0;
if (int num_perimeters = this->region().config().perimeters; num_perimeters > 0) {
Flow external_perimeter_flow = this->flow(frExternalPerimeter);
Flow perimeter_flow = this->flow(frPerimeter);
shell_width += 0.5f * external_perimeter_flow.scaled_width() + external_perimeter_flow.scaled_spacing();
shell_width = 0.5f * external_perimeter_flow.scaled_width() + external_perimeter_flow.scaled_spacing();
shell_width += perimeter_flow.scaled_spacing() * (num_perimeters - 1);
expansion_min = perimeter_flow.scaled_spacing();
} else {
// TODO: Maybe there is better solution when printing with zero perimeters, but this works reasonably well, given the situation
shell_width = float(SCALED_EPSILON);
expansion_min = float(SCALED_EPSILON);;
}
// Scaled expansions of the respective external surfaces.
@ -390,16 +436,18 @@ void LayerRegion::process_external_surfaces(const Layer *lower_layer, const Poly
// Expand the top / bottom / bridge surfaces into the shell thickness solid infills.
double layer_thickness;
ExPolygons shells = union_ex(fill_surfaces_extract_expolygons(m_fill_surfaces.surfaces, {stInternalSolid}, layer_thickness));
ExPolygons shells = union_ex(fill_surfaces_extract_expolygons(m_fill_surfaces.surfaces, { stInternalSolid }, layer_thickness));
ExPolygons sparse = union_ex(fill_surfaces_extract_expolygons(m_fill_surfaces.surfaces, { stInternal }, layer_thickness));
SurfaceCollection bridges;
const auto expansion_params_into_sparse_infill = RegionExpansionParameters::build(expansion_min, expansion_step, max_nr_expansion_steps);
{
BOOST_LOG_TRIVIAL(trace) << "Processing external surface, detecting bridges. layer" << this->layer()->print_z;
const double custom_angle = this->region().config().bridge_angle.value;
const auto params = Algorithm::RegionExpansionParameters::build(expansion_bottom_bridge, expansion_step, max_nr_expansion_steps);
const auto expansion_params_into_solid_infill = RegionExpansionParameters::build(expansion_bottom_bridge, expansion_step, max_nr_expansion_steps);
bridges.surfaces = custom_angle > 0 ?
expand_merge_surfaces(m_fill_surfaces.surfaces, stBottomBridge, shells, params, closing_radius, Geometry::deg2rad(custom_angle)) :
expand_bridges_detect_orientations(m_fill_surfaces.surfaces, shells, params, closing_radius);
expand_merge_surfaces(m_fill_surfaces.surfaces, stBottomBridge, shells, expansion_params_into_solid_infill, sparse, expansion_params_into_sparse_infill, closing_radius, Geometry::deg2rad(custom_angle)) :
expand_bridges_detect_orientations(m_fill_surfaces.surfaces, shells, expansion_params_into_solid_infill, sparse, expansion_params_into_sparse_infill, closing_radius);
BOOST_LOG_TRIVIAL(trace) << "Processing external surface, detecting bridges - done";
#if 0
{
@ -410,15 +458,25 @@ void LayerRegion::process_external_surfaces(const Layer *lower_layer, const Poly
}
Surfaces bottoms = expand_merge_surfaces(m_fill_surfaces.surfaces, stBottom, shells,
Algorithm::RegionExpansionParameters::build(expansion_bottom, expansion_step, max_nr_expansion_steps), closing_radius);
RegionExpansionParameters::build(expansion_bottom, expansion_step, max_nr_expansion_steps),
sparse, expansion_params_into_sparse_infill, closing_radius);
Surfaces tops = expand_merge_surfaces(m_fill_surfaces.surfaces, stTop, shells,
Algorithm::RegionExpansionParameters::build(expansion_top, expansion_step, max_nr_expansion_steps), closing_radius);
RegionExpansionParameters::build(expansion_top, expansion_step, max_nr_expansion_steps),
sparse, expansion_params_into_sparse_infill, closing_radius);
m_fill_surfaces.remove_types({ stBottomBridge, stBottom, stTop, stInternalSolid });
reserve_more(m_fill_surfaces.surfaces, shells.size() + bridges.size() + bottoms.size() + tops.size());
// m_fill_surfaces.remove_types({ stBottomBridge, stBottom, stTop, stInternal, stInternalSolid });
m_fill_surfaces.clear();
reserve_more(m_fill_surfaces.surfaces, shells.size() + sparse.size() + bridges.size() + bottoms.size() + tops.size());
{
Surface solid_templ(stInternalSolid, {});
solid_templ.thickness = layer_thickness;
m_fill_surfaces.append(std::move(shells), solid_templ);
}
{
Surface sparse_templ(stInternal, {});
sparse_templ.thickness = layer_thickness;
m_fill_surfaces.append(std::move(sparse), sparse_templ);
}
m_fill_surfaces.append(std::move(bridges.surfaces));
m_fill_surfaces.append(std::move(bottoms));
m_fill_surfaces.append(std::move(tops));

View File

@ -510,6 +510,8 @@ public:
bool has_solid_mesh() const;
// Detect if object has at least one negative volume mash
bool has_negative_volume_mesh() const;
// Detect if object has at least one sla drain hole
bool has_sla_drain_holes() const { return !sla_drain_holes.empty(); }
bool is_cut() const { return cut_id.id().valid(); }
bool has_connectors() const;

View File

@ -4,6 +4,7 @@
#include <vector>
#include <string>
#include <istream>
#include <cstdint>
namespace Slic3r { namespace png {

View File

@ -2240,7 +2240,7 @@ namespace PresetUtils {
{
const VendorProfile::PrinterModel *out = nullptr;
if (preset.vendor != nullptr) {
auto *printer_model = preset.config.opt<ConfigOptionString>("printer_model");
const auto *printer_model = preset.config.opt<ConfigOptionString>("printer_model");
if (printer_model != nullptr && ! printer_model->value.empty()) {
auto it = std::find_if(preset.vendor->models.begin(), preset.vendor->models.end(), [printer_model](const VendorProfile::PrinterModel &pm) { return pm.id == printer_model->value; });
if (it != preset.vendor->models.end())

View File

@ -68,7 +68,7 @@ static const t_config_enum_values s_keys_map_PrintHostType {
{ "prusalink", htPrusaLink },
{ "prusaconnect", htPrusaConnect },
{ "octoprint", htOctoPrint },
{ "mainsail", htMainSail },
{ "moonraker", htMoonraker },
{ "duet", htDuet },
{ "flashair", htFlashAir },
{ "astrobox", htAstroBox },
@ -1953,7 +1953,7 @@ void PrintConfigDef::init_fff_params()
{ "prusalink", "PrusaLink" },
{ "prusaconnect", "PrusaConnect" },
{ "octoprint", "OctoPrint" },
{ "mainsail", "Mainsail/Fluidd" },
{ "moonraker", "Klipper (via Moonraker)" },
{ "duet", "Duet" },
{ "flashair", "FlashAir" },
{ "astrobox", "AstroBox" },
@ -4214,6 +4214,9 @@ void PrintConfigDef::handle_legacy(t_config_option_key &opt_key, std::string &va
else if (value == "marlinfirmware")
// the "new" marlin firmware flavor used to be called "marlinfirmware" for some time during PrusaSlicer 2.4.0-alpha development.
value = "marlin2";
} else if (opt_key == "host_type" && value == "mainsail") {
// the "mainsail" key (introduced in 2.6.0-alpha6) was renamed to "moonraker" (in 2.6.0-rc1).
value = "moonraker";
} else if (opt_key == "fill_density" && value.find("%") == std::string::npos) {
try {
// fill_density was turned into a percent value

View File

@ -44,7 +44,7 @@ enum class MachineLimitsUsage {
};
enum PrintHostType {
htPrusaLink, htPrusaConnect, htOctoPrint, htMainSail, htDuet, htFlashAir, htAstroBox, htRepetier, htMKS
htPrusaLink, htPrusaConnect, htOctoPrint, htMoonraker, htDuet, htFlashAir, htAstroBox, htRepetier, htMKS
};
enum AuthorizationType {

View File

@ -981,11 +981,12 @@ void PrintObject::detect_surfaces_type()
surface_type_bottom_other);
#else
// Any surface lying on the void is a true bottom bridge (an overhang)
ExPolygons true_bridge = diff_ex(layerm->slices().surfaces, lower_layer->lslices, ApplySafetyOffset::Yes);
// expand the bridges by one extrusion width, to ensure reasonable anchoring whenever possible
true_bridge = intersection_ex(layerm->slices().surfaces,
offset_ex(true_bridge, layerm->bridging_flow(frSolidInfill).scaled_spacing()));
surfaces_append(bottom, true_bridge, surface_type_bottom_other);
surfaces_append(
bottom,
opening_ex(
diff_ex(layerm->slices().surfaces, lower_layer->lslices, ApplySafetyOffset::Yes),
offset),
surface_type_bottom_other);
// if user requested internal shells, we need to identify surfaces
// lying on other slices not belonging to this region
if (interface_shells) {

View File

@ -211,6 +211,12 @@ bool is_main_thread_active()
return get_main_thread_id() == boost::this_thread::get_id();
}
static thread_local ThreadData s_thread_data;
ThreadData& thread_data()
{
return s_thread_data;
}
// Spawn (n - 1) worker threads on Intel TBB thread pool and name them by an index and a system thread ID.
// Also it sets locale of the worker threads to "C" for the G-code generator to produce "." as a decimal separator.
void name_tbb_thread_pool_threads_set_locale()
@ -274,16 +280,16 @@ void set_current_thread_qos()
#endif // __APPLE__
}
void TBBLocalesSetter::on_scheduler_entry(bool is_worker)
void ThreadData::tbb_worker_thread_set_c_locales()
{
// static std::atomic<int> cnt = 0;
// std::cout << "TBBLocalesSetter Entering " << cnt ++ << " ID " << std::this_thread::get_id() << "\n";
if (bool& is_locales_sets = m_is_locales_sets.local(); !is_locales_sets) {
if (! m_tbb_worker_thread_c_locales_set) {
// Set locales of the worker thread to "C".
set_c_locales();
// OSX specific: Elevate QOS on Apple Silicon.
set_current_thread_qos();
is_locales_sets = true;
m_tbb_worker_thread_c_locales_set = true;
}
}

View File

@ -4,6 +4,7 @@
#include <utility>
#include <string>
#include <thread>
#include <random>
#include <boost/thread.hpp>
#include <tbb/task_scheduler_observer.h>
@ -67,6 +68,27 @@ template<class Fn> inline boost::thread create_thread(Fn &&fn)
return create_thread(attrs, std::forward<Fn>(fn));
}
class ThreadData {
public:
std::mt19937& random_generator() {
if (! m_random_generator_initialized) {
std::random_device rd;
m_random_generator.seed(rd());
m_random_generator_initialized = true;
}
return m_random_generator;
}
void tbb_worker_thread_set_c_locales();
private:
std::mt19937 m_random_generator;
bool m_random_generator_initialized { false };
bool m_tbb_worker_thread_c_locales_set { false };
};
ThreadData& thread_data();
// For unknown reasons and in sporadic cases when GCode export is processing, some participating thread
// in tbb::parallel_pipeline has not set locales to "C", probably because this thread is newly spawned.
// So in this class method on_scheduler_entry is called for every thread before it starts participating
@ -79,11 +101,7 @@ class TBBLocalesSetter : public tbb::task_scheduler_observer
public:
TBBLocalesSetter() { this->observe(true); }
~TBBLocalesSetter() override { this->observe(false); };
void on_scheduler_entry(bool is_worker) override;
private:
tbb::enumerable_thread_specific<bool, tbb::cache_aligned_allocator<bool>, tbb::ets_key_usage_type::ets_key_per_instance> m_is_locales_sets{ false };
void on_scheduler_entry(bool /* is_worker */) override { thread_data().tbb_worker_thread_set_c_locales(); }
};
}

View File

@ -255,8 +255,8 @@ set(SLIC3R_GUI_SOURCES
Utils/Http.hpp
Utils/FixModelByWin10.cpp
Utils/FixModelByWin10.hpp
Utils/Mainsail.cpp
Utils/Mainsail.hpp
Utils/Moonraker.cpp
Utils/Moonraker.hpp
Utils/OctoPrint.cpp
Utils/OctoPrint.hpp
Utils/Duet.cpp

View File

@ -1162,6 +1162,10 @@ static bool object_contains_negative_volumes(const Model& model, int obj_id) {
return (0 <= obj_id && obj_id < (int)model.objects.size()) ? model.objects[obj_id]->has_negative_volume_mesh() : false;
}
static bool object_has_sla_drain_holes(const Model& model, int obj_id) {
return (0 <= obj_id && obj_id < (int)model.objects.size()) ? model.objects[obj_id]->has_sla_drain_holes() : false;
}
void GLCanvas3D::SLAView::detect_type_from_volumes(const GLVolumePtrs& volumes)
{
for (auto& [id, type] : m_instances_cache) {
@ -1170,7 +1174,8 @@ void GLCanvas3D::SLAView::detect_type_from_volumes(const GLVolumePtrs& volumes)
for (const GLVolume* v : volumes) {
if (v->volume_idx() == -(int)slaposDrillHoles) {
if (object_contains_negative_volumes(*m_parent.get_model(), v->composite_id.object_id)) {
if (object_contains_negative_volumes(*m_parent.get_model(), v->composite_id.object_id) ||
object_has_sla_drain_holes(*m_parent.get_model(), v->composite_id.object_id)) {
const InstancesCacheItem* instance = find_instance_item(v->composite_id);
assert(instance != nullptr);
set_type(instance->first, ESLAViewType::Processed);
@ -4696,6 +4701,13 @@ std::pair<SlicingParameters, const std::vector<double>> GLCanvas3D::get_layers_h
return ret;
}
void GLCanvas3D::detect_sla_view_type()
{
m_sla_view.detect_type_from_volumes(m_volumes.volumes);
m_sla_view.update_volumes_visibility(m_volumes.volumes);
m_dirty = true;
}
void GLCanvas3D::set_sla_view_type(ESLAViewType type)
{
m_sla_view.set_type(type);

View File

@ -1005,6 +1005,7 @@ public:
std::pair<SlicingParameters, const std::vector<double>> get_layers_height_data(int object_id);
void detect_sla_view_type();
void set_sla_view_type(ESLAViewType type);
void set_sla_view_type(const GLVolume::CompositeID& id, ESLAViewType type);
void enable_sla_view_type_detection() { m_sla_view_type_detection_active = true; }

View File

@ -2281,14 +2281,7 @@ bool GUI_App::load_language(wxString language, bool initial)
}
#endif
#ifdef __APPLE__
// ysFIXME after fix for wxWidgets issue (https://github.com/wxWidgets/wxWidgets/issues/23209)
// Workaround for wxLANGUAGE_CHINESE(...) languages => Allow to continue even if wxLocale is not available.
// Because of translation will works fine, just locales will set to EN
if (! wxLocale::IsAvailable(language_info->Language) && language_info->CanonicalName.BeforeFirst('_') != "zh" ) {
#else
if (! wxLocale::IsAvailable(language_info->Language)) {
#endif
// Loading the language dictionary failed.
wxString message = "Switching PrusaSlicer to language " + language_info->CanonicalName + " failed.";
#if !defined(_WIN32) && !defined(__APPLE__)

View File

@ -855,6 +855,7 @@ void GLGizmoSlaSupports::on_set_state()
m_old_mo_id = -1;
}
m_parent.post_event(SimpleEvent(EVT_GLCANVAS_FORCE_UPDATE));
m_c->instances_hider()->set_hide_full_scene(false);
m_c->selection_info()->set_use_shift(false); // see top of on_render for details

View File

@ -962,6 +962,8 @@ bool GLGizmosManager::activate_gizmo(EType type)
if (type == Undefined) {
// it is deactivation of gizmo
m_current = Undefined;
if (m_parent.current_printer_technology() == ptSLA)
m_parent.detect_sla_view_type();
return true;
}

View File

@ -99,7 +99,6 @@ void ArrangeJob::prepare_selected() {
clear_input();
Model &model = m_plater->model();
double stride = bed_stride(m_plater);
std::vector<const Selection::InstanceIdxsList *>
obj_sel(model.objects.size(), nullptr);
@ -143,12 +142,6 @@ void ArrangeJob::prepare_selected() {
// If the selection was empty arrange everything
if (m_selected.empty())
m_selected.swap(m_unselected);
// The strides have to be removed from the fixed items. For the
// arrangeable (selected) items bed_idx is ignored and the
// translation is irrelevant.
for (auto &p : m_unselected)
p.translation(X) -= p.bed_idx * stride;
}
static void update_arrangepoly_slaprint(arrangement::ArrangePolygon &ret,
@ -261,6 +254,10 @@ void ArrangeJob::prepare()
}
m_min_bed_inset = min_offset;
}
double stride = bed_stride(m_plater);
get_bed_shape(*m_plater->config(), m_bed);
assign_logical_beds(m_unselected, m_bed, stride);
}
void ArrangeJob::process(Ctl &ctl)
@ -268,11 +265,9 @@ void ArrangeJob::process(Ctl &ctl)
static const auto arrangestr = _u8L("Arranging");
arrangement::ArrangeParams params;
arrangement::ArrangeBed bed;
ctl.call_on_main_thread([this, &params, &bed]{
ctl.call_on_main_thread([this, &params]{
prepare();
params = get_arrange_params(m_plater);
get_bed_shape(*m_plater->config(), bed);
coord_t min_inset = get_skirt_offset(m_plater) + m_min_bed_inset;
params.min_bed_distance = std::max(params.min_bed_distance, min_inset);
}).wait();
@ -293,13 +288,13 @@ void ArrangeJob::process(Ctl &ctl)
ctl.update_status(0, arrangestr);
arrangement::arrange(m_selected, m_unselected, bed, params);
arrangement::arrange(m_selected, m_unselected, m_bed, params);
params.progressind = [this, count, &ctl](unsigned st) {
if (st > 0) ctl.update_status(int(count - st) * 100 / status_range(), arrangestr);
};
arrangement::arrange(m_unprintable, {}, bed, params);
arrangement::arrange(m_unprintable, {}, m_bed, params);
// finalize just here.
ctl.update_status(int(count) * 100 / status_range(), ctl.was_canceled() ?
@ -358,7 +353,9 @@ void ArrangeJob::finalize(bool canceled, std::exception_ptr &eptr) {
ap.apply();
}
m_plater->update((unsigned int)Plater::UpdateParams::FORCE_FULL_SCREEN_REFRESH);
m_plater->update(static_cast<unsigned int>(
Plater::UpdateParams::FORCE_FULL_SCREEN_REFRESH));
wxGetApp().obj_manipul()->set_dirty();
if (!m_unarranged.empty()) {
@ -442,4 +439,26 @@ arrangement::ArrangeParams get_arrange_params(Plater *p)
return params;
}
void assign_logical_beds(std::vector<arrangement::ArrangePolygon> &items,
const arrangement::ArrangeBed &bed,
double stride)
{
// The strides have to be removed from the fixed items. For the
// arrangeable (selected) items bed_idx is ignored and the
// translation is irrelevant.
coord_t bedx = bounding_box(bed).min.x();
for (auto &itm : items) {
auto bedidx = std::max(arrangement::UNARRANGED,
static_cast<int>(std::floor(
(get_extents(itm.transformed_poly()).min.x() - bedx) /
stride)));
itm.bed_idx = bedidx;
if (bedidx >= 0)
itm.translation.x() -= bedidx * stride;
}
}
}} // namespace Slic3r::GUI

View File

@ -21,6 +21,7 @@ class ArrangeJob : public Job
ArrangePolygons m_selected, m_unselected, m_unprintable;
std::vector<ModelInstance*> m_unarranged;
arrangement::ArrangeBed m_bed;
coord_t m_min_bed_inset = 0.;
Plater *m_plater;
@ -89,7 +90,6 @@ arrangement::ArrangePolygon get_arrange_poly(T obj, const Plater *plater)
using ArrangePolygon = arrangement::ArrangePolygon;
ArrangePolygon ap = obj.get_arrange_polygon();
ap.bed_idx = get_extents(ap.transformed_poly()).min.x() / bed_stride(plater);
ap.setter = [obj, plater](const ArrangePolygon &p) {
if (p.is_arranged()) {
Vec2d t = p.translation.cast<double>();
@ -109,6 +109,10 @@ arrangement::ArrangeParams get_arrange_params(Plater *p);
coord_t get_skirt_offset(const Plater* plater);
void assign_logical_beds(std::vector<arrangement::ArrangePolygon> &items,
const arrangement::ArrangeBed &bed,
double stride);
}} // namespace Slic3r::GUI
#endif // ARRANGEJOB_HPP

View File

@ -17,7 +17,6 @@ void FillBedJob::prepare()
{
m_selected.clear();
m_unselected.clear();
m_bedpts.clear();
m_min_bed_inset = 0.;
m_object_idx = m_plater->get_selected_object_idx();
@ -41,10 +40,10 @@ void FillBedJob::prepare()
if (m_selected.empty())
return;
m_bedpts = get_bed_shape(*m_plater->config());
Points bedpts = get_bed_shape(*m_plater->config());
auto &objects = m_plater->model().objects;
BoundingBox bedbb = get_extents(m_bedpts);
BoundingBox bedbb = get_extents(bedpts);
for (size_t idx = 0; idx < objects.size(); ++idx)
if (int(idx) != m_object_idx)
@ -72,7 +71,7 @@ void FillBedJob::prepare()
}) / sc;
double fixed_area = unsel_area + m_selected.size() * poly_area;
double bed_area = Polygon{m_bedpts}.area() / sc;
double bed_area = Polygon{bedpts}.area() / sc;
// This is the maximum number of items, the real number will always be close but less.
int needed_items = (bed_area - fixed_area) / poly_area;
@ -85,13 +84,11 @@ void FillBedJob::prepare()
for (int i = 0; i < needed_items; ++i) {
ArrangePolygon ap = template_ap;
ap.poly = m_selected.front().poly;
ap.bed_idx = arrangement::UNARRANGED;
auto m = mi->get_transformation();
ap.setter = [this, mi, m](const ArrangePolygon &p) {
ap.setter = [this, m](const ArrangePolygon &p) {
ModelObject *mo = m_plater->model().objects[m_object_idx];
ModelInstance *inst = mo->add_instance(*mi);
inst->set_transformation(m);
ModelInstance *inst = mo->add_instance(m);
inst->apply_arrange_result(p.translation.cast<double>(), p.rotation);
};
m_selected.emplace_back(ap);
@ -99,14 +96,6 @@ void FillBedJob::prepare()
m_status_range = m_selected.size();
// The strides have to be removed from the fixed items. For the
// arrangeable (selected) items bed_idx is ignored and the
// translation is irrelevant.
double stride = bed_stride(m_plater);
for (auto &p : m_unselected)
if (p.bed_idx > 0)
p.translation(X) -= p.bed_idx * stride;
coord_t min_offset = 0;
for (auto &ap : m_selected) {
min_offset = std::max(ap.inflation, min_offset);
@ -123,6 +112,14 @@ void FillBedJob::prepare()
}
m_min_bed_inset = min_offset;
}
// The strides have to be removed from the fixed items. For the
// arrangeable (selected) items bed_idx is ignored and the
// translation is irrelevant.
double stride = bed_stride(m_plater);
m_bed = arrangement::to_arrange_bed(bedpts);
assign_logical_beds(m_unselected, m_bed, stride);
}
void FillBedJob::process(Ctl &ctl)
@ -154,7 +151,7 @@ void FillBedJob::process(Ctl &ctl)
do_stop = ap.bed_idx > 0 && ap.priority == 0;
};
arrangement::arrange(m_selected, m_unselected, m_bedpts, params);
arrangement::arrange(m_selected, m_unselected, m_bed, params);
// finalize just here.
ctl.update_status(100, ctl.was_canceled() ?
@ -191,7 +188,8 @@ void FillBedJob::finalize(bool canceled, std::exception_ptr &eptr)
model_object->ensure_on_bed();
m_plater->update();
m_plater->update(static_cast<unsigned int>(
Plater::UpdateParams::FORCE_FULL_SCREEN_REFRESH));
// FIXME: somebody explain why this is needed for increase_object_instances
if (inst_cnt == 1)

View File

@ -18,7 +18,7 @@ class FillBedJob : public Job
ArrangePolygons m_unselected;
coord_t m_min_bed_inset = 0.;
Points m_bedpts;
arrangement::ArrangeBed m_bed;
int m_status_range = 0;
Plater *m_plater;

View File

@ -116,7 +116,7 @@ void PresetForPrinter::update_full_printer_name()
wxString printer_name = m_parent->get_printer_name();
wxString preset_name = m_presets_list->GetString(m_presets_list->GetSelection());
m_full_printer_name->SetLabelText(printer_name + " * " + preset_name);
m_full_printer_name->SetLabelText(printer_name + from_u8(PhysicalPrinter::separator()) + preset_name);
}
std::string PresetForPrinter::get_preset_name()
@ -654,6 +654,24 @@ wxString PhysicalPrinterDialog::get_printer_name()
void PhysicalPrinterDialog::update_full_printer_names()
{
// check input symbols for usability
const char* unusable_symbols = "<>[]:/\\|?*\"";
wxString printer_name = m_printer_name->GetValue();
for (size_t i = 0; i < std::strlen(unusable_symbols); i++) {
size_t pos = printer_name.find_first_of(unusable_symbols[i]);
if (pos != std::string::npos) {
wxString str = printer_name.SubString(pos, 1);
printer_name.Remove(pos, 1);
InfoDialog(this, format_wxstr("%1%: \"%2%\" ", _L("Unexpected character"), str),
_L("The following characters are not allowed in the name") + ": " + unusable_symbols).ShowModal();
m_printer_name->SetValue(printer_name);
m_printer_name->SetInsertionPointEnd();
return;
}
}
for (PresetForPrinter* preset : m_presets)
preset->update_full_printer_name();

View File

@ -6477,7 +6477,7 @@ void Plater::export_stl_obj(bool extended, bool selection_only)
const SLAPrintObject *object = this->p->sla_print.get_print_object_by_model_object_id(mo.id());
if (auto m = object->get_mesh_to_print(); !m || m->empty())
if (!object || !object->get_mesh_to_print() || object->get_mesh_to_print()->empty())
mesh = mesh_to_export_fff(mo, instance_id);
else {
const Transform3d mesh_trafo_inv = object->trafo().inverse();
@ -7696,7 +7696,7 @@ PlaterAfterLoadAutoArrange::PlaterAfterLoadAutoArrange()
Plater* plater = wxGetApp().plater();
m_enabled = plater->model().objects.empty() &&
plater->printer_technology() == ptFFF &&
plater->fff_print().config().printer_model.value == "XL";
is_XL_printer(plater->fff_print().config());
}
PlaterAfterLoadAutoArrange::~PlaterAfterLoadAutoArrange()

View File

@ -216,10 +216,10 @@ void Tab::create_preset_tab()
m_mode_sizer = new ModeSizer(panel, int (0.5*em_unit(this)));
const float scale_factor = em_unit(this)*0.1;// GetContentScaleFactor();
m_hsizer = new wxBoxSizer(wxHORIZONTAL);
sizer->Add(m_hsizer, 0, wxEXPAND | wxBOTTOM, 3);
m_hsizer->Add(m_presets_choice, 0, wxLEFT | wxRIGHT | wxTOP | wxALIGN_CENTER_VERTICAL, 3);
m_hsizer->AddSpacer(int(4*scale_factor));
m_top_hsizer = new wxBoxSizer(wxHORIZONTAL);
sizer->Add(m_top_hsizer, 0, wxEXPAND | wxBOTTOM | wxALIGN_CENTER_VERTICAL, 3);
m_top_hsizer->Add(m_presets_choice, 0, wxLEFT | wxRIGHT | wxTOP | wxALIGN_CENTER_VERTICAL, 3);
m_top_hsizer->AddSpacer(int(4*scale_factor));
m_h_buttons_sizer = new wxBoxSizer(wxHORIZONTAL);
m_h_buttons_sizer->Add(m_btn_save_preset, 0, wxALIGN_CENTER_VERTICAL);
@ -243,9 +243,8 @@ void Tab::create_preset_tab()
m_h_buttons_sizer->AddSpacer(int(8*scale_factor));
m_h_buttons_sizer->Add(m_btn_compare_preset, 0, wxALIGN_CENTER_VERTICAL);
m_hsizer->Add(m_h_buttons_sizer, 1, wxEXPAND);
m_hsizer->AddSpacer(int(16*scale_factor));
// m_hsizer->AddStretchSpacer(32);
m_top_hsizer->Add(m_h_buttons_sizer, 1, wxEXPAND | wxALIGN_CENTRE_VERTICAL);
m_top_hsizer->AddSpacer(int(16*scale_factor));
// StretchSpacer has a strange behavior under OSX, so
// There is used just additional sizer for m_mode_sizer with right alignment
if (m_mode_sizer) {
@ -253,8 +252,10 @@ void Tab::create_preset_tab()
// Don't set the 2nd parameter to 1, making the sizer rubbery scalable in Y axis may lead
// to wrong vertical size assigned to wxBitmapComboBoxes, see GH issue #7176.
mode_sizer->Add(m_mode_sizer, 0, wxALIGN_RIGHT);
m_hsizer->Add(mode_sizer, 1, wxALIGN_CENTER_VERTICAL | wxRIGHT, wxOSX ? 15 : 10);
m_top_hsizer->Add(mode_sizer, 1, wxALIGN_CENTER_VERTICAL | wxRIGHT, wxOSX ? 15 : 10);
}
// hide whole top sizer to correct layout later
m_top_hsizer->ShowItems(false);
//Horizontal sizer to hold the tree and the selected page.
m_hsizer = new wxBoxSizer(wxHORIZONTAL);
@ -461,20 +462,15 @@ void Tab::OnActivate()
activate_selected_page([](){});
m_hsizer->Layout();
#ifdef _MSW_DARK_MODE
// Because of DarkMode we use our own Notebook (inherited from wxSiplebook) instead of wxNotebook
// And it looks like first Layout of the page doesn't update a size of the m_presets_choice
// So we have to set correct size explicitely
if (wxSize ok_sz = wxSize(35 * m_em_unit, m_presets_choice->GetBestSize().y);
ok_sz != m_presets_choice->GetSize()) {
m_presets_choice->SetMinSize(ok_sz);
m_presets_choice->SetSize(ok_sz);
GetSizer()->GetItem(size_t(0))->GetSizer()->Layout();
if (wxGetApp().tabs_as_menu())
m_presets_choice->update();
if (m_presets_choice->IsShown())
Refresh(); // Just refresh page, if m_presets_choice is already shown
else {
// on first OnActivate call show top sizer
m_top_hsizer->ShowItems(true);
if (TabFilament* tab = dynamic_cast<TabFilament*>(this))
tab->update_extruder_combobox();
Layout();
}
#endif // _MSW_DARK_MODE
Refresh();
}
void Tab::update_label_colours()
@ -1950,6 +1946,9 @@ void TabFilament::create_extruder_combobox()
void TabFilament::update_extruder_combobox()
{
if (!m_presets_choice->IsShown())
return; // it will be updated later, on OnActive()
const size_t extruder_cnt = static_cast<const ConfigOptionFloats*>(m_preset_bundle->printers.get_edited_preset().config.option("nozzle_diameter"))->values.size();
m_extruders_cb->Show(extruder_cnt > 1);

View File

@ -172,6 +172,7 @@ protected:
ScalableButton* m_btn_delete_preset;
ScalableButton* m_btn_edit_ph_printer {nullptr};
ScalableButton* m_btn_hide_incompatible_presets;
wxBoxSizer* m_top_hsizer;
wxBoxSizer* m_hsizer;
wxBoxSizer* m_h_buttons_sizer;
wxBoxSizer* m_left_sizer;

View File

@ -1,4 +1,4 @@
#include "Mainsail.hpp"
#include "Moonraker.hpp"
#include <algorithm>
#include <sstream>
@ -63,28 +63,28 @@ std::string substitute_host(const std::string& orig_addr, std::string sub_addr)
}
#endif
}
Mainsail::Mainsail(DynamicPrintConfig *config) :
Moonraker::Moonraker(DynamicPrintConfig *config) :
m_host(config->opt_string("print_host")),
m_apikey(config->opt_string("printhost_apikey")),
m_cafile(config->opt_string("printhost_cafile")),
m_ssl_revoke_best_effort(config->opt_bool("printhost_ssl_ignore_revoke"))
{}
const char* Mainsail::get_name() const { return "Mainsail"; }
const char* Moonraker::get_name() const { return "Moonraker"; }
wxString Mainsail::get_test_ok_msg () const
wxString Moonraker::get_test_ok_msg () const
{
return _(L("Connection to Mainsail works correctly."));
return _(L("Connection to Moonraker works correctly."));
}
wxString Mainsail::get_test_failed_msg (wxString &msg) const
wxString Moonraker::get_test_failed_msg (wxString &msg) const
{
return GUI::format_wxstr("%s: %s"
, _L("Could not connect to Mainsail")
, _L("Could not connect to Moonraker")
, msg);
}
bool Mainsail::test(wxString& msg) const
bool Moonraker::test(wxString& msg) const
{
// GET /server/info
@ -142,7 +142,7 @@ bool Mainsail::test(wxString& msg) const
return res;
}
bool Mainsail::upload(PrintHostUpload upload_data, ProgressFn prorgess_fn, ErrorFn error_fn, InfoFn info_fn) const
bool Moonraker::upload(PrintHostUpload upload_data, ProgressFn prorgess_fn, ErrorFn error_fn, InfoFn info_fn) const
{
// POST /server/files/upload
@ -232,7 +232,7 @@ bool Mainsail::upload(PrintHostUpload upload_data, ProgressFn prorgess_fn, Error
return res;
}
void Mainsail::set_auth(Http &http) const
void Moonraker::set_auth(Http &http) const
{
if (!m_apikey.empty())
http.header("X-Api-Key", m_apikey);
@ -240,7 +240,7 @@ void Mainsail::set_auth(Http &http) const
http.ca_file(m_cafile);
}
std::string Mainsail::make_url(const std::string &path) const
std::string Moonraker::make_url(const std::string &path) const
{
if (m_host.find("http://") == 0 || m_host.find("https://") == 0) {
if (m_host.back() == '/') {

View File

@ -1,5 +1,5 @@
#ifndef slic3r_Mainsail_hpp_
#define slic3r_Mainsail_hpp_
#ifndef slic3r_Moonraker_hpp_
#define slic3r_Moonraker_hpp_
#include <string>
#include <wx/string.h>
@ -16,11 +16,11 @@ class DynamicPrintConfig;
class Http;
// https://moonraker.readthedocs.io/en/latest/web_api
class Mainsail : public PrintHost
class Moonraker : public PrintHost
{
public:
Mainsail(DynamicPrintConfig *config);
~Mainsail() override = default;
Moonraker(DynamicPrintConfig *config);
~Moonraker() override = default;
const char* get_name() const override;

View File

@ -19,7 +19,7 @@
#include "AstroBox.hpp"
#include "Repetier.hpp"
#include "MKS.hpp"
#include "Mainsail.hpp"
#include "Moonraker.hpp"
#include "../GUI/PrintHostDialogs.hpp"
namespace fs = boost::filesystem;
@ -55,7 +55,7 @@ PrintHost* PrintHost::get_print_host(DynamicPrintConfig *config)
case htPrusaLink: return new PrusaLink(config);
case htPrusaConnect: return new PrusaConnect(config);
case htMKS: return new MKS(config);
case htMainSail: return new Mainsail(config);
case htMoonraker: return new Moonraker(config);
default: return nullptr;
}
} else {