Merge remote-tracking branch 'origin/ys_wx317_master' into ys_cut
This commit is contained in:
commit
89a7f6bdb1
2
.gitignore
vendored
2
.gitignore
vendored
@ -18,4 +18,4 @@ local-lib
|
||||
build-linux/*
|
||||
deps/build-linux/*
|
||||
**/.DS_Store
|
||||
/.idea/
|
||||
**/.idea/
|
||||
|
@ -458,9 +458,8 @@ if (NOT EIGEN3_FOUND)
|
||||
endif ()
|
||||
include_directories(BEFORE SYSTEM ${EIGEN3_INCLUDE_DIR})
|
||||
|
||||
# Find expat or use bundled version
|
||||
# Always use the system libexpat on Linux.
|
||||
|
||||
# Find expat. We have our overriden FindEXPAT which exports libexpat target
|
||||
# no matter what.
|
||||
find_package(EXPAT REQUIRED)
|
||||
|
||||
add_library(libexpat INTERFACE)
|
||||
|
@ -30,82 +30,101 @@
|
||||
# ``CURL_VERSION_STRING``
|
||||
# The version of curl found.
|
||||
|
||||
# Look for the header file.
|
||||
find_path(CURL_INCLUDE_DIR NAMES curl/curl.h)
|
||||
mark_as_advanced(CURL_INCLUDE_DIR)
|
||||
# First, prefer config scripts
|
||||
set(_q "")
|
||||
if(CURL_FIND_QUIETLY)
|
||||
set(_q QUIET)
|
||||
endif()
|
||||
find_package(CURL ${CURL_FIND_VERSION} CONFIG ${_q})
|
||||
|
||||
if(NOT CURL_LIBRARY)
|
||||
# Look for the library (sorted from most current/relevant entry to least).
|
||||
find_library(CURL_LIBRARY_RELEASE NAMES
|
||||
curl
|
||||
# Windows MSVC prebuilts:
|
||||
curllib
|
||||
libcurl_imp
|
||||
curllib_static
|
||||
# Windows older "Win32 - MSVC" prebuilts (libcurl.lib, e.g. libcurl-7.15.5-win32-msvc.zip):
|
||||
libcurl
|
||||
# Static library on Windows
|
||||
libcurl_a
|
||||
)
|
||||
mark_as_advanced(CURL_LIBRARY_RELEASE)
|
||||
|
||||
find_library(CURL_LIBRARY_DEBUG NAMES
|
||||
# Windows MSVC CMake builds in debug configuration on vcpkg:
|
||||
libcurl-d_imp
|
||||
libcurl-d
|
||||
# Static library on Windows, compiled in debug mode
|
||||
libcurl_a_debug
|
||||
)
|
||||
mark_as_advanced(CURL_LIBRARY_DEBUG)
|
||||
|
||||
include(${CMAKE_CURRENT_LIST_DIR}/SelectLibraryConfigurations_SLIC3R.cmake)
|
||||
select_library_configurations_SLIC3R(CURL)
|
||||
if(NOT CURL_FIND_QUIETLY)
|
||||
if (NOT CURL_FOUND)
|
||||
message(STATUS "Falling back to MODULE search for CURL...")
|
||||
else()
|
||||
message(STATUS "CURL found in ${CURL_DIR}")
|
||||
endif()
|
||||
endif()
|
||||
|
||||
if(CURL_INCLUDE_DIR)
|
||||
foreach(_curl_version_header curlver.h curl.h)
|
||||
if(EXISTS "${CURL_INCLUDE_DIR}/curl/${_curl_version_header}")
|
||||
file(STRINGS "${CURL_INCLUDE_DIR}/curl/${_curl_version_header}" curl_version_str REGEX "^#define[\t ]+LIBCURL_VERSION[\t ]+\".*\"")
|
||||
if (NOT CURL_FOUND)
|
||||
|
||||
string(REGEX REPLACE "^#define[\t ]+LIBCURL_VERSION[\t ]+\"([^\"]*)\".*" "\\1" CURL_VERSION_STRING "${curl_version_str}")
|
||||
unset(curl_version_str)
|
||||
break()
|
||||
endif()
|
||||
endforeach()
|
||||
endif()
|
||||
# Look for the header file.
|
||||
find_path(CURL_INCLUDE_DIR NAMES curl/curl.h)
|
||||
mark_as_advanced(CURL_INCLUDE_DIR)
|
||||
|
||||
include(${CMAKE_CURRENT_LIST_DIR}/FindPackageHandleStandardArgs_SLIC3R.cmake)
|
||||
FIND_PACKAGE_HANDLE_STANDARD_ARGS_SLIC3R(CURL
|
||||
REQUIRED_VARS CURL_LIBRARY CURL_INCLUDE_DIR
|
||||
VERSION_VAR CURL_VERSION_STRING)
|
||||
if(NOT CURL_LIBRARY)
|
||||
# Look for the library (sorted from most current/relevant entry to least).
|
||||
find_library(CURL_LIBRARY_RELEASE NAMES
|
||||
curl
|
||||
# Windows MSVC prebuilts:
|
||||
curllib
|
||||
libcurl_imp
|
||||
curllib_static
|
||||
# Windows older "Win32 - MSVC" prebuilts (libcurl.lib, e.g. libcurl-7.15.5-win32-msvc.zip):
|
||||
libcurl
|
||||
# Static library on Windows
|
||||
libcurl_a
|
||||
)
|
||||
mark_as_advanced(CURL_LIBRARY_RELEASE)
|
||||
|
||||
if(CURL_FOUND)
|
||||
set(CURL_LIBRARIES ${CURL_LIBRARY})
|
||||
set(CURL_INCLUDE_DIRS ${CURL_INCLUDE_DIR})
|
||||
find_library(CURL_LIBRARY_DEBUG NAMES
|
||||
# Windows MSVC CMake builds in debug configuration on vcpkg:
|
||||
libcurl-d_imp
|
||||
libcurl-d
|
||||
# Static library on Windows, compiled in debug mode
|
||||
libcurl_a_debug
|
||||
)
|
||||
mark_as_advanced(CURL_LIBRARY_DEBUG)
|
||||
|
||||
if(NOT TARGET CURL::libcurl)
|
||||
add_library(CURL::libcurl UNKNOWN IMPORTED)
|
||||
set_target_properties(CURL::libcurl PROPERTIES
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${CURL_INCLUDE_DIRS}")
|
||||
include(${CMAKE_CURRENT_LIST_DIR}/SelectLibraryConfigurations_SLIC3R.cmake)
|
||||
select_library_configurations_SLIC3R(CURL)
|
||||
endif()
|
||||
|
||||
if(EXISTS "${CURL_LIBRARY}")
|
||||
if(CURL_INCLUDE_DIR)
|
||||
foreach(_curl_version_header curlver.h curl.h)
|
||||
if(EXISTS "${CURL_INCLUDE_DIR}/curl/${_curl_version_header}")
|
||||
file(STRINGS "${CURL_INCLUDE_DIR}/curl/${_curl_version_header}" curl_version_str REGEX "^#define[\t ]+LIBCURL_VERSION[\t ]+\".*\"")
|
||||
|
||||
string(REGEX REPLACE "^#define[\t ]+LIBCURL_VERSION[\t ]+\"([^\"]*)\".*" "\\1" CURL_VERSION_STRING "${curl_version_str}")
|
||||
unset(curl_version_str)
|
||||
break()
|
||||
endif()
|
||||
endforeach()
|
||||
endif()
|
||||
|
||||
include(${CMAKE_CURRENT_LIST_DIR}/FindPackageHandleStandardArgs_SLIC3R.cmake)
|
||||
FIND_PACKAGE_HANDLE_STANDARD_ARGS_SLIC3R(CURL
|
||||
REQUIRED_VARS CURL_LIBRARY CURL_INCLUDE_DIR
|
||||
VERSION_VAR CURL_VERSION_STRING)
|
||||
|
||||
if(CURL_FOUND)
|
||||
set(CURL_LIBRARIES ${CURL_LIBRARY})
|
||||
set(CURL_INCLUDE_DIRS ${CURL_INCLUDE_DIR})
|
||||
|
||||
if(NOT TARGET CURL::libcurl)
|
||||
add_library(CURL::libcurl UNKNOWN IMPORTED)
|
||||
set_target_properties(CURL::libcurl PROPERTIES
|
||||
IMPORTED_LINK_INTERFACE_LANGUAGES "C"
|
||||
IMPORTED_LOCATION "${CURL_LIBRARY}")
|
||||
endif()
|
||||
if(CURL_LIBRARY_RELEASE)
|
||||
set_property(TARGET CURL::libcurl APPEND PROPERTY
|
||||
IMPORTED_CONFIGURATIONS RELEASE)
|
||||
set_target_properties(CURL::libcurl PROPERTIES
|
||||
IMPORTED_LINK_INTERFACE_LANGUAGES "C"
|
||||
IMPORTED_LOCATION_RELEASE "${CURL_LIBRARY_RELEASE}")
|
||||
endif()
|
||||
if(CURL_LIBRARY_DEBUG)
|
||||
set_property(TARGET CURL::libcurl APPEND PROPERTY
|
||||
IMPORTED_CONFIGURATIONS DEBUG)
|
||||
set_target_properties(CURL::libcurl PROPERTIES
|
||||
IMPORTED_LINK_INTERFACE_LANGUAGES "C"
|
||||
IMPORTED_LOCATION_DEBUG "${CURL_LIBRARY_DEBUG}")
|
||||
INTERFACE_INCLUDE_DIRECTORIES "${CURL_INCLUDE_DIRS}")
|
||||
|
||||
if(EXISTS "${CURL_LIBRARY}")
|
||||
set_target_properties(CURL::libcurl PROPERTIES
|
||||
IMPORTED_LINK_INTERFACE_LANGUAGES "C"
|
||||
IMPORTED_LOCATION "${CURL_LIBRARY}")
|
||||
endif()
|
||||
if(CURL_LIBRARY_RELEASE)
|
||||
set_property(TARGET CURL::libcurl APPEND PROPERTY
|
||||
IMPORTED_CONFIGURATIONS RELEASE)
|
||||
set_target_properties(CURL::libcurl PROPERTIES
|
||||
IMPORTED_LINK_INTERFACE_LANGUAGES "C"
|
||||
IMPORTED_LOCATION_RELEASE "${CURL_LIBRARY_RELEASE}")
|
||||
endif()
|
||||
if(CURL_LIBRARY_DEBUG)
|
||||
set_property(TARGET CURL::libcurl APPEND PROPERTY
|
||||
IMPORTED_CONFIGURATIONS DEBUG)
|
||||
set_target_properties(CURL::libcurl PROPERTIES
|
||||
IMPORTED_LINK_INTERFACE_LANGUAGES "C"
|
||||
IMPORTED_LOCATION_DEBUG "${CURL_LIBRARY_DEBUG}")
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
endif()
|
||||
|
||||
endif (NOT CURL_FOUND)
|
||||
|
4
deps/Boost/Boost.cmake
vendored
4
deps/Boost/Boost.cmake
vendored
@ -75,7 +75,9 @@ file(TO_NATIVE_PATH ${DESTDIR}/usr/local/ _prefix)
|
||||
set(_boost_flags "")
|
||||
if (UNIX)
|
||||
set(_boost_flags "cflags=-fPIC;cxxflags=-fPIC")
|
||||
elseif(APPLE)
|
||||
endif ()
|
||||
|
||||
if(APPLE)
|
||||
set(_boost_flags
|
||||
"cflags=-fPIC -mmacosx-version-min=${DEP_OSX_TARGET};"
|
||||
"cxxflags=-fPIC -mmacosx-version-min=${DEP_OSX_TARGET};"
|
||||
|
1
deps/CMakeLists.txt
vendored
1
deps/CMakeLists.txt
vendored
@ -188,6 +188,7 @@ endif ()
|
||||
|
||||
include(JPEG/JPEG.cmake)
|
||||
include(TIFF/TIFF.cmake)
|
||||
include(NanoSVG/NanoSVG.cmake)
|
||||
include(wxWidgets/wxWidgets.cmake)
|
||||
|
||||
set(_dep_list
|
||||
|
4
deps/GLEW/GLEW.cmake
vendored
4
deps/GLEW/GLEW.cmake
vendored
@ -4,8 +4,8 @@ find_package(OpenGL QUIET REQUIRED)
|
||||
|
||||
prusaslicer_add_cmake_project(
|
||||
GLEW
|
||||
URL https://sourceforge.net/projects/glew/files/glew/2.1.0/glew-2.1.0.zip
|
||||
URL_HASH SHA256=2700383d4de2455f06114fbaf872684f15529d4bdc5cdea69b5fb0e9aa7763f1
|
||||
URL https://sourceforge.net/projects/glew/files/glew/2.2.0/glew-2.2.0.zip
|
||||
URL_HASH SHA256=a9046a913774395a095edcc0b0ac2d81c3aacca61787b39839b941e9be14e0d4
|
||||
SOURCE_SUBDIR build/cmake
|
||||
CMAKE_ARGS
|
||||
-DBUILD_UTILS=OFF
|
||||
|
4
deps/NanoSVG/NanoSVG.cmake
vendored
Normal file
4
deps/NanoSVG/NanoSVG.cmake
vendored
Normal file
@ -0,0 +1,4 @@
|
||||
prusaslicer_add_cmake_project(NanoSVG
|
||||
URL https://github.com/memononen/nanosvg/archive/4c8f0139b62c6e7faa3b67ce1fbe6e63590ed148.zip
|
||||
URL_HASH SHA256=584e084af1a75bf633f79753ce2f6f6ec8686002ca27f35f1037c25675fecfb6
|
||||
)
|
15
deps/wxWidgets/wxWidgets.cmake
vendored
15
deps/wxWidgets/wxWidgets.cmake
vendored
@ -1,5 +1,3 @@
|
||||
set(_wx_git_tag v3.1.4-patched)
|
||||
|
||||
set(_wx_toolkit "")
|
||||
if(CMAKE_SYSTEM_NAME STREQUAL "Linux")
|
||||
set(_gtk_ver 2)
|
||||
@ -15,11 +13,9 @@ if (UNIX AND NOT APPLE) # wxWidgets will not use char as the underlying type for
|
||||
endif()
|
||||
|
||||
prusaslicer_add_cmake_project(wxWidgets
|
||||
# GIT_REPOSITORY "https://github.com/prusa3d/wxWidgets"
|
||||
# GIT_TAG tm_cross_compile #${_wx_git_tag}
|
||||
URL https://github.com/prusa3d/wxWidgets/archive/489f6118256853cf5b299d595868641938566cdb.zip
|
||||
URL_HASH SHA256=5b22d465377cedd8044bba69bea958b248953fd3628c1de4913a84d4e6f6175b
|
||||
DEPENDS ${PNG_PKG} ${ZLIB_PKG} ${EXPAT_PKG} dep_TIFF dep_JPEG
|
||||
URL https://github.com/prusa3d/wxWidgets/archive/e616df45b3a8aedc31beb5540df793dd1f0f3914.zip
|
||||
URL_HASH SHA256=30bc6cad64dce5cdc755e3a4119cfeb24c12d43279e1e062d8ac350d3880f315
|
||||
DEPENDS ${PNG_PKG} ${ZLIB_PKG} ${EXPAT_PKG} dep_TIFF dep_JPEG dep_NanoSVG
|
||||
CMAKE_ARGS
|
||||
-DwxBUILD_PRECOMP=ON
|
||||
${_wx_toolkit}
|
||||
@ -32,13 +28,16 @@ prusaslicer_add_cmake_project(wxWidgets
|
||||
-DwxUSE_OPENGL=ON
|
||||
-DwxUSE_LIBPNG=sys
|
||||
-DwxUSE_ZLIB=sys
|
||||
-DwxUSE_REGEX=builtin
|
||||
-DwxUSE_NANOSVG=sys
|
||||
-DwxUSE_NANOSVG_EXTERNAL=ON
|
||||
-DwxUSE_REGEX=OFF
|
||||
-DwxUSE_LIBXPM=builtin
|
||||
-DwxUSE_LIBJPEG=sys
|
||||
-DwxUSE_LIBTIFF=sys
|
||||
-DwxUSE_EXPAT=sys
|
||||
-DwxUSE_LIBSDL=OFF
|
||||
-DwxUSE_XTEST=OFF
|
||||
-DwxUSE_GLCANVAS_EGL=OFF
|
||||
)
|
||||
|
||||
if (MSVC)
|
||||
|
@ -1,3 +1,5 @@
|
||||
min_slic3r_version = 2.5.0-alpha0
|
||||
0.1.5 Added Ender-3 S1 Pro
|
||||
min_slic3r_version = 2.4.1
|
||||
0.1.4 Added Ender-3 Pro. Added M25 support for some printers.
|
||||
min_slic3r_version = 2.4.0-rc
|
||||
|
@ -5,7 +5,7 @@
|
||||
name = Creality
|
||||
# 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.1.4
|
||||
config_version = 0.1.5
|
||||
# Where to get the updates from?
|
||||
config_update_url = https://files.prusa3d.com/wp-content/uploads/repository/PrusaSlicer-settings-master/live/Creality/
|
||||
# changelog_url = https://files.prusa3d.com/?latest=slicer-profiles&lng=%1%
|
||||
@ -21,7 +21,7 @@ technology = FFF
|
||||
family = ENDER
|
||||
bed_model = ender3_bed.stl
|
||||
bed_texture = ender3.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:ENDER3BLTOUCH]
|
||||
name = Creality Ender-3 BLTouch
|
||||
@ -30,7 +30,7 @@ technology = FFF
|
||||
family = ENDER
|
||||
bed_model = ender3_bed.stl
|
||||
bed_texture = ender3.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:ENDER3PRO]
|
||||
name = Creality Ender-3 Pro
|
||||
@ -39,7 +39,7 @@ technology = FFF
|
||||
family = ENDER
|
||||
bed_model = ender3_bed.stl
|
||||
bed_texture = ender3.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:ENDER3V2]
|
||||
name = Creality Ender-3 V2
|
||||
@ -48,7 +48,7 @@ technology = FFF
|
||||
family = ENDER
|
||||
bed_model = ender3v2_bed.stl
|
||||
bed_texture = ender3v2.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:ENDER3S1]
|
||||
name = Creality Ender-3 S1
|
||||
@ -57,7 +57,16 @@ technology = FFF
|
||||
family = ENDER
|
||||
bed_model = ender3v2_bed.stl
|
||||
bed_texture = ender3v2.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:ENDER3S1PRO]
|
||||
name = Creality Ender-3 S1 Pro
|
||||
variants = 0.4
|
||||
technology = FFF
|
||||
family = ENDER
|
||||
bed_model = ender3v2_bed.stl
|
||||
bed_texture = ender3v2.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:ENDER3MAX]
|
||||
name = Creality Ender-3 Max
|
||||
@ -66,7 +75,7 @@ technology = FFF
|
||||
family = ENDER
|
||||
bed_model = cr10v2_bed.stl
|
||||
bed_texture = cr10spro.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:ENDER4]
|
||||
name = Creality Ender-4
|
||||
@ -75,7 +84,7 @@ technology = FFF
|
||||
family = ENDER
|
||||
bed_model = ender3v2_bed.stl
|
||||
bed_texture = ender3v2.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:ENDER5]
|
||||
name = Creality Ender-5
|
||||
@ -84,7 +93,7 @@ technology = FFF
|
||||
family = ENDER
|
||||
bed_model = ender3_bed.stl
|
||||
bed_texture = ender3.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:ENDER5PLUS]
|
||||
name = Creality Ender-5 Plus
|
||||
@ -93,7 +102,7 @@ technology = FFF
|
||||
family = ENDER
|
||||
bed_model = ender5plus_bed.stl
|
||||
bed_texture = ender5plus.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:ENDER6]
|
||||
name = Creality Ender-6
|
||||
@ -102,7 +111,7 @@ technology = FFF
|
||||
family = ENDER
|
||||
bed_model = ender6_bed.stl
|
||||
bed_texture = ender6.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:ENDER7]
|
||||
name = Creality Ender-7
|
||||
@ -111,7 +120,7 @@ technology = FFF
|
||||
family = ENDER
|
||||
bed_model = ender7_bed.stl
|
||||
bed_texture = ender7.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:ENDER2]
|
||||
name = Creality Ender-2
|
||||
@ -120,7 +129,7 @@ technology = FFF
|
||||
family = ENDER
|
||||
bed_model = ender2_bed.stl
|
||||
bed_texture = ender2.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:ENDER2PRO]
|
||||
name = Creality Ender-2 Pro
|
||||
@ -129,7 +138,7 @@ technology = FFF
|
||||
family = ENDER
|
||||
bed_model = ender2pro_bed.stl
|
||||
bed_texture = ender2pro.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR5PRO]
|
||||
name = Creality CR-5 Pro
|
||||
@ -138,7 +147,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr5pro_bed.stl
|
||||
bed_texture = cr5pro.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR5PROH]
|
||||
name = Creality CR-5 Pro H
|
||||
@ -147,7 +156,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr5pro_bed.stl
|
||||
bed_texture = cr5pro.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR6SE]
|
||||
name = Creality CR-6 SE
|
||||
@ -156,7 +165,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr6se_bed.stl
|
||||
bed_texture = cr6se.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR6MAX]
|
||||
name = Creality CR-6 Max
|
||||
@ -165,7 +174,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr10s4_bed.stl
|
||||
bed_texture = cr10s4.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR10SMART]
|
||||
name = Creality CR-10 SMART
|
||||
@ -174,7 +183,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr10v2_bed.stl
|
||||
bed_texture = cr10spro.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR10MINI]
|
||||
name = Creality CR-10 Mini
|
||||
@ -183,7 +192,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr10mini_bed.stl
|
||||
bed_texture = cr10mini.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR10MAX]
|
||||
name = Creality CR-10 Max
|
||||
@ -192,7 +201,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr10max_bed.stl
|
||||
bed_texture = cr10max.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR10]
|
||||
name = Creality CR-10
|
||||
@ -201,7 +210,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr10_bed.stl
|
||||
bed_texture = cr10.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR10V2]
|
||||
name = Creality CR-10 V2
|
||||
@ -210,7 +219,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr10v2_bed.stl
|
||||
bed_texture = cr10.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR10V3]
|
||||
name = Creality CR-10 V3
|
||||
@ -219,7 +228,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr10v2_bed.stl
|
||||
bed_texture = cr10.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR10S]
|
||||
name = Creality CR-10 S
|
||||
@ -228,7 +237,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr10_bed.stl
|
||||
bed_texture = cr10.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR10SPRO]
|
||||
name = Creality CR-10 S Pro
|
||||
@ -237,7 +246,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr10v2_bed.stl
|
||||
bed_texture = cr10spro.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR10SPROV2]
|
||||
name = Creality CR-10 S Pro V2
|
||||
@ -246,7 +255,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr10v2_bed.stl
|
||||
bed_texture = cr10.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR10S4]
|
||||
name = Creality CR-10 S4
|
||||
@ -255,7 +264,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr10s4_bed.stl
|
||||
bed_texture = cr10s4.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR10S5]
|
||||
name = Creality CR-10 S5
|
||||
@ -264,7 +273,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr10s5_bed.stl
|
||||
bed_texture = cr10s5.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR20]
|
||||
name = Creality CR-20
|
||||
@ -273,7 +282,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = ender3_bed.stl
|
||||
bed_texture = cr20.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR20PRO]
|
||||
name = Creality CR-20 Pro
|
||||
@ -282,7 +291,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = ender3_bed.stl
|
||||
bed_texture = cr20.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR200B]
|
||||
name = Creality CR-200B
|
||||
@ -291,7 +300,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr200b_bed.stl
|
||||
bed_texture = cr200b.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:CR8]
|
||||
name = Creality CR-8
|
||||
@ -300,7 +309,7 @@ technology = FFF
|
||||
family = CR
|
||||
bed_model = cr8_bed.stl
|
||||
bed_texture = cr8.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
#[printer_model:CRX]
|
||||
#name = Creality CR-X
|
||||
@ -309,7 +318,7 @@ default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @
|
||||
#family = CR-X
|
||||
#bed_model = cr10v2_bed.stl
|
||||
#bed_texture = cr10spro.svg
|
||||
#default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
#default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
#[printer_model:CRXPRO]
|
||||
#name = Creality CR-X Pro
|
||||
@ -318,7 +327,7 @@ default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @
|
||||
#family = CR-X
|
||||
#bed_model = cr10v2_bed.stl
|
||||
#bed_texture = cr10spro.svg
|
||||
#default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
#default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
[printer_model:SERMOOND1]
|
||||
name = Creality Sermoon-D1
|
||||
@ -327,7 +336,7 @@ technology = FFF
|
||||
family = SERMOON
|
||||
bed_model = sermoond1_bed.stl
|
||||
bed_texture = sermoond1.svg
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY
|
||||
default_materials = Generic PLA @CREALITY; Generic PETG @CREALITY; Generic ABS @CREALITY; Creality PLA @CREALITY; Prusament PLA @CREALITY; Prusament PETG @CREALITY; AzureFilm PLA @CREALITY; Devil Design PLA @CREALITY; Devil Design PLA Matt @CREALITY; Devil Design PLA Galaxy @CREALITY; Extrudr PLA NX2 @CREALITY; Real Filament PLA @CREALITY; Velleman PLA @CREALITY; 3DJAKE ecoPLA @CREALITY; 3DJAKE ecoPLA Matt @CREALITY; 3DJAKE ecoPLA Tough @CREALITY; 123-3D Jupiter PLA @CREALITY; Verbatim PLA @CREALITY
|
||||
|
||||
# All presets starting with asterisk, for example *common*, are intermediate and they will
|
||||
# not make it into the user interface.
|
||||
@ -842,6 +851,17 @@ filament_cost = 27.44
|
||||
filament_density = 1.29
|
||||
filament_colour = #C7F935
|
||||
|
||||
[filament:Verbatim PLA @CREALITY]
|
||||
inherits = *PLA*
|
||||
filament_vendor = Verbatim
|
||||
temperature = 205
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 210
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 22.99
|
||||
filament_density = 1.24
|
||||
filament_colour = #001ca8
|
||||
|
||||
# Common printer preset
|
||||
[printer:*common*]
|
||||
printer_technology = FFF
|
||||
@ -970,10 +990,7 @@ renamed_from = "Creality ENDER-3 BLTouch"
|
||||
printer_model = ENDER3BLTOUCH
|
||||
|
||||
[printer:Creality Ender-3 Pro]
|
||||
inherits = *common*; *pauseprint*
|
||||
renamed_from = "Creality Ender-3 Pro"
|
||||
bed_shape = 5x0,215x0,215x220,5x220
|
||||
max_print_height = 250
|
||||
inherits = Creality Ender-3; *pauseprint*
|
||||
printer_model = ENDER3PRO
|
||||
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_CREALITY\nPRINTER_MODEL_ENDER3PRO\nPRINTER_HAS_BOWDEN
|
||||
|
||||
@ -992,6 +1009,13 @@ max_print_height = 270
|
||||
printer_model = ENDER3S1
|
||||
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_CREALITY\nPRINTER_MODEL_ENDER3S1
|
||||
|
||||
[printer:Creality Ender-3 S1 Pro]
|
||||
inherits = *common*; *pauseprint*; *spriteextruder*
|
||||
bed_shape = 5x0,215x0,215x220,5x220
|
||||
max_print_height = 270
|
||||
printer_model = ENDER3S1PRO
|
||||
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_CREALITY\nPRINTER_MODEL_ENDER3S1PRO
|
||||
|
||||
[printer:Creality Ender-3 Max]
|
||||
inherits = *common*; *pauseprint*
|
||||
retract_length = 6
|
||||
|
BIN
resources/profiles/Creality/ENDER3S1PRO_thumbnail.png
Normal file
BIN
resources/profiles/Creality/ENDER3S1PRO_thumbnail.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 43 KiB |
@ -1,4 +1,6 @@
|
||||
min_slic3r_version = 2.3.1-beta
|
||||
min_slic3r_version = 2.5.0-alpha0
|
||||
0.0.4 Improve Proton X profiles, Add Proton XE-750 printer
|
||||
min_slic3r_version = 2.4.1
|
||||
0.0.3 Set default filament profile.
|
||||
0.0.2 Improved start gcode, changed filename format
|
||||
0.0.1 Initial version
|
||||
|
@ -3,7 +3,7 @@
|
||||
[vendor]
|
||||
# Vendor name will be shown by the Config Wizard.
|
||||
name = INAT
|
||||
config_version = 0.0.3
|
||||
config_version = 0.0.4
|
||||
config_update_url = https://files.prusa3d.com/wp-content/uploads/repository/PrusaSlicer-settings-master/live/INAT/
|
||||
|
||||
###
|
||||
@ -24,9 +24,16 @@ technology = FFF
|
||||
family = Proton
|
||||
default_materials = PLA @PROTON_X
|
||||
|
||||
[printer_model:PROTON_XE750]
|
||||
name = INAT Proton XE-750
|
||||
variants = 0.4
|
||||
technology = FFF
|
||||
family = Proton
|
||||
default_materials = PLA @PROTON_XE750
|
||||
|
||||
|
||||
###
|
||||
### QUALITY DEFINITIONS
|
||||
### COMMON QUALITY DEFINITIONS
|
||||
###
|
||||
|
||||
[print:*common*]
|
||||
@ -35,14 +42,15 @@ layer_height = 0.2
|
||||
first_layer_height = 0.2
|
||||
perimeters = 3
|
||||
spiral_vase = 0
|
||||
top_solid_layers = 4
|
||||
top_solid_layers = 5
|
||||
bottom_solid_layers = 3
|
||||
top_solid_min_thickness = 0.8
|
||||
top_solid_min_thickness = 1
|
||||
bottom_solid_min_thickness = 0.6
|
||||
extra_perimeters = 1
|
||||
ensure_vertical_shell_thickness = 1
|
||||
avoid_crossing_perimeters = 0
|
||||
thin_walls = 0
|
||||
thick_bridges = 0
|
||||
overhangs = 1
|
||||
seam_position = aligned
|
||||
external_perimeters_first = 0
|
||||
@ -76,7 +84,9 @@ support_material_auto = 1
|
||||
support_material_threshold = 0
|
||||
support_material_enforce_layers = 0
|
||||
raft_layers = 0
|
||||
support_material_contact_distance = 0.2
|
||||
support_material_style = grid
|
||||
support_material_contact_distance = 0.25
|
||||
support_material_bottom_contact_distance = 0.3
|
||||
support_material_pattern = rectilinear
|
||||
support_material_with_sheath = 0
|
||||
support_material_spacing = 5
|
||||
@ -92,8 +102,8 @@ perimeter_speed = 60
|
||||
small_perimeter_speed = 75%
|
||||
external_perimeter_speed = 50%
|
||||
infill_speed = 80
|
||||
solid_infill_speed = 100%
|
||||
top_solid_infill_speed = 30
|
||||
solid_infill_speed = 80%
|
||||
top_solid_infill_speed = 20
|
||||
support_material_speed = 80
|
||||
support_material_interface_speed = 100%
|
||||
bridge_speed = 60
|
||||
@ -126,7 +136,7 @@ infill_overlap = 25%
|
||||
bridge_flow_ratio = 1
|
||||
slice_closing_radius = 0.049
|
||||
resolution = 0
|
||||
xy_size_compensation = 0
|
||||
xy_size_compensation = -0.05
|
||||
elefant_foot_compensation = 0.3
|
||||
clip_multipart_objects = 0
|
||||
#output
|
||||
@ -138,47 +148,50 @@ gcode_label_objects = 0
|
||||
output_filename_format = {input_filename_base}_{filament_type[0]}.gcode
|
||||
|
||||
|
||||
[print:0.2mm Standard @PROTON_X]
|
||||
[print:*common 0.2mm Standard @INAT*]
|
||||
inherits = *common*
|
||||
|
||||
[print:0.2mm Strong @PROTON_X]
|
||||
[print:*common 0.2mm Strong @INAT*]
|
||||
inherits = *common*
|
||||
fill_density = 50%
|
||||
perimeters = 6
|
||||
|
||||
[print:0.2mm Advanced Material @PROTON_X]
|
||||
[print:*common 0.2mm Advanced Material @INAT*]
|
||||
inherits = *common*
|
||||
bottom_solid_layers = 5
|
||||
top_solid_layers = 6
|
||||
skirts = 0
|
||||
brim_width = 30
|
||||
brim_width = 20
|
||||
infill_speed = 60
|
||||
support_material_speed = 60
|
||||
travel_speed = 100
|
||||
first_layer_speed = 20
|
||||
elefant_foot_compensation = 0
|
||||
|
||||
[print:0.12mm Fine @PROTON_X]
|
||||
[print:*common 0.12mm Fine @INAT*]
|
||||
inherits = *common*
|
||||
layer_height = 0.12
|
||||
bottom_solid_layers = 7
|
||||
top_solid_layers = 7
|
||||
infill_every_layers = 2
|
||||
perimeter_speed = 50
|
||||
infill_speed = 50
|
||||
|
||||
[print:0.32mm Draft @PROTON_X]
|
||||
[print:*common 0.32mm Draft @INAT*]
|
||||
inherits = *common*
|
||||
layer_height = 0.32
|
||||
perimeter_speed = 80
|
||||
external_perimeter_speed = 75%
|
||||
infill_speed = 100
|
||||
top_solid_infill_speed = 60
|
||||
fill_density = 15%
|
||||
support_material_style = snug
|
||||
|
||||
###
|
||||
### PRINTER DEFINITIONS
|
||||
### COMMON PRINTER DEFINITIONS
|
||||
###
|
||||
|
||||
[printer:*common*]
|
||||
[printer:*proton_x_common*]
|
||||
printer_vendor = INAT s.r.o.
|
||||
default_filament_profile = "PLA @PROTON_X"
|
||||
#general
|
||||
@ -206,14 +219,14 @@ machine_max_feedrate_z = 10,10
|
||||
machine_max_feedrate_e = 100,100
|
||||
machine_max_acceleration_x = 500,500
|
||||
machine_max_acceleration_y = 500,500
|
||||
machine_max_acceleration_z = 100,100
|
||||
machine_max_acceleration_e = 2000,2000
|
||||
machine_max_acceleration_z = 200,200
|
||||
machine_max_acceleration_e = 8000,8000
|
||||
machine_max_acceleration_extruding = 1000,1000
|
||||
machine_max_acceleration_retracting = 1500,1500
|
||||
machine_max_acceleration_retracting = 8000,8000
|
||||
machine_max_jerk_x = 8,8
|
||||
machine_max_jerk_y = 8,8
|
||||
machine_max_jerk_z = 1,1
|
||||
machine_max_jerk_e = 2.5,2.5
|
||||
machine_max_jerk_z = 3,3
|
||||
machine_max_jerk_e = 10,10
|
||||
machine_min_extruding_rate = 5
|
||||
#extruder 1
|
||||
nozzle_diameter = 0.4
|
||||
@ -233,24 +246,65 @@ wipe = 1
|
||||
retract_before_wipe = 100%
|
||||
|
||||
|
||||
[printer:Proton X Rail]
|
||||
inherits = *common*
|
||||
printer_model = PROTON_X_RAIL
|
||||
printer_variant = 0.4
|
||||
default_print_profile = 0.2mm Standard @PROTON_X
|
||||
gcode_flavor = marlin
|
||||
machine_max_acceleration_y = 800,800
|
||||
|
||||
[printer:Proton X Rod]
|
||||
inherits = *common*
|
||||
printer_model = PROTON_X_ROD
|
||||
printer_variant = 0.4
|
||||
default_print_profile = 0.2mm Standard @PROTON_X
|
||||
[printer:*proton_xe750_common*]
|
||||
printer_vendor = INAT s.r.o.
|
||||
default_filament_profile = "PLA @PROTON_XE750"
|
||||
#general
|
||||
printer_technology = FFF
|
||||
bed_shape = 0x0,600x0,600x500,0x500
|
||||
max_print_height = 750
|
||||
z_offset = 0
|
||||
extruders_count = 2
|
||||
gcode_flavor = marlin
|
||||
silent_mode = 0
|
||||
remaining_times = 1
|
||||
use_relative_e_distances = 0
|
||||
use_firmware_retraction = 0
|
||||
use_volumetric_e = 0
|
||||
variable_layer_height = 1
|
||||
#gcodes
|
||||
start_gcode = G28 ;Home\nG0 Z10 F1000\nG29\nG0 X0 Y0 Z30 F6000\nM84 E\nM0\nG1 Z15.0 F6000 ;Move the platform down 15mm\n
|
||||
end_gcode = M400\nM104 S0\nM140 S0\nM107\n;Retract the filament\nG92 E1\nG1 E-1 F300\nG28 X R5\nG0 Y300 F2000\nM84\nG4 S180\nM81 S30\n
|
||||
color_change_gcode = M600
|
||||
#limits
|
||||
machine_limits_usage = emit_to_gcode
|
||||
machine_max_feedrate_x = 200,200
|
||||
machine_max_feedrate_y = 200,200
|
||||
machine_max_feedrate_z = 10,10
|
||||
machine_max_feedrate_e = 100,100
|
||||
machine_max_acceleration_x = 1500,1500
|
||||
machine_max_acceleration_y = 1500,1500
|
||||
machine_max_acceleration_z = 500,500
|
||||
machine_max_acceleration_e = 20000,20000
|
||||
machine_max_acceleration_extruding = 2000,2000
|
||||
machine_max_acceleration_retracting = 8000,8000
|
||||
machine_max_jerk_x = 12,12
|
||||
machine_max_jerk_y = 12,12
|
||||
machine_max_jerk_z = 3,3
|
||||
machine_max_jerk_e = 20,20
|
||||
machine_min_extruding_rate = 5
|
||||
#extruder 1
|
||||
nozzle_diameter = 0.4,0.4
|
||||
min_layer_height = 0.05,0.05
|
||||
max_layer_height = 0.33,0.33
|
||||
extruder_offset = 0x0,0x0
|
||||
retract_length = 1.5,1.5
|
||||
retract_lift = 0.6,0.6
|
||||
retract_lift_above = 0,0
|
||||
retract_lift_below = 0,0
|
||||
retract_speed = 45,45
|
||||
deretract_speed = 0,0
|
||||
retract_restart_extra = 0,0
|
||||
retract_before_travel = 2,2
|
||||
retract_layer_change = 0,0
|
||||
wipe = 1,1
|
||||
retract_before_wipe = 100%,100%
|
||||
retract_length_toolchange = 37,37
|
||||
extruder_colour = #33CC33;#3399FF
|
||||
|
||||
|
||||
###
|
||||
### MATERIAL DEFINITIONS
|
||||
### COMMON MATERIAL DEFINITIONS
|
||||
###
|
||||
|
||||
[filament:*common*]
|
||||
@ -272,7 +326,7 @@ min_print_speed = 10
|
||||
filament_soluble = 0
|
||||
|
||||
|
||||
[filament:PLA @PROTON_X]
|
||||
[filament:*common PLA @INAT*]
|
||||
inherits = *common*
|
||||
temperature = 210
|
||||
bed_temperature = 60
|
||||
@ -281,11 +335,12 @@ first_layer_bed_temperature = 60
|
||||
filament_type = PLA
|
||||
filament_cost = 20
|
||||
filament_density = 1.25
|
||||
fan_always_on = 1
|
||||
min_fan_speed = 50
|
||||
max_fan_speed = 100
|
||||
|
||||
|
||||
[filament:PETG @PROTON_X]
|
||||
[filament:*common PETG @INAT*]
|
||||
inherits = *common*
|
||||
temperature = 240
|
||||
bed_temperature = 80
|
||||
@ -294,10 +349,11 @@ first_layer_bed_temperature = 80
|
||||
filament_type = PETG
|
||||
filament_cost = 25
|
||||
filament_density = 1.27
|
||||
min_fan_speed = 0
|
||||
fan_always_on = 1
|
||||
min_fan_speed = 25
|
||||
max_fan_speed = 50
|
||||
|
||||
[filament:ABS @PROTON_X]
|
||||
[filament:*common ABS @INAT*]
|
||||
inherits = *common*
|
||||
temperature = 235
|
||||
bed_temperature = 100
|
||||
@ -309,7 +365,7 @@ filament_density = 1.01
|
||||
cooling = 0
|
||||
bridge_fan_speed = 0
|
||||
|
||||
[filament:ASA @PROTON_X]
|
||||
[filament:*common ASA @INAT*]
|
||||
inherits = *common*
|
||||
temperature = 240
|
||||
bed_temperature = 110
|
||||
@ -320,7 +376,7 @@ filament_cost = 22
|
||||
filament_density = 1.07
|
||||
cooling = 0
|
||||
|
||||
[filament:TPE @PROTON_X]
|
||||
[filament:*common TPE @INAT*]
|
||||
inherits = *common*
|
||||
temperature = 220
|
||||
bed_temperature = 40
|
||||
@ -334,7 +390,7 @@ max_fan_speed = 50
|
||||
filament_retract_length = 0.8
|
||||
filament_retract_speed = 25
|
||||
|
||||
[filament:HIPS @PROTON_X]
|
||||
[filament:*common HIPS @INAT*]
|
||||
inherits = *common*
|
||||
temperature = 245
|
||||
bed_temperature = 100
|
||||
@ -347,7 +403,7 @@ min_fan_speed = 0
|
||||
max_fan_speed = 50
|
||||
filament_soluble = 1
|
||||
|
||||
[filament:Nylon @PROTON_X]
|
||||
[filament:*common Nylon @INAT*]
|
||||
inherits = *common*
|
||||
temperature = 235
|
||||
bed_temperature = 130
|
||||
@ -359,19 +415,19 @@ filament_density = 1.01
|
||||
cooling = 0
|
||||
bridge_fan_speed = 0
|
||||
|
||||
[filament:PC @PROTON_X]
|
||||
[filament:*common PC @INAT*]
|
||||
inherits = *common*
|
||||
temperature = 270
|
||||
bed_temperature = 130
|
||||
bed_temperature = 115
|
||||
first_layer_temperature = 270
|
||||
first_layer_bed_temperature = 130
|
||||
first_layer_bed_temperature = 115
|
||||
filament_type = PC
|
||||
filament_cost = 65
|
||||
filament_density = 1.19
|
||||
cooling = 0
|
||||
bridge_fan_speed = 0
|
||||
|
||||
[filament:CPE @PROTON_X]
|
||||
[filament:*common CPE @INAT*]
|
||||
inherits = *common*
|
||||
temperature = 280
|
||||
bed_temperature = 90
|
||||
@ -383,7 +439,7 @@ filament_density = 1.27
|
||||
cooling = 0
|
||||
bridge_fan_speed = 0
|
||||
|
||||
[filament:PEEK @PROTON_X]
|
||||
[filament:*common PEEK @INAT*]
|
||||
inherits = *common*
|
||||
temperature = 440
|
||||
bed_temperature = 150
|
||||
@ -395,7 +451,7 @@ filament_density = 1.3
|
||||
cooling = 0
|
||||
bridge_fan_speed = 0
|
||||
|
||||
[filament:PEI @PROTON_X]
|
||||
[filament:*common PEI @INAT*]
|
||||
inherits = *common*
|
||||
temperature = 400
|
||||
bed_temperature = 150
|
||||
@ -407,7 +463,7 @@ filament_density = 1.27
|
||||
cooling = 0
|
||||
bridge_fan_speed = 0
|
||||
|
||||
[filament:Polymaker PolyMide CoPA @PROTON_X]
|
||||
[filament:*common Polymaker PolyMide CoPA @INAT*]
|
||||
inherits = *common*
|
||||
filament_vendor = Polymaker
|
||||
temperature = 265
|
||||
@ -419,7 +475,7 @@ filament_cost = 93
|
||||
filament_density = 1.12
|
||||
cooling = 0
|
||||
|
||||
[filament:Polymaker PolyMide PA6-CF @PROTON_X]
|
||||
[filament:*common Polymaker PolyMide PA6-CF @INAT*]
|
||||
inherits = *common*
|
||||
filament_vendor = Polymaker
|
||||
temperature = 300
|
||||
@ -431,7 +487,7 @@ filament_cost = 95
|
||||
filament_density = 1.17
|
||||
cooling = 0
|
||||
|
||||
[filament:Polymaker PolyMide PA6-GF @PROTON_X]
|
||||
[filament:*common Polymaker PolyMide PA6-GF @INAT*]
|
||||
inherits = *common*
|
||||
filament_vendor = Polymaker
|
||||
temperature = 300
|
||||
@ -443,20 +499,21 @@ filament_cost = 95
|
||||
filament_density = 1.2
|
||||
cooling = 0
|
||||
|
||||
[filament:Devil Design PETG @PROTON_X]
|
||||
[filament:*common Devil Design PETG @INAT*]
|
||||
inherits = *common*
|
||||
filament_vendor = Devil Design
|
||||
temperature = 250
|
||||
temperature = 245
|
||||
bed_temperature = 80
|
||||
first_layer_temperature = 250
|
||||
first_layer_temperature = 245
|
||||
first_layer_bed_temperature = 80
|
||||
filament_type = PETG
|
||||
filament_cost = 22
|
||||
filament_density = 1.23
|
||||
min_fan_speed = 0
|
||||
fan_always_on = 1
|
||||
min_fan_speed = 25
|
||||
max_fan_speed = 50
|
||||
|
||||
[filament:Filament PM PETG FRJet @PROTON_X]
|
||||
[filament:*common Filament PM PETG FRJet @INAT*]
|
||||
inherits = *common*
|
||||
filament_vendor = Filament PM
|
||||
temperature = 250
|
||||
@ -467,3 +524,207 @@ filament_type = PETG
|
||||
filament_cost = 45.5
|
||||
filament_density = 1.27
|
||||
cooling = 0
|
||||
|
||||
|
||||
######
|
||||
###### PROTON X PRINTERS
|
||||
######
|
||||
|
||||
[printer:Proton X Rail]
|
||||
inherits = *proton_x_common*
|
||||
printer_model = PROTON_X_RAIL
|
||||
printer_variant = 0.4
|
||||
default_print_profile = 0.2mm Standard @PROTON_X
|
||||
gcode_flavor = marlin
|
||||
machine_max_acceleration_x = 800,800
|
||||
machine_max_acceleration_y = 800,800
|
||||
machine_max_jerk_x = 10,10
|
||||
machine_max_jerk_y = 10,10
|
||||
|
||||
[printer:Proton X Rod]
|
||||
inherits = *proton_x_common*
|
||||
printer_model = PROTON_X_ROD
|
||||
printer_variant = 0.4
|
||||
default_print_profile = 0.2mm Standard @PROTON_X
|
||||
gcode_flavor = marlin
|
||||
|
||||
[print:0.2mm Standard @PROTON_X]
|
||||
inherits = *common 0.2mm Standard @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[print:0.2mm Strong @PROTON_X]
|
||||
inherits = *common 0.2mm Strong @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[print:0.2mm Advanced Material @PROTON_X]
|
||||
inherits = *common 0.2mm Advanced Material @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[print:0.12mm Fine @PROTON_X]
|
||||
inherits = *common 0.12mm Fine @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[print:0.32mm Draft @PROTON_X]
|
||||
inherits = *common 0.32mm Draft @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
|
||||
|
||||
[filament:PLA @PROTON_X]
|
||||
inherits =*common PLA @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:PETG @PROTON_X]
|
||||
inherits =*common PETG @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:ABS @PROTON_X]
|
||||
inherits =*common ABS @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:ASA @PROTON_X]
|
||||
inherits =*common ASA @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:TPE @PROTON_X]
|
||||
inherits =*common TPE @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:HIPS @PROTON_X]
|
||||
inherits =*common HIPS @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:Nylon @PROTON_X]
|
||||
inherits =*common Nylon @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:PC @PROTON_X]
|
||||
inherits =*common PC @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:CPE @PROTON_X]
|
||||
inherits =*common CPE @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:PEEK @PROTON_X]
|
||||
inherits =*common PEEK @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:PEI @PROTON_X]
|
||||
inherits =*common PEI @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:Polymaker PolyMide CoPA @PROTON_X]
|
||||
inherits =*common Polymaker PolyMide CoPA @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:Polymaker PolyMide PA6-CF @PROTON_X]
|
||||
inherits =*common Polymaker PolyMide PA6-CF @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:Polymaker PolyMide PA6-GF @PROTON_X]
|
||||
inherits =*common Polymaker PolyMide PA6-GF @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:Devil Design PETG @PROTON_X]
|
||||
inherits =*common Devil Design PETG @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
[filament:Filament PM PETG FRJet @PROTON_X]
|
||||
inherits =*common Filament PM PETG FRJet @INAT*
|
||||
compatible_printers = "Proton X Rail";"Proton X Rod"
|
||||
|
||||
|
||||
|
||||
|
||||
######### #########
|
||||
######### Proton XE 750 #########
|
||||
######### #########
|
||||
|
||||
[printer:Proton XE-750]
|
||||
inherits = *proton_xe750_common*
|
||||
printer_model = PROTON_XE750
|
||||
printer_variant = 0.4
|
||||
default_print_profile = 0.2mm Standard @PROTON_XE750
|
||||
gcode_flavor = marlin
|
||||
|
||||
|
||||
[print:0.2mm Standard @PROTON_XE750]
|
||||
inherits = *common 0.2mm Standard @INAT*
|
||||
compatible_printers = "Proton XE-750"
|
||||
|
||||
[print:0.2mm Strong @PROTON_XE750]
|
||||
inherits = *common 0.2mm Strong @INAT*
|
||||
compatible_printers = "Proton XE-750"
|
||||
|
||||
[print:0.2mm Advanced Material @PROTON_XE750]
|
||||
inherits = *common 0.2mm Advanced Material @INAT*
|
||||
compatible_printers = "Proton XE-750"
|
||||
|
||||
[print:0.12mm Fine @PROTON_XE750]
|
||||
inherits = *common 0.12mm Fine @INAT*
|
||||
compatible_printers = "Proton XE-750"
|
||||
|
||||
[print:0.32mm Draft @PROTON_XE750]
|
||||
inherits = *common 0.32mm Draft @INAT*
|
||||
compatible_printers = "Proton XE-750"
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
[filament:*start_end_gcode @PROTON_XE750*]
|
||||
start_filament_gcode = "; Filament start gcode BEGIN\nM104 S[temperature[current_extruder]]\nG4 S20\n; Filament start gcode END\n"
|
||||
end_filament_gcode = "; Filament end gcode BEGIN\nG0 X-5 Y250 F10000\nM104 S{temperature[current_extruder] - 50}\n; Filament end gcode END\n"
|
||||
compatible_printers = "Proton XE-750"
|
||||
|
||||
|
||||
|
||||
[filament:PLA @PROTON_XE750]
|
||||
inherits =*common PLA @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:PETG @PROTON_XE750]
|
||||
inherits =*common PETG @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:ABS @PROTON_XE750]
|
||||
inherits =*common ABS @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:ASA @PROTON_XE750]
|
||||
inherits =*common ASA @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:TPE @PROTON_XE750]
|
||||
inherits =*common TPE @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:HIPS @PROTON_XE750]
|
||||
inherits =*common HIPS @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:Nylon @PROTON_XE750]
|
||||
inherits =*common Nylon @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:PC @PROTON_XE750]
|
||||
inherits =*common PC @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:CPE @PROTON_XE750]
|
||||
inherits =*common CPE @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:PEEK @PROTON_XE750]
|
||||
inherits =*common PEEK @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:PEI @PROTON_XE750]
|
||||
inherits =*common PEI @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:Polymaker PolyMide CoPA @PROTON_XE750]
|
||||
inherits =*common Polymaker PolyMide CoPA @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:Polymaker PolyMide PA6-CF @PROTON_XE750]
|
||||
inherits =*common Polymaker PolyMide PA6-CF @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:Polymaker PolyMide PA6-GF @PROTON_XE750]
|
||||
inherits =*common Polymaker PolyMide PA6-GF @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:Devil Design PETG @PROTON_XE750]
|
||||
inherits =*common Devil Design PETG @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
||||
[filament:Filament PM PETG FRJet @PROTON_XE750]
|
||||
inherits =*common Filament PM PETG FRJet @INAT*; *start_end_gcode @PROTON_XE750*
|
||||
|
BIN
resources/profiles/INAT/PROTON_XE750_thumbnail.png
Normal file
BIN
resources/profiles/INAT/PROTON_XE750_thumbnail.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 36 KiB |
2
resources/profiles/Infinity3D.idx
Normal file
2
resources/profiles/Infinity3D.idx
Normal file
@ -0,0 +1,2 @@
|
||||
min_slic3r_version = 2.5.0-alpha0
|
||||
1.0.0 Initial Infinity3D bundle
|
812
resources/profiles/Infinity3D.ini
Normal file
812
resources/profiles/Infinity3D.ini
Normal file
@ -0,0 +1,812 @@
|
||||
# Infinity3D profiles
|
||||
|
||||
[vendor]
|
||||
# Vendor name will be shown by the Config Wizard.
|
||||
name = Infinity3D
|
||||
# Configuration version of this file. Config file will only be installed, if the config_version differs.
|
||||
# This means, the server may force the Slic3r configuration to be downgraded.
|
||||
config_version = 1.0.0
|
||||
# Where to get the updates from?
|
||||
config_update_url = https://files.prusa3d.com/wp-content/uploads/repository/PrusaSlicer-settings-master/live/Infinity3D/
|
||||
# The printer models will be shown by the Configuration Wizard in this order,
|
||||
|
||||
[printer_model:DEV-200]
|
||||
name = Infinity3D DEV-200
|
||||
variants = 0.4
|
||||
technology = FFF
|
||||
bed_model = DEV_200_bed.stl
|
||||
bed_texture = DEV_200_texture.svg
|
||||
default_materials = Generic PLA @Infinity3D; Generic PETG @Infinity3D
|
||||
|
||||
[printer_model:DEV-350]
|
||||
name = Infinity3D DEV-350
|
||||
variants = 0.4
|
||||
technology = FFF
|
||||
bed_model = DEV_350_bed.stl
|
||||
bed_texture = DEV_350_texture.svg
|
||||
default_materials = Generic PLA @Infinity3D; Generic PETG @Infinity3D
|
||||
|
||||
[print:*common*]
|
||||
avoid_crossing_perimeters = 1
|
||||
avoid_crossing_perimeters_max_detour = 0
|
||||
bottom_fill_pattern = monotonic
|
||||
bottom_solid_layers = 4
|
||||
bottom_solid_min_thickness = 0
|
||||
bridge_acceleration = 0
|
||||
bridge_angle = 0
|
||||
bridge_flow_ratio = 1
|
||||
bridge_speed = 60
|
||||
brim_separation = 0
|
||||
brim_type = outer_only
|
||||
brim_width = 0
|
||||
clip_multipart_objects = 1
|
||||
complete_objects = 0
|
||||
default_acceleration = 0
|
||||
dont_support_bridges = 1
|
||||
draft_shield = disabled
|
||||
elefant_foot_compensation = 0.1
|
||||
ensure_vertical_shell_thickness = 1
|
||||
external_perimeter_extrusion_width = 0.45
|
||||
external_perimeter_speed = 80%
|
||||
external_perimeters_first = 0
|
||||
extra_perimeters = 0
|
||||
extruder_clearance_height = 25
|
||||
extruder_clearance_radius = 75
|
||||
extrusion_width = 0.45
|
||||
fill_angle = 45
|
||||
fill_density = 20%
|
||||
fill_pattern = gyroid
|
||||
first_layer_acceleration = 0
|
||||
first_layer_acceleration_over_raft = 0
|
||||
first_layer_extrusion_width = 0.45
|
||||
first_layer_height = 0.2
|
||||
first_layer_speed = 45
|
||||
first_layer_speed_over_raft = 45
|
||||
fuzzy_skin = none
|
||||
fuzzy_skin_point_dist = 0.8
|
||||
fuzzy_skin_thickness = 0.3
|
||||
gap_fill_enabled = 1
|
||||
gap_fill_speed = 20
|
||||
gcode_comments = 0
|
||||
gcode_label_objects = 0
|
||||
gcode_resolution = 0.0125
|
||||
gcode_substitutions =
|
||||
infill_acceleration = 0
|
||||
infill_anchor = 600%
|
||||
infill_anchor_max = 50
|
||||
infill_every_layers = 1
|
||||
infill_extruder = 1
|
||||
infill_extrusion_width = 0.45
|
||||
infill_first = 0
|
||||
infill_only_where_needed = 0
|
||||
infill_overlap = 25%
|
||||
infill_speed = 60
|
||||
inherits =
|
||||
interface_shells = 0
|
||||
ironing = 0
|
||||
ironing_flowrate = 15%
|
||||
ironing_spacing = 0.25
|
||||
ironing_speed = 30
|
||||
ironing_type = top
|
||||
layer_height = 0.2
|
||||
max_print_speed = 100
|
||||
max_volumetric_speed = 0
|
||||
min_skirt_length = 4
|
||||
mmu_segmented_region_max_width = 0
|
||||
notes =
|
||||
only_retract_when_crossing_perimeters = 0
|
||||
ooze_prevention = 0
|
||||
output_filename_format = {input_filename_base}_{layer_height}mm_{filament_type[0]}_{printer_model}_{print_time}.gcode
|
||||
overhangs = 0
|
||||
perimeter_acceleration = 0
|
||||
perimeter_extruder = 1
|
||||
perimeter_extrusion_width = 0.45
|
||||
perimeter_speed = 60
|
||||
perimeters = 2
|
||||
post_process =
|
||||
print_settings_id =
|
||||
raft_contact_distance = 0.1
|
||||
raft_expansion = 1.5
|
||||
raft_first_layer_density = 90%
|
||||
raft_first_layer_expansion = 3
|
||||
raft_layers = 0
|
||||
resolution = 0
|
||||
seam_position = nearest
|
||||
single_extruder_multi_material_priming = 1
|
||||
skirt_distance = 5
|
||||
skirt_height = 1
|
||||
skirts = 3
|
||||
slice_closing_radius = 0.049
|
||||
slicing_mode = regular
|
||||
small_perimeter_speed = 70%
|
||||
solid_infill_below_area = 0
|
||||
solid_infill_every_layers = 0
|
||||
solid_infill_extruder = 1
|
||||
solid_infill_extrusion_width= 0.45
|
||||
solid_infill_speed = 80%
|
||||
spiral_vase = 0
|
||||
standby_temperature_delta = -5
|
||||
support_material = 0
|
||||
support_material_angle = 0
|
||||
support_material_auto = 1
|
||||
support_material_bottom_contact_distance = 0
|
||||
support_material_bottom_interface_layers = -1
|
||||
support_material_buildplate_only = 0
|
||||
support_material_closing_radius = 2
|
||||
support_material_contact_distance = 0.15
|
||||
support_material_enforce_layers = 0
|
||||
support_material_extruder = 0
|
||||
support_material_extrusion_width = 0.38
|
||||
support_material_interface_contact_loops = 0
|
||||
support_material_interface_extruder = 0
|
||||
support_material_interface_layers = 2
|
||||
support_material_interface_pattern = rectilinear
|
||||
support_material_interface_spacing = 0.2
|
||||
support_material_interface_speed = 100%
|
||||
support_material_pattern = rectilinear
|
||||
support_material_spacing = 2
|
||||
support_material_speed = 60
|
||||
support_material_style = grid
|
||||
support_material_synchronize_layers = 0
|
||||
support_material_threshold = 45
|
||||
support_material_with_sheath = 0
|
||||
support_material_xy_spacing = 60%
|
||||
thick_bridges = 1
|
||||
thin_walls = 0
|
||||
threads = 8
|
||||
top_fill_pattern = monotonic
|
||||
top_infill_extrusion_width = 0.45
|
||||
top_solid_infill_speed = 60%
|
||||
top_solid_layers = 4
|
||||
top_solid_min_thickness = 0
|
||||
travel_speed = 70
|
||||
travel_speed_z = 0
|
||||
wipe_tower = 0
|
||||
wipe_tower_bridging = 10
|
||||
wipe_tower_brim_width = 2
|
||||
wipe_tower_no_sparse_layers = 0
|
||||
wipe_tower_rotation_angle = 0
|
||||
wipe_tower_width = 60
|
||||
wipe_tower_x = 170
|
||||
wipe_tower_y = 140
|
||||
xy_size_compensation = 0
|
||||
compatible_printers_condition = nozzle_diameter[0]==0.4
|
||||
|
||||
[print:0.06mm SUPERFINE @Infinity3D_DEV_200]
|
||||
inherits = *common*
|
||||
layer_height = 0.06
|
||||
bottom_solid_layers = 12
|
||||
top_solid_layers = 12
|
||||
top_solid_min_thickness = 0.72
|
||||
bottom_solid_min_thickness = 0.72
|
||||
bridge_speed = 45
|
||||
infill_speed = 60
|
||||
perimeter_speed = 50
|
||||
support_material_speed = 50
|
||||
max_print_speed = 60
|
||||
skirt_distance = 10
|
||||
first_layer_speed = 80%
|
||||
first_layer_extrusion_width = 0.45
|
||||
perimeter_extrusion_width = 0.4
|
||||
external_perimeter_extrusion_width = 0.4
|
||||
infill_extrusion_width = 0.4
|
||||
solid_infill_extrusion_width = 0.4
|
||||
top_infill_extrusion_width = 0.4
|
||||
compatible_printers_condition = nozzle_diameter[0]==0.4 and printer_model=="DEV-200"
|
||||
|
||||
[print:0.10mm Fine @Infinity3D_DEV_200]
|
||||
inherits = *common*
|
||||
layer_height = 0.10
|
||||
top_solid_layers = 8
|
||||
bottom_solid_layers = 8
|
||||
bridge_speed = 45
|
||||
infill_speed = 60
|
||||
perimeter_speed = 50
|
||||
support_material_speed = 50
|
||||
max_print_speed = 60
|
||||
skirt_distance = 10
|
||||
first_layer_speed = 80%
|
||||
first_layer_extrusion_width = 0.45
|
||||
perimeter_extrusion_width = 0.4
|
||||
external_perimeter_extrusion_width = 0.4
|
||||
infill_extrusion_width = 0.4
|
||||
solid_infill_extrusion_width = 0.4
|
||||
top_infill_extrusion_width = 0.4
|
||||
compatible_printers_condition = nozzle_diameter[0]==0.4 and printer_model=="DEV-200"
|
||||
|
||||
[print:0.20mm GOOD @Infinity3D_DEV_200]
|
||||
inherits = *common*
|
||||
layer_height = 0.20
|
||||
top_solid_layers = 5
|
||||
bottom_solid_layers = 5
|
||||
bridge_speed = 45
|
||||
infill_speed = 60
|
||||
perimeter_speed = 50
|
||||
support_material_speed = 50
|
||||
max_print_speed = 60
|
||||
skirt_distance = 10
|
||||
first_layer_speed = 80%
|
||||
first_layer_extrusion_width = 0.45
|
||||
perimeter_extrusion_width = 0.4
|
||||
external_perimeter_extrusion_width = 0.4
|
||||
infill_extrusion_width = 0.4
|
||||
solid_infill_extrusion_width = 0.4
|
||||
top_infill_extrusion_width = 0.4
|
||||
compatible_printers_condition = nozzle_diameter[0]==0.4 and printer_model=="DEV-200"
|
||||
|
||||
[print:0.30mm RAPID @Infinity3D_DEV_200]
|
||||
inherits = *common*
|
||||
layer_height = 0.30
|
||||
top_solid_layers = 3
|
||||
bottom_solid_layers = 3
|
||||
bridge_speed = 45
|
||||
infill_speed = 60
|
||||
perimeter_speed = 50
|
||||
support_material_speed = 50
|
||||
max_print_speed = 60
|
||||
skirt_distance = 10
|
||||
first_layer_speed = 80%
|
||||
compatible_printers_condition = nozzle_diameter[0]==0.4 and printer_model=="DEV-200"
|
||||
|
||||
[print:0.40mm FAST @Infinity3D_DEV_200]
|
||||
inherits = *common*
|
||||
layer_height = 0.40
|
||||
top_solid_layers = 3
|
||||
bottom_solid_layers = 3
|
||||
bridge_speed = 45
|
||||
infill_speed = 60
|
||||
perimeter_speed = 50
|
||||
support_material_speed = 50
|
||||
max_print_speed = 60
|
||||
skirt_distance = 10
|
||||
first_layer_speed = 80%
|
||||
support_material_extrusion_width = 0.45
|
||||
compatible_printers_condition = nozzle_diameter[0]==0.4 and printer_model=="DEV-200"
|
||||
|
||||
|
||||
[print:0.06mm SUPERFINE @Infinity3D_DEV_350]
|
||||
inherits = *common*
|
||||
layer_height = 0.06
|
||||
bottom_solid_layers = 12
|
||||
top_solid_layers = 12
|
||||
top_solid_min_thickness = 0.72
|
||||
bottom_solid_min_thickness = 0.72
|
||||
bridge_speed = 45
|
||||
infill_speed = 60
|
||||
perimeter_speed = 50
|
||||
support_material_speed = 50
|
||||
max_print_speed = 60
|
||||
skirt_distance = 10
|
||||
first_layer_speed = 80%
|
||||
first_layer_extrusion_width = 0.45
|
||||
perimeter_extrusion_width = 0.4
|
||||
external_perimeter_extrusion_width = 0.4
|
||||
infill_extrusion_width = 0.4
|
||||
solid_infill_extrusion_width = 0.4
|
||||
top_infill_extrusion_width = 0.4
|
||||
compatible_printers_condition = nozzle_diameter[0]==0.4 and printer_model=="DEV-350"
|
||||
|
||||
[print:0.10mm Fine @Infinity3D_DEV_350]
|
||||
inherits = *common*
|
||||
layer_height = 0.10
|
||||
top_solid_layers = 8
|
||||
bottom_solid_layers = 8
|
||||
bridge_speed = 45
|
||||
infill_speed = 60
|
||||
perimeter_speed = 50
|
||||
support_material_speed = 50
|
||||
max_print_speed = 60
|
||||
skirt_distance = 10
|
||||
first_layer_speed = 80%
|
||||
first_layer_extrusion_width = 0.45
|
||||
perimeter_extrusion_width = 0.4
|
||||
external_perimeter_extrusion_width = 0.4
|
||||
infill_extrusion_width = 0.4
|
||||
solid_infill_extrusion_width = 0.4
|
||||
top_infill_extrusion_width = 0.4
|
||||
compatible_printers_condition = nozzle_diameter[0]==0.4 and printer_model=="DEV-350"
|
||||
|
||||
[print:0.20mm GOOD @Infinity3D_DEV_350]
|
||||
inherits = *common*
|
||||
layer_height = 0.20
|
||||
top_solid_layers = 5
|
||||
bottom_solid_layers = 5
|
||||
bridge_speed = 45
|
||||
infill_speed = 60
|
||||
perimeter_speed = 50
|
||||
support_material_speed = 50
|
||||
max_print_speed = 60
|
||||
skirt_distance = 10
|
||||
first_layer_speed = 80%
|
||||
first_layer_extrusion_width = 0.45
|
||||
perimeter_extrusion_width = 0.4
|
||||
external_perimeter_extrusion_width = 0.4
|
||||
infill_extrusion_width = 0.4
|
||||
solid_infill_extrusion_width = 0.4
|
||||
top_infill_extrusion_width = 0.4
|
||||
compatible_printers_condition = nozzle_diameter[0]==0.4 and printer_model=="DEV-350"
|
||||
|
||||
[print:0.30mm RAPID @Infinity3D_DEV_350]
|
||||
inherits = *common*
|
||||
layer_height = 0.30
|
||||
top_solid_layers = 3
|
||||
bottom_solid_layers = 3
|
||||
bridge_speed = 45
|
||||
infill_speed = 60
|
||||
perimeter_speed = 50
|
||||
support_material_speed = 50
|
||||
max_print_speed = 60
|
||||
skirt_distance = 10
|
||||
first_layer_speed = 80%
|
||||
compatible_printers_condition = nozzle_diameter[0]==0.4 and printer_model=="DEV-350"
|
||||
|
||||
[print:0.40mm FAST @Infinity3D_DEV_350]
|
||||
inherits = *common*
|
||||
layer_height = 0.40
|
||||
top_solid_layers = 3
|
||||
bottom_solid_layers = 3
|
||||
bridge_speed = 45
|
||||
infill_speed = 60
|
||||
perimeter_speed = 50
|
||||
support_material_speed = 50
|
||||
max_print_speed = 60
|
||||
skirt_distance = 10
|
||||
first_layer_speed = 80%
|
||||
support_material_extrusion_width = 0.45
|
||||
compatible_printers_condition = nozzle_diameter[0]==0.4 and printer_model=="DEV-350"
|
||||
|
||||
|
||||
[filament:*common*]
|
||||
bed_temperature = 60
|
||||
bridge_fan_speed = 100
|
||||
compatible_printers =
|
||||
compatible_printers_condition =
|
||||
compatible_prints =
|
||||
compatible_prints_condition =
|
||||
cooling = 1
|
||||
disable_fan_first_layers = 2
|
||||
end_filament_gcode = "; Filament-specific end gcode \n;END gcode for filament\n"
|
||||
extrusion_multiplier = 1
|
||||
fan_always_on = 1
|
||||
fan_below_layer_time = 60
|
||||
filament_colour = #29B2B2
|
||||
filament_cooling_final_speed = 3.4
|
||||
filament_cooling_initial_speed = 2.2
|
||||
filament_cooling_moves = 4
|
||||
filament_cost = 0
|
||||
filament_density = 0
|
||||
filament_deretract_speed = nil
|
||||
filament_diameter = 1.75
|
||||
filament_load_time = 0
|
||||
filament_loading_speed = 28
|
||||
filament_loading_speed_start = 3
|
||||
filament_max_volumetric_speed = 0
|
||||
filament_minimal_purge_on_wipe_tower = 15
|
||||
filament_notes = ""
|
||||
filament_ramming_parameters = "120 100 6.6 6.8 7.2 7.6 7.9 8.2 8.7 9.4 9.9 10.0| 0.05 6.6 0.45 6.8 0.95 7.8 1.45 8.3 1.95 9.7 2.45 10 2.95 7.6 3.45 7.6 3.95 7.6 4.45 7.6 4.95 7.6"
|
||||
filament_retract_before_travel = nil
|
||||
filament_retract_before_wipe = nil
|
||||
filament_retract_layer_change = nil
|
||||
filament_retract_length = nil
|
||||
filament_retract_lift = nil
|
||||
filament_retract_lift_above = nil
|
||||
filament_retract_lift_below = nil
|
||||
filament_retract_restart_extra = nil
|
||||
filament_retract_speed = nil
|
||||
filament_settings_id = ""
|
||||
filament_soluble = 0
|
||||
filament_spool_weight = 0
|
||||
filament_toolchange_delay = 0
|
||||
filament_type = PLA
|
||||
filament_unload_time = 0
|
||||
filament_unloading_speed = 90
|
||||
filament_unloading_speed_start = 100
|
||||
filament_wipe = nil
|
||||
first_layer_bed_temperature = 60
|
||||
first_layer_temperature = 210
|
||||
full_fan_speed_layer = 0
|
||||
inherits =
|
||||
max_fan_speed = 100
|
||||
min_fan_speed = 35
|
||||
min_print_speed = 10
|
||||
slowdown_below_layer_time = 5
|
||||
start_filament_gcode = "; Filament gcode\n"
|
||||
temperature = 210
|
||||
|
||||
[filament:*PLA*]
|
||||
inherits = *common*
|
||||
bed_temperature = 60
|
||||
fan_below_layer_time = 100
|
||||
filament_colour = #DDDDDD
|
||||
filament_max_volumetric_speed = 15
|
||||
filament_type = PLA
|
||||
filament_density = 1.24
|
||||
filament_cost = 20
|
||||
first_layer_bed_temperature = 60
|
||||
first_layer_temperature = 210
|
||||
fan_always_on = 1
|
||||
cooling = 1
|
||||
max_fan_speed = 100
|
||||
min_fan_speed = 100
|
||||
bridge_fan_speed = 100
|
||||
disable_fan_first_layers = 1
|
||||
temperature = 205
|
||||
|
||||
[filament:*PET*]
|
||||
inherits = *common*
|
||||
bed_temperature = 70
|
||||
cooling = 1
|
||||
disable_fan_first_layers = 3
|
||||
fan_below_layer_time = 20
|
||||
filament_colour = #DDDDDD
|
||||
filament_max_volumetric_speed = 8
|
||||
filament_type = PETG
|
||||
filament_density = 1.27
|
||||
filament_cost = 30
|
||||
first_layer_bed_temperature = 70
|
||||
first_layer_temperature = 240
|
||||
fan_always_on = 1
|
||||
max_fan_speed = 50
|
||||
min_fan_speed = 20
|
||||
bridge_fan_speed = 100
|
||||
temperature = 240
|
||||
|
||||
[filament:*ABS*]
|
||||
inherits = *common*
|
||||
bed_temperature = 100
|
||||
cooling = 0
|
||||
disable_fan_first_layers = 3
|
||||
fan_below_layer_time = 20
|
||||
filament_colour = #DDDDDD
|
||||
filament_max_volumetric_speed = 11
|
||||
filament_type = ABS
|
||||
filament_density = 1.04
|
||||
filament_cost = 20
|
||||
first_layer_bed_temperature = 100
|
||||
first_layer_temperature = 245
|
||||
fan_always_on = 0
|
||||
max_fan_speed = 0
|
||||
min_fan_speed = 0
|
||||
bridge_fan_speed = 30
|
||||
top_fan_speed = 0
|
||||
temperature = 245
|
||||
|
||||
[filament:Generic PLA @Infinity3D]
|
||||
inherits = *PLA*
|
||||
renamed_from = "Generic PLA @Infinity3D"
|
||||
filament_vendor = Generic
|
||||
|
||||
[filament:Generic PETG @Infinity3D]
|
||||
inherits = *PET*
|
||||
renamed_from = "Generic PETG @Infinity3D"
|
||||
filament_vendor = Generic
|
||||
|
||||
[filament:Generic ABS @Infinity3D]
|
||||
inherits = *ABS*
|
||||
renamed_from = "Generic ABS @Infinity3D"
|
||||
first_layer_bed_temperature = 90
|
||||
bed_temperature = 90
|
||||
filament_vendor = Generic
|
||||
|
||||
[filament:Infinity3D PLA @Infinity3D]
|
||||
inherits = *PLA*
|
||||
renamed_from = "Infinity3D PLA @Infinity3D"
|
||||
filament_vendor = Infinity3D
|
||||
temperature = 200
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 205
|
||||
first_layer_bed_temperature = 60
|
||||
filament_colour = #42BDD8
|
||||
|
||||
[filament:Infinity3D PETG @Infinity3D]
|
||||
inherits = *PET*
|
||||
renamed_from = "Infinity3D PETG @Infinity3D"
|
||||
filament_vendor = Infinity3D
|
||||
temperature = 240
|
||||
bed_temperature = 70
|
||||
first_layer_temperature = 240
|
||||
first_layer_bed_temperature = 70
|
||||
max_fan_speed = 40
|
||||
min_fan_speed = 20
|
||||
filament_colour = #42BDD8
|
||||
|
||||
[filament:Infinity3D ABS @Infinity3D]
|
||||
inherits = *ABS*
|
||||
renamed_from = "Infinity3D ABS @Infinity3D"
|
||||
filament_vendor = Infinity3D
|
||||
temperature = 240
|
||||
bed_temperature = 90
|
||||
first_layer_temperature = 240
|
||||
first_layer_bed_temperature = 90
|
||||
filament_colour = #42BDD8
|
||||
|
||||
[filament:Prusament PLA @Infinity3D]
|
||||
inherits = *PLA*
|
||||
renamed_from = "Prusament PLA @Infinity3D"
|
||||
filament_vendor = Prusa Polymers
|
||||
temperature = 210
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 215
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 24.99
|
||||
filament_density = 1.24
|
||||
filament_colour = #F94D0C
|
||||
|
||||
[filament:Prusament PETG @Infinity3D]
|
||||
inherits = *PET*
|
||||
renamed_from = "Prusament PETG @Infinity3D"
|
||||
filament_vendor = Prusa Polymers
|
||||
temperature = 245
|
||||
bed_temperature = 70
|
||||
first_layer_temperature = 245
|
||||
first_layer_bed_temperature = 70
|
||||
filament_cost = 24.99
|
||||
filament_density = 1.27
|
||||
filament_colour = #F94D0C
|
||||
|
||||
[filament:AzureFilm PLA @Infinity3D]
|
||||
inherits = *PLA*
|
||||
filament_vendor = AzureFilm
|
||||
temperature = 210
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 215
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 19.97
|
||||
filament_density = 1.24
|
||||
filament_colour = #006AA6
|
||||
|
||||
[filament:Devil Design PLA @Infinity3D]
|
||||
inherits = *PLA*
|
||||
filament_vendor = Devil Design
|
||||
temperature = 215
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 215
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 19.00
|
||||
filament_density = 1.24
|
||||
filament_colour = #FF0000
|
||||
filament_spool_weight = 256
|
||||
|
||||
[filament:Devil Design PLA Matt @Infinity3D]
|
||||
inherits = *PLA*
|
||||
filament_vendor = Devil Design
|
||||
temperature = 205
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 205
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 20.00
|
||||
filament_density = 1.38
|
||||
filament_colour = #FF0000
|
||||
filament_spool_weight = 256
|
||||
|
||||
[filament:Devil Design PLA Galaxy @Infinity3D]
|
||||
inherits = *PLA*
|
||||
renamed_from = "Devil Design PLA (Galaxy) @Infinity3D"
|
||||
filament_vendor = Devil Design
|
||||
temperature = 225
|
||||
bed_temperature = 65
|
||||
first_layer_temperature = 225
|
||||
first_layer_bed_temperature = 65
|
||||
filament_cost = 19.00
|
||||
filament_density = 1.24
|
||||
filament_colour = #FF0000
|
||||
filament_spool_weight = 256
|
||||
|
||||
[filament:Extrudr PLA NX2 @Infinity3D]
|
||||
inherits = *PLA*
|
||||
filament_vendor = Extrudr
|
||||
temperature = 200
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 205
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 23.63
|
||||
filament_density = 1.3
|
||||
filament_colour = #3C4547
|
||||
filament_spool_weight = 256
|
||||
|
||||
[filament:Extrudr GreenTEC Pro @Infinity3D]
|
||||
inherits = *PLA*
|
||||
filament_vendor = Extrudr
|
||||
temperature = 210
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 215
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 56.24
|
||||
filament_density = 1.35
|
||||
filament_colour = #3C4547
|
||||
|
||||
[filament:Real Filament PLA @Infinity3D]
|
||||
inherits = *PLA*
|
||||
filament_vendor = Real Filament
|
||||
temperature = 195
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 200
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 24.99
|
||||
filament_density = 1.24
|
||||
filament_colour = #007ABF
|
||||
|
||||
[filament:Velleman PLA @Infinity3D]
|
||||
inherits = *PLA*
|
||||
filament_vendor = Velleman
|
||||
temperature = 200
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 205
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 27.99
|
||||
filament_density = 1.24
|
||||
filament_colour = #7EA60D
|
||||
|
||||
[filament:3DJAKE ecoPLA @Infinity3D]
|
||||
inherits = *PLA*
|
||||
filament_vendor = 3DJAKE
|
||||
temperature = 200
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 205
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 21.99
|
||||
filament_density = 1.24
|
||||
filament_colour = #125467
|
||||
filament_spool_weight = 238
|
||||
|
||||
[filament:3DJAKE ecoPLA Matt @Infinity3D]
|
||||
inherits = *PLA*
|
||||
filament_vendor = 3DJAKE
|
||||
temperature = 195
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 195
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 24.99
|
||||
filament_density = 1.38
|
||||
filament_colour = #125467
|
||||
filament_spool_weight = 238
|
||||
|
||||
[filament:3DJAKE ecoPLA Tough @Infinity3D]
|
||||
inherits = *PLA*
|
||||
filament_vendor = 3DJAKE
|
||||
temperature = 215
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 215
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 29.99
|
||||
filament_density = 1.21
|
||||
filament_colour = #125467
|
||||
|
||||
[filament:FormFutura Tough PLA @Infinity3D]
|
||||
inherits = *PLA*
|
||||
filament_vendor = FormFutura
|
||||
temperature = 215
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 215
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 46.65
|
||||
filament_density = 1.21
|
||||
filament_colour = #ed000e
|
||||
|
||||
[filament:123-3D Jupiter PLA @Infinity3D]
|
||||
inherits = *PLA*
|
||||
filament_vendor = 123-3D
|
||||
temperature = 200
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 205
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 19.50
|
||||
filament_density = 1.24
|
||||
filament_colour = #FFE200
|
||||
|
||||
[filament:Das Filament PLA @Infinity3D]
|
||||
inherits = *PLA*
|
||||
filament_vendor = Das Filament
|
||||
temperature = 210
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 215
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 20.56
|
||||
filament_density = 1.24
|
||||
filament_colour = #C7F935
|
||||
|
||||
[filament:Das Filament PETG @Infinity3D]
|
||||
inherits = *PET*
|
||||
filament_vendor = Das Filament
|
||||
temperature = 240
|
||||
bed_temperature = 70
|
||||
first_layer_temperature = 240
|
||||
first_layer_bed_temperature = 70
|
||||
filament_cost = 27.44
|
||||
filament_density = 1.29
|
||||
filament_colour = #C7F935
|
||||
|
||||
[filament:Verbatim PLA @Infinity3D]
|
||||
inherits = *PLA*
|
||||
filament_vendor = Verbatim
|
||||
temperature = 205
|
||||
bed_temperature = 60
|
||||
first_layer_temperature = 210
|
||||
first_layer_bed_temperature = 60
|
||||
filament_cost = 22.99
|
||||
filament_density = 1.24
|
||||
filament_colour = #001ca8
|
||||
|
||||
# Common printer preset
|
||||
[printer:*common*]
|
||||
bed_shape = 0x0,350x0,350x350,0x350
|
||||
color_change_gcode = M600
|
||||
cooling_tube_length = 5
|
||||
cooling_tube_retraction = 91.5
|
||||
default_filament_profile = ""
|
||||
default_print_profile =
|
||||
end_gcode = ;End GCode begin\nM140 S0 ;Heated bed heater off\nM104 S0 ;Extruder heater off\nG90 ;absolute positioning\nG92 E0 ;Retract the filament\nG1 E-1 F300 ;retract the filament a bit before lifting the nozzle, to release some of the pressure\nG1 Z350 E-1 F3000 ;move Z up a bit and retract filament even more\nG1 X0 F3000 ;move X to min endstops, so the head is out of the way\nG1 Y350 F3000 ;so the head is out of the way and Plate is moved forward\nM84 ;stepper off\nM107 ; fan off\nM82 ; absolute extrusion\n;End GCode end
|
||||
extra_loading_move = -2
|
||||
extruder_colour = ""
|
||||
extruder_offset = 0x0
|
||||
gcode_flavor = marlin
|
||||
high_current_on_filament_swap = 0
|
||||
machine_limits_usage = time_estimate_only
|
||||
machine_max_acceleration_e = 10000
|
||||
machine_max_acceleration_extruding = 1000
|
||||
machine_max_acceleration_retracting = 1000
|
||||
machine_max_acceleration_travel = 1500
|
||||
machine_max_acceleration_x = 3000
|
||||
machine_max_acceleration_y = 3000
|
||||
machine_max_acceleration_z = 100
|
||||
machine_max_feedrate_e = 25
|
||||
machine_max_feedrate_x = 150
|
||||
machine_max_feedrate_y = 150
|
||||
machine_max_feedrate_z = 50
|
||||
machine_max_jerk_e = 2.5
|
||||
machine_max_jerk_x = 10
|
||||
machine_max_jerk_y = 10
|
||||
machine_max_jerk_z = 0.2
|
||||
machine_min_extruding_rate = 0
|
||||
machine_min_travel_rate = 0
|
||||
max_layer_height = 0.4
|
||||
max_print_height = 350
|
||||
min_layer_height = 0.08
|
||||
nozzle_diameter = 0.4
|
||||
parking_pos_retraction = 92
|
||||
pause_print_gcode =
|
||||
printer_technology = FFF
|
||||
remaining_times = 0
|
||||
retract_before_travel = 2
|
||||
retract_before_wipe = 0%
|
||||
retract_layer_change = 1
|
||||
retract_length = 2
|
||||
retract_length_toolchange = 10
|
||||
retract_lift = 0
|
||||
retract_lift_above = 0
|
||||
retract_lift_below = 328
|
||||
retract_restart_extra = 0
|
||||
retract_restart_extra_toolchange = 0
|
||||
retract_speed = 60
|
||||
deretract_speed = 40
|
||||
silent_mode = 0
|
||||
single_extruder_multi_material = 0
|
||||
start_gcode = Start GCode begin\nM140 S[first_layer_bed_temperature] ;Start Warming Bed\nM104 S[first_layer_temperature] ;Preheat\nG28 ;home\nG29 ;Auto Bed-level\nG90 ;absolute positioning\nG1 X-10 Y-10 F3000 ;Move to corner\nM190 S[first_layer_bed_temperature] ;Wait For Bed Temperature\nM109 S[first_layer_temperature] ;Wait for Hotend Temperature\nG92 E0 ;Zero set extruder position\nG1 E3 F200 ;Feed filament to clear nozzle\nG92 E0 ;Zero set extruder position
|
||||
thumbnails = 16x16,220x124
|
||||
use_firmware_retraction = 0
|
||||
use_relative_e_distances = 0
|
||||
use_volumetric_e = 0
|
||||
variable_layer_height = 1
|
||||
wipe = 0
|
||||
z_offset = 0
|
||||
|
||||
[printer:Infinity3D DEV-350]
|
||||
inherits = *common*
|
||||
printer_model = DEV-350
|
||||
printer_variant = 0.4
|
||||
default_filament_profile = Generic PLA @Infinity3D
|
||||
default_print_profile = 0.20mm GOOD @Infinity3D_DEV_350
|
||||
|
||||
[printer:Infinity3D DEV-200]
|
||||
inherits = *common*
|
||||
printer_model = DEV-200
|
||||
printer_variant = 0.4
|
||||
bed_shape = 0x0,200x0,200x200,0x200
|
||||
thumbnails =
|
||||
variable_layer_height = 0
|
||||
retract_lift_below = 0
|
||||
max_print_height = 235
|
||||
start_gcode = Start GCode begin\nM140 S[first_layer_bed_temperature] ;Start Warming Bed\nM104 S[first_layer_temperature] ;Preheat\nG28 ;home\nG29 ;Auto Bed-level\nG90 ;absolute positioning\nG1 X-10 Y-10 F3000 ;Move to corner\nM190 S[first_layer_bed_temperature] ;Wait For Bed Temperature\nM109 S[first_layer_temperature] ;Wait for Hotend Temperature\nG92 E0 ;Zero set extruder position\nG1 E3 F200 ;Feed filament to clear nozzle\nG92 E0 ;Zero set extruder position
|
||||
end_gcode = ;End GCode begin\nM140 S0 ;Heated bed heater off\nM104 S0 ;Extruder heater off\nG90 ;absolute positioning\nG92 E0 ;Retract the filament\nG1 E-1 F300 ;retract the filament a bit before lifting the nozzle, to release some of the pressure\nG1 Z240 E-1 F3000 ;move Z up a bit and retract filament even more\nG1 X0 F3000 ;move X to min endstops, so the head is out of the way\nG1 Y200 F3000 ;so the head is out of the way and Plate is moved forward\nM84 ;stepper off\nM107 ; fan off\nM82 ; absolute extrusion\n;End GCode end
|
||||
default_filament_profile = Generic PLA @Infinity3D
|
||||
default_print_profile = 0.20mm GOOD @Infinity3D_DEV_200
|
BIN
resources/profiles/Infinity3D/DEV-200_thumbnail.png
Normal file
BIN
resources/profiles/Infinity3D/DEV-200_thumbnail.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 56 KiB |
BIN
resources/profiles/Infinity3D/DEV-350_thumbnail.png
Normal file
BIN
resources/profiles/Infinity3D/DEV-350_thumbnail.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 56 KiB |
BIN
resources/profiles/Infinity3D/DEV_200_bed.stl
Normal file
BIN
resources/profiles/Infinity3D/DEV_200_bed.stl
Normal file
Binary file not shown.
487
resources/profiles/Infinity3D/DEV_200_texture.svg
Normal file
487
resources/profiles/Infinity3D/DEV_200_texture.svg
Normal file
@ -0,0 +1,487 @@
|
||||
<?xml version="1.0" standalone="no"?>
|
||||
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 20010904//EN"
|
||||
"http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd">
|
||||
<svg version="1.0" xmlns="http://www.w3.org/2000/svg"
|
||||
width="2717.000000pt" height="2953.000000pt" viewBox="0 0 2717.000000 2953.000000"
|
||||
preserveAspectRatio="xMidYMid meet">
|
||||
|
||||
<g transform="translate(0.000000,2953.000000) scale(0.100000,-0.100000)"
|
||||
fill="#000000" stroke="none">
|
||||
<path d="M1160 28950 l0 -580 -580 0 c-573 0 -580 0 -580 -20 0 -20 7 -20 580
|
||||
-20 l580 0 0 -570 0 -570 -580 0 c-573 0 -580 0 -580 -20 0 -20 7 -20 580 -20
|
||||
l580 0 0 -575 0 -575 -580 0 c-509 0 -580 -2 -580 -15 0 -13 71 -15 580 -15
|
||||
l580 0 0 -575 0 -575 -580 0 c-509 0 -580 -2 -580 -15 0 -13 71 -15 580 -15
|
||||
l580 0 0 -575 0 -575 -580 0 c-509 0 -580 -2 -580 -15 0 -13 71 -15 580 -15
|
||||
l580 0 0 -575 0 -575 -580 0 c-509 0 -580 -2 -580 -15 0 -13 71 -15 580 -15
|
||||
l580 0 0 -575 0 -575 -580 0 c-573 0 -580 0 -580 -20 0 -20 7 -20 580 -20
|
||||
l580 0 0 -570 0 -570 -580 0 c-573 0 -580 0 -580 -20 0 -20 7 -20 580 -20
|
||||
l580 0 0 -570 0 -570 -580 0 c-573 0 -580 0 -580 -20 0 -20 7 -20 580 -20
|
||||
l580 0 0 -570 0 -570 -580 0 c-573 0 -580 0 -580 -20 0 -20 7 -20 580 -20
|
||||
l580 0 0 -575 0 -575 -580 0 c-509 0 -580 -2 -580 -15 0 -13 71 -15 580 -15
|
||||
l580 0 0 -575 0 -575 -580 0 c-509 0 -580 -2 -580 -15 0 -13 71 -15 580 -15
|
||||
l580 0 0 -575 0 -575 -580 0 c-509 0 -580 -2 -580 -15 0 -13 71 -15 580 -15
|
||||
l580 0 0 -575 0 -575 -580 0 c-509 0 -580 -2 -580 -15 0 -13 71 -15 580 -15
|
||||
l580 0 0 -575 0 -575 -580 0 c-573 0 -580 0 -580 -20 0 -20 7 -20 580 -20
|
||||
l580 0 0 -570 0 -570 -580 0 c-573 0 -580 0 -580 -20 0 -20 7 -20 580 -20
|
||||
l580 0 0 -570 0 -570 -580 0 c-573 0 -580 0 -580 -20 0 -20 7 -20 580 -20
|
||||
l580 0 0 -570 0 -570 -580 0 c-573 0 -580 0 -580 -20 0 -20 7 -20 580 -20
|
||||
l580 0 0 -575 0 -575 -580 0 c-509 0 -580 -2 -580 -15 0 -13 71 -15 580 -15
|
||||
l580 0 0 -575 0 -575 -580 0 c-509 0 -580 -2 -580 -15 0 -13 71 -15 580 -15
|
||||
l580 0 0 -575 0 -575 -580 0 c-509 0 -580 -2 -580 -15 0 -13 71 -15 580 -15
|
||||
l580 0 0 -575 0 -575 -580 0 c-509 0 -580 -2 -580 -15 0 -13 71 -15 580 -15
|
||||
l580 0 0 -575 0 -575 -580 0 c-509 0 -580 -2 -580 -15 0 -13 71 -15 580 -15
|
||||
l580 0 0 -575 0 -575 -580 0 c-573 0 -580 0 -580 -20 0 -20 7 -20 580 -20
|
||||
l580 0 0 -580 c0 -573 0 -580 20 -580 20 0 20 7 20 580 l0 580 575 0 575 0 0
|
||||
-580 c0 -509 2 -580 15 -580 13 0 15 71 15 580 l0 580 575 0 575 0 0 -580 c0
|
||||
-509 2 -580 15 -580 13 0 15 71 15 580 l0 580 575 0 575 0 0 -580 c0 -509 2
|
||||
-580 15 -580 13 0 15 71 15 580 l0 580 575 0 575 0 0 -580 c0 -509 2 -580 15
|
||||
-580 13 0 15 71 15 580 l0 580 575 0 575 0 0 -580 c0 -573 0 -580 20 -580 20
|
||||
0 20 7 20 580 l0 580 570 0 570 0 0 -580 c0 -573 0 -580 20 -580 20 0 20 7 20
|
||||
580 l0 580 570 0 570 0 0 -580 c0 -573 0 -580 20 -580 20 0 20 7 20 580 l0
|
||||
580 570 0 570 0 0 -580 c0 -573 0 -580 20 -580 20 0 20 7 20 580 l0 580 575 0
|
||||
575 0 0 -580 c0 -509 2 -580 15 -580 13 0 15 71 15 580 l0 580 575 0 575 0 0
|
||||
-580 c0 -509 2 -580 15 -580 13 0 15 71 15 580 l0 580 575 0 575 0 0 -580 c0
|
||||
-509 2 -580 15 -580 13 0 15 71 15 580 l0 580 575 0 575 0 0 -580 c0 -509 2
|
||||
-580 15 -580 13 0 15 71 15 580 l0 580 575 0 575 0 0 -580 c0 -573 0 -580 20
|
||||
-580 20 0 20 7 20 580 l0 580 570 0 570 0 0 -580 c0 -573 0 -580 20 -580 20 0
|
||||
20 7 20 580 l0 580 570 0 570 0 0 -580 c0 -573 0 -580 20 -580 20 0 20 7 20
|
||||
580 l0 580 570 0 570 0 0 -580 c0 -573 0 -580 20 -580 20 0 20 7 20 580 l0
|
||||
580 575 0 575 0 0 -580 c0 -509 2 -580 15 -580 13 0 15 71 15 580 l0 580 575
|
||||
0 575 0 0 -580 c0 -509 2 -580 15 -580 13 0 15 71 15 580 l0 580 575 0 575 0
|
||||
0 -580 c0 -509 2 -580 15 -580 13 0 15 71 15 580 l0 580 575 0 575 0 0 -580
|
||||
c0 -509 2 -580 15 -580 13 0 15 71 15 580 l0 580 575 0 575 0 0 -580 c0 -573
|
||||
0 -580 20 -580 20 0 20 7 20 580 l0 580 580 0 c573 0 580 0 580 20 0 20 -7 20
|
||||
-580 20 l-580 0 0 570 0 570 580 0 c573 0 580 0 580 20 0 20 -7 20 -580 20
|
||||
l-580 0 0 575 0 575 580 0 c509 0 580 2 580 15 0 13 -71 15 -580 15 l-580 0 0
|
||||
575 0 575 580 0 c509 0 580 2 580 15 0 13 -71 15 -580 15 l-580 0 0 575 0 575
|
||||
580 0 c509 0 580 2 580 15 0 13 -71 15 -580 15 l-580 0 0 575 0 575 580 0
|
||||
c509 0 580 2 580 15 0 13 -71 15 -580 15 l-580 0 0 575 0 575 580 0 c573 0
|
||||
580 0 580 20 0 20 -7 20 -580 20 l-580 0 0 570 0 570 580 0 c573 0 580 0 580
|
||||
20 0 20 -7 20 -580 20 l-580 0 0 570 0 570 580 0 c573 0 580 0 580 20 0 20 -7
|
||||
20 -580 20 l-580 0 0 570 0 570 580 0 c573 0 580 0 580 20 0 20 -7 20 -580 20
|
||||
l-580 0 0 575 0 575 580 0 c509 0 580 2 580 15 0 13 -71 15 -580 15 l-580 0 0
|
||||
575 0 575 580 0 c509 0 580 2 580 15 0 13 -71 15 -580 15 l-580 0 0 575 0 575
|
||||
580 0 c509 0 580 2 580 15 0 13 -71 15 -580 15 l-580 0 0 575 0 575 580 0
|
||||
c509 0 580 2 580 15 0 13 -71 15 -580 15 l-580 0 0 575 0 575 580 0 c573 0
|
||||
580 0 580 20 0 20 -7 20 -580 20 l-580 0 0 570 0 570 580 0 c573 0 580 0 580
|
||||
20 0 20 -7 20 -580 20 l-580 0 0 570 0 570 580 0 c573 0 580 0 580 20 0 20 -7
|
||||
20 -580 20 l-580 0 0 570 0 570 580 0 c573 0 580 0 580 20 0 20 -7 20 -580 20
|
||||
l-580 0 0 575 0 575 580 0 c509 0 580 2 580 15 0 13 -71 15 -580 15 l-580 0 0
|
||||
575 0 575 580 0 c509 0 580 2 580 15 0 13 -71 15 -580 15 l-580 0 0 575 0 575
|
||||
580 0 c509 0 580 2 580 15 0 13 -71 15 -580 15 l-580 0 0 575 0 575 580 0
|
||||
c509 0 580 2 580 15 0 13 -71 15 -580 15 l-580 0 0 575 0 575 580 0 c573 0
|
||||
580 0 580 20 0 20 -7 20 -580 20 l-580 0 0 570 0 570 580 0 c573 0 580 0 580
|
||||
20 0 20 -7 20 -580 20 l-580 0 0 580 c0 573 0 580 -20 580 -20 0 -20 -7 -20
|
||||
-580 l0 -580 -575 0 -575 0 0 580 c0 509 -2 580 -15 580 -13 0 -15 -71 -15
|
||||
-580 l0 -580 -575 0 -575 0 0 580 c0 509 -2 580 -15 580 -13 0 -15 -71 -15
|
||||
-580 l0 -580 -575 0 -575 0 0 580 c0 509 -2 580 -15 580 -13 0 -15 -71 -15
|
||||
-580 l0 -580 -575 0 -575 0 0 580 c0 509 -2 580 -15 580 -13 0 -15 -71 -15
|
||||
-580 l0 -580 -575 0 -575 0 0 580 c0 509 -2 580 -15 580 -13 0 -15 -71 -15
|
||||
-580 l0 -580 -575 0 -575 0 0 580 c0 573 0 580 -20 580 -20 0 -20 -7 -20 -580
|
||||
l0 -580 -570 0 -570 0 0 580 c0 573 0 580 -20 580 -20 0 -20 -7 -20 -580 l0
|
||||
-580 -570 0 -570 0 0 580 c0 573 0 580 -20 580 -20 0 -20 -7 -20 -580 l0 -580
|
||||
-575 0 -575 0 0 580 c0 509 -2 580 -15 580 -13 0 -15 -71 -15 -580 l0 -580
|
||||
-575 0 -575 0 0 580 c0 509 -2 580 -15 580 -13 0 -15 -71 -15 -580 l0 -580
|
||||
-575 0 -575 0 0 580 c0 509 -2 580 -15 580 -13 0 -15 -71 -15 -580 l0 -580
|
||||
-575 0 -575 0 0 580 c0 509 -2 580 -15 580 -13 0 -15 -71 -15 -580 l0 -580
|
||||
-575 0 -575 0 0 580 c0 573 0 580 -20 580 -20 0 -20 -7 -20 -580 l0 -580 -570
|
||||
0 -570 0 0 580 c0 573 0 580 -20 580 -20 0 -20 -7 -20 -580 l0 -580 -570 0
|
||||
-570 0 0 580 c0 573 0 580 -20 580 -20 0 -20 -7 -20 -580 l0 -580 -570 0 -570
|
||||
0 0 580 c0 573 0 580 -20 580 -20 0 -20 -7 -20 -580 l0 -580 -575 0 -575 0 0
|
||||
580 c0 509 -2 580 -15 580 -13 0 -15 -71 -15 -580 l0 -580 -575 0 -575 0 0
|
||||
580 c0 509 -2 580 -15 580 -13 0 -15 -71 -15 -580 l0 -580 -575 0 -575 0 0
|
||||
580 c0 509 -2 580 -15 580 -13 0 -15 -71 -15 -580 l0 -580 -575 0 -575 0 0
|
||||
580 c0 509 -2 580 -15 580 -13 0 -15 -71 -15 -580 l0 -580 -575 0 -575 0 0
|
||||
580 c0 573 0 580 -20 580 -20 0 -20 -7 -20 -580z m1190 -1190 l0 -570 -575 0
|
||||
-575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570
|
||||
0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0
|
||||
575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z
|
||||
m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0
|
||||
-570 -570 0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570 0
|
||||
-570 0 0 570 0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0 570
|
||||
0 570 570 0 570 0 0 -570z m1190 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0
|
||||
575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z
|
||||
m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0
|
||||
-570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0
|
||||
-575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0 570
|
||||
0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0 570 0 570 570 0
|
||||
570 0 0 -570z m1190 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z
|
||||
m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0
|
||||
-570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0
|
||||
-575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570
|
||||
0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0
|
||||
575 0 0 -570z m-23620 -1185 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570
|
||||
0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0
|
||||
l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m-23620 -1180 l0 -575
|
||||
-575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0
|
||||
0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575
|
||||
575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570
|
||||
0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0
|
||||
575 0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0
|
||||
575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570
|
||||
0 570 0 0 -575z m1190 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m-23620 -1180 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0
|
||||
0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180
|
||||
0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575
|
||||
-575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0
|
||||
0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575
|
||||
570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0
|
||||
l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m-23620 -1180 l0 -575
|
||||
-575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0
|
||||
0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575
|
||||
575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570
|
||||
0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0
|
||||
575 0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0
|
||||
575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570
|
||||
0 570 0 0 -575z m1190 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m-23620 -1180 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0
|
||||
0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180
|
||||
0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575
|
||||
-575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0
|
||||
0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575
|
||||
570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0
|
||||
l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m-23620 -1185 l0 -570
|
||||
-575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0
|
||||
0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570
|
||||
575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0
|
||||
l0 -570 -570 0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570
|
||||
0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0
|
||||
570 0 570 570 0 570 0 0 -570z m1190 0 l0 -570 -575 0 -575 0 0 570 0 570 575
|
||||
0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0
|
||||
l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575
|
||||
0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0
|
||||
570 0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0 570 0 570 570
|
||||
0 570 0 0 -570z m1190 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0
|
||||
l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575
|
||||
0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0
|
||||
570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575
|
||||
0 575 0 0 -570z m-23620 -1180 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0
|
||||
0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180
|
||||
0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570
|
||||
-575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0
|
||||
0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0 570 0 570
|
||||
570 0 570 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0 570 0 570 570 0 570 0 0
|
||||
-570z m1180 0 l0 -570 -570 0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1190 0
|
||||
l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575
|
||||
0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0
|
||||
570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575
|
||||
0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -570 0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1180 0
|
||||
l0 -570 -570 0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1190 0 l0 -570 -575
|
||||
0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0
|
||||
570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575
|
||||
0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0
|
||||
l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m-23620 -1180 l0 -570
|
||||
-575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0
|
||||
0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570
|
||||
575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0
|
||||
l0 -570 -570 0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570
|
||||
0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0
|
||||
570 0 570 570 0 570 0 0 -570z m1190 0 l0 -570 -575 0 -575 0 0 570 0 570 575
|
||||
0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0
|
||||
l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575
|
||||
0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0
|
||||
570 0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0 570 0 570 570
|
||||
0 570 0 0 -570z m1190 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0
|
||||
l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575
|
||||
0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0
|
||||
570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575
|
||||
0 575 0 0 -570z m-23620 -1185 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0
|
||||
0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180
|
||||
0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575
|
||||
-575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0
|
||||
0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575
|
||||
570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0
|
||||
l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m-23620 -1180 l0 -575
|
||||
-575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0
|
||||
0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575
|
||||
575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570
|
||||
0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0
|
||||
575 0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0
|
||||
575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570
|
||||
0 570 0 0 -575z m1190 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m-23620 -1180 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0
|
||||
0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180
|
||||
0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575
|
||||
-575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0
|
||||
0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575
|
||||
570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0
|
||||
l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m-23620 -1180 l0 -575
|
||||
-575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0
|
||||
0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575
|
||||
575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570
|
||||
0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0
|
||||
575 0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0
|
||||
575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570
|
||||
0 570 0 0 -575z m1190 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m-23620 -1180 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0
|
||||
0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180
|
||||
0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575
|
||||
-575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0
|
||||
0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575
|
||||
570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0
|
||||
l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m-23620 -1185 l0 -570
|
||||
-575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0
|
||||
0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570
|
||||
575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0
|
||||
l0 -570 -570 0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570
|
||||
0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0
|
||||
570 0 570 570 0 570 0 0 -570z m1190 0 l0 -570 -575 0 -575 0 0 570 0 570 575
|
||||
0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0
|
||||
l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575
|
||||
0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0
|
||||
570 0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0 570 0 570 570
|
||||
0 570 0 0 -570z m1190 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0
|
||||
l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575
|
||||
0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0
|
||||
570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575
|
||||
0 575 0 0 -570z m-23620 -1180 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0
|
||||
0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180
|
||||
0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570
|
||||
-575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0
|
||||
0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0 570 0 570
|
||||
570 0 570 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0 570 0 570 570 0 570 0 0
|
||||
-570z m1180 0 l0 -570 -570 0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1190 0
|
||||
l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575
|
||||
0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0
|
||||
570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575
|
||||
0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -570 0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1180 0
|
||||
l0 -570 -570 0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1190 0 l0 -570 -575
|
||||
0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0
|
||||
570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575
|
||||
0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0
|
||||
l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m-23620 -1180 l0 -570
|
||||
-575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0
|
||||
0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570
|
||||
575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0
|
||||
l0 -570 -570 0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570
|
||||
0 -570 0 0 570 0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0
|
||||
570 0 570 570 0 570 0 0 -570z m1190 0 l0 -570 -575 0 -575 0 0 570 0 570 575
|
||||
0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0
|
||||
l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575
|
||||
0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0
|
||||
570 0 570 570 0 570 0 0 -570z m1180 0 l0 -570 -570 0 -570 0 0 570 0 570 570
|
||||
0 570 0 0 -570z m1190 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0
|
||||
-570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0
|
||||
l0 -570 -575 0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575
|
||||
0 -575 0 0 570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0
|
||||
570 0 570 575 0 575 0 0 -570z m1180 0 l0 -570 -575 0 -575 0 0 570 0 570 575
|
||||
0 575 0 0 -570z m-23620 -1185 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0
|
||||
0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180
|
||||
0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575
|
||||
-575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0
|
||||
0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575
|
||||
570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0
|
||||
l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m-23620 -1180 l0 -575
|
||||
-575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0
|
||||
0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575
|
||||
575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570
|
||||
0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0
|
||||
575 0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0
|
||||
575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570
|
||||
0 570 0 0 -575z m1190 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m-23620 -1180 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0
|
||||
0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180
|
||||
0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575
|
||||
-575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0
|
||||
0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575
|
||||
570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0
|
||||
l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m-23620 -1180 l0 -575
|
||||
-575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0
|
||||
0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575
|
||||
575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570
|
||||
0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0
|
||||
575 0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0
|
||||
575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570
|
||||
0 570 0 0 -575z m1190 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0
|
||||
-575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575
|
||||
0 575 0 0 -575z m-23620 -1180 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0
|
||||
0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180
|
||||
0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575
|
||||
-575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0
|
||||
0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575
|
||||
570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0
|
||||
-575z m1180 0 l0 -575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1190 0
|
||||
l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575
|
||||
0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0
|
||||
575 0 575 575 0 575 0 0 -575z m11810 -590 l0 -1165 -4705 0 c-4176 0 -4705 2
|
||||
-4705 15 0 8 -9 15 -20 15 -11 0 -20 -7 -20 -15 0 -13 -71 -15 -575 -15 -504
|
||||
0 -575 2 -575 15 0 8 -7 15 -15 15 -8 0 -15 -7 -15 -15 0 -13 -71 -15 -575
|
||||
-15 l-575 0 0 575 c0 377 3 575 10 575 6 0 10 7 10 15 0 8 -4 15 -10 15 -7 0
|
||||
-10 198 -10 575 l0 575 5890 0 5890 0 0 -1165z m-23620 -590 l0 -575 -575 0
|
||||
-575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575
|
||||
0 575 575 0 575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0
|
||||
575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z
|
||||
m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z m1180 0 l0
|
||||
-575 -570 0 -570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570 0
|
||||
-570 0 0 575 0 575 570 0 570 0 0 -575z m1180 0 l0 -575 -570 0 -570 0 0 575
|
||||
0 575 570 0 570 0 0 -575z m1190 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0
|
||||
575 0 0 -575z m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z
|
||||
m1180 0 l0 -575 -575 0 -575 0 0 575 0 575 575 0 575 0 0 -575z"/>
|
||||
</g>
|
||||
</svg>
|
After Width: | Height: | Size: 35 KiB |
BIN
resources/profiles/Infinity3D/DEV_350_bed.stl
Normal file
BIN
resources/profiles/Infinity3D/DEV_350_bed.stl
Normal file
Binary file not shown.
589
resources/profiles/Infinity3D/DEV_350_texture.svg
Normal file
589
resources/profiles/Infinity3D/DEV_350_texture.svg
Normal file
@ -0,0 +1,589 @@
|
||||
<?xml version="1.0" standalone="no"?>
|
||||
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 20010904//EN"
|
||||
"http://www.w3.org/TR/2001/REC-SVG-20010904/DTD/svg10.dtd">
|
||||
<svg version="1.0" xmlns="http://www.w3.org/2000/svg"
|
||||
width="3780.000000pt" height="4134.000000pt" viewBox="0 0 3780.000000 4134.000000"
|
||||
preserveAspectRatio="xMidYMid meet">
|
||||
|
||||
<g transform="translate(0.000000,4134.000000) scale(0.100000,-0.100000)"
|
||||
fill="#000000" stroke="none">
|
||||
<path d="M1618 40273 l-3 -808 -807 -3 c-799 -2 -808 -2 -808 -22 0 -20 9 -20
|
||||
808 -22 l807 -3 0 -795 0 -795 -808 -3 -807 -2 0 -25 0 -25 810 0 810 0 -2
|
||||
-797 -3 -798 -805 -2 c-800 -2 -805 -3 -808 -23 -3 -20 -1 -20 807 -20 l811 0
|
||||
-2 -797 -3 -798 -807 -3 c-800 -2 -808 -2 -808 -22 0 -20 7 -20 810 -20 l810
|
||||
0 0 -800 0 -800 -810 0 -810 0 0 -25 0 -25 810 0 810 0 0 -795 0 -795 -810 0
|
||||
-810 0 0 -25 0 -25 810 0 810 0 -2 -797 -3 -798 -808 -3 c-798 -2 -807 -2
|
||||
-807 -22 0 -20 9 -20 807 -22 l808 -3 0 -795 0 -795 -808 -3 c-805 -2 -808 -2
|
||||
-805 -22 3 -20 9 -21 808 -23 l805 -2 3 -797 2 -798 -810 0 -810 0 0 -25 0
|
||||
-25 810 0 810 0 -2 -797 -3 -798 -807 -3 c-799 -2 -808 -2 -808 -22 0 -20 9
|
||||
-20 808 -22 l807 -3 3 -797 2 -798 -810 0 -810 0 0 -25 0 -25 810 0 810 0 0
|
||||
-795 0 -795 -810 0 -810 0 0 -25 0 -25 810 0 810 0 0 -800 0 -800 -810 0
|
||||
c-803 0 -810 0 -810 -20 0 -20 8 -20 808 -22 l807 -3 3 -797 2 -798 -810 0
|
||||
c-803 0 -810 0 -810 -20 0 -20 8 -20 807 -22 l808 -3 3 -797 2 -798 -810 0
|
||||
-810 0 0 -25 0 -25 808 -2 807 -3 0 -795 0 -795 -808 -3 c-798 -2 -807 -2
|
||||
-807 -22 0 -20 9 -20 808 -22 l807 -3 3 -797 2 -798 -810 0 -810 0 0 -25 0
|
||||
-25 810 0 810 0 0 -795 0 -795 -810 0 -810 0 0 -25 0 -25 810 0 810 0 0 -800
|
||||
0 -800 -810 0 c-803 0 -810 0 -810 -20 0 -20 8 -20 808 -22 l807 -3 3 -797 2
|
||||
-798 -810 0 -810 0 0 -25 0 -25 810 0 810 0 -2 -797 -3 -798 -808 -3 c-799 -2
|
||||
-807 -2 -807 -22 0 -20 7 -20 810 -20 l810 0 -2 -797 -3 -798 -807 -3 c-799
|
||||
-2 -808 -2 -808 -22 0 -20 9 -20 807 -22 l808 -3 0 -800 0 -800 -807 -3 c-709
|
||||
-2 -808 -4 -808 -17 0 -13 98 -15 810 -15 l810 0 0 -800 0 -800 -810 0 -810 0
|
||||
0 -25 0 -25 810 0 810 0 0 -810 0 -810 25 0 25 0 0 808 0 807 795 0 795 0 0
|
||||
-807 0 -808 25 0 25 0 0 810 0 810 798 -2 797 -3 3 -807 c2 -800 2 -808 22
|
||||
-808 20 0 20 7 20 810 l0 810 800 0 800 0 0 -810 0 -810 25 0 25 0 0 808 0
|
||||
807 795 3 795 2 0 -810 0 -810 25 0 25 0 0 810 0 810 798 -2 797 -3 3 -807 c2
|
||||
-799 2 -808 22 -808 20 0 20 9 22 808 l3 807 798 3 797 2 0 -811 c0 -808 0
|
||||
-810 20 -807 20 3 21 8 23 808 l2 805 798 3 797 2 0 -810 0 -810 25 0 25 0 0
|
||||
810 0 810 798 -2 797 -3 3 -807 c2 -799 2 -808 22 -808 20 0 20 9 22 807 l3
|
||||
808 798 3 797 2 0 -810 0 -810 25 0 25 0 0 810 0 810 795 0 795 0 0 -810 0
|
||||
-810 25 0 25 0 0 810 0 810 800 0 800 0 0 -810 c0 -803 0 -810 20 -810 20 0
|
||||
20 8 22 808 l3 807 798 3 797 2 0 -810 c0 -803 0 -810 20 -810 20 0 20 8 22
|
||||
807 l3 808 798 3 797 2 0 -810 0 -810 25 0 25 0 0 810 0 810 798 -2 797 -3 2
|
||||
-805 c2 -799 3 -805 23 -808 20 -3 20 0 22 805 l3 808 798 3 797 2 0 -810 0
|
||||
-810 25 0 25 0 0 810 0 810 795 0 795 0 0 -810 0 -810 25 0 25 0 0 810 0 810
|
||||
800 0 800 0 0 -810 c0 -803 0 -810 20 -810 20 0 20 8 22 808 l3 807 798 3 797
|
||||
2 0 -810 0 -810 25 0 25 0 0 810 0 810 798 -2 797 -3 3 -807 c2 -800 2 -808
|
||||
22 -808 20 0 20 7 20 810 l0 810 798 -2 797 -3 3 -807 c2 -800 2 -808 22 -808
|
||||
20 0 20 7 20 810 l0 810 800 0 800 0 0 -810 0 -810 25 0 25 0 0 810 0 810 811
|
||||
0 810 0 -3 22 -3 23 -807 3 -808 2 0 795 0 795 808 2 807 3 3 23 3 22 -810 0
|
||||
-811 0 0 800 0 800 810 0 c803 0 810 0 810 20 0 20 -7 20 -810 20 l-810 0 0
|
||||
800 0 800 811 0 c808 0 810 0 807 20 -3 20 -8 21 -808 23 l-805 2 -3 797 -2
|
||||
798 807 2 808 3 3 23 3 22 -810 0 -811 0 2 798 3 797 808 3 c799 2 807 2 807
|
||||
22 0 20 -7 20 -810 20 l-810 0 0 800 0 800 811 0 810 0 -3 23 -3 22 -807 3
|
||||
-808 2 0 795 0 795 811 0 810 0 -3 23 -3 22 -807 3 -808 2 0 800 0 800 810 0
|
||||
c803 0 810 0 810 20 0 20 -8 20 -807 22 l-808 3 -3 798 -2 797 811 0 810 0 -3
|
||||
23 -3 22 -808 3 -807 2 2 798 3 797 805 2 c800 2 805 3 808 23 3 20 1 20 -807
|
||||
20 l-811 0 0 800 0 800 810 0 c803 0 810 0 810 20 0 20 -7 20 -810 20 l-810 0
|
||||
0 800 0 800 811 0 810 0 -3 23 -3 22 -807 3 -808 2 0 795 0 795 808 2 c799 3
|
||||
807 3 807 23 0 20 -8 20 -807 23 l-808 2 0 800 0 800 810 0 c803 0 810 0 810
|
||||
20 0 20 -8 20 -807 22 l-808 3 -3 798 -2 797 811 0 810 0 -3 23 -3 22 -805 2
|
||||
-805 3 0 797 0 798 805 2 c800 2 805 3 808 23 3 20 1 20 -807 20 l-811 0 2
|
||||
798 3 797 808 3 c799 2 807 2 807 22 0 20 -7 20 -810 20 l-810 0 0 800 0 800
|
||||
808 2 807 3 3 23 3 22 -810 0 -811 0 2 795 3 795 805 3 805 2 3 23 3 22 -810
|
||||
0 -811 0 0 800 0 800 810 0 c803 0 810 0 810 20 0 20 -7 20 -810 20 l-810 0 0
|
||||
800 0 800 811 0 c808 0 810 0 807 20 -3 20 -8 21 -808 23 l-805 2 0 798 0 797
|
||||
805 3 805 2 3 23 3 22 -810 0 -811 0 2 798 3 797 808 3 c799 2 807 2 807 22 0
|
||||
20 -7 20 -810 20 l-810 0 0 810 0 810 -25 0 -25 0 0 -810 0 -810 -797 2 -798
|
||||
3 -3 808 c-2 798 -2 807 -22 807 -20 0 -20 -9 -22 -807 l-3 -808 -797 -3 -798
|
||||
-2 0 810 c0 803 0 810 -20 810 -20 0 -20 -8 -22 -807 l-3 -808 -797 -3 -798
|
||||
-2 0 810 0 810 -25 0 -25 0 0 -810 0 -810 -797 2 -798 3 -3 808 c-2 798 -2
|
||||
807 -22 807 -20 0 -20 -9 -22 -807 l-3 -808 -797 -3 -798 -2 0 810 c0 803 0
|
||||
810 -20 810 -20 0 -20 -8 -22 -807 l-3 -808 -800 0 -800 0 -3 808 c-2 798 -2
|
||||
807 -22 807 -20 0 -20 -9 -22 -807 l-3 -808 -795 0 -795 0 -3 808 c-2 798 -2
|
||||
807 -22 807 -20 0 -20 -9 -22 -807 l-3 -808 -795 0 -795 0 -3 808 -2 807 -25
|
||||
0 -25 0 0 -810 0 -810 -797 2 -798 3 -3 808 c-2 799 -2 807 -22 807 -20 0 -20
|
||||
-7 -20 -810 l0 -810 -797 2 -798 3 -3 808 c-2 798 -2 807 -22 807 -20 0 -20
|
||||
-9 -22 -807 l-3 -808 -797 -3 -798 -2 0 810 0 810 -25 0 -25 0 0 -810 0 -810
|
||||
-795 0 -795 0 0 810 0 810 -25 0 -25 0 0 -810 0 -810 -797 2 -798 3 -3 808
|
||||
c-2 798 -2 807 -22 807 -20 0 -20 -9 -22 -807 l-3 -808 -795 0 -795 0 -3 808
|
||||
-2 807 -25 0 -25 0 0 -810 0 -810 -797 2 -798 3 0 808 0 807 -22 0 -23 0 -2
|
||||
-807 -3 -808 -795 0 -795 0 -3 808 c-2 798 -2 807 -22 807 -20 0 -20 -9 -22
|
||||
-807 l-3 -808 -797 -3 -798 -2 0 810 0 810 -25 0 -25 0 0 -810 0 -810 -795 0
|
||||
c-629 0 -795 3 -795 13 0 6 0 371 0 810 l0 797 -25 0 -25 0 0 -810 0 -810
|
||||
-800 0 -800 0 0 810 c0 803 0 810 -20 810 -20 0 -20 -8 -22 -807 l-3 -808
|
||||
-797 -3 -798 -2 0 810 0 810 -25 0 -25 0 0 -797 c0 -439 0 -804 0 -810 0 -10
|
||||
-166 -13 -795 -13 -629 0 -795 3 -795 13 0 6 0 371 0 810 l0 797 -25 0 -25 0
|
||||
-2 -807z m1642 -1648 c0 -434 0 -793 0 -797 0 -5 -358 -8 -795 -8 -437 0 -795
|
||||
3 -795 8 0 22 0 1578 0 1585 0 4 358 6 795 5 l795 -3 0 -790z m1645 -5 l0
|
||||
-795 -797 -3 -798 -2 0 800 0 800 798 -2 797 -3 0 -795z m1645 0 l0 -800 -800
|
||||
0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793 0 0 -800z m1640 0 l0
|
||||
-800 -795 0 c-523 0 -795 3 -795 10 0 6 0 363 0 795 0 432 0 787 0 790 0 3
|
||||
358 5 795 5 l795 0 0 -800z m1645 0 l0 -795 -797 -3 -798 -2 0 800 0 800 798
|
||||
-2 797 -3 0 -795z m1640 0 l0 -795 -795 0 -795 0 -3 785 c-1 432 0 791 3 798
|
||||
3 10 168 12 797 10 l793 -3 0 -795z m1645 0 l0 -800 -797 2 -798 3 -3 785 c-1
|
||||
432 0 791 3 798 3 9 173 12 800 12 l795 0 0 -800z m1645 0 l0 -795 -797 -3
|
||||
-798 -2 0 793 c0 437 3 797 7 800 3 4 362 6 797 5 l791 -3 0 -795z m1645 0 l0
|
||||
-800 -797 2 -798 3 -3 785 c-1 432 0 791 3 798 3 9 173 12 800 12 l795 0 0
|
||||
-800z m1640 0 l0 -800 -795 0 -795 0 0 800 0 800 795 0 795 0 0 -800z m1648
|
||||
-2 l2 -798 -800 0 -800 0 0 800 0 800 798 -2 797 -3 3 -797z m1640 -1 l2 -797
|
||||
-797 2 -798 3 -3 785 c-1 432 0 791 3 798 3 10 168 12 797 10 l793 -3 3 -798z
|
||||
m1642 3 l0 -800 -797 2 -798 3 -3 785 c-1 432 0 791 3 798 3 9 173 12 800 12
|
||||
l795 0 0 -800z m1648 -3 l2 -797 -797 2 -798 3 -3 785 c-1 432 0 791 3 798 3
|
||||
10 168 12 797 10 l793 -3 3 -798z m1640 0 l2 -797 -797 2 -798 3 -3 785 c-1
|
||||
432 0 791 3 798 3 10 168 12 797 10 l793 -3 3 -798z m1647 3 l0 -795 -800 0
|
||||
-800 0 -3 785 c-1 432 0 791 3 798 3 10 169 12 802 10 l798 -3 0 -795z m1643
|
||||
-2 l2 -798 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 362 6 797 5 l791 -3 3
|
||||
-797z m1642 2 l0 -800 -797 2 -798 3 -3 785 c-1 432 0 791 3 798 3 9 173 12
|
||||
800 12 l795 0 0 -800z m1645 0 l0 -795 -797 -3 -798 -2 0 800 0 800 798 -2
|
||||
797 -3 0 -795z m1643 -2 l2 -798 -800 0 -800 0 0 800 0 800 798 -2 797 -3 3
|
||||
-797z m1640 -1 l2 -797 -797 2 -798 3 -3 785 c-1 432 0 791 3 798 3 10 168 12
|
||||
797 10 l793 -3 3 -798z m-31218 -1642 l0 -795 -22 -5 c-13 -3 -372 -4 -798 -3
|
||||
l-775 3 -3 790 c-1 435 0 795 2 800 2 7 276 9 800 7 l796 -2 0 -795z m1635 -2
|
||||
l0 -798 -795 0 -795 0 -3 790 c-1 435 0 795 2 800 2 7 275 9 797 8 l794 -3 0
|
||||
-797z m1645 -4 l0 -799 -789 0 c-473 0 -792 4 -796 9 -3 5 -5 364 -5 798 l0
|
||||
788 787 5 c434 3 791 4 796 2 4 -2 7 -363 7 -803z m1648 0 l-3 -794 -795 0
|
||||
-795 0 -3 797 -2 798 792 2 c436 2 796 0 801 -3 4 -3 6 -363 5 -800z m1637 4
|
||||
l0 -798 -775 -3 c-426 -1 -785 0 -797 3 l-23 5 0 794 c0 521 3 795 10 798 5 2
|
||||
364 2 797 1 l788 -3 0 -797z m1640 0 l0 -798 -784 -3 c-571 -1 -787 1 -797 9
|
||||
-12 10 -14 147 -14 799 0 517 3 789 10 792 5 2 364 2 797 1 l788 -3 0 -797z
|
||||
m1648 797 c4 0 7 -358 7 -795 l0 -795 -22 -5 c-13 -3 -372 -4 -798 -3 l-775 3
|
||||
-3 790 c-1 435 0 795 2 800 3 8 901 11 1589 5z m1645 -798 l-3 -797 -795 0
|
||||
-795 0 -3 790 c-1 435 0 795 2 800 2 7 276 9 800 7 l796 -2 -2 -798z m1640 0
|
||||
l-3 -797 -792 -3 -793 -2 0 802 0 803 795 -3 795 -2 -2 -798z m1647 1 l0 -798
|
||||
-797 -3 -798 -2 0 798 c0 439 2 801 4 803 2 2 361 3 798 2 l793 -3 0 -797z
|
||||
m1643 -4 l-3 -794 -775 -3 c-426 -1 -785 0 -797 3 l-23 5 0 795 0 795 793 2
|
||||
c435 2 795 0 800 -3 4 -3 6 -363 5 -800z m1640 0 l-3 -794 -775 -3 c-426 -1
|
||||
-785 0 -797 3 l-23 5 0 795 0 795 793 2 c435 2 795 0 800 -3 4 -3 6 -363 5
|
||||
-800z m3290 0 l-3 -794 -795 0 -795 0 -3 797 -2 798 792 2 c436 2 796 0 801
|
||||
-3 4 -3 6 -363 5 -800z m1652 7 c0 -715 -2 -794 -16 -800 -20 -8 -1558 -8
|
||||
-1578 0 -14 6 -16 85 -16 799 0 520 3 794 10 797 5 2 368 2 805 0 l795 -2 0
|
||||
-794z m1640 -1 l0 -795 -22 -5 c-13 -3 -372 -4 -798 -3 l-775 3 -3 790 c-1
|
||||
435 0 795 2 800 2 7 276 9 800 7 l796 -2 0 -795z m1640 -3 l0 -802 -797 2
|
||||
-798 3 -3 790 c-1 435 0 795 2 800 2 7 278 10 800 10 l796 0 0 -803z m1648 21
|
||||
c1 -428 0 -788 -3 -800 l-5 -23 -795 0 -795 0 0 803 0 802 797 -2 798 -3 3
|
||||
-777z m1637 -20 l0 -798 -797 -3 -798 -2 0 802 0 803 797 -2 798 -3 0 -797z
|
||||
m1643 -4 l-3 -794 -775 -3 c-426 -1 -785 0 -797 3 l-23 5 0 795 0 795 793 2
|
||||
c435 2 795 0 800 -3 4 -3 6 -363 5 -800z m-32865 10 c-2 -435 -5 -795 -9 -800
|
||||
-6 -11 -1584 -13 -1584 -1 0 4 -1 364 -3 800 l-2 792 800 0 800 0 -2 -791z
|
||||
m21365 -6 l-3 -798 -795 0 -795 0 -3 798 -2 797 800 0 800 0 -2 -797z m-21368
|
||||
-1635 c0 -434 0 -792 0 -798 0 -7 -272 -10 -795 -10 -523 0 -795 3 -795 10 0
|
||||
6 0 363 0 795 0 432 0 787 0 790 0 3 358 4 795 3 l795 -3 0 -787z m1648 -5
|
||||
l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800 0 -2 -797z m1642 -3 l0 -800
|
||||
-797 2 -798 3 -3 798 -2 797 800 0 800 0 0 -800z m1640 0 l0 -800 -795 0
|
||||
c-523 0 -795 3 -795 10 0 6 0 363 0 795 0 432 0 787 0 790 0 3 358 5 795 5
|
||||
l795 0 0 -800z m1648 3 l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800 0 -2
|
||||
-797z m1640 0 l-3 -798 -795 0 -795 0 -3 798 -2 797 800 0 800 0 -2 -797z
|
||||
m1643 793 c2 -2 3 -362 1 -800 l-2 -796 -794 0 c-715 0 -794 2 -800 16 -8 21
|
||||
-8 1569 1 1577 7 7 1587 10 1594 3z m1647 -793 l-3 -798 -795 0 -795 0 -3 798
|
||||
-2 797 800 0 800 0 -2 -797z m1642 -3 l0 -800 -797 2 -798 3 -3 798 -2 797
|
||||
800 0 800 0 0 -800z m1640 0 l0 -800 -795 0 -795 0 0 800 0 800 795 0 795 0 0
|
||||
-800z m1648 3 l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800 0 -2 -797z
|
||||
m1642 -3 l0 -800 -797 2 -798 3 -3 798 -2 797 800 0 800 0 0 -800z m1640 0 l0
|
||||
-800 -797 2 -798 3 -3 798 -2 797 800 0 800 0 0 -800z m1648 3 l-3 -798 -795
|
||||
0 -795 0 -3 798 -2 797 800 0 800 0 -2 -797z m1640 0 l-3 -798 -795 0 -795 0
|
||||
-3 798 -2 797 800 0 800 0 -2 -797z m1650 0 l-3 -798 -800 0 -800 0 -3 798 -2
|
||||
797 805 0 805 0 -2 -797z m1640 0 l-3 -798 -795 0 -795 0 -3 798 -2 797 800 0
|
||||
800 0 -2 -797z m1642 -3 l0 -800 -797 2 -798 3 -3 798 -2 797 800 0 800 0 0
|
||||
-800z m1648 20 c1 -426 0 -785 -3 -797 l-5 -23 -795 0 -795 0 0 800 0 800 798
|
||||
-2 797 -3 3 -775z m1640 -17 l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800
|
||||
0 -2 -797z m1642 -3 l0 -800 -797 2 -798 3 -3 798 -2 797 800 0 800 0 0 -800z
|
||||
m-32870 -1640 l0 -795 -795 0 -795 0 0 793 c0 435 0 794 0 797 0 3 358 4 795
|
||||
3 l795 -3 0 -795z m1648 -2 l2 -798 -800 0 -800 0 0 800 0 800 798 -2 797 -3
|
||||
3 -797z m1642 2 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z m1640
|
||||
0 l0 -800 -795 2 -795 3 0 793 c0 435 0 794 0 797 0 3 358 5 795 5 l795 0 0
|
||||
-800z m1648 -2 l2 -798 -800 0 -800 0 0 800 0 800 798 -2 797 -3 3 -797z
|
||||
m1642 2 l0 -800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793
|
||||
0 0 -800z m1641 796 c2 -2 3 -362 1 -800 l-2 -796 -798 2 -797 3 -3 785 c-1
|
||||
432 0 791 3 798 3 9 172 12 798 12 437 0 796 -2 798 -4z m1647 -798 l2 -798
|
||||
-800 0 -800 0 0 800 0 800 798 -2 797 -3 3 -797z m1642 2 l0 -800 -800 0 -800
|
||||
0 0 800 0 800 800 0 800 0 0 -800z m1640 0 l0 -800 -795 0 -795 0 0 800 0 800
|
||||
795 0 795 0 0 -800z m1650 0 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0
|
||||
-800z m1640 0 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z m1640 0
|
||||
l0 -800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793 0 0
|
||||
-800z m1650 0 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z m1640 0
|
||||
l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z m1650 0 l0 -800 -805
|
||||
0 -805 0 0 793 c0 437 3 797 7 800 3 4 366 7 805 7 l798 0 0 -800z m1640 0 l0
|
||||
-800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z m1640 0 l0 -800 -800 0
|
||||
-800 0 0 800 0 800 800 0 800 0 0 -800z m1645 0 l0 -795 -797 -3 -798 -2 0
|
||||
800 0 800 798 -2 797 -3 0 -795z m1645 0 l0 -800 -800 0 -800 0 0 800 0 800
|
||||
800 0 800 0 0 -800z m1640 0 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0
|
||||
-800z m-31220 -1645 l0 -795 -800 0 -800 0 0 793 c0 437 2 796 4 798 2 2 362
|
||||
3 800 1 l796 -2 0 -795z m1638 0 l2 -795 -800 0 -800 0 0 793 c0 437 2 796 4
|
||||
798 2 2 361 3 798 2 l793 -3 3 -795z m3292 -1 l0 -794 -800 0 -800 0 0 795 0
|
||||
795 793 2 c435 2 795 2 800 0 4 -2 7 -361 7 -798z m1640 0 l0 -794 -800 0
|
||||
-800 0 0 795 0 795 793 2 c435 2 795 2 800 0 4 -2 7 -361 7 -798z m1638 1 l2
|
||||
-795 -800 0 -800 0 0 788 c0 484 4 792 9 798 6 5 310 8 798 7 l788 -3 3 -795z
|
||||
m1645 795 c4 0 7 -358 7 -795 l0 -795 -800 0 -800 0 0 793 c0 437 2 796 4 798
|
||||
3 3 1205 2 1589 -1z m1647 -795 l0 -795 -800 0 -800 0 0 793 c0 437 2 796 4
|
||||
798 2 2 362 3 800 1 l796 -2 0 -795z m1640 0 l0 -795 -795 0 -795 0 0 798 0
|
||||
797 795 -3 795 -2 0 -795z m1650 -1 l0 -794 -800 0 -800 0 0 795 0 795 793 2
|
||||
c435 2 795 2 800 0 4 -2 7 -361 7 -798z m1640 0 l0 -794 -800 0 -800 0 0 795
|
||||
0 795 793 2 c435 2 795 2 800 0 4 -2 7 -361 7 -798z m4930 0 l0 -794 -800 0
|
||||
-800 0 0 795 0 795 793 2 c435 2 795 2 800 0 4 -2 7 -361 7 -798z m3290 1 l0
|
||||
-795 -800 0 -800 0 0 793 c0 437 2 796 4 798 2 2 362 3 800 1 l796 -2 0 -795z
|
||||
m1640 3 l0 -798 -800 0 -800 0 0 793 c0 437 2 796 4 798 2 2 362 4 800 4 l796
|
||||
0 0 -797z m1642 787 c4 -5 8 -364 8 -797 l0 -788 -800 0 -800 0 0 798 0 797
|
||||
792 0 c517 0 796 -3 800 -10z m1646 -790 l2 -795 -800 0 -800 0 0 798 0 797
|
||||
797 -2 798 -3 3 -795z m1642 -1 l0 -794 -800 0 -800 0 0 795 0 795 793 2 c435
|
||||
2 795 2 800 0 4 -2 7 -361 7 -798z m-32867 -2 l2 -792 -800 0 -800 0 2 792 c2
|
||||
436 3 794 3 796 0 1 358 1 795 0 l795 -3 3 -793z m4927 3 l0 -795 -801 0
|
||||
c-726 0 -801 1 -795 16 3 9 6 366 6 795 l0 779 795 0 795 0 0 -795z m14790 0
|
||||
l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1650 0 l0 -795 -800
|
||||
0 -800 0 0 795 0 795 800 0 800 0 0 -795z m3290 0 l0 -795 -805 0 -805 0 0
|
||||
795 0 795 805 0 805 0 0 -795z m-24660 -855 c0 -5 0 -364 0 -797 l0 -788 -795
|
||||
0 -795 0 0 788 c0 433 0 792 0 797 0 7 272 10 795 10 523 0 795 -3 795 -10z
|
||||
m1648 -787 l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800 0 -2 -797z m1642
|
||||
-3 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z m1640 0 l0 -800
|
||||
-793 0 c-437 0 -796 2 -798 4 -2 2 -3 362 -1 800 l2 796 795 0 795 0 0 -800z
|
||||
m1648 3 l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800 0 -2 -797z m1640 0
|
||||
l-3 -798 -795 0 -795 0 -3 798 -2 797 800 0 800 0 -2 -797z m1642 7 c0 -434 0
|
||||
-793 0 -797 0 -5 -359 -8 -797 -8 l-798 0 -3 785 c-1 432 0 791 3 798 3 9 173
|
||||
12 800 12 l795 0 0 -790z m1645 -10 l0 -795 -795 0 -795 0 -3 798 -2 797 797
|
||||
-2 798 -3 0 -795z m1645 0 l0 -800 -797 2 -798 3 -3 798 -2 797 800 0 800 0 0
|
||||
-800z m1640 0 l0 -800 -795 0 -795 0 0 800 0 800 795 0 795 0 0 -800z m1648 3
|
||||
l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800 0 -2 -797z m1642 -3 l0 -800
|
||||
-797 2 -798 3 -3 798 -2 797 800 0 800 0 0 -800z m1640 0 l0 -800 -797 2 -798
|
||||
3 -3 785 c-1 432 0 791 3 798 3 9 173 12 800 12 l795 0 0 -800z m1648 3 l-3
|
||||
-798 -795 0 -795 0 -3 798 -2 797 800 0 800 0 -2 -797z m1640 0 l-3 -798 -795
|
||||
0 -795 0 -3 798 -2 797 800 0 800 0 -2 -797z m1650 0 l-3 -798 -800 0 -800 0
|
||||
-3 798 -2 797 805 0 805 0 -2 -797z m1640 0 l-3 -798 -797 -3 -798 -2 0 800 0
|
||||
800 800 0 800 0 -2 -797z m1642 -3 l0 -800 -797 2 -798 3 -3 798 -2 797 800 0
|
||||
800 0 0 -800z m1645 0 l0 -795 -797 -3 -798 -2 0 800 0 800 798 -2 797 -3 0
|
||||
-795z m1643 3 l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800 0 -2 -797z
|
||||
m1642 -3 l0 -800 -797 2 -798 3 -3 798 -2 797 800 0 800 0 0 -800z m-32870
|
||||
-850 c0 -5 0 -364 0 -797 l0 -788 -795 0 -795 0 0 788 c0 433 0 792 0 797 0 7
|
||||
272 10 795 10 523 0 795 -3 795 -10z m1645 -790 l0 -795 -797 -3 -798 -2 0
|
||||
800 0 800 798 -2 797 -3 0 -795z m1645 0 l0 -800 -800 0 -800 0 0 793 c0 437
|
||||
3 797 7 800 3 4 363 7 800 7 l793 0 0 -800z m1640 0 l0 -800 -795 2 -795 3 0
|
||||
788 c0 433 0 792 0 797 0 7 272 10 795 10 l795 0 0 -800z m1645 0 l0 -795
|
||||
-797 -3 -798 -2 0 800 0 800 798 -2 797 -3 0 -795z m1640 0 l0 -795 -795 0
|
||||
-795 0 -3 785 c-1 432 0 791 3 798 3 10 168 12 797 10 l793 -3 0 -795z m1645
|
||||
10 c0 -434 0 -793 0 -797 0 -5 -359 -8 -797 -8 l-798 0 -3 775 c-1 426 0 785
|
||||
3 798 l5 22 795 0 795 0 0 -790z m1645 -10 l0 -795 -797 -3 -798 -2 0 793 c0
|
||||
437 3 797 7 800 3 4 362 6 797 5 l791 -3 0 -795z m1645 0 l0 -800 -797 2 -798
|
||||
3 -3 785 c-1 432 0 791 3 798 3 9 173 12 800 12 l795 0 0 -800z m1640 0 l0
|
||||
-800 -795 0 -795 0 0 800 0 800 795 0 795 0 0 -800z m1648 -2 l2 -798 -800 0
|
||||
-800 0 0 800 0 800 798 -2 797 -3 3 -797z m1642 2 l0 -800 -797 2 -798 3 -3
|
||||
785 c-1 432 0 791 3 798 3 9 173 12 800 12 l795 0 0 -800z m1640 0 l0 -800
|
||||
-797 2 -798 3 -3 785 c-1 432 0 791 3 798 3 9 173 12 800 12 l795 0 0 -800z
|
||||
m1648 -2 l2 -798 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 362 6 797 5
|
||||
l791 -3 3 -797z m1640 -1 l2 -797 -797 2 -798 3 -3 785 c-1 432 0 791 3 798 3
|
||||
10 168 12 797 10 l793 -3 3 -798z m1647 3 l0 -795 -800 0 -800 0 -3 785 c-1
|
||||
432 0 791 3 798 3 10 169 12 802 10 l798 -3 0 -795z m1643 -2 l2 -798 -800 0
|
||||
-800 0 0 793 c0 437 3 797 7 800 3 4 362 6 797 5 l791 -3 3 -797z m1642 2 l0
|
||||
-800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793 0 0 -800z
|
||||
m1645 778 c3 -13 4 -372 3 -798 l-3 -775 -797 -3 -798 -2 0 800 0 800 795 0
|
||||
795 0 5 -22z m1643 -780 l2 -798 -800 0 -800 0 0 800 0 800 798 -2 797 -3 3
|
||||
-797z m1642 2 l0 -800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800
|
||||
7 l793 0 0 -800z m-32875 -849 c3 -5 5 -364 5 -798 l0 -788 -795 0 -795 0 0
|
||||
788 c0 433 0 792 0 797 0 13 1576 14 1585 1z m1639 3 c14 -6 16 -85 16 -800
|
||||
l0 -794 -796 -2 c-438 -2 -798 -1 -800 1 -7 7 -4 1587 3 1594 8 9 1556 9 1577
|
||||
1z m1651 -797 l0 -797 -795 0 -795 0 -3 787 c-1 434 0 794 3 801 3 10 168 12
|
||||
797 10 l793 -3 0 -798z m1645 3 l0 -800 -795 2 -795 3 0 788 c0 434 2 793 5
|
||||
798 4 5 323 9 796 9 l789 0 0 -800z m1645 -2 c0 -439 -3 -798 -7 -798 -5 0
|
||||
-363 0 -798 0 l-790 0 0 793 c0 437 3 797 7 800 3 4 362 6 797 5 l791 -3 0
|
||||
-797z m1640 0 c0 -439 -3 -798 -7 -798 -5 0 -363 0 -798 0 l-790 0 0 794 c0
|
||||
626 3 795 13 799 6 3 365 5 797 4 l785 -2 0 -797z m1640 -1 l0 -797 -788 0
|
||||
c-434 0 -793 2 -798 5 -15 10 -12 1568 3 1583 9 9 195 12 798 10 l785 -3 0
|
||||
-798z m1643 791 c15 -15 18 -1573 3 -1583 -5 -3 -364 -5 -798 -5 l-788 0 -3
|
||||
787 c-1 434 0 794 3 801 6 17 1565 18 1583 0z m1650 -790 l2 -798 -796 -2
|
||||
c-438 -2 -798 -1 -800 1 -7 7 -4 1587 3 1594 3 4 362 6 797 5 l791 -3 3 -797z
|
||||
m1640 0 l2 -798 -795 -2 -795 -3 0 803 0 802 793 -2 792 -3 3 -797z m1647 -1
|
||||
l0 -797 -795 0 -795 0 -3 800 -2 800 797 -2 798 -3 0 -798z m1640 1 c0 -439
|
||||
-3 -798 -7 -798 -5 0 -363 0 -798 0 l-790 0 0 794 c0 626 3 795 13 799 6 3
|
||||
365 5 797 4 l785 -2 0 -797z m1640 -1 l0 -797 -789 0 c-433 0 -792 3 -797 6
|
||||
-5 3 -9 347 -9 794 0 621 3 789 13 793 6 3 365 5 797 4 l785 -2 0 -798z m1653
|
||||
1 l2 -798 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 362 6 797 5 l791 -3 3
|
||||
-797z m1637 0 c0 -439 -3 -798 -7 -798 -5 0 -363 0 -798 0 l-790 0 0 793 c0
|
||||
437 3 797 7 800 3 4 362 6 797 5 l791 -3 0 -797z m1639 796 c14 -6 16 -85 16
|
||||
-800 l0 -794 -795 -2 c-437 -2 -800 -1 -805 0 -16 6 -14 1589 3 1595 18 8
|
||||
1562 8 1581 1z m1640 0 c14 -6 16 -85 16 -800 l0 -794 -796 -2 c-438 -2 -798
|
||||
-1 -800 1 -7 7 -4 1587 3 1594 8 9 1556 9 1577 1z m1656 -796 l0 -803 -797 2
|
||||
-798 3 -3 787 c-1 434 0 794 3 801 3 9 173 12 800 12 l795 0 0 -802z m1644
|
||||
786 c9 -23 7 -1567 -2 -1579 -4 -7 -283 -10 -800 -10 l-792 0 0 803 0 802 794
|
||||
0 c715 0 794 -2 800 -16z m1641 -787 l0 -797 -798 -3 -797 -2 0 803 0 802 798
|
||||
-2 797 -3 0 -798z m1640 1 c0 -439 -3 -798 -7 -798 -5 0 -363 0 -798 0 l-790
|
||||
0 0 794 c0 626 3 795 13 799 6 3 365 5 797 4 l785 -2 0 -797z m-32865 -1640
|
||||
c0 -434 0 -792 0 -798 0 -7 -272 -10 -795 -10 -523 0 -795 3 -795 10 0 6 0
|
||||
363 0 795 0 432 0 787 0 790 0 3 358 4 795 3 l795 -3 0 -787z m1645 -8 l0
|
||||
-795 -797 -3 -798 -2 0 800 0 800 798 -2 797 -3 0 -795z m1645 0 l0 -800 -797
|
||||
2 -798 3 -3 798 -2 797 800 0 800 0 0 -800z m1640 0 l0 -800 -795 0 c-523 0
|
||||
-795 3 -795 10 0 6 0 363 0 795 0 432 0 787 0 790 0 3 358 5 795 5 l795 0 0
|
||||
-800z m1645 0 l0 -795 -797 -3 -798 -2 0 800 0 800 798 -2 797 -3 0 -795z
|
||||
m1643 3 l-3 -798 -795 0 -795 0 -3 785 c-1 432 0 791 3 798 3 9 173 12 800 12
|
||||
l795 0 -2 -797z m1642 3 c0 -433 -3 -792 -6 -797 -3 -5 -347 -9 -794 -9 -709
|
||||
0 -788 2 -794 16 -8 22 -8 1569 1 1577 3 4 364 6 800 5 l793 -3 0 -789z m1645
|
||||
-6 l0 -795 -795 0 -795 0 -3 798 -2 797 797 -2 798 -3 0 -795z m1643 3 l-3
|
||||
-798 -795 0 -795 0 -3 785 c-1 432 0 791 3 798 3 9 173 12 800 12 l795 0 -2
|
||||
-797z m1642 -3 l0 -800 -795 0 -795 0 0 800 0 800 795 0 795 0 0 -800z m1648
|
||||
3 l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800 0 -2 -797z m1640 0 l-3
|
||||
-798 -795 0 -795 0 -3 785 c-1 432 0 791 3 798 3 9 173 12 800 12 l795 0 -2
|
||||
-797z m1642 -3 l0 -800 -797 2 -798 3 -3 785 c-1 432 0 791 3 798 3 9 173 12
|
||||
800 12 l795 0 0 -800z m1648 3 l-3 -798 -795 0 -795 0 -3 798 -2 797 800 0
|
||||
800 0 -2 -797z m1640 0 l-3 -798 -795 0 -795 0 -3 785 c-1 432 0 791 3 798 3
|
||||
9 173 12 800 12 l795 0 -2 -797z m1647 -3 l0 -795 -800 0 -800 0 -3 785 c-1
|
||||
432 0 791 3 798 3 10 169 12 802 10 l798 -3 0 -795z m1643 3 l-3 -798 -795 0
|
||||
-795 0 -3 798 -2 797 800 0 800 0 -2 -797z m1642 -3 l0 -800 -797 2 -798 3 -3
|
||||
798 -2 797 800 0 800 0 0 -800z m1648 20 c1 -426 0 -785 -3 -797 l-5 -23 -795
|
||||
0 -795 0 0 800 0 800 798 -2 797 -3 3 -775z m1640 -17 l-3 -798 -797 -3 -798
|
||||
-2 0 800 0 800 800 0 800 0 -2 -797z m1640 0 l-3 -798 -795 0 -795 0 -3 798
|
||||
-2 797 800 0 800 0 -2 -797z m-32868 -1635 c0 -434 0 -792 0 -798 0 -7 -272
|
||||
-10 -795 -10 -523 0 -795 3 -795 10 0 6 0 363 0 795 0 432 0 787 0 790 0 3
|
||||
358 4 795 3 l795 -3 0 -787z m1648 -10 l2 -798 -800 0 -800 0 0 800 0 800 798
|
||||
-2 797 -3 3 -797z m1642 2 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0
|
||||
-800z m1640 0 l0 -800 -795 0 -795 0 -2 796 c-2 438 -1 798 1 800 2 2 361 4
|
||||
798 4 l793 0 0 -800z m1648 -2 l2 -798 -800 0 -800 0 0 800 0 800 798 -2 797
|
||||
-3 3 -797z m1640 0 l2 -798 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 362 6
|
||||
797 5 l791 -3 3 -797z m1643 798 c2 -2 3 -362 1 -800 l-2 -796 -798 2 -797 3
|
||||
-3 785 c-1 432 0 791 3 798 3 9 172 12 798 12 437 0 796 -2 798 -4z m1644
|
||||
-796 l0 -795 -797 -3 -798 -2 0 793 c0 437 3 797 7 800 3 4 362 6 797 5 l791
|
||||
-3 0 -795z m1645 0 l0 -800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7
|
||||
800 7 l793 0 0 -800z m1640 0 l0 -800 -795 0 -795 0 0 800 0 800 795 0 795 0
|
||||
0 -800z m1648 -2 l2 -798 -800 0 -800 0 0 800 0 800 798 -2 797 -3 3 -797z
|
||||
m1642 2 l0 -800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793
|
||||
0 0 -800z m1640 0 l0 -800 -797 2 -798 3 -3 785 c-1 432 0 791 3 798 3 9 173
|
||||
12 800 12 l795 0 0 -800z m1648 -2 l2 -798 -800 0 -800 0 0 793 c0 437 3 797
|
||||
7 800 3 4 362 6 797 5 l791 -3 3 -797z m1642 2 l0 -800 -800 0 -800 0 0 793
|
||||
c0 437 3 797 7 800 3 4 363 7 800 7 l793 0 0 -800z m1648 -2 l2 -798 -805 0
|
||||
-805 0 0 793 c0 437 3 797 7 800 3 4 365 6 802 5 l796 -3 3 -797z m1640 0 l2
|
||||
-798 -800 0 -800 0 0 800 0 800 798 -2 797 -3 3 -797z m1642 2 l0 -800 -800 0
|
||||
-800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793 0 0 -800z m1645 0 l0
|
||||
-795 -797 -3 -798 -2 0 800 0 800 798 -2 797 -3 0 -795z m1643 -2 l2 -798
|
||||
-800 0 -800 0 0 800 0 800 798 -2 797 -3 3 -797z m1642 2 l0 -800 -800 0 -800
|
||||
0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793 0 0 -800z m-32867 -1642 l-3
|
||||
-793 -795 0 -795 0 -3 793 -2 792 800 0 800 0 -2 -792z m1647 -3 l0 -795 -800
|
||||
0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1640 0 l0 -795 -800 0 -800 0 0
|
||||
795 0 795 800 0 800 0 0 -795z m1640 0 l0 -795 -795 0 -795 0 0 779 c0 429 -3
|
||||
786 -6 795 -6 15 69 16 795 16 l801 0 0 -795z m1650 0 l0 -795 -800 0 -800 0
|
||||
0 795 0 795 800 0 800 0 0 -795z m1640 0 l0 -795 -800 0 -800 0 0 795 0 795
|
||||
800 0 800 0 0 -795z m1640 0 l0 -795 -797 2 -798 3 -3 793 -2 792 800 0 800 0
|
||||
0 -795z m1650 0 l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1640
|
||||
0 l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1640 0 l0 -795
|
||||
-795 0 -795 0 0 795 0 795 795 0 795 0 0 -795z m1650 0 l0 -795 -800 0 -800 0
|
||||
0 795 0 795 800 0 800 0 0 -795z m1640 0 l0 -795 -800 0 -800 0 0 795 0 795
|
||||
800 0 800 0 0 -795z m1640 0 l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0
|
||||
-795z m1650 0 l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1640 0
|
||||
l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1650 0 l0 -795 -805
|
||||
0 -805 0 0 795 0 795 805 0 805 0 0 -795z m1640 0 l0 -795 -800 0 -800 0 0
|
||||
795 0 795 800 0 800 0 0 -795z m1640 0 l0 -795 -800 0 -800 0 0 795 0 795 800
|
||||
0 800 0 0 -795z m1648 3 l-3 -793 -797 -3 -798 -2 0 795 0 795 800 0 800 0 -2
|
||||
-792z m1642 -3 l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1640
|
||||
0 l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m-32870 -1645 l0
|
||||
-795 -795 0 -795 0 0 793 c0 435 0 794 0 797 0 3 358 4 795 3 l795 -3 0 -795z
|
||||
m1648 3 l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800 0 -2 -797z m1642 -3
|
||||
l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z m1640 0 l0 -800 -795
|
||||
2 -795 3 0 793 c0 435 0 794 0 797 0 3 358 5 795 5 l795 0 0 -800z m1648 3
|
||||
l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800 0 -2 -797z m1642 -3 l0 -800
|
||||
-797 2 -798 3 -3 798 -2 797 800 0 800 0 0 -800z m1640 10 c0 -434 0 -793 0
|
||||
-797 0 -5 -359 -8 -797 -8 l-798 0 -3 798 -2 797 800 0 800 0 0 -790z m1648
|
||||
-7 l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800 0 -2 -797z m1642 -3 l0
|
||||
-800 -797 2 -798 3 -3 798 -2 797 800 0 800 0 0 -800z m1640 0 l0 -800 -795 0
|
||||
-795 0 0 800 0 800 795 0 795 0 0 -800z m1650 0 l0 -800 -800 0 -800 0 0 800
|
||||
0 800 800 0 800 0 0 -800z m1640 0 l0 -800 -797 2 -798 3 -3 798 -2 797 800 0
|
||||
800 0 0 -800z m1640 0 l0 -800 -797 2 -798 3 -3 798 -2 797 800 0 800 0 0
|
||||
-800z m1650 0 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z m1640 0
|
||||
l0 -800 -797 2 -798 3 -3 798 -2 797 800 0 800 0 0 -800z m1650 0 l0 -800
|
||||
-802 2 -803 3 -3 798 -2 797 805 0 805 0 0 -800z m1640 0 l0 -800 -800 0 -800
|
||||
0 0 800 0 800 800 0 800 0 0 -800z m1640 0 l0 -800 -800 0 -800 0 0 800 0 800
|
||||
800 0 800 0 0 -800z m1648 3 l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800
|
||||
0 -2 -797z m1642 -3 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z
|
||||
m1640 0 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z m-32870 -850
|
||||
c0 -5 0 -364 0 -797 l0 -788 -795 0 -795 0 0 788 c0 433 0 792 0 797 0 7 272
|
||||
10 795 10 523 0 795 -3 795 -10z m1648 -792 l2 -798 -800 0 -800 0 0 800 0
|
||||
800 798 -2 797 -3 3 -797z m1642 2 l0 -800 -800 0 -800 0 0 800 0 800 800 0
|
||||
800 0 0 -800z m1640 0 l0 -800 -795 2 -795 3 0 788 c0 433 0 792 0 797 0 7
|
||||
272 10 795 10 l795 0 0 -800z m1648 -2 l2 -798 -800 0 -800 0 0 800 0 800 798
|
||||
-2 797 -3 3 -797z m1640 0 l2 -798 -800 0 -800 0 0 793 c0 437 3 797 7 800 3
|
||||
4 362 6 797 5 l791 -3 3 -797z m1642 12 c0 -434 0 -793 0 -797 0 -5 -359 -8
|
||||
-797 -8 l-798 0 -3 785 c-1 432 0 791 3 798 3 9 173 12 800 12 l795 0 0 -790z
|
||||
m1645 -10 l0 -795 -797 -3 -798 -2 0 793 c0 437 3 797 7 800 3 4 362 6 797 5
|
||||
l791 -3 0 -795z m1645 0 l0 -800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4
|
||||
363 7 800 7 l793 0 0 -800z m1640 0 l0 -800 -795 0 -795 0 0 800 0 800 795 0
|
||||
795 0 0 -800z m1648 -2 l2 -798 -800 0 -800 0 0 800 0 800 798 -2 797 -3 3
|
||||
-797z m1642 2 l0 -800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800
|
||||
7 l793 0 0 -800z m1640 0 l0 -800 -797 2 -798 3 -3 785 c-1 432 0 791 3 798 3
|
||||
9 173 12 800 12 l795 0 0 -800z m1648 -2 l2 -798 -800 0 -800 0 0 793 c0 437
|
||||
3 797 7 800 3 4 362 6 797 5 l791 -3 3 -797z m1642 2 l0 -800 -800 0 -800 0 0
|
||||
793 c0 437 3 797 7 800 3 4 363 7 800 7 l793 0 0 -800z m1648 -2 l2 -798 -805
|
||||
0 -805 0 0 793 c0 437 3 797 7 800 3 4 365 6 802 5 l796 -3 3 -797z m1640 0
|
||||
l2 -798 -800 0 -800 0 0 800 0 800 798 -2 797 -3 3 -797z m1642 2 l0 -800
|
||||
-800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793 0 0 -800z m1645
|
||||
0 l0 -795 -797 -3 -798 -2 0 800 0 800 798 -2 797 -3 0 -795z m1643 -2 l2
|
||||
-798 -800 0 -800 0 0 800 0 800 798 -2 797 -3 3 -797z m1642 2 l0 -800 -800 0
|
||||
-800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793 0 0 -800z m-32870 -850
|
||||
c0 -5 0 -364 0 -797 l0 -788 -795 0 -795 0 0 788 c0 433 0 792 0 797 0 7 272
|
||||
10 795 10 523 0 795 -3 795 -10z m1648 -792 l2 -798 -800 0 -800 0 0 800 0
|
||||
800 798 -2 797 -3 3 -797z m1642 2 l0 -800 -800 0 -800 0 0 793 c0 437 3 797
|
||||
7 800 3 4 363 7 800 7 l793 0 0 -800z m1640 0 l0 -800 -795 2 -795 3 0 788 c0
|
||||
434 2 793 5 798 4 5 323 9 796 9 l789 0 0 -800z m1648 -2 l2 -798 -800 0 -800
|
||||
0 0 793 c0 437 3 797 7 800 3 4 362 6 797 5 l791 -3 3 -797z m1640 0 l2 -798
|
||||
-800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 362 6 797 5 l791 -3 3 -797z
|
||||
m1640 0 l2 -798 -800 0 -800 0 0 788 c0 602 3 791 12 800 9 9 195 12 798 10
|
||||
l785 -3 3 -797z m1636 796 c14 -6 16 -85 16 -800 l0 -794 -800 0 -800 0 0 793
|
||||
c0 437 3 797 7 800 8 9 1556 9 1577 1z m1654 -796 l2 -798 -800 0 -800 0 0
|
||||
793 c0 437 3 797 7 800 3 4 362 6 797 5 l791 -3 3 -797z m1640 0 l2 -798 -795
|
||||
0 -795 0 0 800 0 800 793 -2 792 -3 3 -797z m1647 0 c0 -439 -3 -798 -7 -798
|
||||
-5 0 -363 0 -798 0 l-790 0 0 800 0 800 798 -2 797 -3 0 -797z m1643 0 l2
|
||||
-798 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 362 6 797 5 l791 -3 3 -797z
|
||||
m1642 2 l0 -800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793
|
||||
0 0 -800z m1648 -2 l2 -798 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 362 6
|
||||
797 5 l791 -3 3 -797z m1640 0 l2 -798 -800 0 -800 0 0 793 c0 437 3 797 7
|
||||
800 3 4 362 6 797 5 l791 -3 3 -797z m1650 0 l2 -798 -805 0 -805 0 0 793 c0
|
||||
437 3 797 7 800 3 4 365 6 802 5 l796 -3 3 -797z m1640 0 l2 -798 -800 0 -800
|
||||
0 0 793 c0 437 3 797 7 800 3 4 362 6 797 5 l791 -3 3 -797z m1642 2 l0 -800
|
||||
-800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793 0 0 -800z m1645
|
||||
778 c8 -35 1 -1578 -7 -1578 -5 0 -363 0 -798 0 l-790 0 0 800 0 800 795 0
|
||||
795 0 5 -22z m1643 -780 l2 -798 -800 0 -800 0 0 800 0 800 798 -2 797 -3 3
|
||||
-797z m1640 0 l2 -798 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 362 6 797
|
||||
5 l791 -3 3 -797z m-32868 -1648 l0 -795 -795 0 -795 0 0 793 c0 435 0 794 0
|
||||
797 0 3 358 4 795 3 l795 -3 0 -795z m1645 0 l0 -795 -797 -3 -798 -2 0 800 0
|
||||
800 798 -2 797 -3 0 -795z m1645 0 l0 -800 -797 2 -798 3 -3 798 -2 797 800 0
|
||||
800 0 0 -800z m1640 0 l0 -800 -793 0 c-437 0 -796 2 -798 4 -2 2 -3 362 -1
|
||||
800 l2 796 795 0 795 0 0 -800z m1645 0 l0 -795 -795 0 -795 0 -3 798 -2 797
|
||||
797 -2 798 -3 0 -795z m1640 0 l0 -795 -795 0 -795 0 -3 785 c-1 432 0 791 3
|
||||
798 3 10 168 12 797 10 l793 -3 0 -795z m1643 3 l-3 -798 -775 -3 c-426 -1
|
||||
-785 0 -797 3 l-23 5 0 789 c0 433 3 791 7 794 3 4 363 7 800 7 l793 0 -2
|
||||
-797z m1647 -3 l0 -795 -795 0 -795 0 -3 798 -2 797 797 -2 798 -3 0 -795z
|
||||
m1643 3 l-3 -798 -795 0 -795 0 -3 785 c-1 432 0 791 3 798 3 9 173 12 800 12
|
||||
l795 0 -2 -797z m1640 0 l-3 -798 -792 -3 -793 -2 0 800 0 800 795 0 795 0 -2
|
||||
-797z m1650 0 l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800 0 -2 -797z
|
||||
m1640 0 l-3 -798 -795 0 -795 0 -3 785 c-1 432 0 791 3 798 3 9 173 12 800 12
|
||||
l795 0 -2 -797z m1642 -3 l0 -800 -797 2 -798 3 -3 785 c-1 432 0 791 3 798 3
|
||||
9 173 12 800 12 l795 0 0 -800z m1648 3 l-3 -798 -795 0 -795 0 -3 798 -2 797
|
||||
800 0 800 0 -2 -797z m1640 0 l-3 -798 -795 0 -795 0 -3 785 c-1 432 0 791 3
|
||||
798 3 9 173 12 800 12 l795 0 -2 -797z m1647 -3 l0 -795 -800 0 -800 0 -3 785
|
||||
c-1 432 0 791 3 798 3 10 169 12 802 10 l798 -3 0 -795z m1643 3 l-3 -798
|
||||
-795 0 -795 0 -3 798 -2 797 800 0 800 0 -2 -797z m1642 -3 l0 -800 -797 2
|
||||
-798 3 -3 798 -2 797 800 0 800 0 0 -800z m1645 0 l0 -795 -797 -3 -798 -2 0
|
||||
800 0 800 798 -2 797 -3 0 -795z m1643 3 l-3 -798 -797 -3 -798 -2 0 800 0
|
||||
800 800 0 800 0 -2 -797z m1640 0 l-3 -798 -795 0 -795 0 -3 798 -2 797 800 0
|
||||
800 0 -2 -797z m-32868 -853 c0 -5 0 -364 0 -797 l0 -788 -795 0 -795 0 0 788
|
||||
c0 433 0 792 0 797 0 7 272 10 795 10 523 0 795 -3 795 -10z m1645 -790 l0
|
||||
-795 -797 -3 -798 -2 0 800 0 800 798 -2 797 -3 0 -795z m1645 0 l0 -800 -800
|
||||
0 -800 0 0 800 0 800 800 0 800 0 0 -800z m1640 0 l0 -800 -795 2 -795 3 0
|
||||
788 c0 433 0 792 0 797 0 7 272 10 795 10 l795 0 0 -800z m1645 0 l0 -795
|
||||
-797 -3 -798 -2 0 800 0 800 798 -2 797 -3 0 -795z m1643 -3 l2 -797 -797 2
|
||||
-798 3 -3 785 c-1 432 0 791 3 798 3 10 168 12 797 10 l793 -3 3 -798z m1642
|
||||
3 l0 -800 -797 2 -798 3 -3 785 c-1 432 0 791 3 798 3 9 173 12 800 12 l795 0
|
||||
0 -800z m1645 0 l0 -795 -797 -3 -798 -2 0 793 c0 437 3 797 7 800 3 4 362 6
|
||||
797 5 l791 -3 0 -795z m1645 0 l0 -800 -800 0 -800 0 0 793 c0 437 3 797 7
|
||||
800 3 4 363 7 800 7 l793 0 0 -800z m1640 0 l0 -800 -795 0 -795 0 0 800 0
|
||||
800 795 0 795 0 0 -800z m1648 -2 l2 -798 -800 0 -800 0 0 800 0 800 798 -2
|
||||
797 -3 3 -797z m1642 2 l0 -800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4
|
||||
363 7 800 7 l793 0 0 -800z m1640 0 l0 -800 -797 2 -798 3 -3 785 c-1 432 0
|
||||
791 3 798 3 9 173 12 800 12 l795 0 0 -800z m1648 -2 l2 -798 -800 0 -800 0 0
|
||||
793 c0 437 3 797 7 800 3 4 362 6 797 5 l791 -3 3 -797z m1642 2 l0 -800 -800
|
||||
0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793 0 0 -800z m1648 -3
|
||||
l2 -797 -802 2 -803 3 -3 785 c-1 432 0 791 3 798 3 10 169 12 802 10 l798 -3
|
||||
3 -798z m1640 1 l2 -798 -800 0 -800 0 0 800 0 800 798 -2 797 -3 3 -797z
|
||||
m1642 2 l0 -800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793
|
||||
0 0 -800z m1645 0 l0 -795 -797 -3 -798 -2 0 800 0 800 798 -2 797 -3 0 -795z
|
||||
m1643 -2 l2 -798 -800 0 -800 0 0 800 0 800 798 -2 797 -3 3 -797z m1642 2 l0
|
||||
-800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793 0 0 -800z
|
||||
m-32870 -1645 l0 -790 -795 0 -795 0 0 788 c0 433 0 789 0 792 0 3 358 4 795
|
||||
3 l795 -3 0 -790z m1650 0 l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0
|
||||
-795z m1640 0 l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1640 0
|
||||
l0 -795 -795 2 -795 3 0 788 c0 433 0 789 0 792 0 3 358 5 795 5 l795 0 0
|
||||
-795z m1650 0 l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1640 0
|
||||
l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1641 791 c2 -2 3
|
||||
-360 1 -795 l-2 -791 -798 2 -797 3 -3 780 c-1 429 0 786 3 793 3 9 172 12
|
||||
798 12 437 0 796 -2 798 -4z m1644 -791 l0 -790 -797 -3 -798 -2 0 795 0 795
|
||||
798 -2 797 -3 0 -790z m1645 0 l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0
|
||||
0 -795z m1640 0 l0 -795 -795 0 -795 0 0 795 0 795 795 0 795 0 0 -795z m1650
|
||||
0 l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1640 0 l0 -795
|
||||
-800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1640 0 l0 -795 -797 2 -798 3
|
||||
-3 780 c-1 429 0 786 3 793 3 9 173 12 800 12 l795 0 0 -795z m1650 0 l0 -795
|
||||
-800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1640 0 l0 -795 -800 0 -800 0
|
||||
0 795 0 795 800 0 800 0 0 -795z m1650 0 l0 -795 -802 2 -803 3 -3 793 -2 792
|
||||
805 0 805 0 0 -795z m1640 0 l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0
|
||||
-795z m1640 0 l0 -795 -800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1645 0
|
||||
l0 -790 -797 -3 -798 -2 0 795 0 795 798 -2 797 -3 0 -790z m1645 0 l0 -795
|
||||
-800 0 -800 0 0 795 0 795 800 0 800 0 0 -795z m1640 0 l0 -795 -800 0 -800 0
|
||||
0 795 0 795 800 0 800 0 0 -795z m-32870 -1637 c0 -434 0 -792 0 -798 0 -7
|
||||
-272 -10 -795 -10 -523 0 -795 3 -795 10 0 6 0 363 0 795 0 432 0 787 0 790 0
|
||||
3 358 4 795 3 l795 -3 0 -787z m1645 -8 l0 -795 -797 -3 -798 -2 0 800 0 800
|
||||
798 -2 797 -3 0 -795z m1645 0 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0
|
||||
0 -800z m1640 0 l0 -800 -795 0 c-523 0 -795 3 -795 10 0 6 0 363 0 795 0 432
|
||||
0 787 0 790 0 3 358 5 795 5 l795 0 0 -800z m1645 0 l0 -795 -797 -3 -798 -2
|
||||
0 800 0 800 798 -2 797 -3 0 -795z m1645 0 l0 -800 -797 2 -798 3 -3 785 c-1
|
||||
432 0 791 3 798 3 9 173 12 800 12 l795 0 0 -800z m1641 796 c2 -2 3 -362 1
|
||||
-800 l-2 -796 -798 2 -797 3 -3 785 c-1 432 0 791 3 798 3 9 172 12 798 12
|
||||
437 0 796 -2 798 -4z m1644 -796 l0 -795 -797 -3 -798 -2 0 800 0 800 798 -2
|
||||
797 -3 0 -795z m1645 0 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z
|
||||
m1640 0 l0 -800 -795 0 -795 0 0 800 0 800 795 0 795 0 0 -800z m1650 0 l0
|
||||
-800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z m1640 0 l0 -800 -797 2
|
||||
-798 3 -3 798 -2 797 800 0 800 0 0 -800z m1640 0 l0 -800 -797 2 -798 3 -3
|
||||
785 c-1 432 0 791 3 798 3 9 173 12 800 12 l795 0 0 -800z m1650 0 l0 -800
|
||||
-800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z m1640 0 l0 -800 -797 2 -798 3
|
||||
-3 798 -2 797 800 0 800 0 0 -800z m1650 0 l0 -800 -802 2 -803 3 -3 785 c-1
|
||||
432 0 791 3 798 3 9 174 12 805 12 l800 0 0 -800z m1640 0 l0 -800 -800 0
|
||||
-800 0 0 800 0 800 800 0 800 0 0 -800z m1640 0 l0 -800 -800 0 -800 0 0 800
|
||||
0 800 800 0 800 0 0 -800z m1645 0 l0 -795 -797 -3 -798 -2 0 800 0 800 798
|
||||
-2 797 -3 0 -795z m1645 0 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0
|
||||
-800z m1640 0 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z m-32870
|
||||
-1632 c0 -434 0 -792 0 -798 0 -7 -272 -10 -795 -10 -523 0 -795 3 -795 10 0
|
||||
6 0 363 0 795 0 432 0 787 0 790 0 3 358 4 795 3 l795 -3 0 -787z m1645 -8 l0
|
||||
-795 -797 -3 -798 -2 0 800 0 800 798 -2 797 -3 0 -795z m1645 0 l0 -800 -800
|
||||
0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800 7 l793 0 0 -800z m1640 0 l0
|
||||
-800 -795 0 c-523 0 -795 3 -795 10 0 6 0 363 0 795 0 432 0 787 0 790 0 3
|
||||
358 5 795 5 l795 0 0 -800z m1645 0 l0 -795 -797 -3 -798 -2 0 800 0 800 798
|
||||
-2 797 -3 0 -795z m1643 -2 l2 -798 -800 0 -800 0 0 793 c0 437 3 797 7 800 3
|
||||
4 362 6 797 5 l791 -3 3 -797z m1643 798 c2 -2 3 -362 1 -800 l-2 -796 -798 2
|
||||
-797 3 -3 785 c-1 432 0 791 3 798 3 9 172 12 798 12 437 0 796 -2 798 -4z
|
||||
m1644 -796 l0 -795 -797 -3 -798 -2 0 793 c0 437 3 797 7 800 3 4 362 6 797 5
|
||||
l791 -3 0 -795z m1645 0 l0 -800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4
|
||||
363 7 800 7 l793 0 0 -800z m1640 0 l0 -800 -795 0 -795 0 0 800 0 800 795 0
|
||||
795 0 0 -800z m1648 -2 l2 -798 -800 0 -800 0 0 800 0 800 798 -2 797 -3 3
|
||||
-797z m1642 2 l0 -800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7 800
|
||||
7 l793 0 0 -800z m1640 0 l0 -800 -797 2 -798 3 -3 785 c-1 432 0 791 3 798 3
|
||||
9 173 12 800 12 l795 0 0 -800z m1648 -2 l2 -798 -800 0 -800 0 0 793 c0 437
|
||||
3 797 7 800 3 4 362 6 797 5 l791 -3 3 -797z m1640 0 l2 -798 -800 0 -800 0 0
|
||||
793 c0 437 3 797 7 800 3 4 362 6 797 5 l791 -3 3 -797z m1650 -1 l2 -797
|
||||
-802 2 -803 3 -3 785 c-1 432 0 791 3 798 3 10 169 12 802 10 l798 -3 3 -798z
|
||||
m1640 1 l2 -798 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 362 6 797 5 l791
|
||||
-3 3 -797z m1642 2 l0 -800 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 363 7
|
||||
800 7 l793 0 0 -800z m1645 0 l0 -795 -797 -3 -798 -2 0 800 0 800 798 -2 797
|
||||
-3 0 -795z m1643 -2 l2 -798 -800 0 -800 0 0 800 0 800 798 -2 797 -3 3 -797z
|
||||
m1640 0 l2 -798 -800 0 -800 0 0 793 c0 437 3 797 7 800 3 4 362 6 797 5 l791
|
||||
-3 3 -797z m-16430 -1649 l-3 -794 -797 -3 -798 -2 0 800 0 800 793 2 c435 2
|
||||
795 0 800 -3 4 -3 6 -363 5 -800z m13150 0 l-3 -794 -797 -3 -798 -2 0 800 0
|
||||
800 793 2 c435 2 795 0 800 -3 4 -3 6 -363 5 -800z m-29585 4 l-3 -798 -795 0
|
||||
-795 0 -3 798 -2 797 800 0 800 0 -2 -797z m1645 0 l-3 -798 -797 -3 -798 -2
|
||||
0 800 0 800 800 0 800 0 -2 -797z m1642 -3 l0 -800 -797 2 -798 3 -3 798 -2
|
||||
797 800 0 800 0 0 -800z m1640 0 l0 -800 -795 2 -795 3 -3 798 -2 797 798 0
|
||||
797 0 0 -800z m1648 3 l-3 -798 -795 0 -795 0 -3 798 -2 797 800 0 800 0 -2
|
||||
-797z m1640 0 l-3 -798 -795 0 -795 0 -3 798 -2 797 800 0 800 0 -2 -797z
|
||||
m1647 5 c0 -517 -3 -796 -10 -800 -12 -9 -1556 -11 -1579 -2 -14 6 -16 85 -16
|
||||
800 l0 794 803 0 802 0 0 -792z m1643 -5 l-3 -798 -795 0 -795 0 -3 798 -2
|
||||
797 800 0 800 0 -2 -797z m1640 0 l-3 -798 -795 0 -795 0 -3 798 -2 797 800 0
|
||||
800 0 -2 -797z m1640 0 l-3 -798 -792 -3 -793 -2 0 800 0 800 795 0 795 0 -2
|
||||
-797z m3290 0 l-3 -798 -795 0 -795 0 -3 798 -2 797 800 0 800 0 -2 -797z
|
||||
m1642 -3 l0 -800 -797 2 -798 3 -3 798 -2 797 800 0 800 0 0 -800z m1648 3
|
||||
l-3 -798 -795 0 -795 0 -3 798 -2 797 800 0 800 0 -2 -797z m1640 0 l-3 -798
|
||||
-795 0 -795 0 -3 798 -2 797 800 0 800 0 -2 -797z m1650 0 l-3 -798 -800 0
|
||||
-800 0 -3 798 -2 797 805 0 805 0 -2 -797z m1640 0 l-3 -798 -795 0 -795 0 -3
|
||||
798 -2 797 800 0 800 0 -2 -797z m1642 -3 l0 -800 -797 2 -798 3 -3 798 -2
|
||||
797 800 0 800 0 0 -800z m3288 3 l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0
|
||||
800 0 -2 -797z m1640 0 l-3 -798 -795 0 -795 0 -3 798 -2 797 800 0 800 0 -2
|
||||
-797z m-32868 -853 c0 -5 0 -364 0 -797 l0 -788 -795 0 -795 0 0 788 c0 433 0
|
||||
792 0 797 0 7 272 10 795 10 523 0 795 -3 795 -10z m1645 -790 l0 -795 -797
|
||||
-3 -798 -2 0 800 0 800 798 -2 797 -3 0 -795z m1645 0 l0 -800 -800 0 -800 0
|
||||
0 800 0 800 800 0 800 0 0 -800z m1640 0 l0 -800 -795 2 -795 3 0 788 c0 433
|
||||
0 792 0 797 0 7 272 10 795 10 l795 0 0 -800z m1645 0 l0 -795 -797 -3 -798
|
||||
-2 0 800 0 800 798 -2 797 -3 0 -795z m1643 3 l-3 -798 -795 0 -795 0 -3 785
|
||||
c-1 432 0 791 3 798 3 9 173 12 800 12 l795 0 -2 -797z m1642 7 c0 -434 0
|
||||
-793 0 -797 0 -5 -359 -8 -797 -8 l-798 0 -3 785 c-1 432 0 791 3 798 3 9 173
|
||||
12 800 12 l795 0 0 -790z m1645 -10 l0 -795 -797 -3 -798 -2 0 800 0 800 798
|
||||
-2 797 -3 0 -795z m1645 0 l0 -800 -797 2 -798 3 -3 798 -2 797 800 0 800 0 0
|
||||
-800z m1640 0 l0 -800 -795 0 -795 0 0 800 0 800 795 0 795 0 0 -800z m1648 3
|
||||
l-3 -798 -797 -3 -798 -2 0 800 0 800 800 0 800 0 -2 -797z m1642 -3 l0 -800
|
||||
-797 2 -798 3 -3 798 -2 797 800 0 800 0 0 -800z m1640 0 l0 -800 -797 2 -798
|
||||
3 -3 785 c-1 432 0 791 3 798 3 9 173 12 800 12 l795 0 0 -800z m1648 3 l-3
|
||||
-798 -795 0 -795 0 -3 798 -2 797 800 0 800 0 -2 -797z m1642 -3 l0 -800 -797
|
||||
2 -798 3 -3 798 -2 797 800 0 800 0 0 -800z m1648 3 l-3 -798 -800 0 -800 0
|
||||
-3 785 c-1 432 0 791 3 798 3 9 174 12 805 12 l800 0 -2 -797z m1642 -3 l0
|
||||
-800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z m1640 0 l0 -800 -797 2
|
||||
-798 3 -3 798 -2 797 800 0 800 0 0 -800z m1645 0 l0 -795 -797 -3 -798 -2 0
|
||||
800 0 800 798 -2 797 -3 0 -795z m1645 0 l0 -800 -800 0 -800 0 0 800 0 800
|
||||
800 0 800 0 0 -800z m1640 0 l0 -800 -797 2 -798 3 -3 798 -2 797 800 0 800 0
|
||||
0 -800z m-32870 -850 c0 -5 0 -363 0 -795 0 -432 0 -789 0 -795 0 -7 -272 -10
|
||||
-795 -10 -523 0 -795 3 -795 10 0 6 0 363 0 795 0 432 0 790 0 795 0 7 272 10
|
||||
795 10 523 0 795 -3 795 -10z m1645 -795 l0 -800 -795 0 -795 0 -3 803 -2 802
|
||||
797 -2 798 -3 0 -800z m1645 0 l0 -805 -797 2 -798 3 -3 803 -2 802 800 0 800
|
||||
0 0 -805z m1640 0 l0 -805 -795 0 c-523 0 -795 3 -795 10 0 6 0 363 0 795 0
|
||||
432 0 790 0 795 0 7 272 10 795 10 l795 0 0 -805z m1645 0 l0 -800 -795 0
|
||||
-795 0 -3 803 -2 802 797 -2 798 -3 0 -800z m1640 0 l0 -800 -795 0 -795 0 -3
|
||||
790 c-1 435 0 796 3 803 3 10 168 12 797 10 l793 -3 0 -800z m1643 3 l-3 -803
|
||||
-784 -3 c-571 -1 -787 1 -797 9 -12 10 -14 147 -14 799 0 432 3 790 7 793 3 4
|
||||
363 7 800 7 l793 0 -2 -802z m1650 0 l2 -798 -22 -5 c-13 -3 -372 -4 -798 -3
|
||||
l-775 3 -3 803 -2 802 797 -2 798 -3 3 -797z m1640 0 l-3 -803 -795 0 -795 0
|
||||
-3 790 c-1 435 0 796 3 803 3 9 173 12 800 12 l795 0 -2 -802z m1640 0 l-3
|
||||
-803 -792 -3 -793 -2 0 805 0 805 795 0 795 0 -2 -802z m1650 0 l-3 -803 -797
|
||||
-3 -798 -2 0 805 0 805 800 0 800 0 -2 -802z m16432 -818 l0 -1620 -6550 0
|
||||
c-6543 0 -6550 0 -6550 20 0 15 -7 20 -25 20 -18 0 -25 -5 -25 -20 0 -20 -7
|
||||
-20 -800 -20 -793 0 -800 0 -800 20 0 13 -7 20 -20 20 -13 0 -20 -7 -20 -20 0
|
||||
-20 -7 -20 -800 -20 l-800 0 0 800 c0 704 2 800 15 800 8 0 15 7 15 15 0 9 -7
|
||||
18 -15 21 -13 5 -15 103 -15 798 0 436 3 796 7 799 3 4 3691 7 8195 7 l8188 0
|
||||
0 -1620z m-32870 -820 l0 -795 -795 0 -795 0 0 793 c0 435 0 794 0 797 0 3
|
||||
358 4 795 3 l795 -3 0 -795z m1648 -2 l2 -798 -800 0 -800 0 0 800 0 800 798
|
||||
-2 797 -3 3 -797z m1642 2 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0
|
||||
-800z m1640 0 l0 -800 -795 2 -795 3 0 793 c0 435 0 794 0 797 0 3 358 5 795
|
||||
5 l795 0 0 -800z m1650 0 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0
|
||||
-800z m1640 0 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z m1641
|
||||
796 c2 -2 3 -362 1 -800 l-2 -796 -798 2 -797 3 -3 785 c-1 432 0 791 3 798 3
|
||||
9 172 12 798 12 437 0 796 -2 798 -4z m1647 -798 l2 -798 -800 0 -800 0 0 800
|
||||
0 800 798 -2 797 -3 3 -797z m1642 2 l0 -800 -800 0 -800 0 0 800 0 800 800 0
|
||||
800 0 0 -800z m1640 0 l0 -800 -795 0 -795 0 0 800 0 800 795 0 795 0 0 -800z
|
||||
m1650 0 l0 -800 -800 0 -800 0 0 800 0 800 800 0 800 0 0 -800z"/>
|
||||
</g>
|
||||
</svg>
|
After Width: | Height: | Size: 42 KiB |
@ -105,7 +105,10 @@ if (SLIC3R_GUI)
|
||||
# wrong libs for opengl in the link line and it does not link to it by himself.
|
||||
# libslic3r_gui will link to opengl anyway, so lets override wx
|
||||
list(FILTER wxWidgets_LIBRARIES EXCLUDE REGEX OpenGL)
|
||||
|
||||
|
||||
if (UNIX AND NOT APPLE)
|
||||
list(APPEND wxWidgets_LIBRARIES X11 wayland-client wayland-egl EGL)
|
||||
endif ()
|
||||
# list(REMOVE_ITEM wxWidgets_LIBRARIES oleacc)
|
||||
message(STATUS "wx libs: ${wxWidgets_LIBRARIES}")
|
||||
|
||||
|
@ -66,16 +66,25 @@ public:
|
||||
return this->success;
|
||||
}
|
||||
|
||||
void unload_opengl_dll()
|
||||
bool unload_opengl_dll()
|
||||
{
|
||||
if (this->hOpenGL) {
|
||||
BOOL released = FreeLibrary(this->hOpenGL);
|
||||
if (released)
|
||||
printf("System OpenGL library released\n");
|
||||
if (this->hOpenGL != nullptr) {
|
||||
if (::FreeLibrary(this->hOpenGL) != FALSE) {
|
||||
if (::GetModuleHandle(L"opengl32.dll") == nullptr) {
|
||||
printf("System OpenGL library successfully released\n");
|
||||
this->hOpenGL = nullptr;
|
||||
return true;
|
||||
}
|
||||
else
|
||||
printf("System OpenGL library released but not removed\n");
|
||||
}
|
||||
else
|
||||
printf("System OpenGL library NOT released\n");
|
||||
this->hOpenGL = nullptr;
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool is_version_greater_or_equal_to(unsigned int major, unsigned int minor) const
|
||||
@ -270,20 +279,26 @@ int wmain(int argc, wchar_t **argv)
|
||||
// https://wiki.qt.io/Cross_compiling_Mesa_for_Windows
|
||||
// http://download.qt.io/development_releases/prebuilt/llvmpipe/windows/
|
||||
if (load_mesa) {
|
||||
opengl_version_check.unload_opengl_dll();
|
||||
wchar_t path_to_mesa[MAX_PATH + 1] = { 0 };
|
||||
wcscpy(path_to_mesa, path_to_exe);
|
||||
wcscat(path_to_mesa, L"mesa\\opengl32.dll");
|
||||
printf("Loading MESA OpenGL library: %S\n", path_to_mesa);
|
||||
HINSTANCE hInstance_OpenGL = LoadLibraryExW(path_to_mesa, nullptr, 0);
|
||||
if (hInstance_OpenGL == nullptr) {
|
||||
printf("MESA OpenGL library was not loaded\n");
|
||||
} else
|
||||
printf("MESA OpenGL library was loaded sucessfully\n");
|
||||
bool res = opengl_version_check.unload_opengl_dll();
|
||||
if (!res) {
|
||||
MessageBox(nullptr, L"PrusaSlicer was unable to automatically switch to MESA OpenGL library\nPlease, try to run the application using the '--sw-renderer' option.\n",
|
||||
L"PrusaSlicer Warning", MB_OK);
|
||||
return -1;
|
||||
}
|
||||
else {
|
||||
wchar_t path_to_mesa[MAX_PATH + 1] = { 0 };
|
||||
wcscpy(path_to_mesa, path_to_exe);
|
||||
wcscat(path_to_mesa, L"mesa\\opengl32.dll");
|
||||
printf("Loading MESA OpenGL library: %S\n", path_to_mesa);
|
||||
HINSTANCE hInstance_OpenGL = LoadLibraryExW(path_to_mesa, nullptr, 0);
|
||||
if (hInstance_OpenGL == nullptr)
|
||||
printf("MESA OpenGL library was not loaded\n");
|
||||
else
|
||||
printf("MESA OpenGL library was loaded sucessfully\n");
|
||||
}
|
||||
}
|
||||
#endif /* SLIC3R_GUI */
|
||||
|
||||
|
||||
wchar_t path_to_slic3r[MAX_PATH + 1] = { 0 };
|
||||
wcscpy(path_to_slic3r, path_to_exe);
|
||||
wcscat(path_to_slic3r, L"PrusaSlicer.dll");
|
||||
|
@ -2290,6 +2290,12 @@ void Clipper::ProcessHorizontal(TEdge *horzEdge)
|
||||
|
||||
if (horzEdge->OutIdx >= 0 && !IsOpen) //note: may be done multiple times
|
||||
{
|
||||
#ifdef CLIPPERLIB_USE_XYZ
|
||||
if (dir == dLeftToRight)
|
||||
SetZ(e->Curr, *horzEdge, *e);
|
||||
else
|
||||
SetZ(e->Curr, *e, *horzEdge);
|
||||
#endif
|
||||
op1 = AddOutPt(horzEdge, e->Curr);
|
||||
TEdge* eNextHorz = m_SortedEdges;
|
||||
while (eNextHorz)
|
||||
@ -2614,6 +2620,9 @@ void Clipper::ProcessEdgesAtTopOfScanbeam(const cInt topY)
|
||||
{
|
||||
e->Curr.x() = TopX( *e, topY );
|
||||
e->Curr.y() = topY;
|
||||
#ifdef CLIPPERLIB_USE_XYZ
|
||||
e->Curr.z() = topY == e->Top.y() ? e->Top.z() : (topY == e->Bot.y() ? e->Bot.z() : 0);
|
||||
#endif
|
||||
}
|
||||
|
||||
//When StrictlySimple and 'e' is being touched by another edge, then
|
||||
|
@ -446,6 +446,57 @@ namespace detail {
|
||||
}
|
||||
}
|
||||
|
||||
// Real-time collision detection, Ericson, Chapter 5
|
||||
template<typename Vector>
|
||||
static inline Vector closest_point_to_triangle(const Vector &p, const Vector &a, const Vector &b, const Vector &c)
|
||||
{
|
||||
using Scalar = typename Vector::Scalar;
|
||||
// Check if P in vertex region outside A
|
||||
Vector ab = b - a;
|
||||
Vector ac = c - a;
|
||||
Vector ap = p - a;
|
||||
Scalar d1 = ab.dot(ap);
|
||||
Scalar d2 = ac.dot(ap);
|
||||
if (d1 <= 0 && d2 <= 0)
|
||||
return a;
|
||||
// Check if P in vertex region outside B
|
||||
Vector bp = p - b;
|
||||
Scalar d3 = ab.dot(bp);
|
||||
Scalar d4 = ac.dot(bp);
|
||||
if (d3 >= 0 && d4 <= d3)
|
||||
return b;
|
||||
// Check if P in edge region of AB, if so return projection of P onto AB
|
||||
Scalar vc = d1*d4 - d3*d2;
|
||||
if (a != b && vc <= 0 && d1 >= 0 && d3 <= 0) {
|
||||
Scalar v = d1 / (d1 - d3);
|
||||
return a + v * ab;
|
||||
}
|
||||
// Check if P in vertex region outside C
|
||||
Vector cp = p - c;
|
||||
Scalar d5 = ab.dot(cp);
|
||||
Scalar d6 = ac.dot(cp);
|
||||
if (d6 >= 0 && d5 <= d6)
|
||||
return c;
|
||||
// Check if P in edge region of AC, if so return projection of P onto AC
|
||||
Scalar vb = d5*d2 - d1*d6;
|
||||
if (vb <= 0 && d2 >= 0 && d6 <= 0) {
|
||||
Scalar w = d2 / (d2 - d6);
|
||||
return a + w * ac;
|
||||
}
|
||||
// Check if P in edge region of BC, if so return projection of P onto BC
|
||||
Scalar va = d3*d6 - d5*d4;
|
||||
if (va <= 0 && (d4 - d3) >= 0 && (d5 - d6) >= 0) {
|
||||
Scalar w = (d4 - d3) / ((d4 - d3) + (d5 - d6));
|
||||
return b + w * (c - b);
|
||||
}
|
||||
// P inside face region. Compute Q through its barycentric coordinates (u,v,w)
|
||||
Scalar denom = Scalar(1.0) / (va + vb + vc);
|
||||
Scalar v = vb * denom;
|
||||
Scalar w = vc * denom;
|
||||
return a + ab * v + ac * w; // = u*a + v*b + w*c, u = va * denom = 1.0-v-w
|
||||
};
|
||||
|
||||
|
||||
// Nothing to do with COVID-19 social distancing.
|
||||
template<typename AVertexType, typename AIndexedFaceType, typename ATreeType, typename AVectorType>
|
||||
struct IndexedTriangleSetDistancer {
|
||||
@ -453,74 +504,36 @@ namespace detail {
|
||||
using IndexedFaceType = AIndexedFaceType;
|
||||
using TreeType = ATreeType;
|
||||
using VectorType = AVectorType;
|
||||
using ScalarType = typename VectorType::Scalar;
|
||||
|
||||
const std::vector<VertexType> &vertices;
|
||||
const std::vector<IndexedFaceType> &faces;
|
||||
const TreeType &tree;
|
||||
|
||||
const VectorType origin;
|
||||
|
||||
inline VectorType closest_point_to_origin(size_t primitive_index,
|
||||
ScalarType& squared_distance){
|
||||
const auto &triangle = this->faces[primitive_index];
|
||||
VectorType closest_point = closest_point_to_triangle<VectorType>(origin,
|
||||
this->vertices[triangle(0)].template cast<ScalarType>(),
|
||||
this->vertices[triangle(1)].template cast<ScalarType>(),
|
||||
this->vertices[triangle(2)].template cast<ScalarType>());
|
||||
squared_distance = (origin - closest_point).squaredNorm();
|
||||
return closest_point;
|
||||
}
|
||||
};
|
||||
|
||||
// Real-time collision detection, Ericson, Chapter 5
|
||||
template<typename Vector>
|
||||
static inline Vector closest_point_to_triangle(const Vector &p, const Vector &a, const Vector &b, const Vector &c)
|
||||
{
|
||||
using Scalar = typename Vector::Scalar;
|
||||
// Check if P in vertex region outside A
|
||||
Vector ab = b - a;
|
||||
Vector ac = c - a;
|
||||
Vector ap = p - a;
|
||||
Scalar d1 = ab.dot(ap);
|
||||
Scalar d2 = ac.dot(ap);
|
||||
if (d1 <= 0 && d2 <= 0)
|
||||
return a;
|
||||
// Check if P in vertex region outside B
|
||||
Vector bp = p - b;
|
||||
Scalar d3 = ab.dot(bp);
|
||||
Scalar d4 = ac.dot(bp);
|
||||
if (d3 >= 0 && d4 <= d3)
|
||||
return b;
|
||||
// Check if P in edge region of AB, if so return projection of P onto AB
|
||||
Scalar vc = d1*d4 - d3*d2;
|
||||
if (a != b && vc <= 0 && d1 >= 0 && d3 <= 0) {
|
||||
Scalar v = d1 / (d1 - d3);
|
||||
return a + v * ab;
|
||||
}
|
||||
// Check if P in vertex region outside C
|
||||
Vector cp = p - c;
|
||||
Scalar d5 = ab.dot(cp);
|
||||
Scalar d6 = ac.dot(cp);
|
||||
if (d6 >= 0 && d5 <= d6)
|
||||
return c;
|
||||
// Check if P in edge region of AC, if so return projection of P onto AC
|
||||
Scalar vb = d5*d2 - d1*d6;
|
||||
if (vb <= 0 && d2 >= 0 && d6 <= 0) {
|
||||
Scalar w = d2 / (d2 - d6);
|
||||
return a + w * ac;
|
||||
}
|
||||
// Check if P in edge region of BC, if so return projection of P onto BC
|
||||
Scalar va = d3*d6 - d5*d4;
|
||||
if (va <= 0 && (d4 - d3) >= 0 && (d5 - d6) >= 0) {
|
||||
Scalar w = (d4 - d3) / ((d4 - d3) + (d5 - d6));
|
||||
return b + w * (c - b);
|
||||
}
|
||||
// P inside face region. Compute Q through its barycentric coordinates (u,v,w)
|
||||
Scalar denom = Scalar(1.0) / (va + vb + vc);
|
||||
Scalar v = vb * denom;
|
||||
Scalar w = vc * denom;
|
||||
return a + ab * v + ac * w; // = u*a + v*b + w*c, u = va * denom = 1.0-v-w
|
||||
};
|
||||
|
||||
template<typename IndexedTriangleSetDistancerType, typename Scalar>
|
||||
static inline Scalar squared_distance_to_indexed_triangle_set_recursive(
|
||||
IndexedTriangleSetDistancerType &distancer,
|
||||
template<typename IndexedPrimitivesDistancerType, typename Scalar>
|
||||
static inline Scalar squared_distance_to_indexed_primitives_recursive(
|
||||
IndexedPrimitivesDistancerType &distancer,
|
||||
size_t node_idx,
|
||||
Scalar low_sqr_d,
|
||||
Scalar up_sqr_d,
|
||||
size_t &i,
|
||||
Eigen::PlainObjectBase<typename IndexedTriangleSetDistancerType::VectorType> &c)
|
||||
Eigen::PlainObjectBase<typename IndexedPrimitivesDistancerType::VectorType> &c)
|
||||
{
|
||||
using Vector = typename IndexedTriangleSetDistancerType::VectorType;
|
||||
using Vector = typename IndexedPrimitivesDistancerType::VectorType;
|
||||
|
||||
if (low_sqr_d > up_sqr_d)
|
||||
return low_sqr_d;
|
||||
@ -538,13 +551,9 @@ namespace detail {
|
||||
assert(node.is_valid());
|
||||
if (node.is_leaf())
|
||||
{
|
||||
const auto &triangle = distancer.faces[node.idx];
|
||||
Vector c_candidate = closest_point_to_triangle<Vector>(
|
||||
distancer.origin,
|
||||
distancer.vertices[triangle(0)].template cast<Scalar>(),
|
||||
distancer.vertices[triangle(1)].template cast<Scalar>(),
|
||||
distancer.vertices[triangle(2)].template cast<Scalar>());
|
||||
set_min((c_candidate - distancer.origin).squaredNorm(), node.idx, c_candidate);
|
||||
Scalar sqr_dist;
|
||||
Vector c_candidate = distancer.closest_point_to_origin(node.idx, sqr_dist);
|
||||
set_min(sqr_dist, node.idx, c_candidate);
|
||||
}
|
||||
else
|
||||
{
|
||||
@ -561,7 +570,7 @@ namespace detail {
|
||||
{
|
||||
size_t i_left;
|
||||
Vector c_left = c;
|
||||
Scalar sqr_d_left = squared_distance_to_indexed_triangle_set_recursive(distancer, left_node_idx, low_sqr_d, up_sqr_d, i_left, c_left);
|
||||
Scalar sqr_d_left = squared_distance_to_indexed_primitives_recursive(distancer, left_node_idx, low_sqr_d, up_sqr_d, i_left, c_left);
|
||||
set_min(sqr_d_left, i_left, c_left);
|
||||
looked_left = true;
|
||||
};
|
||||
@ -569,13 +578,13 @@ namespace detail {
|
||||
{
|
||||
size_t i_right;
|
||||
Vector c_right = c;
|
||||
Scalar sqr_d_right = squared_distance_to_indexed_triangle_set_recursive(distancer, right_node_idx, low_sqr_d, up_sqr_d, i_right, c_right);
|
||||
Scalar sqr_d_right = squared_distance_to_indexed_primitives_recursive(distancer, right_node_idx, low_sqr_d, up_sqr_d, i_right, c_right);
|
||||
set_min(sqr_d_right, i_right, c_right);
|
||||
looked_right = true;
|
||||
};
|
||||
|
||||
// must look left or right if in box
|
||||
using BBoxScalar = typename IndexedTriangleSetDistancerType::TreeType::BoundingBox::Scalar;
|
||||
using BBoxScalar = typename IndexedPrimitivesDistancerType::TreeType::BoundingBox::Scalar;
|
||||
if (node_left.bbox.contains(distancer.origin.template cast<BBoxScalar>()))
|
||||
look_left();
|
||||
if (node_right.bbox.contains(distancer.origin.template cast<BBoxScalar>()))
|
||||
@ -747,7 +756,7 @@ inline typename VectorType::Scalar squared_distance_to_indexed_triangle_set(
|
||||
auto distancer = detail::IndexedTriangleSetDistancer<VertexType, IndexedFaceType, TreeType, VectorType>
|
||||
{ vertices, faces, tree, point };
|
||||
return tree.empty() ? Scalar(-1) :
|
||||
detail::squared_distance_to_indexed_triangle_set_recursive(distancer, size_t(0), Scalar(0), std::numeric_limits<Scalar>::infinity(), hit_idx_out, hit_point_out);
|
||||
detail::squared_distance_to_indexed_primitives_recursive(distancer, size_t(0), Scalar(0), std::numeric_limits<Scalar>::infinity(), hit_idx_out, hit_point_out);
|
||||
}
|
||||
|
||||
// Decides if exists some triangle in defined radius on a 3D indexed triangle set using a pre-built AABBTreeIndirect::Tree.
|
||||
@ -779,7 +788,7 @@ inline bool is_any_triangle_in_radius(
|
||||
return false;
|
||||
}
|
||||
|
||||
detail::squared_distance_to_indexed_triangle_set_recursive(distancer, size_t(0), Scalar(0), max_distance_squared, hit_idx, hit_point);
|
||||
detail::squared_distance_to_indexed_primitives_recursive(distancer, size_t(0), Scalar(0), max_distance_squared, hit_idx, hit_point);
|
||||
|
||||
return hit_point.allFinite();
|
||||
}
|
||||
|
112
src/libslic3r/AABBTreeLines.hpp
Normal file
112
src/libslic3r/AABBTreeLines.hpp
Normal file
@ -0,0 +1,112 @@
|
||||
#ifndef SRC_LIBSLIC3R_AABBTREELINES_HPP_
|
||||
#define SRC_LIBSLIC3R_AABBTREELINES_HPP_
|
||||
|
||||
#include "libslic3r/Point.hpp"
|
||||
#include "libslic3r/EdgeGrid.hpp"
|
||||
#include "libslic3r/AABBTreeIndirect.hpp"
|
||||
#include "libslic3r/Line.hpp"
|
||||
|
||||
namespace Slic3r {
|
||||
|
||||
namespace AABBTreeLines {
|
||||
|
||||
namespace detail {
|
||||
|
||||
template<typename ALineType, typename ATreeType, typename AVectorType>
|
||||
struct IndexedLinesDistancer {
|
||||
using LineType = ALineType;
|
||||
using TreeType = ATreeType;
|
||||
using VectorType = AVectorType;
|
||||
using ScalarType = typename VectorType::Scalar;
|
||||
|
||||
const std::vector<LineType> &lines;
|
||||
const TreeType &tree;
|
||||
|
||||
const VectorType origin;
|
||||
|
||||
inline VectorType closest_point_to_origin(size_t primitive_index,
|
||||
ScalarType &squared_distance) {
|
||||
VectorType nearest_point;
|
||||
const LineType &line = lines[primitive_index];
|
||||
squared_distance = line_alg::distance_to_squared(line, origin, &nearest_point);
|
||||
return nearest_point;
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
|
||||
// Build a balanced AABB Tree over a vector of float lines, balancing the tree
|
||||
// on centroids of the lines.
|
||||
// Epsilon is applied to the bounding boxes of the AABB Tree to cope with numeric inaccuracies
|
||||
// during tree traversal.
|
||||
template<typename LineType>
|
||||
inline AABBTreeIndirect::Tree<2, typename LineType::Scalar> build_aabb_tree_over_indexed_lines(
|
||||
const std::vector<LineType> &lines,
|
||||
//FIXME do we want to apply an epsilon?
|
||||
const float eps = 0)
|
||||
{
|
||||
using TreeType = AABBTreeIndirect::Tree<2, typename LineType::Scalar>;
|
||||
// using CoordType = typename TreeType::CoordType;
|
||||
using VectorType = typename TreeType::VectorType;
|
||||
using BoundingBox = typename TreeType::BoundingBox;
|
||||
|
||||
struct InputType {
|
||||
size_t idx() const {
|
||||
return m_idx;
|
||||
}
|
||||
const BoundingBox& bbox() const {
|
||||
return m_bbox;
|
||||
}
|
||||
const VectorType& centroid() const {
|
||||
return m_centroid;
|
||||
}
|
||||
|
||||
size_t m_idx;
|
||||
BoundingBox m_bbox;
|
||||
VectorType m_centroid;
|
||||
};
|
||||
|
||||
std::vector<InputType> input;
|
||||
input.reserve(lines.size());
|
||||
const VectorType veps(eps, eps);
|
||||
for (size_t i = 0; i < lines.size(); ++i) {
|
||||
const LineType &line = lines[i];
|
||||
InputType n;
|
||||
n.m_idx = i;
|
||||
n.m_centroid = (line.a + line.b) * 0.5;
|
||||
n.m_bbox = BoundingBox(line.a, line.a);
|
||||
n.m_bbox.extend(line.b);
|
||||
n.m_bbox.min() -= veps;
|
||||
n.m_bbox.max() += veps;
|
||||
input.emplace_back(n);
|
||||
}
|
||||
|
||||
TreeType out;
|
||||
out.build(std::move(input));
|
||||
return out;
|
||||
}
|
||||
|
||||
// Finding a closest line, its closest point and squared distance to the closest point
|
||||
// Returns squared distance to the closest point or -1 if the input is empty.
|
||||
template<typename LineType, typename TreeType, typename VectorType>
|
||||
inline typename VectorType::Scalar squared_distance_to_indexed_lines(
|
||||
const std::vector<LineType> &lines,
|
||||
const TreeType &tree,
|
||||
const VectorType &point,
|
||||
size_t &hit_idx_out,
|
||||
Eigen::PlainObjectBase<VectorType> &hit_point_out)
|
||||
{
|
||||
using Scalar = typename VectorType::Scalar;
|
||||
auto distancer = detail::IndexedLinesDistancer<LineType, TreeType, VectorType>
|
||||
{ lines, tree, point };
|
||||
return tree.empty() ?
|
||||
Scalar(-1) :
|
||||
AABBTreeIndirect::detail::squared_distance_to_indexed_primitives_recursive(distancer, size_t(0), Scalar(0),
|
||||
std::numeric_limits<Scalar>::infinity(), hit_idx_out, hit_point_out);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
#endif /* SRC_LIBSLIC3R_AABBTREELINES_HPP_ */
|
@ -1,11 +1,12 @@
|
||||
#ifndef ASTAR_HPP
|
||||
#define ASTAR_HPP
|
||||
|
||||
#include <cmath> // std::isinf() is here
|
||||
#include <unordered_map>
|
||||
|
||||
#include "libslic3r/Point.hpp"
|
||||
#include "libslic3r/MutablePriorityQueue.hpp"
|
||||
|
||||
#include <unordered_map>
|
||||
|
||||
namespace Slic3r { namespace astar {
|
||||
|
||||
// Input interface for the Astar algorithm. Specialize this struct for a
|
||||
@ -34,6 +35,8 @@ template<class T> struct TracerTraits_
|
||||
// Get the estimated distance heuristic from node 'n' to the destination.
|
||||
// This is referred to as the h value in AStar context.
|
||||
// If node 'n' is the goal, this function should return a negative value.
|
||||
// Note that this heuristic should be admissible (never bigger than the real
|
||||
// cost) in order for Astar to work.
|
||||
static float goal_heuristic(const T &tracer, const Node &n)
|
||||
{
|
||||
return tracer.goal_heuristic(n);
|
||||
@ -50,131 +53,136 @@ template<class T> struct TracerTraits_
|
||||
template<class T>
|
||||
using TracerNodeT = typename TracerTraits_<remove_cvref_t<T>>::Node;
|
||||
|
||||
namespace detail {
|
||||
// Helper functions dispatching calls through the TracerTraits_ interface
|
||||
constexpr auto Unassigned = std::numeric_limits<size_t>::max();
|
||||
|
||||
template<class T> using TracerTraits = TracerTraits_<remove_cvref_t<T>>;
|
||||
|
||||
template<class T, class Fn>
|
||||
void foreach_reachable(const T &tracer, const TracerNodeT<T> &from, Fn &&fn)
|
||||
template<class Tracer>
|
||||
struct QNode // Queue node. Keeps track of scores g, and h
|
||||
{
|
||||
TracerTraits<T>::foreach_reachable(tracer, from, fn);
|
||||
}
|
||||
TracerNodeT<Tracer> node; // The actual node itself
|
||||
size_t queue_id; // Position in the open queue or Unassigned if closed
|
||||
size_t parent; // unique id of the parent or Unassigned
|
||||
|
||||
template<class T>
|
||||
float trace_distance(const T &tracer, const TracerNodeT<T> &a, const TracerNodeT<T> &b)
|
||||
{
|
||||
return TracerTraits<T>::distance(tracer, a, b);
|
||||
}
|
||||
float g, h;
|
||||
float f() const { return g + h; }
|
||||
|
||||
template<class T>
|
||||
float goal_heuristic(const T &tracer, const TracerNodeT<T> &n)
|
||||
{
|
||||
return TracerTraits<T>::goal_heuristic(tracer, n);
|
||||
}
|
||||
|
||||
template<class T>
|
||||
size_t unique_id(const T &tracer, const TracerNodeT<T> &n)
|
||||
{
|
||||
return TracerTraits<T>::unique_id(tracer, n);
|
||||
}
|
||||
|
||||
} // namespace astar_detail
|
||||
QNode(TracerNodeT<Tracer> n = {},
|
||||
size_t p = Unassigned,
|
||||
float gval = std::numeric_limits<float>::infinity(),
|
||||
float hval = 0.f)
|
||||
: node{std::move(n)}
|
||||
, parent{p}
|
||||
, queue_id{InvalidQueueID}
|
||||
, g{gval}
|
||||
, h{hval}
|
||||
{}
|
||||
};
|
||||
|
||||
// Run the AStar algorithm on a tracer implementation.
|
||||
// The 'tracer' argument encapsulates the domain (grid, point cloud, etc...)
|
||||
// The 'source' argument is the starting node.
|
||||
// The 'out' argument is the output iterator into which the output nodes are
|
||||
// written.
|
||||
// Note that no destination node is given. The tracer's goal_heuristic() method
|
||||
// should return a negative value if a node is a destination node.
|
||||
template<class Tracer, class It>
|
||||
bool search_route(const Tracer &tracer, const TracerNodeT<Tracer> &source, It out)
|
||||
// written. For performance reasons, the order is reverse, from the destination
|
||||
// to the source -- (destination included, source is not).
|
||||
// The 'cached_nodes' argument is an optional associative container to hold a
|
||||
// QNode entry for each visited node. Any compatible container can be used
|
||||
// (like std::map or maps with different allocators, even a sufficiently large
|
||||
// std::vector).
|
||||
//
|
||||
// Note that no destination node is given in the signature. The tracer's
|
||||
// goal_heuristic() method should return a negative value if a node is a
|
||||
// destination node.
|
||||
template<class Tracer,
|
||||
class It,
|
||||
class NodeMap = std::unordered_map<size_t, QNode<Tracer>>>
|
||||
bool search_route(const Tracer &tracer,
|
||||
const TracerNodeT<Tracer> &source,
|
||||
It out,
|
||||
NodeMap &&cached_nodes = {})
|
||||
{
|
||||
using namespace detail;
|
||||
using Node = TracerNodeT<Tracer>;
|
||||
using QNode = QNode<Tracer>;
|
||||
using TracerTraits = TracerTraits_<remove_cvref_t<Tracer>>;
|
||||
|
||||
using Node = TracerNodeT<Tracer>;
|
||||
enum class QueueType { Open, Closed, None };
|
||||
|
||||
struct QNode // Queue node. Keeps track of scores g, and h
|
||||
{
|
||||
Node node; // The actual node itself
|
||||
QueueType qtype = QueueType::None; // Which queue holds this node
|
||||
|
||||
float g = 0.f, h = 0.f;
|
||||
float f() const { return g + h; }
|
||||
};
|
||||
|
||||
// TODO: apply a linear memory allocator
|
||||
using QMap = std::unordered_map<size_t, QNode>;
|
||||
|
||||
// The traversed nodes are stored here encapsulated in QNodes
|
||||
QMap cached_nodes;
|
||||
|
||||
struct LessPred { // Comparison functor needed by MutablePriorityQueue
|
||||
QMap &m;
|
||||
struct LessPred { // Comparison functor needed by the priority queue
|
||||
NodeMap &m;
|
||||
bool operator ()(size_t node_a, size_t node_b) {
|
||||
auto ait = m.find(node_a);
|
||||
auto bit = m.find(node_b);
|
||||
assert (ait != m.end() && bit != m.end());
|
||||
|
||||
return ait->second.f() < bit->second.f();
|
||||
return m[node_a].f() < m[node_b].f();
|
||||
}
|
||||
};
|
||||
|
||||
auto qopen =
|
||||
make_mutable_priority_queue<size_t, false>([](size_t, size_t){},
|
||||
LessPred{cached_nodes});
|
||||
auto qopen = make_mutable_priority_queue<size_t, true>(
|
||||
[&cached_nodes](size_t el, size_t qidx) {
|
||||
cached_nodes[el].queue_id = qidx;
|
||||
},
|
||||
LessPred{cached_nodes});
|
||||
|
||||
auto qclosed =
|
||||
make_mutable_priority_queue<size_t, false>([](size_t, size_t){},
|
||||
LessPred{cached_nodes});
|
||||
QNode initial{source, /*parent = */ Unassigned, /*g = */0.f};
|
||||
size_t source_id = TracerTraits::unique_id(tracer, source);
|
||||
cached_nodes[source_id] = initial;
|
||||
qopen.push(source_id);
|
||||
|
||||
QNode initial{source, QueueType::Open};
|
||||
cached_nodes.insert({unique_id(tracer, source), initial});
|
||||
qopen.push(unique_id(tracer, source));
|
||||
size_t goal_id = TracerTraits::goal_heuristic(tracer, source) < 0.f ?
|
||||
source_id :
|
||||
Unassigned;
|
||||
|
||||
bool goal_reached = false;
|
||||
|
||||
while (!goal_reached && !qopen.empty()) {
|
||||
while (goal_id == Unassigned && !qopen.empty()) {
|
||||
size_t q_id = qopen.top();
|
||||
qopen.pop();
|
||||
QNode q = cached_nodes.at(q_id);
|
||||
QNode &q = cached_nodes[q_id];
|
||||
|
||||
foreach_reachable(tracer, q.node, [&](const Node &nd) {
|
||||
if (goal_reached) return goal_reached;
|
||||
// This should absolutely be initialized in the cache already
|
||||
assert(!std::isinf(q.g));
|
||||
|
||||
TracerTraits::foreach_reachable(tracer, q.node, [&](const Node &succ_nd) {
|
||||
if (goal_id != Unassigned)
|
||||
return true;
|
||||
|
||||
float h = TracerTraits::goal_heuristic(tracer, succ_nd);
|
||||
float dst = TracerTraits::distance(tracer, q.node, succ_nd);
|
||||
size_t succ_id = TracerTraits::unique_id(tracer, succ_nd);
|
||||
QNode qsucc_nd{succ_nd, q_id, q.g + dst, h};
|
||||
|
||||
float h = goal_heuristic(tracer, nd);
|
||||
if (h < 0.f) {
|
||||
goal_reached = true;
|
||||
goal_id = succ_id;
|
||||
cached_nodes[succ_id] = qsucc_nd;
|
||||
} else {
|
||||
float dst = trace_distance(tracer, q.node, nd);
|
||||
QNode qnd{nd, QueueType::None, q.g + dst, h};
|
||||
size_t qnd_id = unique_id(tracer, nd);
|
||||
// If succ_id is not in cache, it gets created with g = infinity
|
||||
QNode &prev_nd = cached_nodes[succ_id];
|
||||
|
||||
auto it = cached_nodes.find(qnd_id);
|
||||
if (qsucc_nd.g < prev_nd.g) {
|
||||
// new route is better, apply it:
|
||||
|
||||
if (it == cached_nodes.end() ||
|
||||
(it->second.qtype != QueueType::None && qnd.f() < it->second.f())) {
|
||||
qnd.qtype = QueueType::Open;
|
||||
cached_nodes.insert_or_assign(qnd_id, qnd);
|
||||
qopen.push(qnd_id);
|
||||
// Save the old queue id, it would be lost after the next line
|
||||
size_t queue_id = prev_nd.queue_id;
|
||||
|
||||
// The cache needs to be updated either way
|
||||
prev_nd = qsucc_nd;
|
||||
|
||||
if (queue_id == InvalidQueueID)
|
||||
// was in closed or unqueued, rescheduling
|
||||
qopen.push(succ_id);
|
||||
else // was in open, updating
|
||||
qopen.update(queue_id);
|
||||
}
|
||||
}
|
||||
|
||||
return goal_reached;
|
||||
return goal_id != Unassigned;
|
||||
});
|
||||
|
||||
q.qtype = QueueType::Closed;
|
||||
cached_nodes.insert_or_assign(q_id, q);
|
||||
qclosed.push(q_id);
|
||||
|
||||
// write the output
|
||||
*out = q.node;
|
||||
++out;
|
||||
}
|
||||
|
||||
return goal_reached;
|
||||
// Write the output, do not reverse. Clients can do so if they need to.
|
||||
if (goal_id != Unassigned) {
|
||||
const QNode *q = &cached_nodes[goal_id];
|
||||
while (q->parent != Unassigned) {
|
||||
assert(!std::isinf(q->g)); // Uninitialized nodes are NOT allowed
|
||||
|
||||
*out = q->node;
|
||||
++out;
|
||||
q = &cached_nodes[q->parent];
|
||||
}
|
||||
}
|
||||
|
||||
return goal_id != Unassigned;
|
||||
}
|
||||
|
||||
}} // namespace Slic3r::astar
|
||||
|
@ -230,8 +230,13 @@ static std::string appconfig_md5_hash_line(const std::string_view data)
|
||||
return "# MD5 checksum " + md5_digest_str + "\n";
|
||||
};
|
||||
|
||||
struct ConfigFileInfo {
|
||||
bool correct_checksum {false};
|
||||
bool contains_null {false};
|
||||
};
|
||||
|
||||
// Assume that the last line with the comment inside the config file contains a checksum and that the user didn't modify the config file.
|
||||
static bool verify_config_file_checksum(boost::nowide::ifstream &ifs)
|
||||
static ConfigFileInfo check_config_file_and_verify_checksum(boost::nowide::ifstream &ifs)
|
||||
{
|
||||
auto read_whole_config_file = [&ifs]() -> std::string {
|
||||
std::stringstream ss;
|
||||
@ -240,7 +245,8 @@ static bool verify_config_file_checksum(boost::nowide::ifstream &ifs)
|
||||
};
|
||||
|
||||
ifs.seekg(0, boost::nowide::ifstream::beg);
|
||||
std::string whole_config = read_whole_config_file();
|
||||
const std::string whole_config = read_whole_config_file();
|
||||
const bool contains_null = whole_config.find_first_of('\0') != std::string::npos;
|
||||
|
||||
// The checksum should be on the last line in the config file.
|
||||
if (size_t last_comment_pos = whole_config.find_last_of('#'); last_comment_pos != std::string::npos) {
|
||||
@ -249,9 +255,9 @@ static bool verify_config_file_checksum(boost::nowide::ifstream &ifs)
|
||||
// When the checksum isn't found, the checksum was not saved correctly, it was removed or it is an older config file without the checksum.
|
||||
// If the checksum is incorrect, then the file was either not saved correctly or modified.
|
||||
if (std::string_view(whole_config.c_str() + last_comment_pos, whole_config.size() - last_comment_pos) == appconfig_md5_hash_line({ whole_config.data(), last_comment_pos }))
|
||||
return true;
|
||||
return {true, contains_null};
|
||||
}
|
||||
return false;
|
||||
return {false, contains_null};
|
||||
}
|
||||
#endif
|
||||
|
||||
@ -269,14 +275,25 @@ std::string AppConfig::load(const std::string &path)
|
||||
ifs.open(path);
|
||||
#ifdef WIN32
|
||||
// Verify the checksum of the config file without taking just for debugging purpose.
|
||||
if (!verify_config_file_checksum(ifs))
|
||||
BOOST_LOG_TRIVIAL(info) << "The configuration file " << path <<
|
||||
" has a wrong MD5 checksum or the checksum is missing. This may indicate a file corruption or a harmless user edit.";
|
||||
const ConfigFileInfo config_file_info = check_config_file_and_verify_checksum(ifs);
|
||||
if (!config_file_info.correct_checksum)
|
||||
BOOST_LOG_TRIVIAL(info)
|
||||
<< "The configuration file " << path
|
||||
<< " has a wrong MD5 checksum or the checksum is missing. This may indicate a file corruption or a harmless user edit.";
|
||||
|
||||
if (!config_file_info.correct_checksum && config_file_info.contains_null) {
|
||||
BOOST_LOG_TRIVIAL(info) << "The configuration file " + path + " is corrupted, because it is contains null characters.";
|
||||
throw Slic3r::CriticalException("The configuration file contains null characters.");
|
||||
}
|
||||
|
||||
ifs.seekg(0, boost::nowide::ifstream::beg);
|
||||
#endif
|
||||
pt::read_ini(ifs, tree);
|
||||
} catch (pt::ptree_error& ex) {
|
||||
try {
|
||||
pt::read_ini(ifs, tree);
|
||||
} catch (pt::ptree_error &ex) {
|
||||
throw Slic3r::CriticalException(ex.what());
|
||||
}
|
||||
} catch (Slic3r::CriticalException &ex) {
|
||||
#ifdef WIN32
|
||||
// The configuration file is corrupted, try replacing it with the backup configuration.
|
||||
ifs.close();
|
||||
@ -284,29 +301,29 @@ std::string AppConfig::load(const std::string &path)
|
||||
if (boost::filesystem::exists(backup_path)) {
|
||||
// Compute checksum of the configuration backup file and try to load configuration from it when the checksum is correct.
|
||||
boost::nowide::ifstream backup_ifs(backup_path);
|
||||
if (!verify_config_file_checksum(backup_ifs)) {
|
||||
BOOST_LOG_TRIVIAL(error) << format("Both \"%1%\" and \"%2%\" are corrupted. It isn't possible to restore configuration from the backup.", path, backup_path);
|
||||
if (const ConfigFileInfo config_file_info = check_config_file_and_verify_checksum(backup_ifs); !config_file_info.correct_checksum || config_file_info.contains_null) {
|
||||
BOOST_LOG_TRIVIAL(error) << format(R"(Both "%1%" and "%2%" are corrupted. It isn't possible to restore configuration from the backup.)", path, backup_path);
|
||||
backup_ifs.close();
|
||||
boost::filesystem::remove(backup_path);
|
||||
} else if (std::string error_message; copy_file(backup_path, path, error_message, false) != SUCCESS) {
|
||||
BOOST_LOG_TRIVIAL(error) << format("Configuration file \"%1%\" is corrupted. Failed to restore from backup \"%2%\": %3%", path, backup_path, error_message);
|
||||
BOOST_LOG_TRIVIAL(error) << format(R"(Configuration file "%1%" is corrupted. Failed to restore from backup "%2%": %3%)", path, backup_path, error_message);
|
||||
backup_ifs.close();
|
||||
boost::filesystem::remove(backup_path);
|
||||
} else {
|
||||
BOOST_LOG_TRIVIAL(info) << format("Configuration file \"%1%\" was corrupted. It has been succesfully restored from the backup \"%2%\".", path, backup_path);
|
||||
BOOST_LOG_TRIVIAL(info) << format(R"(Configuration file "%1%" was corrupted. It has been successfully restored from the backup "%2%".)", path, backup_path);
|
||||
// Try parse configuration file after restore from backup.
|
||||
try {
|
||||
ifs.open(path);
|
||||
pt::read_ini(ifs, tree);
|
||||
recovered = true;
|
||||
} catch (pt::ptree_error& ex) {
|
||||
BOOST_LOG_TRIVIAL(info) << format("Failed to parse configuration file \"%1%\" after it has been restored from backup: %2%", path, ex.what());
|
||||
BOOST_LOG_TRIVIAL(info) << format(R"(Failed to parse configuration file "%1%" after it has been restored from backup: %2%)", path, ex.what());
|
||||
}
|
||||
}
|
||||
} else
|
||||
#endif // WIN32
|
||||
BOOST_LOG_TRIVIAL(info) << format("Failed to parse configuration file \"%1%\": %2%", path, ex.what());
|
||||
if (! recovered) {
|
||||
BOOST_LOG_TRIVIAL(info) << format(R"(Failed to parse configuration file "%1%": %2%)", path, ex.what());
|
||||
if (!recovered) {
|
||||
// Report the initial error of parsing PrusaSlicer.ini.
|
||||
// Error while parsing config file. We'll customize the error message and rethrow to be displayed.
|
||||
// ! But to avoid the use of _utf8 (related to use of wxWidgets)
|
||||
|
@ -238,7 +238,7 @@ BuildVolume::ObjectState object_state_templ(const indexed_triangle_set &its, con
|
||||
const stl_vertex p2 = trafo * its.vertices[tri(iedge)];
|
||||
assert(sign(p1) == s[iprev]);
|
||||
assert(sign(p2) == s[iedge]);
|
||||
assert(p1.z() * p2.z() < 0);
|
||||
assert((p1.z() - world_min_z) * (p2.z() - world_min_z) < 0);
|
||||
// Edge crosses the z plane. Calculate intersection point with the plane.
|
||||
const float t = (world_min_z - p1.z()) / (p2.z() - p1.z());
|
||||
(is_inside(Vec3f(p1.x() + (p2.x() - p1.x()) * t, p1.y() + (p2.y() - p1.y()) * t, world_min_z)) ? inside : outside) = true;
|
||||
|
@ -1,29 +1,34 @@
|
||||
#include "../Print.hpp"
|
||||
#include "../ShortestPath.hpp"
|
||||
|
||||
#include "FillLightning.hpp"
|
||||
#include "Lightning/Generator.hpp"
|
||||
#include "../Surface.hpp"
|
||||
|
||||
#include <cstdlib>
|
||||
#include <cmath>
|
||||
#include <algorithm>
|
||||
#include <numeric>
|
||||
|
||||
namespace Slic3r::FillLightning {
|
||||
|
||||
Polylines Filler::fill_surface(const Surface *surface, const FillParams ¶ms)
|
||||
void Filler::_fill_surface_single(
|
||||
const FillParams ¶ms,
|
||||
unsigned int thickness_layers,
|
||||
const std::pair<float, Point> &direction,
|
||||
ExPolygon expolygon,
|
||||
Polylines &polylines_out)
|
||||
{
|
||||
const Layer &layer = generator->getTreesForLayer(this->layer_id);
|
||||
return layer.convertToLines(to_polygons(surface->expolygon), generator->infilll_extrusion_width());
|
||||
const Layer &layer = generator->getTreesForLayer(this->layer_id);
|
||||
Polylines fill_lines = layer.convertToLines(to_polygons(expolygon), scaled<coord_t>(0.5 * this->spacing - this->overlap));
|
||||
|
||||
if (params.dont_connect() || fill_lines.size() <= 1) {
|
||||
append(polylines_out, chain_polylines(std::move(fill_lines)));
|
||||
} else
|
||||
connect_infill(std::move(fill_lines), expolygon, polylines_out, this->spacing, params);
|
||||
}
|
||||
|
||||
void GeneratorDeleter::operator()(Generator *p) {
|
||||
delete p;
|
||||
}
|
||||
|
||||
GeneratorPtr build_generator(const PrintObject &print_object)
|
||||
GeneratorPtr build_generator(const PrintObject &print_object, const std::function<void()> &throw_on_cancel_callback)
|
||||
{
|
||||
return GeneratorPtr(new Generator(print_object));
|
||||
return GeneratorPtr(new Generator(print_object, throw_on_cancel_callback));
|
||||
}
|
||||
|
||||
} // namespace Slic3r::FillAdaptive
|
||||
|
@ -14,7 +14,7 @@ class Generator;
|
||||
struct GeneratorDeleter { void operator()(Generator *p); };
|
||||
using GeneratorPtr = std::unique_ptr<Generator, GeneratorDeleter>;
|
||||
|
||||
GeneratorPtr build_generator(const PrintObject &print_object);
|
||||
GeneratorPtr build_generator(const PrintObject &print_object, const std::function<void()> &throw_on_cancel_callback);
|
||||
|
||||
class Filler : public Slic3r::Fill
|
||||
{
|
||||
@ -24,8 +24,13 @@ public:
|
||||
Generator *generator { nullptr };
|
||||
protected:
|
||||
Fill* clone() const override { return new Filler(*this); }
|
||||
// Perform the fill.
|
||||
Polylines fill_surface(const Surface *surface, const FillParams ¶ms) override;
|
||||
|
||||
void _fill_surface_single(const FillParams ¶ms,
|
||||
unsigned int thickness_layers,
|
||||
const std::pair<float, Point> &direction,
|
||||
ExPolygon expolygon,
|
||||
Polylines &polylines_out) override;
|
||||
|
||||
// Let the G-code export reoder the infill lines.
|
||||
bool no_sort() const override { return false; }
|
||||
};
|
||||
|
@ -3043,14 +3043,18 @@ Polylines FillSupportBase::fill_surface(const Surface *surface, const FillParams
|
||||
return polylines_out;
|
||||
}
|
||||
|
||||
Points sample_grid_pattern(const ExPolygon &expolygon, coord_t spacing)
|
||||
// Lightning infill assumes that the distance between any two sampled points is always
|
||||
// at least equal to the value of spacing. To meet this assumption, we need to use
|
||||
// BoundingBox for whole layers instead of bounding box just around processing ExPolygon.
|
||||
// Using just BoundingBox around processing ExPolygon could produce two points closer
|
||||
// than spacing (in cases where two ExPolygon are closer than spacing).
|
||||
Points sample_grid_pattern(const ExPolygon &expolygon, coord_t spacing, const BoundingBox &global_bounding_box)
|
||||
{
|
||||
ExPolygonWithOffset poly_with_offset(expolygon, 0, 0, 0);
|
||||
BoundingBox bounding_box = poly_with_offset.bounding_box_src();
|
||||
std::vector<SegmentedIntersectionLine> segs = slice_region_by_vertical_lines(
|
||||
poly_with_offset,
|
||||
(bounding_box.max.x() - bounding_box.min.x() + spacing - 1) / spacing,
|
||||
bounding_box.min.x(),
|
||||
(global_bounding_box.max.x() - global_bounding_box.min.x() + spacing - 1) / spacing,
|
||||
global_bounding_box.min.x(),
|
||||
spacing);
|
||||
|
||||
Points out;
|
||||
@ -3066,17 +3070,17 @@ Points sample_grid_pattern(const ExPolygon &expolygon, coord_t spacing)
|
||||
return out;
|
||||
}
|
||||
|
||||
Points sample_grid_pattern(const ExPolygons &expolygons, coord_t spacing)
|
||||
Points sample_grid_pattern(const ExPolygons &expolygons, coord_t spacing, const BoundingBox &global_bounding_box)
|
||||
{
|
||||
Points out;
|
||||
for (const ExPolygon &expoly : expolygons)
|
||||
append(out, sample_grid_pattern(expoly, spacing));
|
||||
append(out, sample_grid_pattern(expoly, spacing, global_bounding_box));
|
||||
return out;
|
||||
}
|
||||
|
||||
Points sample_grid_pattern(const Polygons &polygons, coord_t spacing)
|
||||
Points sample_grid_pattern(const Polygons &polygons, coord_t spacing, const BoundingBox &global_bounding_box)
|
||||
{
|
||||
return sample_grid_pattern(union_ex(polygons), spacing);
|
||||
return sample_grid_pattern(union_ex(polygons), spacing, global_bounding_box);
|
||||
}
|
||||
|
||||
} // namespace Slic3r
|
||||
|
@ -109,9 +109,9 @@ protected:
|
||||
float _layer_angle(size_t idx) const override { return 0.f; }
|
||||
};
|
||||
|
||||
Points sample_grid_pattern(const ExPolygon &expolygon, coord_t spacing);
|
||||
Points sample_grid_pattern(const ExPolygons &expolygons, coord_t spacing);
|
||||
Points sample_grid_pattern(const Polygons &polygons, coord_t spacing);
|
||||
Points sample_grid_pattern(const ExPolygon &expolygon, coord_t spacing, const BoundingBox &global_bounding_box);
|
||||
Points sample_grid_pattern(const ExPolygons &expolygons, coord_t spacing, const BoundingBox &global_bounding_box);
|
||||
Points sample_grid_pattern(const Polygons &polygons, coord_t spacing, const BoundingBox &global_bounding_box);
|
||||
|
||||
} // namespace Slic3r
|
||||
|
||||
|
@ -5,11 +5,36 @@
|
||||
#include "../FillRectilinear.hpp"
|
||||
#include "../../ClipperUtils.hpp"
|
||||
|
||||
#include <tbb/parallel_for.h>
|
||||
|
||||
#ifdef LIGHTNING_DISTANCE_FIELD_DEBUG_OUTPUT
|
||||
#include "../../SVG.hpp"
|
||||
#endif
|
||||
|
||||
namespace Slic3r::FillLightning
|
||||
{
|
||||
|
||||
constexpr coord_t radius_per_cell_size = 6; // The cell-size should be small compared to the radius, but not so small as to be inefficient.
|
||||
|
||||
#ifdef LIGHTNING_DISTANCE_FIELD_DEBUG_OUTPUT
|
||||
void export_distance_field_to_svg(const std::string &path, const Polygons &outline, const Polygons &overhang, const std::list<DistanceField::UnsupportedCell> &unsupported_points, const Points &points = {})
|
||||
{
|
||||
coordf_t stroke_width = scaled<coordf_t>(0.01);
|
||||
BoundingBox bbox = get_extents(outline);
|
||||
|
||||
bbox.offset(SCALED_EPSILON);
|
||||
SVG svg(path, bbox);
|
||||
svg.draw_outline(outline, "green", stroke_width);
|
||||
svg.draw_outline(overhang, "blue", stroke_width);
|
||||
|
||||
for (const DistanceField::UnsupportedCell &cell : unsupported_points)
|
||||
svg.draw(cell.loc, "cyan", coord_t(stroke_width));
|
||||
|
||||
for (const Point &pt : points)
|
||||
svg.draw(pt, "red", coord_t(stroke_width));
|
||||
}
|
||||
#endif
|
||||
|
||||
DistanceField::DistanceField(const coord_t& radius, const Polygons& current_outline, const BoundingBox& current_outlines_bbox, const Polygons& current_overhang) :
|
||||
m_cell_size(radius / radius_per_cell_size),
|
||||
m_supporting_radius(radius),
|
||||
@ -17,37 +42,54 @@ DistanceField::DistanceField(const coord_t& radius, const Polygons& current_outl
|
||||
{
|
||||
m_supporting_radius2 = Slic3r::sqr(int64_t(radius));
|
||||
// Sample source polygons with a regular grid sampling pattern.
|
||||
const BoundingBox overhang_bbox = get_extents(current_overhang);
|
||||
for (const ExPolygon &expoly : union_ex(current_overhang)) {
|
||||
for (const Point &p : sample_grid_pattern(expoly, m_cell_size)) {
|
||||
// Find a squared distance to the source expolygon boundary.
|
||||
double d2 = std::numeric_limits<double>::max();
|
||||
for (size_t icontour = 0; icontour <= expoly.holes.size(); ++icontour) {
|
||||
const Polygon &contour = icontour == 0 ? expoly.contour : expoly.holes[icontour - 1];
|
||||
if (contour.size() > 2) {
|
||||
Point prev = contour.points.back();
|
||||
for (const Point &p2 : contour.points) {
|
||||
d2 = std::min(d2, Line::distance_to_squared(p, prev, p2));
|
||||
prev = p2;
|
||||
const Points sampled_points = sample_grid_pattern(expoly, m_cell_size, overhang_bbox);
|
||||
const size_t unsupported_points_prev_size = m_unsupported_points.size();
|
||||
m_unsupported_points.resize(unsupported_points_prev_size + sampled_points.size());
|
||||
|
||||
tbb::parallel_for(tbb::blocked_range<size_t>(0, sampled_points.size()), [&self = *this, &expoly = std::as_const(expoly), &sampled_points = std::as_const(sampled_points), &unsupported_points_prev_size = std::as_const(unsupported_points_prev_size)](const tbb::blocked_range<size_t> &range) -> void {
|
||||
for (size_t sp_idx = range.begin(); sp_idx < range.end(); ++sp_idx) {
|
||||
const Point &sp = sampled_points[sp_idx];
|
||||
// Find a squared distance to the source expolygon boundary.
|
||||
double d2 = std::numeric_limits<double>::max();
|
||||
for (size_t icontour = 0; icontour <= expoly.holes.size(); ++icontour) {
|
||||
const Polygon &contour = icontour == 0 ? expoly.contour : expoly.holes[icontour - 1];
|
||||
if (contour.size() > 2) {
|
||||
Point prev = contour.points.back();
|
||||
for (const Point &p2 : contour.points) {
|
||||
d2 = std::min(d2, Line::distance_to_squared(sp, prev, p2));
|
||||
prev = p2;
|
||||
}
|
||||
}
|
||||
}
|
||||
self.m_unsupported_points[unsupported_points_prev_size + sp_idx] = {sp, coord_t(std::sqrt(d2))};
|
||||
assert(self.m_unsupported_points_bbox.contains(sp));
|
||||
}
|
||||
m_unsupported_points.emplace_back(p, sqrt(d2));
|
||||
assert(m_unsupported_points_bbox.contains(p));
|
||||
}
|
||||
}); // end of parallel_for
|
||||
}
|
||||
m_unsupported_points.sort([&radius](const UnsupportedCell &a, const UnsupportedCell &b) {
|
||||
std::stable_sort(m_unsupported_points.begin(), m_unsupported_points.end(), [&radius](const UnsupportedCell &a, const UnsupportedCell &b) {
|
||||
constexpr coord_t prime_for_hash = 191;
|
||||
return std::abs(b.dist_to_boundary - a.dist_to_boundary) > radius ?
|
||||
a.dist_to_boundary < b.dist_to_boundary :
|
||||
(PointHash{}(a.loc) % prime_for_hash) < (PointHash{}(b.loc) % prime_for_hash);
|
||||
});
|
||||
for (auto it = m_unsupported_points.begin(); it != m_unsupported_points.end(); ++it) {
|
||||
UnsupportedCell& cell = *it;
|
||||
m_unsupported_points_grid.emplace(this->to_grid_point(cell.loc), it);
|
||||
}
|
||||
|
||||
m_unsupported_points_erased.resize(m_unsupported_points.size());
|
||||
std::fill(m_unsupported_points_erased.begin(), m_unsupported_points_erased.end(), false);
|
||||
|
||||
m_unsupported_points_grid.initialize(m_unsupported_points, [&self = std::as_const(*this)](const Point &p) -> Point { return self.to_grid_point(p); });
|
||||
|
||||
// Because the distance between two points is at least one axis equal to m_cell_size, every cell
|
||||
// in m_unsupported_points_grid contains exactly one point.
|
||||
assert(m_unsupported_points.size() == m_unsupported_points_grid.size());
|
||||
|
||||
#ifdef LIGHTNING_DISTANCE_FIELD_DEBUG_OUTPUT
|
||||
{
|
||||
static int iRun = 0;
|
||||
export_distance_field_to_svg(debug_out_path("FillLightning-DistanceField-%d.svg", iRun++), current_outline, current_overhang, m_unsupported_points);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
void DistanceField::update(const Point& to_node, const Point& added_leaf)
|
||||
@ -96,12 +138,11 @@ void DistanceField::update(const Point& to_node, const Point& added_leaf)
|
||||
}
|
||||
// Inside a circle at the end of the new leaf, or inside a rotated rectangle.
|
||||
// Remove unsupported leafs at this grid location.
|
||||
if (auto it = m_unsupported_points_grid.find(grid_addr); it != m_unsupported_points_grid.end()) {
|
||||
std::list<UnsupportedCell>::iterator& list_it = it->second;
|
||||
UnsupportedCell& cell = *list_it;
|
||||
if (const size_t cell_idx = m_unsupported_points_grid.find_cell_idx(grid_addr); cell_idx != std::numeric_limits<size_t>::max()) {
|
||||
const UnsupportedCell &cell = m_unsupported_points[cell_idx];
|
||||
if ((cell.loc - added_leaf).cast<int64_t>().squaredNorm() <= m_supporting_radius2) {
|
||||
m_unsupported_points.erase(list_it);
|
||||
m_unsupported_points_grid.erase(it);
|
||||
m_unsupported_points_erased[cell_idx] = true;
|
||||
m_unsupported_points_grid.mark_erased(grid_addr);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -8,6 +8,8 @@
|
||||
#include "../../Point.hpp"
|
||||
#include "../../Polygon.hpp"
|
||||
|
||||
//#define LIGHTNING_DISTANCE_FIELD_DEBUG_OUTPUT
|
||||
|
||||
namespace Slic3r::FillLightning
|
||||
{
|
||||
|
||||
@ -38,11 +40,17 @@ public:
|
||||
* \return ``true`` if successful, or ``false`` if there are no more points
|
||||
* to consider.
|
||||
*/
|
||||
bool tryGetNextPoint(Point* p) const {
|
||||
if (m_unsupported_points.empty())
|
||||
return false;
|
||||
*p = m_unsupported_points.front().loc;
|
||||
return true;
|
||||
bool tryGetNextPoint(Point *out_unsupported_location, size_t *out_unsupported_cell_idx, const size_t start_idx = 0) const
|
||||
{
|
||||
for (size_t point_idx = start_idx; point_idx < m_unsupported_points.size(); ++point_idx) {
|
||||
if (!m_unsupported_points_erased[point_idx]) {
|
||||
*out_unsupported_cell_idx = point_idx;
|
||||
*out_unsupported_location = m_unsupported_points[point_idx].loc;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/*!
|
||||
@ -77,7 +85,6 @@ protected:
|
||||
*/
|
||||
struct UnsupportedCell
|
||||
{
|
||||
UnsupportedCell(const Point &loc, coord_t dist_to_boundary) : loc(loc), dist_to_boundary(dist_to_boundary) {}
|
||||
// The position of the center of this cell.
|
||||
Point loc;
|
||||
// How far this cell is removed from the ``current_outline`` polygon, the edge of the infill area.
|
||||
@ -87,7 +94,8 @@ protected:
|
||||
/*!
|
||||
* Cells which still need to be supported at some point.
|
||||
*/
|
||||
std::list<UnsupportedCell> m_unsupported_points;
|
||||
std::vector<UnsupportedCell> m_unsupported_points;
|
||||
std::vector<bool> m_unsupported_points_erased;
|
||||
|
||||
/*!
|
||||
* BoundingBox of all points in m_unsupported_points. Used for mapping of sign integer numbers to positive integer numbers.
|
||||
@ -98,7 +106,84 @@ protected:
|
||||
* Links the unsupported points to a grid point, so that we can quickly look
|
||||
* up the cell belonging to a certain position in the grid.
|
||||
*/
|
||||
std::unordered_map<Point, std::list<UnsupportedCell>::iterator, PointHash> m_unsupported_points_grid;
|
||||
|
||||
class UnsupportedPointsGrid
|
||||
{
|
||||
public:
|
||||
UnsupportedPointsGrid() = default;
|
||||
void initialize(const std::vector<UnsupportedCell> &unsupported_points, const std::function<Point(const Point &)> &map_cell_to_grid)
|
||||
{
|
||||
if (unsupported_points.empty())
|
||||
return;
|
||||
|
||||
BoundingBox unsupported_points_bbox;
|
||||
for (const UnsupportedCell &cell : unsupported_points)
|
||||
unsupported_points_bbox.merge(cell.loc);
|
||||
|
||||
m_size = unsupported_points.size();
|
||||
m_grid_range = BoundingBox(map_cell_to_grid(unsupported_points_bbox.min), map_cell_to_grid(unsupported_points_bbox.max));
|
||||
m_grid_size = m_grid_range.size() + Point::Ones();
|
||||
|
||||
m_data.assign(m_grid_size.y() * m_grid_size.x(), std::numeric_limits<size_t>::max());
|
||||
m_data_erased.assign(m_grid_size.y() * m_grid_size.x(), true);
|
||||
|
||||
for (size_t cell_idx = 0; cell_idx < unsupported_points.size(); ++cell_idx) {
|
||||
const size_t flat_idx = map_to_flat_array(map_cell_to_grid(unsupported_points[cell_idx].loc));
|
||||
assert(m_data[flat_idx] == std::numeric_limits<size_t>::max());
|
||||
m_data[flat_idx] = cell_idx;
|
||||
m_data_erased[flat_idx] = false;
|
||||
}
|
||||
}
|
||||
|
||||
size_t size() const { return m_size; }
|
||||
|
||||
size_t find_cell_idx(const Point &grid_addr)
|
||||
{
|
||||
if (!m_grid_range.contains(grid_addr))
|
||||
return std::numeric_limits<size_t>::max();
|
||||
|
||||
if (const size_t flat_idx = map_to_flat_array(grid_addr); !m_data_erased[flat_idx]) {
|
||||
assert(m_data[flat_idx] != std::numeric_limits<size_t>::max());
|
||||
return m_data[flat_idx];
|
||||
}
|
||||
|
||||
return std::numeric_limits<size_t>::max();
|
||||
}
|
||||
|
||||
void mark_erased(const Point &grid_addr)
|
||||
{
|
||||
assert(m_grid_range.contains(grid_addr));
|
||||
if (!m_grid_range.contains(grid_addr))
|
||||
return;
|
||||
|
||||
const size_t flat_idx = map_to_flat_array(grid_addr);
|
||||
assert(!m_data_erased[flat_idx] && m_data[flat_idx] != std::numeric_limits<size_t>::max());
|
||||
assert(m_size != 0);
|
||||
|
||||
m_data_erased[flat_idx] = true;
|
||||
--m_size;
|
||||
}
|
||||
|
||||
private:
|
||||
size_t m_size = 0;
|
||||
|
||||
BoundingBox m_grid_range;
|
||||
Point m_grid_size;
|
||||
|
||||
std::vector<size_t> m_data;
|
||||
std::vector<bool> m_data_erased;
|
||||
|
||||
inline size_t map_to_flat_array(const Point &loc) const
|
||||
{
|
||||
const Point offset_loc = loc - m_grid_range.min;
|
||||
const size_t flat_idx = m_grid_size.x() * offset_loc.y() + offset_loc.x();
|
||||
assert(offset_loc.x() >= 0 && offset_loc.y() >= 0);
|
||||
assert(flat_idx < size_t(m_grid_size.y() * m_grid_size.x()));
|
||||
return flat_idx;
|
||||
}
|
||||
};
|
||||
|
||||
UnsupportedPointsGrid m_unsupported_points_grid;
|
||||
|
||||
/*!
|
||||
* Maps the point to the grid coordinates.
|
||||
@ -113,6 +198,10 @@ protected:
|
||||
Point from_grid_point(const Point &point) const {
|
||||
return point * m_cell_size + m_unsupported_points_bbox.min;
|
||||
}
|
||||
|
||||
#ifdef LIGHTNING_DISTANCE_FIELD_DEBUG_OUTPUT
|
||||
friend void export_distance_field_to_svg(const std::string &path, const Polygons &outline, const Polygons &overhang, const std::list<DistanceField::UnsupportedCell> &unsupported_points, const Points &points);
|
||||
#endif
|
||||
};
|
||||
|
||||
} // namespace Slic3r::FillLightning
|
||||
|
@ -7,7 +7,6 @@
|
||||
#include "../../ClipperUtils.hpp"
|
||||
#include "../../Layer.hpp"
|
||||
#include "../../Print.hpp"
|
||||
#include "../../Surface.hpp"
|
||||
|
||||
/* Possible future tasks/optimizations,etc.:
|
||||
* - Improve connecting heuristic to favor connecting to shorter trees
|
||||
@ -25,7 +24,7 @@
|
||||
|
||||
namespace Slic3r::FillLightning {
|
||||
|
||||
Generator::Generator(const PrintObject &print_object)
|
||||
Generator::Generator(const PrintObject &print_object, const std::function<void()> &throw_on_cancel_callback)
|
||||
{
|
||||
const PrintConfig &print_config = print_object.print()->config();
|
||||
const PrintObjectConfig &object_config = print_object.config();
|
||||
@ -47,24 +46,23 @@ Generator::Generator(const PrintObject &print_object)
|
||||
m_prune_length = coord_t(layer_thickness * std::tan(lightning_infill_prune_angle));
|
||||
m_straightening_max_distance = coord_t(layer_thickness * std::tan(lightning_infill_straightening_angle));
|
||||
|
||||
generateInitialInternalOverhangs(print_object);
|
||||
generateTrees(print_object);
|
||||
generateInitialInternalOverhangs(print_object, throw_on_cancel_callback);
|
||||
generateTrees(print_object, throw_on_cancel_callback);
|
||||
}
|
||||
|
||||
void Generator::generateInitialInternalOverhangs(const PrintObject &print_object)
|
||||
void Generator::generateInitialInternalOverhangs(const PrintObject &print_object, const std::function<void()> &throw_on_cancel_callback)
|
||||
{
|
||||
m_overhang_per_layer.resize(print_object.layers().size());
|
||||
// FIXME: It can be adjusted to improve bonding between infill and perimeters.
|
||||
const float infill_wall_offset = 0;// m_infill_extrusion_width;
|
||||
|
||||
Polygons infill_area_above;
|
||||
//Iterate from top to bottom, to subtract the overhang areas above from the overhang areas on the layer below, to get only overhang in the top layer where it is overhanging.
|
||||
for (int layer_nr = int(print_object.layers().size()) - 1; layer_nr >= 0; layer_nr--) {
|
||||
for (int layer_nr = int(print_object.layers().size()) - 1; layer_nr >= 0; --layer_nr) {
|
||||
throw_on_cancel_callback();
|
||||
Polygons infill_area_here;
|
||||
for (const LayerRegion* layerm : print_object.get_layer(layer_nr)->regions())
|
||||
for (const Surface& surface : layerm->fill_surfaces.surfaces)
|
||||
if (surface.surface_type == stInternal || surface.surface_type == stInternalVoid)
|
||||
append(infill_area_here, infill_wall_offset == 0 ? surface.expolygon : offset(surface.expolygon, infill_wall_offset));
|
||||
append(infill_area_here, to_polygons(surface.expolygon));
|
||||
|
||||
//Remove the part of the infill area that is already supported by the walls.
|
||||
Polygons overhang = diff(offset(infill_area_here, -float(m_wall_supporting_radius)), infill_area_above);
|
||||
@ -80,20 +78,20 @@ const Layer& Generator::getTreesForLayer(const size_t& layer_id) const
|
||||
return m_lightning_layers[layer_id];
|
||||
}
|
||||
|
||||
void Generator::generateTrees(const PrintObject &print_object)
|
||||
void Generator::generateTrees(const PrintObject &print_object, const std::function<void()> &throw_on_cancel_callback)
|
||||
{
|
||||
m_lightning_layers.resize(print_object.layers().size());
|
||||
// FIXME: It can be adjusted to improve bonding between infill and perimeters.
|
||||
const coord_t infill_wall_offset = 0;// m_infill_extrusion_width;
|
||||
|
||||
std::vector<Polygons> infill_outlines(print_object.layers().size(), Polygons());
|
||||
|
||||
// For-each layer from top to bottom:
|
||||
for (int layer_id = int(print_object.layers().size()) - 1; layer_id >= 0; layer_id--)
|
||||
for (int layer_id = int(print_object.layers().size()) - 1; layer_id >= 0; layer_id--) {
|
||||
throw_on_cancel_callback();
|
||||
for (const LayerRegion *layerm : print_object.get_layer(layer_id)->regions())
|
||||
for (const Surface &surface : layerm->fill_surfaces.surfaces)
|
||||
if (surface.surface_type == stInternal || surface.surface_type == stInternalVoid)
|
||||
append(infill_outlines[layer_id], infill_wall_offset == 0 ? surface.expolygon : offset(surface.expolygon, infill_wall_offset));
|
||||
append(infill_outlines[layer_id], to_polygons(surface.expolygon));
|
||||
}
|
||||
|
||||
// For various operations its beneficial to quickly locate nearby features on the polygon:
|
||||
const size_t top_layer_id = print_object.layers().size() - 1;
|
||||
@ -102,6 +100,7 @@ void Generator::generateTrees(const PrintObject &print_object)
|
||||
|
||||
// For-each layer from top to bottom:
|
||||
for (int layer_id = int(top_layer_id); layer_id >= 0; layer_id--) {
|
||||
throw_on_cancel_callback();
|
||||
Layer ¤t_lightning_layer = m_lightning_layers[layer_id];
|
||||
const Polygons ¤t_outlines = infill_outlines[layer_id];
|
||||
const BoundingBox ¤t_outlines_bbox = get_extents(current_outlines);
|
||||
@ -109,7 +108,7 @@ void Generator::generateTrees(const PrintObject &print_object)
|
||||
// register all trees propagated from the previous layer as to-be-reconnected
|
||||
std::vector<NodeSPtr> to_be_reconnected_tree_roots = current_lightning_layer.tree_roots;
|
||||
|
||||
current_lightning_layer.generateNewTrees(m_overhang_per_layer[layer_id], current_outlines, current_outlines_bbox, outlines_locator, m_supporting_radius, m_wall_supporting_radius);
|
||||
current_lightning_layer.generateNewTrees(m_overhang_per_layer[layer_id], current_outlines, current_outlines_bbox, outlines_locator, m_supporting_radius, m_wall_supporting_radius, throw_on_cancel_callback);
|
||||
current_lightning_layer.reconnectRoots(to_be_reconnected_tree_roots, current_outlines, current_outlines_bbox, outlines_locator, m_supporting_radius, m_wall_supporting_radius);
|
||||
|
||||
// Initialize trees for next lower layer from the current one.
|
||||
@ -121,6 +120,9 @@ void Generator::generateTrees(const PrintObject &print_object)
|
||||
if (const BoundingBox &outlines_locator_bbox = outlines_locator.bbox(); outlines_locator_bbox.defined)
|
||||
below_outlines_bbox.merge(outlines_locator_bbox);
|
||||
|
||||
if (!current_lightning_layer.tree_roots.empty())
|
||||
below_outlines_bbox.merge(get_extents(current_lightning_layer.tree_roots).inflated(SCALED_EPSILON));
|
||||
|
||||
outlines_locator.set_bbox(below_outlines_bbox);
|
||||
outlines_locator.create(below_outlines, locator_cell_size);
|
||||
|
||||
|
@ -43,9 +43,8 @@ public:
|
||||
* This generator will pre-compute things in preparation of generating
|
||||
* Lightning Infill for the infill areas in that mesh. The infill areas must
|
||||
* already be calculated at this point.
|
||||
* \param mesh The mesh to generate infill for.
|
||||
*/
|
||||
explicit Generator(const PrintObject &print_object);
|
||||
explicit Generator(const PrintObject &print_object, const std::function<void()> &throw_on_cancel_callback);
|
||||
|
||||
/*!
|
||||
* Get a tree of paths generated for a certain layer of the mesh.
|
||||
@ -69,12 +68,12 @@ protected:
|
||||
* only when support is generated. For this pattern, we also need to
|
||||
* generate overhang areas for the inside of the model.
|
||||
*/
|
||||
void generateInitialInternalOverhangs(const PrintObject &print_object);
|
||||
void generateInitialInternalOverhangs(const PrintObject &print_object, const std::function<void()> &throw_on_cancel_callback);
|
||||
|
||||
/*!
|
||||
* Calculate the tree structure of all layers.
|
||||
*/
|
||||
void generateTrees(const PrintObject &print_object);
|
||||
void generateTrees(const PrintObject &print_object, const std::function<void()> &throw_on_cancel_callback);
|
||||
|
||||
float m_infill_extrusion_width;
|
||||
|
||||
|
@ -10,6 +10,10 @@
|
||||
#include "../../Geometry.hpp"
|
||||
#include "Utils.hpp"
|
||||
|
||||
#include <tbb/parallel_for.h>
|
||||
#include <tbb/blocked_range2d.h>
|
||||
#include <mutex>
|
||||
|
||||
namespace Slic3r::FillLightning {
|
||||
|
||||
coord_t Layer::getWeightedDistance(const Point& boundary_loc, const Point& unsupported_location)
|
||||
@ -44,18 +48,22 @@ void Layer::generateNewTrees
|
||||
const BoundingBox& current_outlines_bbox,
|
||||
const EdgeGrid::Grid& outlines_locator,
|
||||
const coord_t supporting_radius,
|
||||
const coord_t wall_supporting_radius
|
||||
const coord_t wall_supporting_radius,
|
||||
const std::function<void()> &throw_on_cancel_callback
|
||||
)
|
||||
{
|
||||
DistanceField distance_field(supporting_radius, current_outlines, current_outlines_bbox, current_overhang);
|
||||
throw_on_cancel_callback();
|
||||
|
||||
SparseNodeGrid tree_node_locator;
|
||||
fillLocator(tree_node_locator, current_outlines_bbox);
|
||||
|
||||
// Until no more points need to be added to support all:
|
||||
// Determine next point from tree/outline areas via distance-field
|
||||
Point unsupported_location;
|
||||
while (distance_field.tryGetNextPoint(&unsupported_location)) {
|
||||
size_t unsupported_cell_idx = 0;
|
||||
Point unsupported_location;
|
||||
while (distance_field.tryGetNextPoint(&unsupported_location, &unsupported_cell_idx, unsupported_cell_idx)) {
|
||||
throw_on_cancel_callback();
|
||||
GroundingLocation grounding_loc = getBestGroundingLocation(
|
||||
unsupported_location, current_outlines, current_outlines_bbox, outlines_locator, supporting_radius, wall_supporting_radius, tree_node_locator);
|
||||
|
||||
@ -126,9 +134,10 @@ GroundingLocation Layer::getBestGroundingLocation
|
||||
if (contour.size() > 2) {
|
||||
Point prev = contour.points.back();
|
||||
for (const Point &p2 : contour.points) {
|
||||
if (double d = Line::distance_to_squared(unsupported_location, prev, p2); d < d2) {
|
||||
Point closest_point;
|
||||
if (double d = line_alg::distance_to_squared(Line{prev, p2}, unsupported_location, &closest_point); d < d2) {
|
||||
d2 = d;
|
||||
node_location = Geometry::foot_pt({ prev, p2 }, unsupported_location).cast<coord_t>();
|
||||
node_location = closest_point;
|
||||
}
|
||||
prev = p2;
|
||||
}
|
||||
@ -137,30 +146,52 @@ GroundingLocation Layer::getBestGroundingLocation
|
||||
|
||||
const auto within_dist = coord_t((node_location - unsupported_location).cast<double>().norm());
|
||||
|
||||
NodeSPtr sub_tree{ nullptr };
|
||||
coord_t current_dist = getWeightedDistance(node_location, unsupported_location);
|
||||
NodeSPtr sub_tree{nullptr};
|
||||
coord_t current_dist = getWeightedDistance(node_location, unsupported_location);
|
||||
if (current_dist >= wall_supporting_radius) { // Only reconnect tree roots to other trees if they are not already close to the outlines.
|
||||
const coord_t search_radius = std::min(current_dist, within_dist);
|
||||
BoundingBox region(unsupported_location - Point(search_radius, search_radius), unsupported_location + Point(search_radius + locator_cell_size, search_radius + locator_cell_size));
|
||||
region.min = to_grid_point(region.min, current_outlines_bbox);
|
||||
region.max = to_grid_point(region.max, current_outlines_bbox);
|
||||
Point grid_addr;
|
||||
for (grid_addr.y() = region.min.y(); grid_addr.y() < region.max.y(); ++ grid_addr.y())
|
||||
for (grid_addr.x() = region.min.x(); grid_addr.x() < region.max.x(); ++ grid_addr.x()) {
|
||||
auto it_range = tree_node_locator.equal_range(grid_addr);
|
||||
for (auto it = it_range.first; it != it_range.second; ++ it) {
|
||||
auto candidate_sub_tree = it->second.lock();
|
||||
if ((candidate_sub_tree && candidate_sub_tree != exclude_tree) &&
|
||||
!(exclude_tree && exclude_tree->hasOffspring(candidate_sub_tree)) &&
|
||||
!polygonCollidesWithLineSegment(unsupported_location, candidate_sub_tree->getLocation(), outline_locator)) {
|
||||
const coord_t candidate_dist = candidate_sub_tree->getWeightedDistance(unsupported_location, supporting_radius);
|
||||
if (candidate_dist < current_dist) {
|
||||
current_dist = candidate_dist;
|
||||
sub_tree = candidate_sub_tree;
|
||||
|
||||
Point current_dist_grid_addr{std::numeric_limits<coord_t>::lowest(), std::numeric_limits<coord_t>::lowest()};
|
||||
std::mutex current_dist_mutex;
|
||||
tbb::parallel_for(tbb::blocked_range2d<coord_t>(region.min.y(), region.max.y(), region.min.x(), region.max.x()), [¤t_dist, current_dist_copy = current_dist, ¤t_dist_mutex, &sub_tree, ¤t_dist_grid_addr, &exclude_tree = std::as_const(exclude_tree), &outline_locator = std::as_const(outline_locator), &supporting_radius = std::as_const(supporting_radius), &tree_node_locator = std::as_const(tree_node_locator), &unsupported_location = std::as_const(unsupported_location)](const tbb::blocked_range2d<coord_t> &range) -> void {
|
||||
for (coord_t grid_addr_y = range.rows().begin(); grid_addr_y < range.rows().end(); ++grid_addr_y)
|
||||
for (coord_t grid_addr_x = range.cols().begin(); grid_addr_x < range.cols().end(); ++grid_addr_x) {
|
||||
const Point local_grid_addr{grid_addr_x, grid_addr_y};
|
||||
NodeSPtr local_sub_tree{nullptr};
|
||||
coord_t local_current_dist = current_dist_copy;
|
||||
const auto it_range = tree_node_locator.equal_range(local_grid_addr);
|
||||
for (auto it = it_range.first; it != it_range.second; ++it) {
|
||||
const NodeSPtr candidate_sub_tree = it->second.lock();
|
||||
if ((candidate_sub_tree && candidate_sub_tree != exclude_tree) &&
|
||||
!(exclude_tree && exclude_tree->hasOffspring(candidate_sub_tree)) &&
|
||||
!polygonCollidesWithLineSegment(unsupported_location, candidate_sub_tree->getLocation(), outline_locator)) {
|
||||
if (const coord_t candidate_dist = candidate_sub_tree->getWeightedDistance(unsupported_location, supporting_radius); candidate_dist < local_current_dist) {
|
||||
local_current_dist = candidate_dist;
|
||||
local_sub_tree = candidate_sub_tree;
|
||||
}
|
||||
}
|
||||
}
|
||||
// To always get the same result in a parallel version as in a non-parallel version,
|
||||
// we need to preserve that for the same current_dist, we select the same sub_tree
|
||||
// as in the non-parallel version. For this purpose, inside the variable
|
||||
// current_dist_grid_addr is stored from with 2D grid position assigned sub_tree comes.
|
||||
// And when there are two sub_tree with the same current_dist, one which will be found
|
||||
// the first in the non-parallel version is selected.
|
||||
{
|
||||
std::lock_guard<std::mutex> lock(current_dist_mutex);
|
||||
if (local_current_dist < current_dist ||
|
||||
(local_current_dist == current_dist && (grid_addr_y < current_dist_grid_addr.y() ||
|
||||
(grid_addr_y == current_dist_grid_addr.y() && grid_addr_x < current_dist_grid_addr.x())))) {
|
||||
current_dist = local_current_dist;
|
||||
sub_tree = local_sub_tree;
|
||||
current_dist_grid_addr = local_grid_addr;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}); // end of parallel_for
|
||||
}
|
||||
|
||||
return ! sub_tree ?
|
||||
@ -402,15 +433,14 @@ static unsigned int moveInside(const Polygons& polygons, Point& from, int distan
|
||||
}
|
||||
#endif
|
||||
|
||||
// Returns 'added someting'.
|
||||
Polylines Layer::convertToLines(const Polygons& limit_to_outline, const coord_t line_width) const
|
||||
Polylines Layer::convertToLines(const Polygons& limit_to_outline, const coord_t line_overlap) const
|
||||
{
|
||||
if (tree_roots.empty())
|
||||
return {};
|
||||
|
||||
Polylines result_lines;
|
||||
for (const auto &tree : tree_roots)
|
||||
tree->convertToPolylines(result_lines, line_width);
|
||||
tree->convertToPolylines(result_lines, line_overlap);
|
||||
|
||||
return intersection_pl(result_lines, limit_to_outline);
|
||||
}
|
||||
|
@ -44,7 +44,8 @@ public:
|
||||
const BoundingBox& current_outlines_bbox,
|
||||
const EdgeGrid::Grid& outline_locator,
|
||||
coord_t supporting_radius,
|
||||
coord_t wall_supporting_radius
|
||||
coord_t wall_supporting_radius,
|
||||
const std::function<void()> &throw_on_cancel_callback
|
||||
);
|
||||
|
||||
/*! Determine & connect to connection point in tree/outline.
|
||||
@ -79,7 +80,7 @@ public:
|
||||
coord_t wall_supporting_radius
|
||||
);
|
||||
|
||||
Polylines convertToLines(const Polygons& limit_to_outline, coord_t line_width) const;
|
||||
Polylines convertToLines(const Polygons& limit_to_outline, coord_t line_overlap) const;
|
||||
|
||||
coord_t getWeightedDistance(const Point& boundary_loc, const Point& unsupported_location);
|
||||
|
||||
|
@ -180,7 +180,11 @@ bool lineSegmentPolygonsIntersection(const Point& a, const Point& b, const EdgeG
|
||||
} visitor { outline_locator, a.cast<double>(), b.cast<double>() };
|
||||
|
||||
outline_locator.visit_cells_intersecting_line(a, b, visitor);
|
||||
return visitor.d2min < double(within_max_dist) * double(within_max_dist);
|
||||
if (visitor.d2min < double(within_max_dist) * double(within_max_dist)) {
|
||||
result = Point(visitor.intersection_pt);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool Node::realign(const Polygons& outlines, const EdgeGrid::Grid& outline_locator, std::vector<NodeSPtr>& rerooted_parts)
|
||||
@ -343,12 +347,12 @@ coord_t Node::prune(const coord_t& pruning_distance)
|
||||
return max_distance_pruned;
|
||||
}
|
||||
|
||||
void Node::convertToPolylines(Polylines &output, const coord_t line_width) const
|
||||
void Node::convertToPolylines(Polylines &output, const coord_t line_overlap) const
|
||||
{
|
||||
Polylines result;
|
||||
result.emplace_back();
|
||||
convertToPolylines(0, result);
|
||||
removeJunctionOverlap(result, line_width);
|
||||
removeJunctionOverlap(result, line_overlap);
|
||||
append(output, std::move(result));
|
||||
}
|
||||
|
||||
@ -372,10 +376,10 @@ void Node::convertToPolylines(size_t long_line_idx, Polylines &output) const
|
||||
}
|
||||
}
|
||||
|
||||
void Node::removeJunctionOverlap(Polylines &result_lines, const coord_t line_width) const
|
||||
void Node::removeJunctionOverlap(Polylines &result_lines, const coord_t line_overlap) const
|
||||
{
|
||||
const coord_t reduction = line_width / 2; // TODO make configurable?
|
||||
size_t res_line_idx = 0;
|
||||
const coord_t reduction = line_overlap;
|
||||
size_t res_line_idx = 0;
|
||||
while (res_line_idx < result_lines.size()) {
|
||||
Polyline &polyline = result_lines[res_line_idx];
|
||||
if (polyline.size() <= 1) {
|
||||
|
@ -46,7 +46,7 @@ public:
|
||||
{
|
||||
struct EnableMakeShared : public Node
|
||||
{
|
||||
EnableMakeShared(Arg&&...arg) : Node(std::forward<Arg>(arg)...) {}
|
||||
explicit EnableMakeShared(Arg&&...arg) : Node(std::forward<Arg>(arg)...) {}
|
||||
};
|
||||
return std::make_shared<EnableMakeShared>(std::forward<Arg>(arg)...);
|
||||
}
|
||||
@ -179,16 +179,16 @@ public:
|
||||
*/
|
||||
bool hasOffspring(const NodeSPtr& to_be_checked) const;
|
||||
|
||||
protected:
|
||||
Node() = delete; // Don't allow empty contruction
|
||||
|
||||
protected:
|
||||
/*!
|
||||
* Construct a new node, either for insertion in a tree or as root.
|
||||
* \param p The physical location in the 2D layer that this node represents.
|
||||
* Connecting other nodes to this node indicates that a line segment should
|
||||
* be drawn between those two physical positions.
|
||||
*/
|
||||
Node(const Point& p, const std::optional<Point>& last_grounding_location = std::nullopt);
|
||||
explicit Node(const Point& p, const std::optional<Point>& last_grounding_location = std::nullopt);
|
||||
|
||||
/*!
|
||||
* Copy this node and its entire sub-tree.
|
||||
@ -239,7 +239,7 @@ public:
|
||||
*
|
||||
* \param output all branches in this tree connected into polylines
|
||||
*/
|
||||
void convertToPolylines(Polylines &output, coord_t line_width) const;
|
||||
void convertToPolylines(Polylines &output, coord_t line_overlap) const;
|
||||
|
||||
/*! If this was ever a direct child of the root, it'll have a previous grounding location.
|
||||
*
|
||||
@ -260,7 +260,7 @@ protected:
|
||||
*/
|
||||
void convertToPolylines(size_t long_line_idx, Polylines &output) const;
|
||||
|
||||
void removeJunctionOverlap(Polylines &polylines, coord_t line_width) const;
|
||||
void removeJunctionOverlap(Polylines &polylines, coord_t line_overlap) const;
|
||||
|
||||
bool m_is_root;
|
||||
Point m_p;
|
||||
@ -269,6 +269,9 @@ protected:
|
||||
|
||||
std::optional<Point> m_last_grounding_location; //<! The last known grounding location, see 'getLastGroundingLocation()'.
|
||||
|
||||
friend BoundingBox get_extents(const NodeSPtr &root_node);
|
||||
friend BoundingBox get_extents(const std::vector<NodeSPtr> &tree_roots);
|
||||
|
||||
#ifdef LIGHTNING_TREE_NODE_DEBUG_OUTPUT
|
||||
friend void export_to_svg(const NodeSPtr &root_node, Slic3r::SVG &svg);
|
||||
friend void export_to_svg(const std::string &path, const Polygons &contour, const std::vector<NodeSPtr> &root_nodes);
|
||||
@ -278,6 +281,23 @@ protected:
|
||||
bool inside(const Polygons &polygons, const Point &p);
|
||||
bool lineSegmentPolygonsIntersection(const Point& a, const Point& b, const EdgeGrid::Grid& outline_locator, Point& result, coord_t within_max_dist);
|
||||
|
||||
inline BoundingBox get_extents(const NodeSPtr &root_node)
|
||||
{
|
||||
BoundingBox bbox;
|
||||
for (const NodeSPtr &children : root_node->m_children)
|
||||
bbox.merge(get_extents(children));
|
||||
bbox.merge(root_node->getLocation());
|
||||
return bbox;
|
||||
}
|
||||
|
||||
inline BoundingBox get_extents(const std::vector<NodeSPtr> &tree_roots)
|
||||
{
|
||||
BoundingBox bbox;
|
||||
for (const NodeSPtr &root_node : tree_roots)
|
||||
bbox.merge(get_extents(root_node));
|
||||
return bbox;
|
||||
}
|
||||
|
||||
#ifdef LIGHTNING_TREE_NODE_DEBUG_OUTPUT
|
||||
void export_to_svg(const NodeSPtr &root_node, SVG &svg);
|
||||
void export_to_svg(const std::string &path, const Polygons &contour, const std::vector<NodeSPtr> &root_nodes);
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -35,6 +35,8 @@
|
||||
#include "SVG.hpp"
|
||||
|
||||
#include <tbb/parallel_for.h>
|
||||
#include <tbb/task_scheduler_observer.h>
|
||||
#include <tbb/enumerable_thread_specific.h>
|
||||
|
||||
// Intel redesigned some TBB interface considerably when merging TBB with their oneAPI set of libraries, see GH #7332.
|
||||
// We are using quite an old TBB 2017 U7. Before we update our build servers, let's use the old API, which is deprecated in up to date TBB.
|
||||
@ -1488,6 +1490,32 @@ void GCode::_do_export(Print& print, GCodeOutputStream &file, ThumbnailsGenerato
|
||||
print.throw_if_canceled();
|
||||
}
|
||||
|
||||
// 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
|
||||
// in tbb::parallel_pipeline to ensure that locales are set correctly
|
||||
|
||||
// For tbb::parallel_pipeline, it seems that on_scheduler_entry is called for every layer and every filter.
|
||||
// We ensure using thread-local storage that locales will be set to "C" just once for any participating thread.
|
||||
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
|
||||
{
|
||||
if (bool &is_locales_sets = m_is_locales_sets.local(); !is_locales_sets) {
|
||||
// Set locales of the worker thread to "C".
|
||||
set_c_locales();
|
||||
is_locales_sets = true;
|
||||
}
|
||||
}
|
||||
|
||||
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};
|
||||
};
|
||||
|
||||
// Process all layers of all objects (non-sequential mode) with a parallel pipeline:
|
||||
// Generate G-code, run the filters (vase mode, cooling buffer), run the G-code analyser
|
||||
// and export G-code into file.
|
||||
@ -1531,6 +1559,10 @@ void GCode::process_layers(
|
||||
[&output_stream](std::string s) { output_stream.write(s); }
|
||||
);
|
||||
|
||||
// It registers a handler that sets locales to "C" before any TBB thread starts participating in tbb::parallel_pipeline.
|
||||
// Handler is unregistered when the destructor is called.
|
||||
TBBLocalesSetter locales_setter;
|
||||
|
||||
// The pipeline elements are joined using const references, thus no copying is performed.
|
||||
output_stream.find_replace_supress();
|
||||
if (m_spiral_vase && m_find_replace)
|
||||
@ -1584,6 +1616,10 @@ void GCode::process_layers(
|
||||
[&output_stream](std::string s) { output_stream.write(s); }
|
||||
);
|
||||
|
||||
// It registers a handler that sets locales to "C" before any TBB thread starts participating in tbb::parallel_pipeline.
|
||||
// Handler is unregistered when the destructor is called.
|
||||
TBBLocalesSetter locales_setter;
|
||||
|
||||
// The pipeline elements are joined using const references, thus no copying is performed.
|
||||
output_stream.find_replace_supress();
|
||||
if (m_spiral_vase && m_find_replace)
|
||||
|
@ -313,9 +313,60 @@ Transform3d assemble_transform(const Vec3d& translation, const Vec3d& rotation,
|
||||
return transform;
|
||||
}
|
||||
|
||||
void assemble_transform(Transform3d& transform, const Transform3d& translation, const Transform3d& rotation, const Transform3d& scale, const Transform3d& mirror)
|
||||
{
|
||||
transform = translation * rotation * scale * mirror;
|
||||
}
|
||||
|
||||
Transform3d assemble_transform(const Transform3d& translation, const Transform3d& rotation, const Transform3d& scale, const Transform3d& mirror)
|
||||
{
|
||||
Transform3d transform;
|
||||
assemble_transform(transform, translation, rotation, scale, mirror);
|
||||
return transform;
|
||||
}
|
||||
|
||||
void translation_transform(Transform3d& transform, const Vec3d& translation)
|
||||
{
|
||||
transform = Transform3d::Identity();
|
||||
transform.translate(translation);
|
||||
}
|
||||
|
||||
Transform3d translation_transform(const Vec3d& translation)
|
||||
{
|
||||
Transform3d transform;
|
||||
translation_transform(transform, translation);
|
||||
return transform;
|
||||
}
|
||||
|
||||
void rotation_transform(Transform3d& transform, const Vec3d& rotation)
|
||||
{
|
||||
transform = Transform3d::Identity();
|
||||
transform.rotate(Eigen::AngleAxisd(rotation.z(), Vec3d::UnitZ()) * Eigen::AngleAxisd(rotation.y(), Vec3d::UnitY()) * Eigen::AngleAxisd(rotation.x(), Vec3d::UnitX()));
|
||||
}
|
||||
|
||||
Transform3d rotation_transform(const Vec3d& rotation)
|
||||
{
|
||||
Transform3d transform;
|
||||
rotation_transform(transform, rotation);
|
||||
return transform;
|
||||
}
|
||||
|
||||
void scale_transform(Transform3d& transform, const Vec3d& scale)
|
||||
{
|
||||
transform = Transform3d::Identity();
|
||||
transform.scale(scale);
|
||||
}
|
||||
|
||||
Transform3d scale_transform(const Vec3d& scale)
|
||||
{
|
||||
Transform3d transform;
|
||||
scale_transform(transform, scale);
|
||||
return transform;
|
||||
}
|
||||
|
||||
Vec3d extract_euler_angles(const Eigen::Matrix<double, 3, 3, Eigen::DontAlign>& rotation_matrix)
|
||||
{
|
||||
// reference: http://www.gregslabaugh.net/publications/euler.pdf
|
||||
// reference: http://eecs.qmul.ac.uk/~gslabaugh/publications/euler.pdf
|
||||
Vec3d angles1 = Vec3d::Zero();
|
||||
Vec3d angles2 = Vec3d::Zero();
|
||||
if (std::abs(std::abs(rotation_matrix(2, 0)) - 1.0) < 1e-5) {
|
||||
@ -363,6 +414,54 @@ Vec3d extract_euler_angles(const Transform3d& transform)
|
||||
return extract_euler_angles(m);
|
||||
}
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Transform3d Transformation::get_offset_matrix() const
|
||||
{
|
||||
return assemble_transform(get_offset());
|
||||
}
|
||||
|
||||
static Transform3d extract_rotation(const Transform3d& trafo)
|
||||
{
|
||||
Matrix3d rotation;
|
||||
Matrix3d scale;
|
||||
trafo.computeRotationScaling(&rotation, &scale);
|
||||
return Transform3d(rotation);
|
||||
}
|
||||
|
||||
static Transform3d extract_scale(const Transform3d& trafo)
|
||||
{
|
||||
Matrix3d rotation;
|
||||
Matrix3d scale;
|
||||
trafo.computeRotationScaling(&rotation, &scale);
|
||||
return Transform3d(scale);
|
||||
}
|
||||
|
||||
static std::pair<Transform3d, Transform3d> extract_rotation_scale(const Transform3d& trafo)
|
||||
{
|
||||
Matrix3d rotation;
|
||||
Matrix3d scale;
|
||||
trafo.computeRotationScaling(&rotation, &scale);
|
||||
return { Transform3d(rotation), Transform3d(scale) };
|
||||
}
|
||||
|
||||
static bool contains_skew(const Transform3d& trafo)
|
||||
{
|
||||
Matrix3d rotation;
|
||||
Matrix3d scale;
|
||||
trafo.computeRotationScaling(&rotation, &scale);
|
||||
return !scale.isDiagonal();
|
||||
}
|
||||
|
||||
Vec3d Transformation::get_rotation() const
|
||||
{
|
||||
return extract_euler_angles(extract_rotation(m_matrix));
|
||||
}
|
||||
|
||||
Transform3d Transformation::get_rotation_matrix() const
|
||||
{
|
||||
return extract_rotation(m_matrix);
|
||||
}
|
||||
#else
|
||||
bool Transformation::Flags::needs_update(bool dont_translate, bool dont_rotate, bool dont_scale, bool dont_mirror) const
|
||||
{
|
||||
return (this->dont_translate != dont_translate) || (this->dont_rotate != dont_rotate) || (this->dont_scale != dont_scale) || (this->dont_mirror != dont_mirror);
|
||||
@ -400,12 +499,19 @@ void Transformation::set_offset(Axis axis, double offset)
|
||||
m_dirty = true;
|
||||
}
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void Transformation::set_rotation(const Vec3d& rotation)
|
||||
{
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const Vec3d offset = get_offset();
|
||||
m_matrix = rotation_transform(rotation) * extract_scale(m_matrix);
|
||||
m_matrix.translation() = offset;
|
||||
#else
|
||||
set_rotation(X, rotation.x());
|
||||
set_rotation(Y, rotation.y());
|
||||
set_rotation(Z, rotation.z());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
void Transformation::set_rotation(Axis axis, double rotation)
|
||||
@ -414,32 +520,106 @@ void Transformation::set_rotation(Axis axis, double rotation)
|
||||
if (is_approx(std::abs(rotation), 2.0 * double(PI)))
|
||||
rotation = 0.0;
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
auto [curr_rotation, scale] = extract_rotation_scale(m_matrix);
|
||||
Vec3d angles = extract_euler_angles(curr_rotation);
|
||||
angles[axis] = rotation;
|
||||
|
||||
const Vec3d offset = get_offset();
|
||||
m_matrix = rotation_transform(angles) * scale;
|
||||
m_matrix.translation() = offset;
|
||||
#else
|
||||
if (m_rotation(axis) != rotation) {
|
||||
m_rotation(axis) = rotation;
|
||||
m_dirty = true;
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Vec3d Transformation::get_scaling_factor() const
|
||||
{
|
||||
const Transform3d scale = extract_scale(m_matrix);
|
||||
return { scale(0, 0), scale(1, 1), scale(2, 2) };
|
||||
}
|
||||
|
||||
Transform3d Transformation::get_scaling_factor_matrix() const
|
||||
{
|
||||
return extract_scale(m_matrix);
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void Transformation::set_scaling_factor(const Vec3d& scaling_factor)
|
||||
{
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
assert(scaling_factor.x() > 0.0 && scaling_factor.y() > 0.0 && scaling_factor.z() > 0.0);
|
||||
|
||||
const Vec3d offset = get_offset();
|
||||
m_matrix = extract_rotation(m_matrix) * scale_transform(scaling_factor);
|
||||
m_matrix.translation() = offset;
|
||||
#else
|
||||
set_scaling_factor(X, scaling_factor.x());
|
||||
set_scaling_factor(Y, scaling_factor.y());
|
||||
set_scaling_factor(Z, scaling_factor.z());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
void Transformation::set_scaling_factor(Axis axis, double scaling_factor)
|
||||
{
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
assert(scaling_factor > 0.0);
|
||||
auto [rotation, scale] = extract_rotation_scale(m_matrix);
|
||||
scale(axis, axis) = scaling_factor;
|
||||
|
||||
const Vec3d offset = get_offset();
|
||||
m_matrix = rotation * scale;
|
||||
m_matrix.translation() = offset;
|
||||
#else
|
||||
if (m_scaling_factor(axis) != std::abs(scaling_factor)) {
|
||||
m_scaling_factor(axis) = std::abs(scaling_factor);
|
||||
m_dirty = true;
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Vec3d Transformation::get_mirror() const
|
||||
{
|
||||
const Transform3d scale = extract_scale(m_matrix);
|
||||
return { scale(0, 0) / std::abs(scale(0, 0)), scale(1, 1) / std::abs(scale(1, 1)), scale(2, 2) / std::abs(scale(2, 2)) };
|
||||
}
|
||||
|
||||
Transform3d Transformation::get_mirror_matrix() const
|
||||
{
|
||||
const Vec3d scale = get_scaling_factor();
|
||||
return scale_transform({ scale.x() / std::abs(scale.x()), scale.y() / std::abs(scale.y()), scale.z() / std::abs(scale.z()) });
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void Transformation::set_mirror(const Vec3d& mirror)
|
||||
{
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Vec3d copy(mirror);
|
||||
const Vec3d abs_mirror = copy.cwiseAbs();
|
||||
for (int i = 0; i < 3; ++i) {
|
||||
if (abs_mirror(i) == 0.0)
|
||||
copy(i) = 1.0;
|
||||
else if (abs_mirror(i) != 1.0)
|
||||
copy(i) /= abs_mirror(i);
|
||||
}
|
||||
|
||||
const Vec3d curr_scale = get_scaling_factor();
|
||||
const Vec3d signs = curr_scale.cwiseProduct(copy);
|
||||
set_scaling_factor({
|
||||
signs.x() < 0.0 ? std::abs(curr_scale.x()) * copy.x() : curr_scale.x(),
|
||||
signs.y() < 0.0 ? std::abs(curr_scale.y()) * copy.y() : curr_scale.y(),
|
||||
signs.z() < 0.0 ? std::abs(curr_scale.z()) * copy.z() : curr_scale.z()
|
||||
});
|
||||
#else
|
||||
set_mirror(X, mirror.x());
|
||||
set_mirror(Y, mirror.y());
|
||||
set_mirror(Z, mirror.z());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
void Transformation::set_mirror(Axis axis, double mirror)
|
||||
@ -450,12 +630,24 @@ void Transformation::set_mirror(Axis axis, double mirror)
|
||||
else if (abs_mirror != 1.0)
|
||||
mirror /= abs_mirror;
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const double curr_scale = get_scaling_factor(axis);
|
||||
const double sign = curr_scale * mirror;
|
||||
set_scaling_factor(axis, sign < 0.0 ? std::abs(curr_scale) * mirror : curr_scale);
|
||||
#else
|
||||
if (m_mirror(axis) != mirror) {
|
||||
m_mirror(axis) = mirror;
|
||||
m_dirty = true;
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
bool Transformation::has_skew() const
|
||||
{
|
||||
return contains_skew(m_matrix);
|
||||
}
|
||||
#else
|
||||
void Transformation::set_from_transform(const Transform3d& transform)
|
||||
{
|
||||
// offset
|
||||
@ -493,17 +685,62 @@ void Transformation::set_from_transform(const Transform3d& transform)
|
||||
// if (!m_matrix.isApprox(transform))
|
||||
// std::cout << "something went wrong in extracting data from matrix" << std::endl;
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void Transformation::reset()
|
||||
{
|
||||
#if !ENABLE_WORLD_COORDINATE
|
||||
m_offset = Vec3d::Zero();
|
||||
m_rotation = Vec3d::Zero();
|
||||
m_scaling_factor = Vec3d::Ones();
|
||||
m_mirror = Vec3d::Ones();
|
||||
#endif // !ENABLE_WORLD_COORDINATE
|
||||
m_matrix = Transform3d::Identity();
|
||||
#if !ENABLE_WORLD_COORDINATE
|
||||
m_dirty = false;
|
||||
#endif // !ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
void Transformation::reset_skew()
|
||||
{
|
||||
Matrix3d rotation;
|
||||
Matrix3d scale;
|
||||
m_matrix.computeRotationScaling(&rotation, &scale);
|
||||
|
||||
const double average_scale = std::cbrt(scale(0, 0) * scale(1, 1) * scale(2, 2));
|
||||
|
||||
scale(0, 0) = average_scale;
|
||||
scale(1, 1) = average_scale;
|
||||
scale(2, 2) = average_scale;
|
||||
|
||||
scale(0, 1) = 0.0;
|
||||
scale(0, 2) = 0.0;
|
||||
scale(1, 0) = 0.0;
|
||||
scale(1, 2) = 0.0;
|
||||
scale(2, 0) = 0.0;
|
||||
scale(2, 1) = 0.0;
|
||||
|
||||
const Vec3d offset = get_offset();
|
||||
m_matrix = rotation * scale;
|
||||
m_matrix.translation() = offset;
|
||||
}
|
||||
|
||||
Transform3d Transformation::get_matrix_no_offset() const
|
||||
{
|
||||
Transformation copy(*this);
|
||||
copy.reset_offset();
|
||||
return copy.get_matrix();
|
||||
}
|
||||
|
||||
Transform3d Transformation::get_matrix_no_scaling_factor() const
|
||||
{
|
||||
Transformation copy(*this);
|
||||
copy.reset_scaling_factor();
|
||||
copy.reset_mirror();
|
||||
return copy.get_matrix();
|
||||
}
|
||||
#else
|
||||
const Transform3d& Transformation::get_matrix(bool dont_translate, bool dont_rotate, bool dont_scale, bool dont_mirror) const
|
||||
{
|
||||
if (m_dirty || m_flags.needs_update(dont_translate, dont_rotate, dont_scale, dont_mirror)) {
|
||||
@ -520,12 +757,14 @@ const Transform3d& Transformation::get_matrix(bool dont_translate, bool dont_rot
|
||||
|
||||
return m_matrix;
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
Transformation Transformation::operator * (const Transformation& other) const
|
||||
{
|
||||
return Transformation(get_matrix() * other.get_matrix());
|
||||
}
|
||||
|
||||
#if !ENABLE_WORLD_COORDINATE
|
||||
Transformation Transformation::volume_to_bed_transformation(const Transformation& instance_transformation, const BoundingBoxf3& bbox)
|
||||
{
|
||||
Transformation out;
|
||||
@ -571,8 +810,7 @@ Transformation Transformation::volume_to_bed_transformation(const Transformation
|
||||
out.set_scaling_factor(Vec3d(std::abs(scale.x()), std::abs(scale.y()), std::abs(scale.z())));
|
||||
out.set_mirror(Vec3d(scale.x() > 0 ? 1. : -1, scale.y() > 0 ? 1. : -1, scale.z() > 0 ? 1. : -1));
|
||||
}
|
||||
else
|
||||
{
|
||||
else {
|
||||
// General anisotropic scaling, general rotation.
|
||||
// Keep the modifier mesh in the instance coordinate system, so the modifier mesh will not be aligned with the world.
|
||||
// Scale it to get the required size.
|
||||
@ -581,6 +819,7 @@ Transformation Transformation::volume_to_bed_transformation(const Transformation
|
||||
|
||||
return out;
|
||||
}
|
||||
#endif // !ENABLE_WORLD_COORDINATE
|
||||
|
||||
// For parsing a transformation matrix from 3MF / AMF.
|
||||
Transform3d transform3d_from_string(const std::string& transform_str)
|
||||
@ -619,7 +858,7 @@ Eigen::Quaterniond rotation_xyz_diff(const Vec3d &rot_xyz_from, const Vec3d &rot
|
||||
double rotation_diff_z(const Vec3d &rot_xyz_from, const Vec3d &rot_xyz_to)
|
||||
{
|
||||
const Eigen::AngleAxisd angle_axis(rotation_xyz_diff(rot_xyz_from, rot_xyz_to));
|
||||
const Vec3d axis = angle_axis.axis();
|
||||
const Vec3d& axis = angle_axis.axis();
|
||||
const double angle = angle_axis.angle();
|
||||
#ifndef NDEBUG
|
||||
if (std::abs(angle) > 1e-8) {
|
||||
|
@ -323,7 +323,8 @@ bool arrange(
|
||||
// 4) rotate Y
|
||||
// 5) rotate Z
|
||||
// 6) translate
|
||||
void assemble_transform(Transform3d& transform, const Vec3d& translation = Vec3d::Zero(), const Vec3d& rotation = Vec3d::Zero(), const Vec3d& scale = Vec3d::Ones(), const Vec3d& mirror = Vec3d::Ones());
|
||||
void assemble_transform(Transform3d& transform, const Vec3d& translation = Vec3d::Zero(), const Vec3d& rotation = Vec3d::Zero(),
|
||||
const Vec3d& scale = Vec3d::Ones(), const Vec3d& mirror = Vec3d::Ones());
|
||||
|
||||
// Returns the transform obtained by assembling the given transformations in the following order:
|
||||
// 1) mirror
|
||||
@ -332,7 +333,43 @@ void assemble_transform(Transform3d& transform, const Vec3d& translation = Vec3d
|
||||
// 4) rotate Y
|
||||
// 5) rotate Z
|
||||
// 6) translate
|
||||
Transform3d assemble_transform(const Vec3d& translation = Vec3d::Zero(), const Vec3d& rotation = Vec3d::Zero(), const Vec3d& scale = Vec3d::Ones(), const Vec3d& mirror = Vec3d::Ones());
|
||||
Transform3d assemble_transform(const Vec3d& translation = Vec3d::Zero(), const Vec3d& rotation = Vec3d::Zero(),
|
||||
const Vec3d& scale = Vec3d::Ones(), const Vec3d& mirror = Vec3d::Ones());
|
||||
|
||||
// Sets the given transform by multiplying the given transformations in the following order:
|
||||
// T = translation * rotation * scale * mirror
|
||||
void assemble_transform(Transform3d& transform, const Transform3d& translation = Transform3d::Identity(),
|
||||
const Transform3d& rotation = Transform3d::Identity(), const Transform3d& scale = Transform3d::Identity(),
|
||||
const Transform3d& mirror = Transform3d::Identity());
|
||||
|
||||
// Returns the transform obtained by multiplying the given transformations in the following order:
|
||||
// T = translation * rotation * scale * mirror
|
||||
Transform3d assemble_transform(const Transform3d& translation = Transform3d::Identity(), const Transform3d& rotation = Transform3d::Identity(),
|
||||
const Transform3d& scale = Transform3d::Identity(), const Transform3d& mirror = Transform3d::Identity());
|
||||
|
||||
// Sets the given transform by assembling the given translation
|
||||
void translation_transform(Transform3d& transform, const Vec3d& translation);
|
||||
|
||||
// Returns the transform obtained by assembling the given translation
|
||||
Transform3d translation_transform(const Vec3d& translation);
|
||||
|
||||
// Sets the given transform by assembling the given rotations in the following order:
|
||||
// 1) rotate X
|
||||
// 2) rotate Y
|
||||
// 3) rotate Z
|
||||
void rotation_transform(Transform3d& transform, const Vec3d& rotation);
|
||||
|
||||
// Returns the transform obtained by assembling the given rotations in the following order:
|
||||
// 1) rotate X
|
||||
// 2) rotate Y
|
||||
// 3) rotate Z
|
||||
Transform3d rotation_transform(const Vec3d& rotation);
|
||||
|
||||
// Sets the given transform by assembling the given scale factors
|
||||
void scale_transform(Transform3d& transform, const Vec3d& scale);
|
||||
|
||||
// Returns the transform obtained by assembling the given scale factors
|
||||
Transform3d scale_transform(const Vec3d& scale);
|
||||
|
||||
// Returns the euler angles extracted from the given rotation matrix
|
||||
// Warning -> The matrix should not contain any scale or shear !!!
|
||||
@ -344,6 +381,9 @@ Vec3d extract_euler_angles(const Transform3d& transform);
|
||||
|
||||
class Transformation
|
||||
{
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Transform3d m_matrix{ Transform3d::Identity() };
|
||||
#else
|
||||
struct Flags
|
||||
{
|
||||
bool dont_translate{ true };
|
||||
@ -363,8 +403,26 @@ class Transformation
|
||||
mutable Transform3d m_matrix{ Transform3d::Identity() };
|
||||
mutable Flags m_flags;
|
||||
mutable bool m_dirty{ false };
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
public:
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Transformation() = default;
|
||||
explicit Transformation(const Transform3d& transform) : m_matrix(transform) {}
|
||||
|
||||
Vec3d get_offset() const { return m_matrix.translation(); }
|
||||
double get_offset(Axis axis) const { return get_offset()[axis]; }
|
||||
|
||||
Transform3d get_offset_matrix() const;
|
||||
|
||||
void set_offset(const Vec3d& offset) { m_matrix.translation() = offset; }
|
||||
void set_offset(Axis axis, double offset) { m_matrix.translation()[axis] = offset; }
|
||||
|
||||
Vec3d get_rotation() const;
|
||||
double get_rotation(Axis axis) const { return get_rotation()[axis]; }
|
||||
|
||||
Transform3d get_rotation_matrix() const;
|
||||
#else
|
||||
Transformation();
|
||||
explicit Transformation(const Transform3d& transform);
|
||||
|
||||
@ -376,47 +434,103 @@ public:
|
||||
|
||||
const Vec3d& get_rotation() const { return m_rotation; }
|
||||
double get_rotation(Axis axis) const { return m_rotation(axis); }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void set_rotation(const Vec3d& rotation);
|
||||
void set_rotation(Axis axis, double rotation);
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Vec3d get_scaling_factor() const;
|
||||
double get_scaling_factor(Axis axis) const { return get_scaling_factor()[axis]; }
|
||||
|
||||
Transform3d get_scaling_factor_matrix() const;
|
||||
|
||||
bool is_scaling_uniform() const {
|
||||
const Vec3d scale = get_scaling_factor();
|
||||
return std::abs(scale.x() - scale.y()) < 1e-8 && std::abs(scale.x() - scale.z()) < 1e-8;
|
||||
}
|
||||
#else
|
||||
const Vec3d& get_scaling_factor() const { return m_scaling_factor; }
|
||||
double get_scaling_factor(Axis axis) const { return m_scaling_factor(axis); }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void set_scaling_factor(const Vec3d& scaling_factor);
|
||||
void set_scaling_factor(Axis axis, double scaling_factor);
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Vec3d get_mirror() const;
|
||||
double get_mirror(Axis axis) const { return get_mirror()[axis]; }
|
||||
|
||||
Transform3d get_mirror_matrix() const;
|
||||
|
||||
bool is_left_handed() const {
|
||||
const Vec3d mirror = get_mirror();
|
||||
return mirror.x() * mirror.y() * mirror.z() < 0.0;
|
||||
}
|
||||
#else
|
||||
bool is_scaling_uniform() const { return std::abs(m_scaling_factor.x() - m_scaling_factor.y()) < 1e-8 && std::abs(m_scaling_factor.x() - m_scaling_factor.z()) < 1e-8; }
|
||||
|
||||
const Vec3d& get_mirror() const { return m_mirror; }
|
||||
double get_mirror(Axis axis) const { return m_mirror(axis); }
|
||||
bool is_left_handed() const { return m_mirror.x() * m_mirror.y() * m_mirror.z() < 0.; }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void set_mirror(const Vec3d& mirror);
|
||||
void set_mirror(Axis axis, double mirror);
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
bool has_skew() const;
|
||||
#else
|
||||
void set_from_transform(const Transform3d& transform);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void reset();
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
void reset_offset() { set_offset(Vec3d::Zero()); }
|
||||
void reset_rotation() { set_rotation(Vec3d::Zero()); }
|
||||
void reset_scaling_factor() { set_scaling_factor(Vec3d::Ones()); }
|
||||
void reset_mirror() { set_mirror(Vec3d::Ones()); }
|
||||
void reset_skew();
|
||||
|
||||
const Transform3d& get_matrix() const { return m_matrix; }
|
||||
Transform3d get_matrix_no_offset() const;
|
||||
Transform3d get_matrix_no_scaling_factor() const;
|
||||
|
||||
void set_matrix(const Transform3d& transform) { m_matrix = transform; }
|
||||
#else
|
||||
const Transform3d& get_matrix(bool dont_translate = false, bool dont_rotate = false, bool dont_scale = false, bool dont_mirror = false) const;
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
Transformation operator * (const Transformation& other) const;
|
||||
|
||||
#if !ENABLE_WORLD_COORDINATE
|
||||
// Find volume transformation, so that the chained (instance_trafo * volume_trafo) will be as close to identity
|
||||
// as possible in least squares norm in regard to the 8 corners of bbox.
|
||||
// Bounding box is expected to be centered around zero in all axes.
|
||||
static Transformation volume_to_bed_transformation(const Transformation& instance_transformation, const BoundingBoxf3& bbox);
|
||||
#endif // !ENABLE_WORLD_COORDINATE
|
||||
|
||||
private:
|
||||
friend class cereal::access;
|
||||
template<class Archive> void serialize(Archive & ar) { ar(m_offset, m_rotation, m_scaling_factor, m_mirror); }
|
||||
explicit Transformation(int) : m_dirty(true) {}
|
||||
template <class Archive> static void load_and_construct(Archive &ar, cereal::construct<Transformation> &construct)
|
||||
{
|
||||
// Calling a private constructor with special "int" parameter to indicate that no construction is necessary.
|
||||
construct(1);
|
||||
ar(construct.ptr()->m_offset, construct.ptr()->m_rotation, construct.ptr()->m_scaling_factor, construct.ptr()->m_mirror);
|
||||
}
|
||||
friend class cereal::access;
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
template<class Archive> void serialize(Archive& ar) { ar(m_matrix); }
|
||||
explicit Transformation(int) {}
|
||||
template <class Archive> static void load_and_construct(Archive& ar, cereal::construct<Transformation>& construct)
|
||||
{
|
||||
// Calling a private constructor with special "int" parameter to indicate that no construction is necessary.
|
||||
construct(1);
|
||||
ar(construct.ptr()->m_matrix);
|
||||
}
|
||||
#else
|
||||
template<class Archive> void serialize(Archive& ar) { ar(m_offset, m_rotation, m_scaling_factor, m_mirror); }
|
||||
explicit Transformation(int) : m_dirty(true) {}
|
||||
template <class Archive> static void load_and_construct(Archive& ar, cereal::construct<Transformation>& construct)
|
||||
{
|
||||
// Calling a private constructor with special "int" parameter to indicate that no construction is necessary.
|
||||
construct(1);
|
||||
ar(construct.ptr()->m_offset, construct.ptr()->m_rotation, construct.ptr()->m_scaling_factor, construct.ptr()->m_mirror);
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
};
|
||||
|
||||
// For parsing a transformation matrix from 3MF / AMF.
|
||||
|
@ -43,6 +43,25 @@ std::string float_to_string_decimal_point(double value, int precision = -1);
|
||||
//std::string float_to_string_decimal_point(float value, int precision = -1);
|
||||
double string_to_double_decimal_point(const std::string_view str, size_t* pos = nullptr);
|
||||
|
||||
// Set locales to "C".
|
||||
inline void set_c_locales()
|
||||
{
|
||||
#ifdef _WIN32
|
||||
_configthreadlocale(_ENABLE_PER_THREAD_LOCALE);
|
||||
std::setlocale(LC_ALL, "C");
|
||||
#else
|
||||
// We are leaking some memory here, because the newlocale() produced memory will never be released.
|
||||
// This is not a problem though, as there will be a maximum one worker thread created per physical thread.
|
||||
uselocale(newlocale(
|
||||
#ifdef __APPLE__
|
||||
LC_ALL_MASK
|
||||
#else // some Unix / Linux / BSD
|
||||
LC_ALL
|
||||
#endif
|
||||
, "C", nullptr));
|
||||
#endif
|
||||
}
|
||||
|
||||
} // namespace Slic3r
|
||||
|
||||
#endif // slic3r_LocalesUtils_hpp_
|
||||
|
@ -947,7 +947,11 @@ const BoundingBoxf3& ModelObject::raw_bounding_box() const
|
||||
if (this->instances.empty())
|
||||
throw Slic3r::InvalidArgument("Can't call raw_bounding_box() with no instances");
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const Transform3d inst_matrix = this->instances.front()->get_transformation().get_matrix_no_offset();
|
||||
#else
|
||||
const Transform3d& inst_matrix = this->instances.front()->get_transformation().get_matrix(true);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
for (const ModelVolume *v : this->volumes)
|
||||
if (v->is_model_part())
|
||||
m_raw_bounding_box.merge(v->mesh().transformed_bounding_box(inst_matrix * v->get_matrix()));
|
||||
@ -959,9 +963,15 @@ const BoundingBoxf3& ModelObject::raw_bounding_box() const
|
||||
BoundingBoxf3 ModelObject::instance_bounding_box(size_t instance_idx, bool dont_translate) const
|
||||
{
|
||||
BoundingBoxf3 bb;
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const Transform3d inst_matrix = dont_translate ?
|
||||
this->instances[instance_idx]->get_transformation().get_matrix_no_offset() :
|
||||
this->instances[instance_idx]->get_transformation().get_matrix();
|
||||
|
||||
#else
|
||||
const Transform3d& inst_matrix = this->instances[instance_idx]->get_transformation().get_matrix(dont_translate);
|
||||
for (ModelVolume *v : this->volumes)
|
||||
{
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
for (ModelVolume *v : this->volumes) {
|
||||
if (v->is_model_part())
|
||||
bb.merge(v->mesh().transformed_bounding_box(inst_matrix * v->get_matrix()));
|
||||
}
|
||||
@ -1730,9 +1740,12 @@ void ModelObject::split(ModelObjectPtrs* new_objects)
|
||||
new_object->add_instance(*model_instance);
|
||||
ModelVolume* new_vol = new_object->add_volume(*volume, std::move(mesh));
|
||||
|
||||
for (ModelInstance* model_instance : new_object->instances)
|
||||
{
|
||||
for (ModelInstance* model_instance : new_object->instances) {
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Vec3d shift = model_instance->get_transformation().get_matrix_no_offset() * new_vol->get_offset();
|
||||
#else
|
||||
Vec3d shift = model_instance->get_transformation().get_matrix(true) * new_vol->get_offset();
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
model_instance->set_offset(model_instance->get_offset() + shift);
|
||||
}
|
||||
|
||||
@ -1774,9 +1787,11 @@ void ModelObject::bake_xy_rotation_into_meshes(size_t instance_idx)
|
||||
assert(instance_idx < this->instances.size());
|
||||
|
||||
const Geometry::Transformation reference_trafo = this->instances[instance_idx]->get_transformation();
|
||||
#if !ENABLE_WORLD_COORDINATE
|
||||
if (Geometry::is_rotation_ninety_degrees(reference_trafo.get_rotation()))
|
||||
// nothing to do, scaling in the world coordinate space is possible in the representation of Geometry::Transformation.
|
||||
return;
|
||||
#endif // !ENABLE_WORLD_COORDINATE
|
||||
|
||||
bool left_handed = reference_trafo.is_left_handed();
|
||||
bool has_mirrorring = ! reference_trafo.get_mirror().isApprox(Vec3d(1., 1., 1.));
|
||||
@ -1794,8 +1809,18 @@ void ModelObject::bake_xy_rotation_into_meshes(size_t instance_idx)
|
||||
|
||||
// Adjust the meshes.
|
||||
// Transformation to be applied to the meshes.
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Geometry::Transformation reference_trafo_mod = reference_trafo;
|
||||
reference_trafo_mod.reset_offset();
|
||||
if (uniform_scaling)
|
||||
reference_trafo_mod.reset_scaling_factor();
|
||||
if (!has_mirrorring)
|
||||
reference_trafo_mod.reset_mirror();
|
||||
Eigen::Matrix3d mesh_trafo_3x3 = reference_trafo_mod.get_matrix().matrix().block<3, 3>(0, 0);
|
||||
#else
|
||||
Eigen::Matrix3d mesh_trafo_3x3 = reference_trafo.get_matrix(true, false, uniform_scaling, ! has_mirrorring).matrix().block<3, 3>(0, 0);
|
||||
Transform3d volume_offset_correction = this->instances[instance_idx]->get_transformation().get_matrix().inverse() * reference_trafo.get_matrix();
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
Transform3d volume_offset_correction = this->instances[instance_idx]->get_transformation().get_matrix().inverse() * reference_trafo.get_matrix();
|
||||
for (ModelVolume *model_volume : this->volumes) {
|
||||
const Geometry::Transformation volume_trafo = model_volume->get_transformation();
|
||||
bool volume_left_handed = volume_trafo.is_left_handed();
|
||||
@ -1804,7 +1829,17 @@ void ModelObject::bake_xy_rotation_into_meshes(size_t instance_idx)
|
||||
std::abs(volume_trafo.get_scaling_factor().x() - volume_trafo.get_scaling_factor().z()) < EPSILON;
|
||||
double volume_new_scaling_factor = volume_uniform_scaling ? volume_trafo.get_scaling_factor().x() : 1.;
|
||||
// Transform the mesh.
|
||||
Matrix3d volume_trafo_3x3 = volume_trafo.get_matrix(true, false, volume_uniform_scaling, !volume_has_mirrorring).matrix().block<3, 3>(0, 0);
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Geometry::Transformation volume_trafo_mod = volume_trafo;
|
||||
volume_trafo_mod.reset_offset();
|
||||
if (volume_uniform_scaling)
|
||||
volume_trafo_mod.reset_scaling_factor();
|
||||
if (!volume_has_mirrorring)
|
||||
volume_trafo_mod.reset_mirror();
|
||||
Eigen::Matrix3d volume_trafo_3x3 = volume_trafo_mod.get_matrix().matrix().block<3, 3>(0, 0);
|
||||
#else
|
||||
Matrix3d volume_trafo_3x3 = volume_trafo.get_matrix(true, false, volume_uniform_scaling, !volume_has_mirrorring).matrix().block<3, 3>(0, 0);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
// Following method creates a new shared_ptr<TriangleMesh>
|
||||
model_volume->transform_this_mesh(mesh_trafo_3x3 * volume_trafo_3x3, left_handed != volume_left_handed);
|
||||
// Reset the rotation, scaling and mirroring.
|
||||
@ -1851,7 +1886,11 @@ double ModelObject::get_instance_min_z(size_t instance_idx) const
|
||||
double min_z = DBL_MAX;
|
||||
|
||||
const ModelInstance* inst = instances[instance_idx];
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const Transform3d mi = inst->get_matrix_no_offset();
|
||||
#else
|
||||
const Transform3d& mi = inst->get_matrix(true);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
for (const ModelVolume* v : volumes) {
|
||||
if (!v->is_model_part())
|
||||
@ -1872,7 +1911,11 @@ double ModelObject::get_instance_max_z(size_t instance_idx) const
|
||||
double max_z = -DBL_MAX;
|
||||
|
||||
const ModelInstance* inst = instances[instance_idx];
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const Transform3d mi = inst->get_matrix_no_offset();
|
||||
#else
|
||||
const Transform3d& mi = inst->get_matrix(true);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
for (const ModelVolume* v : volumes) {
|
||||
if (!v->is_model_part())
|
||||
@ -2298,14 +2341,22 @@ void ModelVolume::convert_from_meters()
|
||||
|
||||
void ModelInstance::transform_mesh(TriangleMesh* mesh, bool dont_translate) const
|
||||
{
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
mesh->transform(dont_translate ? get_matrix_no_offset() : get_matrix());
|
||||
#else
|
||||
mesh->transform(get_matrix(dont_translate));
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
BoundingBoxf3 ModelInstance::transform_mesh_bounding_box(const TriangleMesh& mesh, bool dont_translate) const
|
||||
{
|
||||
// Rotate around mesh origin.
|
||||
TriangleMesh copy(mesh);
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
copy.transform(get_transformation().get_rotation_matrix());
|
||||
#else
|
||||
copy.transform(get_matrix(true, false, true, true));
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
BoundingBoxf3 bbox = copy.bounding_box();
|
||||
|
||||
if (!empty(bbox)) {
|
||||
@ -2330,12 +2381,20 @@ BoundingBoxf3 ModelInstance::transform_mesh_bounding_box(const TriangleMesh& mes
|
||||
|
||||
BoundingBoxf3 ModelInstance::transform_bounding_box(const BoundingBoxf3 &bbox, bool dont_translate) const
|
||||
{
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
return bbox.transformed(dont_translate ? get_matrix_no_offset() : get_matrix());
|
||||
#else
|
||||
return bbox.transformed(get_matrix(dont_translate));
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
Vec3d ModelInstance::transform_vector(const Vec3d& v, bool dont_translate) const
|
||||
{
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
return dont_translate ? get_matrix_no_offset() * v : get_matrix() * v;
|
||||
#else
|
||||
return get_matrix(dont_translate) * v;
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
void ModelInstance::transform_polygon(Polygon* polygon) const
|
||||
|
@ -781,15 +781,26 @@ public:
|
||||
|
||||
const Geometry::Transformation& get_transformation() const { return m_transformation; }
|
||||
void set_transformation(const Geometry::Transformation& transformation) { m_transformation = transformation; }
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
void set_transformation(const Transform3d& trafo) { m_transformation.set_matrix(trafo); }
|
||||
|
||||
Vec3d get_offset() const { return m_transformation.get_offset(); }
|
||||
#else
|
||||
void set_transformation(const Transform3d &trafo) { m_transformation.set_from_transform(trafo); }
|
||||
|
||||
const Vec3d& get_offset() const { return m_transformation.get_offset(); }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
double get_offset(Axis axis) const { return m_transformation.get_offset(axis); }
|
||||
|
||||
void set_offset(const Vec3d& offset) { m_transformation.set_offset(offset); }
|
||||
void set_offset(Axis axis, double offset) { m_transformation.set_offset(axis, offset); }
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Vec3d get_rotation() const { return m_transformation.get_rotation(); }
|
||||
#else
|
||||
const Vec3d& get_rotation() const { return m_transformation.get_rotation(); }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
double get_rotation(Axis axis) const { return m_transformation.get_rotation(axis); }
|
||||
|
||||
void set_rotation(const Vec3d& rotation) { m_transformation.set_rotation(rotation); }
|
||||
@ -801,7 +812,11 @@ public:
|
||||
void set_scaling_factor(const Vec3d& scaling_factor) { m_transformation.set_scaling_factor(scaling_factor); }
|
||||
void set_scaling_factor(Axis axis, double scaling_factor) { m_transformation.set_scaling_factor(axis, scaling_factor); }
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Vec3d get_mirror() const { return m_transformation.get_mirror(); }
|
||||
#else
|
||||
const Vec3d& get_mirror() const { return m_transformation.get_mirror(); }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
double get_mirror(Axis axis) const { return m_transformation.get_mirror(axis); }
|
||||
bool is_left_handed() const { return m_transformation.is_left_handed(); }
|
||||
|
||||
@ -810,7 +825,12 @@ public:
|
||||
void convert_from_imperial_units();
|
||||
void convert_from_meters();
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const Transform3d& get_matrix() const { return m_transformation.get_matrix(); }
|
||||
Transform3d get_matrix_no_offset() const { return m_transformation.get_matrix_no_offset(); }
|
||||
#else
|
||||
const Transform3d& get_matrix(bool dont_translate = false, bool dont_rotate = false, bool dont_scale = false, bool dont_mirror = false) const { return m_transformation.get_matrix(dont_translate, dont_rotate, dont_scale, dont_mirror); }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void set_new_unique_id() {
|
||||
ObjectBase::set_new_unique_id();
|
||||
@ -1013,25 +1033,41 @@ public:
|
||||
const Geometry::Transformation& get_transformation() const { return m_transformation; }
|
||||
void set_transformation(const Geometry::Transformation& transformation) { m_transformation = transformation; }
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Vec3d get_offset() const { return m_transformation.get_offset(); }
|
||||
#else
|
||||
const Vec3d& get_offset() const { return m_transformation.get_offset(); }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
double get_offset(Axis axis) const { return m_transformation.get_offset(axis); }
|
||||
|
||||
void set_offset(const Vec3d& offset) { m_transformation.set_offset(offset); }
|
||||
void set_offset(Axis axis, double offset) { m_transformation.set_offset(axis, offset); }
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Vec3d get_rotation() const { return m_transformation.get_rotation(); }
|
||||
#else
|
||||
const Vec3d& get_rotation() const { return m_transformation.get_rotation(); }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
double get_rotation(Axis axis) const { return m_transformation.get_rotation(axis); }
|
||||
|
||||
void set_rotation(const Vec3d& rotation) { m_transformation.set_rotation(rotation); }
|
||||
void set_rotation(Axis axis, double rotation) { m_transformation.set_rotation(axis, rotation); }
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Vec3d get_scaling_factor() const { return m_transformation.get_scaling_factor(); }
|
||||
#else
|
||||
const Vec3d& get_scaling_factor() const { return m_transformation.get_scaling_factor(); }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
double get_scaling_factor(Axis axis) const { return m_transformation.get_scaling_factor(axis); }
|
||||
|
||||
void set_scaling_factor(const Vec3d& scaling_factor) { m_transformation.set_scaling_factor(scaling_factor); }
|
||||
void set_scaling_factor(Axis axis, double scaling_factor) { m_transformation.set_scaling_factor(axis, scaling_factor); }
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
Vec3d get_mirror() const { return m_transformation.get_mirror(); }
|
||||
#else
|
||||
const Vec3d& get_mirror() const { return m_transformation.get_mirror(); }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
double get_mirror(Axis axis) const { return m_transformation.get_mirror(axis); }
|
||||
bool is_left_handed() const { return m_transformation.is_left_handed(); }
|
||||
|
||||
@ -1049,7 +1085,12 @@ public:
|
||||
// To be called on an external polygon. It does not translate the polygon, only rotates and scales.
|
||||
void transform_polygon(Polygon* polygon) const;
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const Transform3d& get_matrix() const { return m_transformation.get_matrix(); }
|
||||
Transform3d get_matrix_no_offset() const { return m_transformation.get_matrix_no_offset(); }
|
||||
#else
|
||||
const Transform3d& get_matrix(bool dont_translate = false, bool dont_rotate = false, bool dont_scale = false, bool dont_mirror = false) const { return m_transformation.get_matrix(dont_translate, dont_rotate, dont_scale, dont_mirror); }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
bool is_printable() const { return object->printable && printable && (print_volume_state == ModelInstancePVS_Inside); }
|
||||
|
||||
|
@ -3,6 +3,13 @@
|
||||
|
||||
#include <assert.h>
|
||||
#include <type_traits>
|
||||
#include <vector>
|
||||
#include <limits>
|
||||
#include <cstdlib> // adds size_t (without std::)
|
||||
|
||||
namespace Slic3r {
|
||||
|
||||
constexpr auto InvalidQueueID = std::numeric_limits<size_t>::max();
|
||||
|
||||
template<typename T, typename IndexSetter, typename LessPredicate, const bool ResetIndexWhenRemoved = false>
|
||||
class MutablePriorityQueue
|
||||
@ -21,7 +28,7 @@ public:
|
||||
MutablePriorityQueue& operator=(MutablePriorityQueue &&) = default;
|
||||
|
||||
// This class modifies the outside data through the m_index_setter
|
||||
// and thus it should not be copied. The semantics are similar to std::unique_ptr
|
||||
// and thus it should not be copied. The semantics is similar to std::unique_ptr
|
||||
MutablePriorityQueue(const MutablePriorityQueue &) = delete;
|
||||
MutablePriorityQueue& operator=(const MutablePriorityQueue &) = delete;
|
||||
|
||||
@ -38,6 +45,7 @@ public:
|
||||
bool empty() const { return m_heap.empty(); }
|
||||
T& operator[](std::size_t idx) noexcept { return m_heap[idx]; }
|
||||
const T& operator[](std::size_t idx) const noexcept { return m_heap[idx]; }
|
||||
static constexpr size_t invalid_id() { return InvalidQueueID; }
|
||||
|
||||
using iterator = typename std::vector<T>::iterator;
|
||||
using const_iterator = typename std::vector<T>::const_iterator;
|
||||
@ -66,14 +74,10 @@ MutablePriorityQueue<T, IndexSetter, LessPredicate, ResetIndexWhenRemoved> make_
|
||||
template<class T, class LessPredicate, class IndexSetter, const bool ResetIndexWhenRemoved>
|
||||
inline void MutablePriorityQueue<T, LessPredicate, IndexSetter, ResetIndexWhenRemoved>::clear()
|
||||
{
|
||||
#ifdef NDEBUG
|
||||
// Only mark as removed from the queue in release mode, if configured so.
|
||||
if (ResetIndexWhenRemoved)
|
||||
#endif /* NDEBUG */
|
||||
{
|
||||
if constexpr (ResetIndexWhenRemoved) {
|
||||
for (size_t idx = 0; idx < m_heap.size(); ++ idx)
|
||||
// Mark as removed from the queue.
|
||||
m_index_setter(m_heap[idx], std::numeric_limits<size_t>::max());
|
||||
m_index_setter(m_heap[idx], this->invalid_id());
|
||||
}
|
||||
m_heap.clear();
|
||||
}
|
||||
@ -100,13 +104,9 @@ template<class T, class LessPredicate, class IndexSetter, const bool ResetIndexW
|
||||
inline void MutablePriorityQueue<T, LessPredicate, IndexSetter, ResetIndexWhenRemoved>::pop()
|
||||
{
|
||||
assert(! m_heap.empty());
|
||||
#ifdef NDEBUG
|
||||
// Only mark as removed from the queue in release mode, if configured so.
|
||||
if (ResetIndexWhenRemoved)
|
||||
#endif /* NDEBUG */
|
||||
{
|
||||
if constexpr (ResetIndexWhenRemoved) {
|
||||
// Mark as removed from the queue.
|
||||
m_index_setter(m_heap.front(), std::numeric_limits<size_t>::max());
|
||||
m_index_setter(m_heap.front(), this->invalid_id());
|
||||
}
|
||||
if (m_heap.size() > 1) {
|
||||
m_heap.front() = m_heap.back();
|
||||
@ -121,13 +121,10 @@ template<class T, class LessPredicate, class IndexSetter, const bool ResetIndexW
|
||||
inline void MutablePriorityQueue<T, LessPredicate, IndexSetter, ResetIndexWhenRemoved>::remove(size_t idx)
|
||||
{
|
||||
assert(idx < m_heap.size());
|
||||
#ifdef NDEBUG
|
||||
// Only mark as removed from the queue in release mode, if configured so.
|
||||
if (ResetIndexWhenRemoved)
|
||||
#endif /* NDEBUG */
|
||||
{
|
||||
if constexpr (ResetIndexWhenRemoved) {
|
||||
// Mark as removed from the queue.
|
||||
m_index_setter(m_heap[idx], std::numeric_limits<size_t>::max());
|
||||
m_index_setter(m_heap[idx], this->invalid_id());
|
||||
}
|
||||
if (idx + 1 == m_heap.size()) {
|
||||
m_heap.pop_back();
|
||||
@ -274,6 +271,14 @@ public:
|
||||
{}
|
||||
~MutableSkipHeapPriorityQueue() { clear(); }
|
||||
|
||||
MutableSkipHeapPriorityQueue(MutableSkipHeapPriorityQueue &&) = default;
|
||||
MutableSkipHeapPriorityQueue &operator=(MutableSkipHeapPriorityQueue &&) = default;
|
||||
|
||||
// This class modifies the outside data through the m_index_setter
|
||||
// and thus it should not be copied. The semantics is similar to std::unique_ptr
|
||||
MutableSkipHeapPriorityQueue(const MutableSkipHeapPriorityQueue &) = delete;
|
||||
MutableSkipHeapPriorityQueue &operator=(const MutableSkipHeapPriorityQueue &) = delete;
|
||||
|
||||
void clear();
|
||||
// Reserve one unused element per miniheap.
|
||||
void reserve(size_t cnt) { m_heap.reserve(cnt + ((cnt + (address::block_size - 1)) / (address::block_size - 1))); }
|
||||
@ -285,9 +290,12 @@ public:
|
||||
void update(size_t idx) { assert(! address::is_padding(idx)); T item = m_heap[idx]; remove(idx); push(item); }
|
||||
// There is one padding element storead at each miniheap, thus lower the number of elements by the number of miniheaps.
|
||||
size_t size() const noexcept { return m_heap.size() - (m_heap.size() + address::block_size - 1) / address::block_size; }
|
||||
// Number of heap elements including padding. heap_size() >= size().
|
||||
size_t heap_size() const noexcept { return m_heap.size(); }
|
||||
bool empty() const { return m_heap.empty(); }
|
||||
T& operator[](std::size_t idx) noexcept { assert(! address::is_padding(idx)); return m_heap[idx]; }
|
||||
const T& operator[](std::size_t idx) const noexcept { assert(! address::is_padding(idx)); return m_heap[idx]; }
|
||||
static constexpr size_t invalid_id() { return InvalidQueueID; }
|
||||
|
||||
protected:
|
||||
void update_heap_up(size_t top, size_t bottom);
|
||||
@ -317,15 +325,11 @@ MutableSkipHeapPriorityQueue<T, IndexSetter, LessPredicate, BlockSize, ResetInde
|
||||
template<class T, class LessPredicate, class IndexSetter, std::size_t blocking, const bool ResetIndexWhenRemoved>
|
||||
inline void MutableSkipHeapPriorityQueue<T, LessPredicate, IndexSetter, blocking, ResetIndexWhenRemoved>::clear()
|
||||
{
|
||||
#ifdef NDEBUG
|
||||
// Only mark as removed from the queue in release mode, if configured so.
|
||||
if (ResetIndexWhenRemoved)
|
||||
#endif /* NDEBUG */
|
||||
{
|
||||
if constexpr (ResetIndexWhenRemoved) {
|
||||
for (size_t idx = 0; idx < m_heap.size(); ++ idx)
|
||||
// Mark as removed from the queue.
|
||||
if (! address::is_padding(idx))
|
||||
m_index_setter(m_heap[idx], std::numeric_limits<size_t>::max());
|
||||
m_index_setter(m_heap[idx], this->invalid_id());
|
||||
}
|
||||
m_heap.clear();
|
||||
}
|
||||
@ -356,13 +360,9 @@ template<class T, class LessPredicate, class IndexSetter, std::size_t blocking,
|
||||
inline void MutableSkipHeapPriorityQueue<T, LessPredicate, IndexSetter, blocking, ResetIndexWhenRemoved>::pop()
|
||||
{
|
||||
assert(! m_heap.empty());
|
||||
#ifdef NDEBUG
|
||||
// Only mark as removed from the queue in release mode, if configured so.
|
||||
if (ResetIndexWhenRemoved)
|
||||
#endif /* NDEBUG */
|
||||
{
|
||||
if constexpr (ResetIndexWhenRemoved) {
|
||||
// Mark as removed from the queue.
|
||||
m_index_setter(m_heap[1], std::numeric_limits<size_t>::max());
|
||||
m_index_setter(m_heap[1], this->invalid_id());
|
||||
}
|
||||
// Zero'th element is padding, thus non-empty queue must have at least two elements.
|
||||
if (m_heap.size() > 2) {
|
||||
@ -379,13 +379,9 @@ inline void MutableSkipHeapPriorityQueue<T, LessPredicate, IndexSetter, blocking
|
||||
{
|
||||
assert(idx < m_heap.size());
|
||||
assert(! address::is_padding(idx));
|
||||
#ifdef NDEBUG
|
||||
// Only mark as removed from the queue in release mode, if configured so.
|
||||
if (ResetIndexWhenRemoved)
|
||||
#endif /* NDEBUG */
|
||||
{
|
||||
if constexpr (ResetIndexWhenRemoved) {
|
||||
// Mark as removed from the queue.
|
||||
m_index_setter(m_heap[idx], std::numeric_limits<size_t>::max());
|
||||
m_index_setter(m_heap[idx], this->invalid_id());
|
||||
}
|
||||
if (idx + 1 == m_heap.size()) {
|
||||
this->pop_back();
|
||||
@ -458,4 +454,6 @@ inline void MutableSkipHeapPriorityQueue<T, LessPredicate, IndexSetter, blocking
|
||||
}
|
||||
}
|
||||
|
||||
} // namespace Slic3r
|
||||
|
||||
#endif /* slic3r_MutablePriorityQueue_hpp_ */
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -1,7 +1,7 @@
|
||||
#include <cassert>
|
||||
|
||||
#include "PresetBundle.hpp"
|
||||
#include "libslic3r.h"
|
||||
#include "PresetBundle.hpp"
|
||||
#include "Utils.hpp"
|
||||
#include "Model.hpp"
|
||||
#include "format.hpp"
|
||||
@ -453,6 +453,11 @@ void PresetBundle::save_changes_for_preset(const std::string& new_name, Preset::
|
||||
presets.get_edited_preset().config.apply_only(presets.get_selected_preset().config, unselected_options);
|
||||
}
|
||||
|
||||
#if ENABLE_COPY_CUSTOM_BED_MODEL_AND_TEXTURE
|
||||
if (type == Preset::TYPE_PRINTER)
|
||||
copy_bed_model_and_texture_if_needed(presets.get_edited_preset().config);
|
||||
#endif // ENABLE_COPY_CUSTOM_BED_MODEL_AND_TEXTURE
|
||||
|
||||
// Save the preset into Slic3r::data_dir / presets / section_name / preset_name.ini
|
||||
presets.save_current_preset(new_name);
|
||||
// Mark the print & filament enabled if they are compatible with the currently selected preset.
|
||||
@ -1860,4 +1865,32 @@ void PresetBundle::set_default_suppressed(bool default_suppressed)
|
||||
printers.set_default_suppressed(default_suppressed);
|
||||
}
|
||||
|
||||
#if ENABLE_COPY_CUSTOM_BED_MODEL_AND_TEXTURE
|
||||
void copy_bed_model_and_texture_if_needed(DynamicPrintConfig& config)
|
||||
{
|
||||
const boost::filesystem::path user_dir = boost::filesystem::absolute(boost::filesystem::path(data_dir()) / "printer").make_preferred();
|
||||
const boost::filesystem::path res_dir = boost::filesystem::absolute(boost::filesystem::path(resources_dir()) / "profiles").make_preferred();
|
||||
|
||||
auto do_copy = [&user_dir, &res_dir](ConfigOptionString* cfg, const std::string& type) {
|
||||
if (cfg == nullptr || cfg->value.empty())
|
||||
return;
|
||||
|
||||
const boost::filesystem::path src_dir = boost::filesystem::absolute(boost::filesystem::path(cfg->value)).make_preferred().parent_path();
|
||||
if (src_dir != user_dir && src_dir.parent_path() != res_dir) {
|
||||
const std::string dst_value = (user_dir / boost::filesystem::path(cfg->value).filename()).string();
|
||||
std::string error;
|
||||
if (copy_file_inner(cfg->value, dst_value, error) == SUCCESS)
|
||||
cfg->value = dst_value;
|
||||
else {
|
||||
BOOST_LOG_TRIVIAL(error) << "Copying from " << cfg->value << " to " << dst_value << " failed. Unable to set custom bed " << type << ". [" << error << "]";
|
||||
cfg->value = "";
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
do_copy(config.option<ConfigOptionString>("bed_custom_texture"), "texture");
|
||||
do_copy(config.option<ConfigOptionString>("bed_custom_model"), "model");
|
||||
}
|
||||
#endif // ENABLE_COPY_CUSTOM_BED_MODEL_AND_TEXTURE
|
||||
|
||||
} // namespace Slic3r
|
||||
|
@ -178,6 +178,12 @@ private:
|
||||
|
||||
ENABLE_ENUM_BITMASK_OPERATORS(PresetBundle::LoadConfigBundleAttribute)
|
||||
|
||||
#if ENABLE_COPY_CUSTOM_BED_MODEL_AND_TEXTURE
|
||||
// Copies bed texture and model files to 'data_dir()\printer' folder, if needed
|
||||
// and updates the config accordingly
|
||||
extern void copy_bed_model_and_texture_if_needed(DynamicPrintConfig& config);
|
||||
#endif // ENABLE_COPY_CUSTOM_BED_MODEL_AND_TEXTURE
|
||||
|
||||
} // namespace Slic3r
|
||||
|
||||
#endif /* slic3r_PresetBundle_hpp_ */
|
||||
|
@ -13,6 +13,7 @@
|
||||
#include "GCode.hpp"
|
||||
#include "GCode/WipeTower.hpp"
|
||||
#include "Utils.hpp"
|
||||
#include "BuildVolume.hpp"
|
||||
|
||||
#include <float.h>
|
||||
|
||||
@ -387,7 +388,7 @@ bool Print::sequential_print_horizontal_clearance_valid(const Print& print, Poly
|
||||
Geometry::assemble_transform({ 0.0, 0.0, model_instance0->get_offset().z() }, model_instance0->get_rotation(), model_instance0->get_scaling_factor(), model_instance0->get_mirror())),
|
||||
// Shrink the extruder_clearance_radius a tiny bit, so that if the object arrangement algorithm placed the objects
|
||||
// exactly by satisfying the extruder_clearance_radius, this test will not trigger collision.
|
||||
float(scale_(0.5 * print.config().extruder_clearance_radius.value - EPSILON)),
|
||||
float(scale_(0.5 * print.config().extruder_clearance_radius.value - BuildVolume::BedEpsilon)),
|
||||
jtRound, scale_(0.1)).front());
|
||||
}
|
||||
// Make a copy, so it may be rotated for instances.
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -464,7 +464,7 @@ FillLightning::GeneratorPtr PrintObject::prepare_lightning_infill_data()
|
||||
break;
|
||||
}
|
||||
|
||||
return has_lightning_infill ? FillLightning::build_generator(std::as_const(*this)) : FillLightning::GeneratorPtr();
|
||||
return has_lightning_infill ? FillLightning::build_generator(std::as_const(*this), [this]() -> void { this->throw_if_canceled(); }) : FillLightning::GeneratorPtr();
|
||||
}
|
||||
|
||||
void PrintObject::clear_layers()
|
||||
|
@ -288,7 +288,7 @@ template<unsigned MAX_ITER>
|
||||
struct RotfinderBoilerplate {
|
||||
static constexpr unsigned MAX_TRIES = MAX_ITER;
|
||||
|
||||
int status = 0;
|
||||
int status = 0, prev_status = 0;
|
||||
TriangleMesh mesh;
|
||||
unsigned max_tries;
|
||||
const RotOptimizeParams ¶ms;
|
||||
@ -314,13 +314,20 @@ struct RotfinderBoilerplate {
|
||||
|
||||
RotfinderBoilerplate(const ModelObject &mo, const RotOptimizeParams &p)
|
||||
: mesh{get_mesh_to_rotate(mo)}
|
||||
, params{p}
|
||||
, max_tries(p.accuracy() * MAX_TRIES)
|
||||
{
|
||||
, params{p}
|
||||
{}
|
||||
|
||||
void statusfn() {
|
||||
int s = status * 100 / max_tries;
|
||||
if (s != prev_status) {
|
||||
params.statuscb()(s);
|
||||
prev_status = s;
|
||||
}
|
||||
|
||||
++status;
|
||||
}
|
||||
|
||||
void statusfn() { params.statuscb()(++status * 100.0 / max_tries); }
|
||||
bool stopcond() { return ! params.statuscb()(-1); }
|
||||
};
|
||||
|
||||
|
@ -195,7 +195,15 @@ std::vector<std::pair<size_t, bool>> chain_segments_greedy_constrained_reversals
|
||||
}
|
||||
|
||||
// Initialize a heap of end points sorted by the lowest distance to the next valid point of a path.
|
||||
auto queue = make_mutable_priority_queue<EndPoint*, false>(
|
||||
auto queue = make_mutable_priority_queue<EndPoint*,
|
||||
#ifndef NDEBUG
|
||||
// In debug mode, reset indices when removing an item from the queue for debugging purposes.
|
||||
true
|
||||
#else // NDEBUG
|
||||
// In release mode, don't reset indices when removing an item from the queue.
|
||||
false
|
||||
#endif // NDEBUG
|
||||
>(
|
||||
[](EndPoint *ep, size_t idx){ ep->heap_idx = idx; },
|
||||
[](EndPoint *l, EndPoint *r){ return l->distance_out < r->distance_out; });
|
||||
queue.reserve(end_points.size() * 2 - 1);
|
||||
@ -213,7 +221,7 @@ std::vector<std::pair<size_t, bool>> chain_segments_greedy_constrained_reversals
|
||||
assert(ep.chain_id == 0);
|
||||
} else {
|
||||
// End point is NOT on the heap, therefore it is part of the output path.
|
||||
assert(ep.heap_idx == std::numeric_limits<size_t>::max());
|
||||
assert(ep.heap_idx == queue.invalid_id());
|
||||
assert(ep.chain_id != 0);
|
||||
if (&ep == first_point) {
|
||||
assert(ep.edge_out == nullptr);
|
||||
@ -222,7 +230,7 @@ std::vector<std::pair<size_t, bool>> chain_segments_greedy_constrained_reversals
|
||||
// Detect loops.
|
||||
for (EndPoint *pt = &ep; pt != nullptr;) {
|
||||
// Out of queue. It is a final point.
|
||||
assert(pt->heap_idx == std::numeric_limits<size_t>::max());
|
||||
assert(pt->heap_idx == queue.invalid_id());
|
||||
EndPoint *pt_other = &end_points[(pt - &end_points.front()) ^ 1];
|
||||
if (pt_other->heap_idx < queue.size())
|
||||
// The other side of this segment is undecided yet.
|
||||
|
@ -50,7 +50,7 @@
|
||||
// Enable showing time estimate for travel moves in legend
|
||||
#define ENABLE_TRAVEL_TIME (1 && ENABLE_2_5_0_ALPHA1)
|
||||
// Enable not killing focus in object manipulator fields when hovering over 3D scene
|
||||
#define ENABLE_OBJECT_MANIPULATOR_FOCUS (1 && ENABLE_2_5_0_ALPHA1)
|
||||
#define ENABLE_OBJECT_MANIPULATOR_FOCUS (0 && ENABLE_2_5_0_ALPHA1)
|
||||
// Enable removal of wipe tower magic object_id equal to 1000
|
||||
#define ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL (1 && ENABLE_2_5_0_ALPHA1)
|
||||
// Enable removal of legacy OpenGL calls
|
||||
@ -69,6 +69,8 @@
|
||||
#define ENABLE_SHOW_TOOLPATHS_COG (1 && ENABLE_2_5_0_ALPHA1)
|
||||
// Enable recalculating toolpaths when switching to/from volumetric rate visualization
|
||||
#define ENABLE_VOLUMETRIC_RATE_TOOLPATHS_RECALC (1 && ENABLE_2_5_0_ALPHA1)
|
||||
// Enable editing volumes transformation in world coordinates and instances in local coordinates
|
||||
#define ENABLE_WORLD_COORDINATE (1 && ENABLE_2_5_0_ALPHA1)
|
||||
// Enable modified camera control using mouse
|
||||
#define ENABLE_NEW_CAMERA_MOVEMENTS (1 && ENABLE_2_5_0_ALPHA1)
|
||||
// Enable modified rectangle selection
|
||||
@ -81,6 +83,7 @@
|
||||
#define ENABLE_USED_FILAMENT_POST_PROCESS (1 && ENABLE_2_5_0_ALPHA1)
|
||||
// Enable gizmo grabbers to share common models
|
||||
#define ENABLE_GIZMO_GRABBER_REFACTOR (1 && ENABLE_2_5_0_ALPHA1)
|
||||
|
||||
// Enable copy of custom bed model and texture
|
||||
#define ENABLE_COPY_CUSTOM_BED_MODEL_AND_TEXTURE (1 && ENABLE_2_5_0_ALPHA1)
|
||||
|
||||
#endif // _prusaslicer_technologies_h_
|
||||
|
@ -15,6 +15,7 @@
|
||||
|
||||
#include "Thread.hpp"
|
||||
#include "Utils.hpp"
|
||||
#include "LocalesUtils.hpp"
|
||||
|
||||
namespace Slic3r {
|
||||
|
||||
@ -234,21 +235,8 @@ void name_tbb_thread_pool_threads_set_locale()
|
||||
std::ostringstream name;
|
||||
name << "slic3r_tbb_" << range.begin();
|
||||
set_current_thread_name(name.str().c_str());
|
||||
// Set locales of the worker thread to "C".
|
||||
#ifdef _WIN32
|
||||
_configthreadlocale(_ENABLE_PER_THREAD_LOCALE);
|
||||
std::setlocale(LC_ALL, "C");
|
||||
#else
|
||||
// We are leaking some memory here, because the newlocale() produced memory will never be released.
|
||||
// This is not a problem though, as there will be a maximum one worker thread created per physical thread.
|
||||
uselocale(newlocale(
|
||||
#ifdef __APPLE__
|
||||
LC_ALL_MASK
|
||||
#else // some Unix / Linux / BSD
|
||||
LC_ALL
|
||||
#endif
|
||||
, "C", nullptr));
|
||||
#endif
|
||||
// Set locales of the worker thread to "C".
|
||||
set_c_locales();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
@ -4,7 +4,6 @@
|
||||
#include "libslic3r_version.h"
|
||||
#define GCODEVIEWER_APP_NAME "PrusaSlicer G-code Viewer"
|
||||
#define GCODEVIEWER_APP_KEY "PrusaSlicerGcodeViewer"
|
||||
#define GCODEVIEWER_BUILD_ID std::string("PrusaSlicer G-code Viewer-") + std::string(SLIC3R_VERSION) + std::string("-UNKNOWN")
|
||||
|
||||
// this needs to be included early for MSVC (listing it in Build.PL is not enough)
|
||||
#include <memory>
|
||||
|
@ -1 +0,0 @@
|
||||
Upstream source: https://github.com/memononen/nanosvg/tree/c1f6e209c16b18b46aa9f45d7e619acf42c29726
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -85,6 +85,8 @@ set(SLIC3R_GUI_SOURCES
|
||||
GUI/GUI_App.hpp
|
||||
GUI/GUI_Utils.cpp
|
||||
GUI/GUI_Utils.hpp
|
||||
GUI/GUI_Geometry.cpp
|
||||
GUI/GUI_Geometry.hpp
|
||||
GUI/I18N.cpp
|
||||
GUI/I18N.hpp
|
||||
GUI/MainFrame.cpp
|
||||
@ -129,6 +131,8 @@ set(SLIC3R_GUI_SOURCES
|
||||
GUI/2DBed.hpp
|
||||
GUI/3DBed.cpp
|
||||
GUI/3DBed.hpp
|
||||
GUI/CoordAxes.cpp
|
||||
GUI/CoordAxes.hpp
|
||||
GUI/Camera.cpp
|
||||
GUI/Camera.hpp
|
||||
GUI/wxExtensions.cpp
|
||||
@ -172,6 +176,7 @@ set(SLIC3R_GUI_SOURCES
|
||||
GUI/Jobs/Worker.hpp
|
||||
GUI/Jobs/BoostThreadWorker.hpp
|
||||
GUI/Jobs/BoostThreadWorker.cpp
|
||||
GUI/Jobs/UIThreadWorker.hpp
|
||||
GUI/Jobs/BusyCursorJob.hpp
|
||||
GUI/Jobs/PlaterWorker.hpp
|
||||
GUI/Jobs/ArrangeJob.hpp
|
||||
@ -246,8 +251,12 @@ set(SLIC3R_GUI_SOURCES
|
||||
Utils/TCPConsole.hpp
|
||||
Utils/MKS.cpp
|
||||
Utils/MKS.hpp
|
||||
Utils/WinRegistry.cpp
|
||||
Utils/WinRegistry.hpp
|
||||
)
|
||||
|
||||
find_package(NanoSVG REQUIRED)
|
||||
|
||||
if (APPLE)
|
||||
list(APPEND SLIC3R_GUI_SOURCES
|
||||
Utils/RetinaHelperImpl.mm
|
||||
@ -272,7 +281,7 @@ endforeach()
|
||||
|
||||
encoding_check(libslic3r_gui)
|
||||
|
||||
target_link_libraries(libslic3r_gui libslic3r avrdude libcereal imgui GLEW::GLEW OpenGL::GL hidapi libcurl ${wxWidgets_LIBRARIES})
|
||||
target_link_libraries(libslic3r_gui libslic3r avrdude libcereal imgui GLEW::GLEW OpenGL::GL hidapi libcurl ${wxWidgets_LIBRARIES} NanoSVG::nanosvg NanoSVG::nanosvgrast)
|
||||
|
||||
if (MSVC)
|
||||
target_link_libraries(libslic3r_gui Setupapi.lib)
|
||||
|
@ -102,6 +102,7 @@ const float* GeometryBuffer::get_vertices_data() const
|
||||
}
|
||||
#endif // !ENABLE_LEGACY_OPENGL_REMOVAL
|
||||
|
||||
#if !ENABLE_WORLD_COORDINATE
|
||||
const float Bed3D::Axes::DefaultStemRadius = 0.5f;
|
||||
const float Bed3D::Axes::DefaultStemLength = 25.0f;
|
||||
const float Bed3D::Axes::DefaultTipRadius = 2.5f * Bed3D::Axes::DefaultStemRadius;
|
||||
@ -179,6 +180,7 @@ void Bed3D::Axes::render()
|
||||
|
||||
glsafe(::glDisable(GL_DEPTH_TEST));
|
||||
}
|
||||
#endif // !ENABLE_WORLD_COORDINATE
|
||||
|
||||
bool Bed3D::set_shape(const Pointfs& bed_shape, const double max_print_height, const std::string& custom_texture, const std::string& custom_model, bool force_as_custom)
|
||||
{
|
||||
@ -341,7 +343,11 @@ BoundingBoxf3 Bed3D::calc_extended_bounding_box() const
|
||||
out.max.z() = 0.0;
|
||||
// extend to contain axes
|
||||
out.merge(m_axes.get_origin() + m_axes.get_total_length() * Vec3d::Ones());
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
out.merge(out.min + Vec3d(-m_axes.get_tip_radius(), -m_axes.get_tip_radius(), out.max.z()));
|
||||
#else
|
||||
out.merge(out.min + Vec3d(-Axes::DefaultTipRadius, -Axes::DefaultTipRadius, out.max.z()));
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
// extend to contain model, if any
|
||||
BoundingBoxf3 model_bb = m_model.get_bounding_box();
|
||||
if (model_bb.defined) {
|
||||
@ -539,7 +545,15 @@ std::tuple<Bed3D::Type, std::string, std::string> Bed3D::detect_type(const Point
|
||||
void Bed3D::render_axes()
|
||||
{
|
||||
if (m_build_volume.valid())
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
#if ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
m_axes.render(Transform3d::Identity(), 0.25f);
|
||||
#else
|
||||
m_axes.render(0.25f);
|
||||
#endif // ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
#else
|
||||
m_axes.render();
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
#if ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
|
@ -3,7 +3,11 @@
|
||||
|
||||
#include "GLTexture.hpp"
|
||||
#include "3DScene.hpp"
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
#include "CoordAxes.hpp"
|
||||
#else
|
||||
#include "GLModel.hpp"
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
#include "libslic3r/BuildVolume.hpp"
|
||||
#if ENABLE_LEGACY_OPENGL_REMOVAL
|
||||
@ -44,6 +48,7 @@ public:
|
||||
|
||||
class Bed3D
|
||||
{
|
||||
#if !ENABLE_WORLD_COORDINATE
|
||||
class Axes
|
||||
{
|
||||
public:
|
||||
@ -67,6 +72,7 @@ class Bed3D
|
||||
float get_total_length() const { return m_stem_length + DefaultTipLength; }
|
||||
void render();
|
||||
};
|
||||
#endif // !ENABLE_WORLD_COORDINATE
|
||||
|
||||
public:
|
||||
enum class Type : unsigned char
|
||||
@ -107,7 +113,11 @@ private:
|
||||
#if !ENABLE_LEGACY_OPENGL_REMOVAL
|
||||
unsigned int m_vbo_id{ 0 };
|
||||
#endif // !ENABLE_LEGACY_OPENGL_REMOVAL
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
CoordAxes m_axes;
|
||||
#else
|
||||
Axes m_axes;
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
float m_scale_factor{ 1.0f };
|
||||
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -221,8 +221,7 @@ AboutDialog::AboutDialog()
|
||||
main_sizer->Add(hsizer, 0, wxEXPAND | wxALL, 20);
|
||||
|
||||
// logo
|
||||
m_logo_bitmap = ScalableBitmap(this, wxGetApp().logo_name(), 192);
|
||||
m_logo = new wxStaticBitmap(this, wxID_ANY, m_logo_bitmap.bmp());
|
||||
m_logo = new wxStaticBitmap(this, wxID_ANY, *get_bmp_bundle(wxGetApp().logo_name(), 192));
|
||||
hsizer->Add(m_logo, 1, wxALIGN_CENTER_VERTICAL);
|
||||
|
||||
wxBoxSizer* vsizer = new wxBoxSizer(wxVERTICAL);
|
||||
@ -322,8 +321,8 @@ AboutDialog::AboutDialog()
|
||||
|
||||
void AboutDialog::on_dpi_changed(const wxRect &suggested_rect)
|
||||
{
|
||||
m_logo_bitmap.msw_rescale();
|
||||
m_logo->SetBitmap(m_logo_bitmap.bmp());
|
||||
// m_logo_bitmap.msw_rescale();
|
||||
// m_logo->SetBitmap(m_logo_bitmap.bmp());
|
||||
|
||||
const wxFont& font = GetFont();
|
||||
const int fs = font.GetPointSize() - 1;
|
||||
|
@ -15,10 +15,8 @@
|
||||
#include <wx/rawbmp.h>
|
||||
#endif /* __WXGTK2__ */
|
||||
|
||||
//#define NANOSVG_IMPLEMENTATION
|
||||
#include "nanosvg/nanosvg.h"
|
||||
#define NANOSVGRAST_IMPLEMENTATION
|
||||
#include "nanosvg/nanosvgrast.h"
|
||||
#include <nanosvg/nanosvg.h>
|
||||
#include <nanosvg/nanosvgrast.h>
|
||||
|
||||
namespace Slic3r { namespace GUI {
|
||||
|
||||
@ -62,7 +60,168 @@ static wxBitmap wxImage_to_wxBitmap_with_alpha(wxImage &&image, float scale = 1.
|
||||
#endif
|
||||
}
|
||||
|
||||
wxBitmap* BitmapCache::insert(const std::string &bitmap_key, size_t width, size_t height)
|
||||
wxBitmapBundle* BitmapCache::insert_bndl(const std::string& name, const std::vector<wxBitmapBundle*>& bmps)
|
||||
{
|
||||
wxVector<wxBitmap> bitmaps;
|
||||
|
||||
std::set<double> scales = {1.0};
|
||||
#ifndef __linux__
|
||||
|
||||
#ifdef __APPLE__
|
||||
scales.emplace(m_scale);
|
||||
#else
|
||||
size_t disp_cnt = wxDisplay::GetCount();
|
||||
for (size_t disp = 0; disp < disp_cnt; ++disp)
|
||||
scales.emplace(wxDisplay(disp).GetScaleFactor());
|
||||
#endif
|
||||
|
||||
#endif // !__linux__
|
||||
|
||||
for (double scale : scales) {
|
||||
size_t width = 0;
|
||||
size_t height = 0;
|
||||
for (const wxBitmapBundle* bmp_bndl : bmps) {
|
||||
#ifdef __APPLE__
|
||||
wxSize size = bmp_bndl->GetDefaultSize();
|
||||
#else
|
||||
wxSize size = bmp_bndl->GetPreferredBitmapSizeAtScale(scale);
|
||||
#endif
|
||||
width += size.GetWidth();
|
||||
height = std::max<size_t>(height, size.GetHeight());
|
||||
}
|
||||
|
||||
std::string bitmap_key = name + "," +float_to_string_decimal_point(scale);
|
||||
|
||||
#ifdef __WXGTK2__
|
||||
// Broken alpha workaround
|
||||
wxImage image(width, height);
|
||||
image.InitAlpha();
|
||||
// Fill in with a white color.
|
||||
memset(image.GetData(), 0x0ff, width * height * 3);
|
||||
// Fill in with full transparency.
|
||||
memset(image.GetAlpha(), 0, width * height);
|
||||
size_t x = 0;
|
||||
for (const wxBitmapBundle* bmp_bndl : bmps) {
|
||||
wxBitmap bmp = bmp_bndl->GetBitmap(bmp_bndl->GetDefaultSize());
|
||||
if (bmp.GetWidth() > 0) {
|
||||
if (bmp.GetDepth() == 32) {
|
||||
wxAlphaPixelData data(bmp);
|
||||
//FIXME The following method is missing from wxWidgets 3.1.1.
|
||||
// It looks like the wxWidgets 3.0.3 called the wrapped bitmap's UseAlpha().
|
||||
//data.UseAlpha();
|
||||
if (data) {
|
||||
for (int r = 0; r < bmp.GetHeight(); ++r) {
|
||||
wxAlphaPixelData::Iterator src(data);
|
||||
src.Offset(data, 0, r);
|
||||
unsigned char* dst_pixels = image.GetData() + (x + r * width) * 3;
|
||||
unsigned char* dst_alpha = image.GetAlpha() + x + r * width;
|
||||
for (int c = 0; c < bmp.GetWidth(); ++c, ++src) {
|
||||
*dst_pixels++ = src.Red();
|
||||
*dst_pixels++ = src.Green();
|
||||
*dst_pixels++ = src.Blue();
|
||||
*dst_alpha++ = src.Alpha();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (bmp.GetDepth() == 24) {
|
||||
wxNativePixelData data(bmp);
|
||||
if (data) {
|
||||
for (int r = 0; r < bmp.GetHeight(); ++r) {
|
||||
wxNativePixelData::Iterator src(data);
|
||||
src.Offset(data, 0, r);
|
||||
unsigned char* dst_pixels = image.GetData() + (x + r * width) * 3;
|
||||
unsigned char* dst_alpha = image.GetAlpha() + x + r * width;
|
||||
for (int c = 0; c < bmp.GetWidth(); ++c, ++src) {
|
||||
*dst_pixels++ = src.Red();
|
||||
*dst_pixels++ = src.Green();
|
||||
*dst_pixels++ = src.Blue();
|
||||
*dst_alpha++ = wxALPHA_OPAQUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
x += bmp.GetScaledWidth();
|
||||
}
|
||||
|
||||
bitmaps.push_back(* this->insert(bitmap_key, wxImage_to_wxBitmap_with_alpha(std::move(image))));
|
||||
|
||||
#else
|
||||
|
||||
wxBitmap* bitmap = this->insert(bitmap_key, width, height, scale);
|
||||
wxMemoryDC memDC;
|
||||
memDC.SelectObject(*bitmap);
|
||||
memDC.SetBackground(*wxTRANSPARENT_BRUSH);
|
||||
memDC.Clear();
|
||||
size_t x = 0;
|
||||
for (const wxBitmapBundle* bmp_bndl : bmps) {
|
||||
wxBitmap bmp = bmp_bndl->GetBitmap(bmp_bndl->GetPreferredBitmapSizeAtScale(scale));
|
||||
|
||||
if (bmp.GetWidth() > 0)
|
||||
memDC.DrawBitmap(bmp, x, 0, true);
|
||||
// we should "move" with step equal to non-scaled width
|
||||
#ifdef __APPLE__
|
||||
x += bmp.GetScaledWidth();
|
||||
#else
|
||||
x += bmp.GetWidth();
|
||||
#endif
|
||||
}
|
||||
memDC.SelectObject(wxNullBitmap);
|
||||
bitmaps.push_back(*bitmap);
|
||||
|
||||
#endif
|
||||
}
|
||||
|
||||
return insert_bndl(name, bitmaps);
|
||||
}
|
||||
|
||||
wxBitmapBundle* BitmapCache::insert_bndl(const std::string &bitmap_key, const char* data, size_t width, size_t height)
|
||||
{
|
||||
wxBitmapBundle* bndl = nullptr;
|
||||
auto it = m_bndl_map.find(bitmap_key);
|
||||
if (it == m_bndl_map.end()) {
|
||||
bndl = new wxBitmapBundle(wxBitmapBundle::FromSVG(data, wxSize(width, height)));
|
||||
m_bndl_map[bitmap_key] = bndl;
|
||||
}
|
||||
else {
|
||||
bndl = it->second;
|
||||
*bndl = wxBitmapBundle::FromSVG(data, wxSize(width, height));
|
||||
}
|
||||
return bndl;
|
||||
}
|
||||
|
||||
wxBitmapBundle* BitmapCache::insert_bndl(const std::string& bitmap_key, const wxBitmapBundle& bmp)
|
||||
{
|
||||
wxBitmapBundle* bndl = nullptr;
|
||||
auto it = m_bndl_map.find(bitmap_key);
|
||||
if (it == m_bndl_map.end()) {
|
||||
bndl = new wxBitmapBundle(bmp);
|
||||
m_bndl_map[bitmap_key] = bndl;
|
||||
}
|
||||
else {
|
||||
bndl = it->second;
|
||||
*bndl = wxBitmapBundle(bmp);
|
||||
}
|
||||
return bndl;
|
||||
}
|
||||
|
||||
wxBitmapBundle* BitmapCache::insert_bndl(const std::string& bitmap_key, const wxVector<wxBitmap>& bmps)
|
||||
{
|
||||
wxBitmapBundle* bndl = nullptr;
|
||||
auto it = m_bndl_map.find(bitmap_key);
|
||||
if (it == m_bndl_map.end()) {
|
||||
bndl = new wxBitmapBundle(wxBitmapBundle::FromBitmaps(bmps));
|
||||
m_bndl_map[bitmap_key] = bndl;
|
||||
}
|
||||
else {
|
||||
bndl = it->second;
|
||||
*bndl = wxBitmapBundle::FromBitmaps(bmps);
|
||||
}
|
||||
return bndl;
|
||||
}
|
||||
|
||||
wxBitmap* BitmapCache::insert(const std::string &bitmap_key, size_t width, size_t height, double scale/* = -1.0*/)
|
||||
{
|
||||
wxBitmap *bitmap = nullptr;
|
||||
auto it = m_map.find(bitmap_key);
|
||||
@ -78,7 +237,7 @@ wxBitmap* BitmapCache::insert(const std::string &bitmap_key, size_t width, size_
|
||||
// So, We need to let the Mac OS wxBitmap implementation
|
||||
// know that the image may already be scaled appropriately for Retina,
|
||||
// and thereby that it's not supposed to upscale it.
|
||||
bitmap->CreateScaled(width, height, -1, m_scale);
|
||||
bitmap->CreateScaled(width, height, -1, scale < 0.0 ? m_scale : scale);
|
||||
#endif
|
||||
m_map[bitmap_key] = bitmap;
|
||||
} else {
|
||||
@ -107,110 +266,6 @@ wxBitmap* BitmapCache::insert(const std::string &bitmap_key, const wxBitmap &bmp
|
||||
return bitmap;
|
||||
}
|
||||
|
||||
wxBitmap* BitmapCache::insert(const std::string &bitmap_key, const wxBitmap &bmp, const wxBitmap &bmp2)
|
||||
{
|
||||
// Copying the wxBitmaps is cheap as the bitmap's content is reference counted.
|
||||
const wxBitmap bmps[2] = { bmp, bmp2 };
|
||||
return this->insert(bitmap_key, bmps, bmps + 2);
|
||||
}
|
||||
|
||||
wxBitmap* BitmapCache::insert(const std::string &bitmap_key, const wxBitmap &bmp, const wxBitmap &bmp2, const wxBitmap &bmp3)
|
||||
{
|
||||
// Copying the wxBitmaps is cheap as the bitmap's content is reference counted.
|
||||
const wxBitmap bmps[3] = { bmp, bmp2, bmp3 };
|
||||
return this->insert(bitmap_key, bmps, bmps + 3);
|
||||
}
|
||||
|
||||
wxBitmap* BitmapCache::insert(const std::string &bitmap_key, const wxBitmap *begin, const wxBitmap *end)
|
||||
{
|
||||
size_t width = 0;
|
||||
size_t height = 0;
|
||||
for (const wxBitmap *bmp = begin; bmp != end; ++ bmp) {
|
||||
#ifdef __APPLE__
|
||||
width += bmp->GetScaledWidth();
|
||||
height = std::max<size_t>(height, bmp->GetScaledHeight());
|
||||
#else
|
||||
width += bmp->GetWidth();
|
||||
height = std::max<size_t>(height, bmp->GetHeight());
|
||||
#endif
|
||||
}
|
||||
|
||||
#ifdef __WXGTK2__
|
||||
// Broken alpha workaround
|
||||
wxImage image(width, height);
|
||||
image.InitAlpha();
|
||||
// Fill in with a white color.
|
||||
memset(image.GetData(), 0x0ff, width * height * 3);
|
||||
// Fill in with full transparency.
|
||||
memset(image.GetAlpha(), 0, width * height);
|
||||
size_t x = 0;
|
||||
for (const wxBitmap *bmp = begin; bmp != end; ++ bmp) {
|
||||
if (bmp->GetWidth() > 0) {
|
||||
if (bmp->GetDepth() == 32) {
|
||||
wxAlphaPixelData data(*const_cast<wxBitmap*>(bmp));
|
||||
//FIXME The following method is missing from wxWidgets 3.1.1.
|
||||
// It looks like the wxWidgets 3.0.3 called the wrapped bitmap's UseAlpha().
|
||||
//data.UseAlpha();
|
||||
if (data) {
|
||||
for (int r = 0; r < bmp->GetHeight(); ++ r) {
|
||||
wxAlphaPixelData::Iterator src(data);
|
||||
src.Offset(data, 0, r);
|
||||
unsigned char *dst_pixels = image.GetData() + (x + r * width) * 3;
|
||||
unsigned char *dst_alpha = image.GetAlpha() + x + r * width;
|
||||
for (int c = 0; c < bmp->GetWidth(); ++ c, ++ src) {
|
||||
*dst_pixels ++ = src.Red();
|
||||
*dst_pixels ++ = src.Green();
|
||||
*dst_pixels ++ = src.Blue();
|
||||
*dst_alpha ++ = src.Alpha();
|
||||
}
|
||||
}
|
||||
}
|
||||
} else if (bmp->GetDepth() == 24) {
|
||||
wxNativePixelData data(*const_cast<wxBitmap*>(bmp));
|
||||
if (data) {
|
||||
for (int r = 0; r < bmp->GetHeight(); ++ r) {
|
||||
wxNativePixelData::Iterator src(data);
|
||||
src.Offset(data, 0, r);
|
||||
unsigned char *dst_pixels = image.GetData() + (x + r * width) * 3;
|
||||
unsigned char *dst_alpha = image.GetAlpha() + x + r * width;
|
||||
for (int c = 0; c < bmp->GetWidth(); ++ c, ++ src) {
|
||||
*dst_pixels ++ = src.Red();
|
||||
*dst_pixels ++ = src.Green();
|
||||
*dst_pixels ++ = src.Blue();
|
||||
*dst_alpha ++ = wxALPHA_OPAQUE;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
x += bmp->GetWidth();
|
||||
}
|
||||
return this->insert(bitmap_key, wxImage_to_wxBitmap_with_alpha(std::move(image)));
|
||||
|
||||
#else
|
||||
|
||||
wxBitmap *bitmap = this->insert(bitmap_key, width, height);
|
||||
wxMemoryDC memDC;
|
||||
memDC.SelectObject(*bitmap);
|
||||
memDC.SetBackground(*wxTRANSPARENT_BRUSH);
|
||||
memDC.Clear();
|
||||
size_t x = 0;
|
||||
for (const wxBitmap *bmp = begin; bmp != end; ++ bmp) {
|
||||
if (bmp->GetWidth() > 0)
|
||||
memDC.DrawBitmap(*bmp, x, 0, true);
|
||||
#ifdef __APPLE__
|
||||
// we should "move" with step equal to non-scaled width
|
||||
x += bmp->GetScaledWidth();
|
||||
#else
|
||||
x += bmp->GetWidth();
|
||||
#endif
|
||||
}
|
||||
memDC.SelectObject(wxNullBitmap);
|
||||
return bitmap;
|
||||
|
||||
#endif
|
||||
}
|
||||
|
||||
wxBitmap* BitmapCache::insert_raw_rgba(const std::string &bitmap_key, unsigned width, unsigned height, const unsigned char *raw_data, const bool grayscale/* = false*/)
|
||||
{
|
||||
wxImage image(width, height);
|
||||
@ -299,6 +354,92 @@ error:
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void BitmapCache::nsvgGetDataFromFileWithReplace(const char* filename, std::string& data_str, const std::map<std::string, std::string>& replaces)
|
||||
{
|
||||
FILE* fp = NULL;
|
||||
size_t size;
|
||||
char* data = NULL;
|
||||
|
||||
fp = boost::nowide::fopen(filename, "rb");
|
||||
if (!fp) goto error;
|
||||
fseek(fp, 0, SEEK_END);
|
||||
size = ftell(fp);
|
||||
fseek(fp, 0, SEEK_SET);
|
||||
data = (char*)malloc(size + 1);
|
||||
if (data == NULL) goto error;
|
||||
if (fread(data, 1, size, fp) != size) goto error;
|
||||
data[size] = '\0'; // Must be null terminated.
|
||||
fclose(fp);
|
||||
|
||||
data_str.assign(data);
|
||||
for (auto val : replaces)
|
||||
boost::replace_all(data_str, val.first, val.second);
|
||||
|
||||
free(data);
|
||||
return;
|
||||
|
||||
error:
|
||||
if (fp) fclose(fp);
|
||||
if (data) free(data);
|
||||
return;
|
||||
}
|
||||
|
||||
wxBitmapBundle* BitmapCache::from_svg(const std::string& bitmap_name, unsigned target_width, unsigned target_height,
|
||||
const bool dark_mode, const std::string& new_color /*= ""*/)
|
||||
{
|
||||
if (target_width == 0)
|
||||
target_width = target_height;
|
||||
std::string bitmap_key = bitmap_name + (target_height != 0 ?
|
||||
"-h" + std::to_string(target_height) :
|
||||
"-w" + std::to_string(target_width))
|
||||
+ (dark_mode ? "-dm" : "")
|
||||
+ new_color;
|
||||
|
||||
auto it = m_bndl_map.find(bitmap_key);
|
||||
if (it != m_bndl_map.end())
|
||||
return it->second;
|
||||
|
||||
// map of color replaces
|
||||
std::map<std::string, std::string> replaces;
|
||||
if (dark_mode)
|
||||
replaces["\"#808080\""] = "\"#FFFFFF\"";
|
||||
if (!new_color.empty())
|
||||
replaces["\"#ED6B21\""] = "\"" + new_color + "\"";
|
||||
|
||||
std::string str;
|
||||
nsvgGetDataFromFileWithReplace(Slic3r::var(bitmap_name + ".svg").c_str(), str, replaces);
|
||||
if (str.empty())
|
||||
return nullptr;
|
||||
|
||||
return insert_bndl(bitmap_key, str.data(), target_width, target_height);
|
||||
}
|
||||
|
||||
wxBitmapBundle* BitmapCache::from_png(const std::string& bitmap_name, unsigned width, unsigned height)
|
||||
{
|
||||
std::string bitmap_key = bitmap_name + (height != 0 ?
|
||||
"-h" + std::to_string(height) :
|
||||
"-w" + std::to_string(width));
|
||||
|
||||
auto it = m_bndl_map.find(bitmap_key);
|
||||
if (it != m_bndl_map.end())
|
||||
return it->second;
|
||||
|
||||
wxImage image;
|
||||
if (!image.LoadFile(Slic3r::GUI::from_u8(Slic3r::var(bitmap_name + ".png")), wxBITMAP_TYPE_PNG) ||
|
||||
image.GetWidth() == 0 || image.GetHeight() == 0)
|
||||
return nullptr;
|
||||
|
||||
if (height != 0 && unsigned(image.GetHeight()) != height)
|
||||
width = unsigned(0.5f + float(image.GetWidth()) * height / image.GetHeight());
|
||||
else if (width != 0 && unsigned(image.GetWidth()) != width)
|
||||
height = unsigned(0.5f + float(image.GetHeight()) * width / image.GetWidth());
|
||||
|
||||
if (height != 0 && width != 0)
|
||||
image.Rescale(width, height, wxIMAGE_QUALITY_BILINEAR);
|
||||
|
||||
return this->insert_bndl(bitmap_key, wxImage_to_wxBitmap_with_alpha(std::move(image)));
|
||||
}
|
||||
|
||||
wxBitmap* BitmapCache::load_svg(const std::string &bitmap_name, unsigned target_width, unsigned target_height,
|
||||
const bool grayscale/* = false*/, const bool dark_mode/* = false*/, const std::string& new_color /*= ""*/)
|
||||
{
|
||||
@ -352,9 +493,9 @@ wxBitmap* BitmapCache::load_svg(const std::string &bitmap_name, unsigned target_
|
||||
|
||||
return this->insert_raw_rgba(bitmap_key, width, height, data.data(), grayscale);
|
||||
}
|
||||
|
||||
/*
|
||||
//we make scaled solid bitmaps only for the cases, when its will be used with scaled SVG icon in one output bitmap
|
||||
wxBitmap BitmapCache::mksolid(size_t width, size_t height, unsigned char r, unsigned char g, unsigned char b, unsigned char transparency, bool suppress_scaling/* = false*/, size_t border_width /*= 0*/, bool dark_mode/* = false*/)
|
||||
wxBitmap BitmapCache::mksolid(size_t width, size_t height, unsigned char r, unsigned char g, unsigned char b, unsigned char transparency, bool suppress_scaling/* = false* /, size_t border_width /*= 0* /, bool dark_mode/* = false* /)
|
||||
{
|
||||
double scale = suppress_scaling ? 1.0f : m_scale;
|
||||
width *= scale;
|
||||
@ -396,6 +537,89 @@ wxBitmap BitmapCache::mksolid(size_t width, size_t height, unsigned char r, unsi
|
||||
|
||||
return wxImage_to_wxBitmap_with_alpha(std::move(image), scale);
|
||||
}
|
||||
*/
|
||||
//we make scaled solid bitmaps only for the cases, when its will be used with scaled SVG icon in one output bitmap
|
||||
wxBitmapBundle BitmapCache::mksolid(size_t width_in, size_t height_in, unsigned char r, unsigned char g, unsigned char b, unsigned char transparency, size_t border_width /*= 0*/, bool dark_mode/* = false*/)
|
||||
{
|
||||
wxVector<wxBitmap> bitmaps;
|
||||
|
||||
std::set<double> scales = { 1.0 };
|
||||
#ifndef __linux__
|
||||
|
||||
#ifdef __APPLE__
|
||||
scales.emplace(m_scale);
|
||||
#else
|
||||
size_t disp_cnt = wxDisplay::GetCount();
|
||||
for (size_t disp = 0; disp < disp_cnt; ++disp)
|
||||
scales.emplace(wxDisplay(disp).GetScaleFactor());
|
||||
#endif
|
||||
|
||||
#endif // !__linux__
|
||||
|
||||
for (double scale : scales) {
|
||||
size_t width = width_in * scale;
|
||||
size_t height = height_in * scale;
|
||||
|
||||
wxImage image(width, height);
|
||||
image.InitAlpha();
|
||||
unsigned char* imgdata = image.GetData();
|
||||
unsigned char* imgalpha = image.GetAlpha();
|
||||
for (size_t i = 0; i < width * height; ++i) {
|
||||
*imgdata++ = r;
|
||||
*imgdata++ = g;
|
||||
*imgdata++ = b;
|
||||
*imgalpha++ = transparency;
|
||||
}
|
||||
|
||||
// Add border, make white/light spools easier to see
|
||||
if (border_width > 0) {
|
||||
|
||||
// Restrict to width of image
|
||||
if (border_width > height) border_width = height - 1;
|
||||
if (border_width > width) border_width = width - 1;
|
||||
|
||||
auto px_data = (uint8_t*)image.GetData();
|
||||
auto a_data = (uint8_t*)image.GetAlpha();
|
||||
|
||||
for (size_t x = 0; x < width; ++x) {
|
||||
for (size_t y = 0; y < height; ++y) {
|
||||
if (x < border_width || y < border_width ||
|
||||
x >= (width - border_width) || y >= (height - border_width)) {
|
||||
const size_t idx = (x + y * width);
|
||||
const size_t idx_rgb = (x + y * width) * 3;
|
||||
px_data[idx_rgb] = px_data[idx_rgb + 1] = px_data[idx_rgb + 2] = dark_mode ? 245u : 110u;
|
||||
a_data[idx] = 255u;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bitmaps.push_back(wxImage_to_wxBitmap_with_alpha(std::move(image), scale));
|
||||
}
|
||||
return wxBitmapBundle::FromBitmaps(bitmaps);
|
||||
}
|
||||
|
||||
wxBitmapBundle* BitmapCache::mksolid_bndl(size_t width, size_t height, const std::string& color, size_t border_width, bool dark_mode)
|
||||
{
|
||||
std::string bitmap_key = (color.empty() ? "empty" : color) + "-h" + std::to_string(height) + "-w" + std::to_string(width) + (dark_mode ? "-dm" : "");
|
||||
|
||||
wxBitmapBundle* bndl = nullptr;
|
||||
auto it = m_bndl_map.find(bitmap_key);
|
||||
if (it == m_bndl_map.end()) {
|
||||
if (color.empty())
|
||||
bndl = new wxBitmapBundle(mksolid(width, height, 0, 0, 0, wxALPHA_TRANSPARENT, size_t(0)));
|
||||
else {
|
||||
ColorRGB rgb;// [3] ;
|
||||
decode_color(color, rgb);
|
||||
bndl = new wxBitmapBundle(mksolid(width, height, rgb.r_uchar(), rgb.g_uchar(), rgb.b_uchar(), wxALPHA_OPAQUE, border_width, dark_mode));
|
||||
}
|
||||
m_bndl_map[bitmap_key] = bndl;
|
||||
}
|
||||
else
|
||||
return it->second;
|
||||
|
||||
return bndl;
|
||||
}
|
||||
|
||||
} // namespace GUI
|
||||
} // namespace Slic3r
|
||||
|
@ -24,15 +24,19 @@ public:
|
||||
void clear();
|
||||
double scale() { return m_scale; }
|
||||
|
||||
wxBitmapBundle* find_bndl(const std::string &name) { auto it = m_bndl_map.find(name); return (it == m_bndl_map.end()) ? nullptr : it->second; }
|
||||
const wxBitmapBundle* find_bndl(const std::string &name) const { return const_cast<BitmapCache*>(this)->find_bndl(name); }
|
||||
wxBitmap* find(const std::string &name) { auto it = m_map.find(name); return (it == m_map.end()) ? nullptr : it->second; }
|
||||
const wxBitmap* find(const std::string &name) const { return const_cast<BitmapCache*>(this)->find(name); }
|
||||
|
||||
wxBitmap* insert(const std::string &name, size_t width, size_t height);
|
||||
wxBitmapBundle* insert_bndl(const std::string& bitmap_key, const char* data, size_t width, size_t height);
|
||||
wxBitmapBundle* insert_bndl(const std::string& bitmap_key, const wxBitmapBundle &bmp);
|
||||
wxBitmapBundle* insert_bndl(const std::string& bitmap_key, const wxVector<wxBitmap>& bmps);
|
||||
wxBitmapBundle* insert_bndl(const std::string& name, const std::vector<wxBitmapBundle*>& bmps);
|
||||
wxBitmapBundle* insert_raw_rgba_bndl(const std::string &bitmap_key, unsigned width, unsigned height, const unsigned char *raw_data, const bool grayscale = false);
|
||||
|
||||
wxBitmap* insert(const std::string &name, size_t width, size_t height, double scale = -1.0);
|
||||
wxBitmap* insert(const std::string &name, const wxBitmap &bmp);
|
||||
wxBitmap* insert(const std::string &name, const wxBitmap &bmp, const wxBitmap &bmp2);
|
||||
wxBitmap* insert(const std::string &name, const wxBitmap &bmp, const wxBitmap &bmp2, const wxBitmap &bmp3);
|
||||
wxBitmap* insert(const std::string &name, const std::vector<wxBitmap> &bmps) { return this->insert(name, &bmps.front(), &bmps.front() + bmps.size()); }
|
||||
wxBitmap* insert(const std::string &name, const wxBitmap *begin, const wxBitmap *end);
|
||||
wxBitmap* insert_raw_rgba(const std::string &bitmap_key, unsigned width, unsigned height, const unsigned char *raw_data, const bool grayscale = false);
|
||||
|
||||
// Load png from resources/icons. bitmap_key is given without the .png suffix. Bitmap will be rescaled to provided height/width if nonzero.
|
||||
@ -42,15 +46,21 @@ public:
|
||||
// And makes replases befor parsing
|
||||
// replace_map containes old_value->new_value
|
||||
static NSVGimage* nsvgParseFromFileWithReplace(const char* filename, const char* units, float dpi, const std::map<std::string, std::string>& replaces);
|
||||
// Gets a data from SVG file and makes replases
|
||||
// replace_map containes old_value->new_value
|
||||
static void nsvgGetDataFromFileWithReplace(const char* filename, std::string& data_str, const std::map<std::string, std::string>& replaces);
|
||||
wxBitmapBundle* from_svg(const std::string& bitmap_name, unsigned target_width, unsigned target_height, const bool dark_mode, const std::string& new_color = "");
|
||||
wxBitmapBundle* from_png(const std::string& bitmap_name, unsigned width, unsigned height);
|
||||
// Load svg from resources/icons. bitmap_key is given without the .svg suffix. SVG will be rasterized to provided height/width.
|
||||
wxBitmap* load_svg(const std::string &bitmap_key, unsigned width = 0, unsigned height = 0, const bool grayscale = false, const bool dark_mode = false, const std::string& new_color = "");
|
||||
|
||||
wxBitmap mksolid(size_t width, size_t height, unsigned char r, unsigned char g, unsigned char b, unsigned char transparency, bool suppress_scaling = false, size_t border_width = 0, bool dark_mode = false);
|
||||
wxBitmap mksolid(size_t width, size_t height, const ColorRGB& rgb, bool suppress_scaling = false, size_t border_width = 0, bool dark_mode = false) { return mksolid(width, height, rgb.r_uchar(), rgb.g_uchar(), rgb.b_uchar(), wxALPHA_OPAQUE, suppress_scaling, border_width, dark_mode); }
|
||||
wxBitmap mkclear(size_t width, size_t height) { return mksolid(width, height, 0, 0, 0, wxALPHA_TRANSPARENT); }
|
||||
wxBitmapBundle mksolid(size_t width, size_t height, unsigned char r, unsigned char g, unsigned char b, unsigned char transparency, size_t border_width = 0, bool dark_mode = false);
|
||||
wxBitmapBundle* mksolid_bndl(size_t width, size_t height, const std::string& color = std::string(), size_t border_width = 0, bool dark_mode = false);
|
||||
wxBitmapBundle* mkclear_bndl(size_t width, size_t height) { return mksolid_bndl(width, height); }
|
||||
|
||||
private:
|
||||
std::map<std::string, wxBitmap*> m_map;
|
||||
std::map<std::string, wxBitmapBundle*> m_bndl_map;
|
||||
double m_gs = 0.2; // value, used for image.ConvertToGreyscale(m_gs, m_gs, m_gs)
|
||||
double m_scale = 1.0; // value, used for correct scaling of SVG icons on Retina display
|
||||
};
|
||||
|
@ -54,17 +54,6 @@ using Slic3r::GUI::format_wxstr;
|
||||
namespace Slic3r {
|
||||
namespace GUI {
|
||||
|
||||
/* For PresetComboBox we use bitmaps that are created from images that are already scaled appropriately for Retina
|
||||
* (Contrary to the intuition, the `scale` argument for Bitmap's constructor doesn't mean
|
||||
* "please scale this to such and such" but rather
|
||||
* "the wxImage is already sized for backing scale such and such". )
|
||||
* Unfortunately, the constructor changes the size of wxBitmap too.
|
||||
* Thus We need to use unscaled size value for bitmaps that we use
|
||||
* to avoid scaled size of control items.
|
||||
* For this purpose control drawing methods and
|
||||
* control size calculation methods (virtual) are overridden.
|
||||
**/
|
||||
|
||||
BitmapComboBox::BitmapComboBox(wxWindow* parent,
|
||||
wxWindowID id/* = wxID_ANY*/,
|
||||
const wxString& value/* = wxEmptyString*/,
|
||||
@ -90,72 +79,6 @@ BitmapComboBox::~BitmapComboBox()
|
||||
{
|
||||
}
|
||||
|
||||
#ifdef __APPLE__
|
||||
bool BitmapComboBox::OnAddBitmap(const wxBitmap& bitmap)
|
||||
{
|
||||
if (bitmap.IsOk())
|
||||
{
|
||||
// we should use scaled! size values of bitmap
|
||||
int width = (int)bitmap.GetScaledWidth();
|
||||
int height = (int)bitmap.GetScaledHeight();
|
||||
|
||||
if (m_usedImgSize.x < 0)
|
||||
{
|
||||
// If size not yet determined, get it from this image.
|
||||
m_usedImgSize.x = width;
|
||||
m_usedImgSize.y = height;
|
||||
|
||||
// Adjust control size to vertically fit the bitmap
|
||||
wxWindow* ctrl = GetControl();
|
||||
ctrl->InvalidateBestSize();
|
||||
wxSize newSz = ctrl->GetBestSize();
|
||||
wxSize sz = ctrl->GetSize();
|
||||
if (newSz.y > sz.y)
|
||||
ctrl->SetSize(sz.x, newSz.y);
|
||||
else
|
||||
DetermineIndent();
|
||||
}
|
||||
|
||||
wxCHECK_MSG(width == m_usedImgSize.x && height == m_usedImgSize.y,
|
||||
false,
|
||||
"you can only add images of same size");
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
void BitmapComboBox::OnDrawItem(wxDC& dc,
|
||||
const wxRect& rect,
|
||||
int item,
|
||||
int flags) const
|
||||
{
|
||||
const wxBitmap& bmp = *(static_cast<wxBitmap*>(m_bitmaps[item]));
|
||||
if (bmp.IsOk())
|
||||
{
|
||||
// we should use scaled! size values of bitmap
|
||||
wxCoord w = bmp.GetScaledWidth();
|
||||
wxCoord h = bmp.GetScaledHeight();
|
||||
|
||||
const int imgSpacingLeft = 4;
|
||||
|
||||
// Draw the image centered
|
||||
dc.DrawBitmap(bmp,
|
||||
rect.x + (m_usedImgSize.x - w) / 2 + imgSpacingLeft,
|
||||
rect.y + (rect.height - h) / 2,
|
||||
true);
|
||||
}
|
||||
|
||||
wxString text = GetString(item);
|
||||
if (!text.empty())
|
||||
dc.DrawText(text,
|
||||
rect.x + m_imgAreaWidth + 1,
|
||||
rect.y + (rect.height - dc.GetCharHeight()) / 2);
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef _WIN32
|
||||
|
||||
int BitmapComboBox::Append(const wxString& item)
|
||||
@ -166,18 +89,11 @@ int BitmapComboBox::Append(const wxString& item)
|
||||
//2. But then set width to 0 value for no using of bitmap left and right spacing
|
||||
//3. Set this empty bitmap to the at list one item and BitmapCombobox will be recreated correct
|
||||
|
||||
wxBitmap bitmap(1, int(1.6 * wxGetApp().em_unit() + 1));
|
||||
{
|
||||
// bitmap.SetWidth(0); is depricated now
|
||||
// so, use next code
|
||||
bitmap.UnShare();// AllocExclusive();
|
||||
bitmap.GetGDIImageData()->m_width = 0;
|
||||
}
|
||||
|
||||
wxBitmapBundle bitmap = *get_empty_bmp_bundle(1, 16);
|
||||
OnAddBitmap(bitmap);
|
||||
|
||||
const int n = wxComboBox::Append(item);
|
||||
if (n != wxNOT_FOUND)
|
||||
DoSetItemBitmap(n, bitmap);
|
||||
|
||||
return n;
|
||||
}
|
||||
|
||||
|
@ -29,28 +29,13 @@ BitmapComboBox(wxWindow* parent,
|
||||
#ifdef _WIN32
|
||||
int Append(const wxString& item);
|
||||
#endif
|
||||
int Append(const wxString& item, const wxBitmap& bitmap)
|
||||
int Append(const wxString& item, const wxBitmapBundle& bitmap)
|
||||
{
|
||||
return wxBitmapComboBox::Append(item, bitmap);
|
||||
}
|
||||
|
||||
protected:
|
||||
|
||||
#ifdef __APPLE__
|
||||
/* For PresetComboBox we use bitmaps that are created from images that are already scaled appropriately for Retina
|
||||
* (Contrary to the intuition, the `scale` argument for Bitmap's constructor doesn't mean
|
||||
* "please scale this to such and such" but rather
|
||||
* "the wxImage is already sized for backing scale such and such". )
|
||||
* Unfortunately, the constructor changes the size of wxBitmap too.
|
||||
* Thus We need to use unscaled size value for bitmaps that we use
|
||||
* to avoid scaled size of control items.
|
||||
* For this purpose control drawing methods and
|
||||
* control size calculation methods (virtual) are overridden.
|
||||
**/
|
||||
bool OnAddBitmap(const wxBitmap& bitmap) override;
|
||||
void OnDrawItem(wxDC& dc, const wxRect& rect, int item, int flags) const override;
|
||||
#endif
|
||||
|
||||
#ifdef _WIN32
|
||||
bool MSWOnDraw(WXDRAWITEMSTRUCT* item) override;
|
||||
void DrawBackground_(wxDC& dc, const wxRect& rect, int WXUNUSED(item), int flags) const;
|
||||
|
@ -17,9 +17,6 @@ void ButtonsDescription::FillSizerWithTextColorDescriptions(wxSizer* sizer, wxWi
|
||||
wxFlexGridSizer* grid_sizer = new wxFlexGridSizer(3, 5, 5);
|
||||
sizer->Add(grid_sizer, 0, wxEXPAND);
|
||||
|
||||
ScalableBitmap bmp_delete = ScalableBitmap(parent, "cross");
|
||||
ScalableBitmap bmp_delete_focus = ScalableBitmap(parent, "cross_focus");
|
||||
|
||||
auto add_color = [grid_sizer, parent](wxColourPickerCtrl** color_picker, const wxColour& color, const wxColour& def_color, wxString label_text) {
|
||||
// wrap the label_text to the max 80 characters
|
||||
if (label_text.Len() > 80) {
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -519,7 +519,7 @@ private:
|
||||
ssize_t item_hover;
|
||||
size_t last_page;
|
||||
|
||||
int item_height() const { return std::max(bullet_black.bmp().GetSize().GetHeight(), em_w) + em_w; }
|
||||
int item_height() const { return std::max(bullet_black.GetHeight(), em_w) + em_w; }
|
||||
|
||||
void on_paint(wxPaintEvent &evt);
|
||||
void on_mouse_move(wxMouseEvent &evt);
|
||||
|
104
src/slic3r/GUI/CoordAxes.cpp
Normal file
104
src/slic3r/GUI/CoordAxes.cpp
Normal file
@ -0,0 +1,104 @@
|
||||
#include "libslic3r/libslic3r.h"
|
||||
|
||||
#include "CoordAxes.hpp"
|
||||
#include "GUI_App.hpp"
|
||||
#include "3DScene.hpp"
|
||||
#if ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
#include "Plater.hpp"
|
||||
#include "Camera.hpp"
|
||||
#endif // ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
|
||||
#include <GL/glew.h>
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
|
||||
namespace Slic3r {
|
||||
namespace GUI {
|
||||
|
||||
const float CoordAxes::DefaultStemRadius = 0.5f;
|
||||
const float CoordAxes::DefaultStemLength = 25.0f;
|
||||
const float CoordAxes::DefaultTipRadius = 2.5f * CoordAxes::DefaultStemRadius;
|
||||
const float CoordAxes::DefaultTipLength = 5.0f;
|
||||
|
||||
#if ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
void CoordAxes::render(const Transform3d& trafo, float emission_factor)
|
||||
#else
|
||||
void CoordAxes::render(float emission_factor)
|
||||
#endif // ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
{
|
||||
#if ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
auto render_axis = [this](GLShaderProgram& shader, const Transform3d& transform) {
|
||||
const Camera& camera = wxGetApp().plater()->get_camera();
|
||||
const Transform3d matrix = camera.get_view_matrix() * transform;
|
||||
shader.set_uniform("view_model_matrix", matrix);
|
||||
shader.set_uniform("projection_matrix", camera.get_projection_matrix());
|
||||
shader.set_uniform("normal_matrix", (Matrix3d)matrix.matrix().block(0, 0, 3, 3).inverse().transpose());
|
||||
m_arrow.render();
|
||||
#else
|
||||
auto render_axis = [this](const Transform3f& transform) {
|
||||
glsafe(::glPushMatrix());
|
||||
glsafe(::glMultMatrixf(transform.data()));
|
||||
m_arrow.render();
|
||||
glsafe(::glPopMatrix());
|
||||
#endif // ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
};
|
||||
|
||||
if (!m_arrow.is_initialized())
|
||||
m_arrow.init_from(stilized_arrow(16, m_tip_radius, m_tip_length, m_stem_radius, m_stem_length));
|
||||
|
||||
GLShaderProgram* curr_shader = wxGetApp().get_current_shader();
|
||||
GLShaderProgram* shader = wxGetApp().get_shader("gouraud_light");
|
||||
if (shader == nullptr)
|
||||
return;
|
||||
|
||||
if (curr_shader != nullptr)
|
||||
curr_shader->stop_using();
|
||||
|
||||
shader->start_using();
|
||||
shader->set_uniform("emission_factor", emission_factor);
|
||||
|
||||
// x axis
|
||||
#if ENABLE_LEGACY_OPENGL_REMOVAL
|
||||
m_arrow.set_color(ColorRGBA::X());
|
||||
#else
|
||||
m_arrow.set_color(-1, ColorRGBA::X());
|
||||
#endif // ENABLE_LEGACY_OPENGL_REMOVAL
|
||||
#if ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
render_axis(*shader, trafo * Geometry::assemble_transform(m_origin, { 0.0, 0.5 * M_PI, 0.0 }));
|
||||
#else
|
||||
render_axis(Geometry::assemble_transform(m_origin, { 0.0, 0.5 * M_PI, 0.0 }).cast<float>());
|
||||
#endif // ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
|
||||
// y axis
|
||||
#if ENABLE_LEGACY_OPENGL_REMOVAL
|
||||
m_arrow.set_color(ColorRGBA::Y());
|
||||
#else
|
||||
m_arrow.set_color(-1, ColorRGBA::Y());
|
||||
#endif // ENABLE_LEGACY_OPENGL_REMOVAL
|
||||
#if ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
render_axis(*shader, trafo * Geometry::assemble_transform(m_origin, { -0.5 * M_PI, 0.0, 0.0 }));
|
||||
#else
|
||||
render_axis(Geometry::assemble_transform(m_origin, { -0.5 * M_PI, 0.0, 0.0 }).cast<float>());
|
||||
#endif // ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
|
||||
// z axis
|
||||
#if ENABLE_LEGACY_OPENGL_REMOVAL
|
||||
m_arrow.set_color(ColorRGBA::Z());
|
||||
#else
|
||||
m_arrow.set_color(-1, ColorRGBA::Z());
|
||||
#endif // ENABLE_LEGACY_OPENGL_REMOVAL
|
||||
#if ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
render_axis(*shader, trafo * Geometry::assemble_transform(m_origin));
|
||||
#else
|
||||
render_axis(Geometry::assemble_transform(m_origin).cast<float>());
|
||||
#endif // ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
|
||||
shader->stop_using();
|
||||
if (curr_shader != nullptr)
|
||||
curr_shader->start_using();
|
||||
}
|
||||
|
||||
} // GUI
|
||||
} // Slic3r
|
||||
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
64
src/slic3r/GUI/CoordAxes.hpp
Normal file
64
src/slic3r/GUI/CoordAxes.hpp
Normal file
@ -0,0 +1,64 @@
|
||||
#ifndef slic3r_CoordAxes_hpp_
|
||||
#define slic3r_CoordAxes_hpp_
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
#include "GLModel.hpp"
|
||||
|
||||
namespace Slic3r {
|
||||
namespace GUI {
|
||||
|
||||
class CoordAxes
|
||||
{
|
||||
public:
|
||||
static const float DefaultStemRadius;
|
||||
static const float DefaultStemLength;
|
||||
static const float DefaultTipRadius;
|
||||
static const float DefaultTipLength;
|
||||
|
||||
private:
|
||||
Vec3d m_origin{ Vec3d::Zero() };
|
||||
float m_stem_radius{ DefaultStemRadius };
|
||||
float m_stem_length{ DefaultStemLength };
|
||||
float m_tip_radius{ DefaultTipRadius };
|
||||
float m_tip_length{ DefaultTipLength };
|
||||
GLModel m_arrow;
|
||||
|
||||
public:
|
||||
const Vec3d& get_origin() const { return m_origin; }
|
||||
void set_origin(const Vec3d& origin) { m_origin = origin; }
|
||||
void set_stem_radius(float radius) {
|
||||
m_stem_radius = radius;
|
||||
m_arrow.reset();
|
||||
}
|
||||
void set_stem_length(float length) {
|
||||
m_stem_length = length;
|
||||
m_arrow.reset();
|
||||
}
|
||||
void set_tip_radius(float radius) {
|
||||
m_tip_radius = radius;
|
||||
m_arrow.reset();
|
||||
}
|
||||
void set_tip_length(float length) {
|
||||
m_tip_length = length;
|
||||
m_arrow.reset();
|
||||
}
|
||||
|
||||
float get_stem_radius() const { return m_stem_radius; }
|
||||
float get_stem_length() const { return m_stem_length; }
|
||||
float get_tip_radius() const { return m_tip_radius; }
|
||||
float get_tip_length() const { return m_tip_length; }
|
||||
float get_total_length() const { return m_stem_length + m_tip_length; }
|
||||
|
||||
#if ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
void render(const Transform3d& trafo, float emission_factor = 0.0f);
|
||||
#else
|
||||
void render(float emission_factor = 0.0f);
|
||||
#endif // ENABLE_GL_SHADERS_ATTRIBUTES
|
||||
};
|
||||
|
||||
} // GUI
|
||||
} // Slic3r
|
||||
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
#endif // slic3r_CoordAxes_hpp_
|
@ -86,24 +86,24 @@ Control::Control( wxWindow *parent,
|
||||
|
||||
m_bmp_thumb_higher = (style == wxSL_HORIZONTAL ? ScalableBitmap(this, "thumb_right") : ScalableBitmap(this, "thumb_up"));
|
||||
m_bmp_thumb_lower = (style == wxSL_HORIZONTAL ? ScalableBitmap(this, "thumb_left") : ScalableBitmap(this, "thumb_down"));
|
||||
m_thumb_size = m_bmp_thumb_lower.GetBmpSize();
|
||||
m_thumb_size = m_bmp_thumb_lower.GetSize();
|
||||
|
||||
m_bmp_add_tick_on = ScalableBitmap(this, "colorchange_add");
|
||||
m_bmp_add_tick_off = ScalableBitmap(this, "colorchange_add_f");
|
||||
m_bmp_del_tick_on = ScalableBitmap(this, "colorchange_del");
|
||||
m_bmp_del_tick_off = ScalableBitmap(this, "colorchange_del_f");
|
||||
m_tick_icon_dim = m_bmp_add_tick_on.GetBmpWidth();
|
||||
m_tick_icon_dim = m_bmp_add_tick_on.GetWidth();
|
||||
|
||||
m_bmp_one_layer_lock_on = ScalableBitmap(this, "lock_closed");
|
||||
m_bmp_one_layer_lock_off = ScalableBitmap(this, "lock_closed_f");
|
||||
m_bmp_one_layer_unlock_on = ScalableBitmap(this, "lock_open");
|
||||
m_bmp_one_layer_unlock_off = ScalableBitmap(this, "lock_open_f");
|
||||
m_lock_icon_dim = m_bmp_one_layer_lock_on.GetBmpWidth();
|
||||
m_lock_icon_dim = m_bmp_one_layer_lock_on.GetWidth();
|
||||
|
||||
m_bmp_revert = ScalableBitmap(this, "undo");
|
||||
m_revert_icon_dim = m_bmp_revert.GetBmpWidth();
|
||||
m_revert_icon_dim = m_bmp_revert.GetWidth();
|
||||
m_bmp_cog = ScalableBitmap(this, "cog");
|
||||
m_cog_icon_dim = m_bmp_cog.GetBmpWidth();
|
||||
m_cog_icon_dim = m_bmp_cog.GetWidth();
|
||||
|
||||
m_selection = ssUndef;
|
||||
m_ticks.set_pause_print_msg(_utf8(L("Place bearings in slots and resume printing")));
|
||||
@ -155,26 +155,11 @@ void Control::msw_rescale()
|
||||
{
|
||||
m_font = GUI::wxGetApp().normal_font();
|
||||
|
||||
m_bmp_thumb_higher.msw_rescale();
|
||||
m_bmp_thumb_lower .msw_rescale();
|
||||
m_thumb_size = m_bmp_thumb_lower.bmp().GetSize();
|
||||
|
||||
m_bmp_add_tick_on .msw_rescale();
|
||||
m_bmp_add_tick_off.msw_rescale();
|
||||
m_bmp_del_tick_on .msw_rescale();
|
||||
m_bmp_del_tick_off.msw_rescale();
|
||||
m_tick_icon_dim = m_bmp_add_tick_on.bmp().GetSize().x;
|
||||
|
||||
m_bmp_one_layer_lock_on .msw_rescale();
|
||||
m_bmp_one_layer_lock_off .msw_rescale();
|
||||
m_bmp_one_layer_unlock_on .msw_rescale();
|
||||
m_bmp_one_layer_unlock_off.msw_rescale();
|
||||
m_lock_icon_dim = m_bmp_one_layer_lock_on.bmp().GetSize().x;
|
||||
|
||||
m_bmp_revert.msw_rescale();
|
||||
m_revert_icon_dim = m_bmp_revert.bmp().GetSize().x;
|
||||
m_bmp_cog.msw_rescale();
|
||||
m_cog_icon_dim = m_bmp_cog.bmp().GetSize().x;
|
||||
m_thumb_size = m_bmp_thumb_lower.GetSize();
|
||||
m_tick_icon_dim = m_bmp_add_tick_on.GetWidth();
|
||||
m_lock_icon_dim = m_bmp_one_layer_lock_on.GetWidth();
|
||||
m_revert_icon_dim = m_bmp_revert.GetWidth();
|
||||
m_cog_icon_dim = m_bmp_cog.GetWidth();
|
||||
|
||||
SLIDER_MARGIN = 4 + GUI::wxGetApp().em_unit();
|
||||
|
||||
@ -189,22 +174,18 @@ void Control::sys_color_changed()
|
||||
{
|
||||
GUI::wxGetApp().UpdateDarkUI(GetParent());
|
||||
|
||||
m_bmp_add_tick_on .msw_rescale();
|
||||
m_bmp_add_tick_off.msw_rescale();
|
||||
m_bmp_del_tick_on .msw_rescale();
|
||||
m_bmp_del_tick_off.msw_rescale();
|
||||
m_tick_icon_dim = m_bmp_add_tick_on.GetBmpWidth();
|
||||
m_bmp_add_tick_on .sys_color_changed();
|
||||
m_bmp_add_tick_off.sys_color_changed();
|
||||
m_bmp_del_tick_on .sys_color_changed();
|
||||
m_bmp_del_tick_off.sys_color_changed();
|
||||
|
||||
m_bmp_one_layer_lock_on .msw_rescale();
|
||||
m_bmp_one_layer_lock_off .msw_rescale();
|
||||
m_bmp_one_layer_unlock_on .msw_rescale();
|
||||
m_bmp_one_layer_unlock_off.msw_rescale();
|
||||
m_lock_icon_dim = m_bmp_one_layer_lock_on.GetBmpWidth();
|
||||
m_bmp_one_layer_lock_on .sys_color_changed();
|
||||
m_bmp_one_layer_lock_off .sys_color_changed();
|
||||
m_bmp_one_layer_unlock_on .sys_color_changed();
|
||||
m_bmp_one_layer_unlock_off.sys_color_changed();
|
||||
|
||||
m_bmp_revert.msw_rescale();
|
||||
m_revert_icon_dim = m_bmp_revert.GetBmpWidth();
|
||||
m_bmp_cog.msw_rescale();
|
||||
m_cog_icon_dim = m_bmp_cog.GetBmpWidth();
|
||||
m_bmp_revert.sys_color_changed();
|
||||
m_bmp_cog .sys_color_changed();
|
||||
}
|
||||
|
||||
int Control::GetActiveValue() const
|
||||
@ -604,9 +585,12 @@ void Control::draw_action_icon(wxDC& dc, const wxPoint pt_beg, const wxPoint pt_
|
||||
return;
|
||||
}
|
||||
|
||||
wxBitmap* icon = m_focus == fiActionIcon ? &m_bmp_add_tick_off.bmp() : &m_bmp_add_tick_on.bmp();
|
||||
//wxBitmap* icon = m_focus == fiActionIcon ? &m_bmp_add_tick_off.bmp() : &m_bmp_add_tick_on.bmp();
|
||||
//if (m_ticks.ticks.find(TickCode{tick}) != m_ticks.ticks.end())
|
||||
// icon = m_focus == fiActionIcon ? &m_bmp_del_tick_off.bmp() : &m_bmp_del_tick_on.bmp();
|
||||
ScalableBitmap* icon = m_focus == fiActionIcon ? &m_bmp_add_tick_off : &m_bmp_add_tick_on;
|
||||
if (m_ticks.ticks.find(TickCode{tick}) != m_ticks.ticks.end())
|
||||
icon = m_focus == fiActionIcon ? &m_bmp_del_tick_off.bmp() : &m_bmp_del_tick_on.bmp();
|
||||
icon = m_focus == fiActionIcon ? &m_bmp_del_tick_off : &m_bmp_del_tick_on;
|
||||
|
||||
wxCoord x_draw, y_draw;
|
||||
is_horizontal() ? x_draw = pt_beg.x - 0.5*m_tick_icon_dim : y_draw = pt_beg.y - 0.5*m_tick_icon_dim;
|
||||
@ -615,10 +599,12 @@ void Control::draw_action_icon(wxDC& dc, const wxPoint pt_beg, const wxPoint pt_
|
||||
else
|
||||
is_horizontal() ? y_draw = pt_beg.y - m_tick_icon_dim-2 : x_draw = pt_end.x + 3;
|
||||
|
||||
if (m_draw_mode == dmSequentialFffPrint)
|
||||
dc.DrawBitmap(create_scaled_bitmap("colorchange_add", nullptr, 16, true), x_draw, y_draw);
|
||||
if (m_draw_mode == dmSequentialFffPrint) {
|
||||
wxBitmap disabled_add = get_bmp_bundle("colorchange_add")->GetBitmapFor(this).ConvertToDisabled();
|
||||
dc.DrawBitmap(disabled_add, x_draw, y_draw);
|
||||
}
|
||||
else
|
||||
dc.DrawBitmap(*icon, x_draw, y_draw);
|
||||
dc.DrawBitmap((*icon).get_bitmap(), x_draw, y_draw);
|
||||
|
||||
//update rect of the tick action icon
|
||||
m_rect_tick_action = wxRect(x_draw, y_draw, m_tick_icon_dim, m_tick_icon_dim);
|
||||
@ -851,7 +837,7 @@ void Control::draw_thumb_item(wxDC& dc, const wxPoint& pos, const SelectedSlider
|
||||
{
|
||||
wxCoord x_draw = pos.x - int(0.5 * m_thumb_size.x);
|
||||
wxCoord y_draw = pos.y - int(0.5 * m_thumb_size.y);
|
||||
dc.DrawBitmap(selection == ssLower ? m_bmp_thumb_lower.bmp() : m_bmp_thumb_higher.bmp(), x_draw, y_draw);
|
||||
dc.DrawBitmap(selection == ssLower ? m_bmp_thumb_lower.get_bitmap() : m_bmp_thumb_higher.get_bitmap(), x_draw, y_draw);
|
||||
|
||||
// Update thumb rect
|
||||
update_thumb_rect(x_draw, y_draw, selection);
|
||||
@ -945,12 +931,12 @@ void Control::draw_ticks(wxDC& dc)
|
||||
|
||||
// Draw icon for "Pause print", "Custom Gcode" or conflict tick
|
||||
if (!icon_name.empty()) {
|
||||
wxBitmap icon = create_scaled_bitmap(icon_name);
|
||||
wxBitmapBundle* icon = get_bmp_bundle(icon_name);
|
||||
wxCoord x_draw, y_draw;
|
||||
is_horizontal() ? x_draw = pos - 0.5 * m_tick_icon_dim : y_draw = pos - 0.5 * m_tick_icon_dim;
|
||||
is_horizontal() ? y_draw = mid + 22 : x_draw = mid + m_thumb_size.x + 3;
|
||||
|
||||
dc.DrawBitmap(icon, x_draw, y_draw);
|
||||
dc.DrawBitmap(icon->GetBitmapFor(this), x_draw, y_draw);
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -1262,9 +1248,12 @@ void Control::draw_one_layer_icon(wxDC& dc)
|
||||
if (m_draw_mode == dmSequentialGCodeView)
|
||||
return;
|
||||
|
||||
const wxBitmap& icon = m_is_one_layer ?
|
||||
m_focus == fiOneLayerIcon ? m_bmp_one_layer_lock_off.bmp() : m_bmp_one_layer_lock_on.bmp() :
|
||||
m_focus == fiOneLayerIcon ? m_bmp_one_layer_unlock_off.bmp() : m_bmp_one_layer_unlock_on.bmp();
|
||||
//const wxBitmap& icon = m_is_one_layer ?
|
||||
// m_focus == fiOneLayerIcon ? m_bmp_one_layer_lock_off.bmp() : m_bmp_one_layer_lock_on.bmp() :
|
||||
// m_focus == fiOneLayerIcon ? m_bmp_one_layer_unlock_off.bmp() : m_bmp_one_layer_unlock_on.bmp();
|
||||
const ScalableBitmap& icon = m_is_one_layer ?
|
||||
m_focus == fiOneLayerIcon ? m_bmp_one_layer_lock_off : m_bmp_one_layer_lock_on :
|
||||
m_focus == fiOneLayerIcon ? m_bmp_one_layer_unlock_off : m_bmp_one_layer_unlock_on;
|
||||
|
||||
int width, height;
|
||||
get_size(&width, &height);
|
||||
@ -1273,7 +1262,7 @@ void Control::draw_one_layer_icon(wxDC& dc)
|
||||
is_horizontal() ? x_draw = width-2 : x_draw = 0.5*width - 0.5*m_lock_icon_dim;
|
||||
is_horizontal() ? y_draw = 0.5*height - 0.5*m_lock_icon_dim : y_draw = height-2;
|
||||
|
||||
dc.DrawBitmap(icon, x_draw, y_draw);
|
||||
dc.DrawBitmap(icon.bmp().GetBitmapFor(this), x_draw, y_draw);
|
||||
|
||||
//update rect of the lock/unlock icon
|
||||
m_rect_one_layer_icon = wxRect(x_draw, y_draw, m_lock_icon_dim, m_lock_icon_dim);
|
||||
@ -1291,7 +1280,7 @@ void Control::draw_revert_icon(wxDC& dc)
|
||||
is_horizontal() ? x_draw = width-2 : x_draw = 0.25*SLIDER_MARGIN;
|
||||
is_horizontal() ? y_draw = 0.25*SLIDER_MARGIN: y_draw = height-2;
|
||||
|
||||
dc.DrawBitmap(m_bmp_revert.bmp(), x_draw, y_draw);
|
||||
dc.DrawBitmap(m_bmp_revert.get_bitmap(), x_draw, y_draw);
|
||||
|
||||
//update rect of the lock/unlock icon
|
||||
m_rect_revert_icon = wxRect(x_draw, y_draw, m_revert_icon_dim, m_revert_icon_dim);
|
||||
@ -1315,7 +1304,7 @@ void Control::draw_cog_icon(wxDC& dc)
|
||||
is_horizontal() ? y_draw = height - m_cog_icon_dim - 2 : y_draw = height - 2;
|
||||
}
|
||||
|
||||
dc.DrawBitmap(m_bmp_cog.bmp(), x_draw, y_draw);
|
||||
dc.DrawBitmap(m_bmp_cog.get_bitmap(), x_draw, y_draw);
|
||||
|
||||
//update rect of the lock/unlock icon
|
||||
m_rect_cog_icon = wxRect(x_draw, y_draw, m_cog_icon_dim, m_cog_icon_dim);
|
||||
@ -1673,7 +1662,7 @@ void Control::append_change_extruder_menu_item(wxMenu* menu, bool switch_current
|
||||
if (extruders_cnt > 1) {
|
||||
std::array<int, 2> active_extruders = get_active_extruders_for_tick(m_selection == ssLower ? m_lower_value : m_higher_value);
|
||||
|
||||
std::vector<wxBitmap*> icons = get_extruder_color_icons(true);
|
||||
std::vector<wxBitmapBundle*> icons = get_extruder_color_icons(true);
|
||||
|
||||
wxMenu* change_extruder_menu = new wxMenu();
|
||||
|
||||
@ -1684,7 +1673,7 @@ void Control::append_change_extruder_menu_item(wxMenu* menu, bool switch_current
|
||||
|
||||
if (m_mode == MultiAsSingle)
|
||||
append_menu_item(change_extruder_menu, wxID_ANY, item_name, "",
|
||||
[this, i](wxCommandEvent&) { add_code_as_tick(ToolChange, i); }, *icons[i-1], menu,
|
||||
[this, i](wxCommandEvent&) { add_code_as_tick(ToolChange, i); }, icons[i-1], menu,
|
||||
[is_active_extruder]() { return !is_active_extruder; }, GUI::wxGetApp().plater());
|
||||
}
|
||||
|
||||
@ -1722,7 +1711,7 @@ void Control::append_add_color_change_menu_item(wxMenu* menu, bool switch_curren
|
||||
format_wxstr(_L("Switch code to Color change (%1%) for:"), gcode(ColorChange)) :
|
||||
format_wxstr(_L("Add color change (%1%) for:"), gcode(ColorChange));
|
||||
wxMenuItem* add_color_change_menu_item = menu->AppendSubMenu(add_color_change_menu, menu_name, "");
|
||||
add_color_change_menu_item->SetBitmap(create_menu_bitmap("colorchange_add_m"));
|
||||
add_color_change_menu_item->SetBitmap(*get_bmp_bundle("colorchange_add_m"));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -33,6 +33,15 @@ wxIMPLEMENT_DYNAMIC_CLASS(DataViewBitmapText, wxObject)
|
||||
|
||||
IMPLEMENT_VARIANT_OBJECT(DataViewBitmapText)
|
||||
|
||||
static wxSize get_size(const wxBitmap& icon)
|
||||
{
|
||||
#ifdef __WIN32__
|
||||
return icon.GetSize();
|
||||
#else
|
||||
return icon.GetScaledSize();
|
||||
#endif
|
||||
}
|
||||
|
||||
// ---------------------------------------------------------
|
||||
// BitmapTextRenderer
|
||||
// ---------------------------------------------------------
|
||||
@ -124,11 +133,7 @@ bool BitmapTextRenderer::Render(wxRect rect, wxDC *dc, int state)
|
||||
const wxBitmap& icon = m_value.GetBitmap();
|
||||
if (icon.IsOk())
|
||||
{
|
||||
#ifdef __APPLE__
|
||||
wxSize icon_sz = icon.GetScaledSize();
|
||||
#else
|
||||
wxSize icon_sz = icon.GetSize();
|
||||
#endif
|
||||
wxSize icon_sz = get_size(icon);
|
||||
dc->DrawBitmap(icon, rect.x, rect.y + (rect.height - icon_sz.y) / 2);
|
||||
xoffset = icon_sz.x + 4;
|
||||
}
|
||||
@ -264,11 +269,13 @@ bool BitmapChoiceRenderer::Render(wxRect rect, wxDC* dc, int state)
|
||||
const wxBitmap& icon = m_value.GetBitmap();
|
||||
if (icon.IsOk())
|
||||
{
|
||||
dc->DrawBitmap(icon, rect.x, rect.y + (rect.height - icon.GetHeight()) / 2);
|
||||
xoffset = icon.GetWidth() + 4;
|
||||
wxSize icon_sz = get_size(icon);
|
||||
|
||||
dc->DrawBitmap(icon, rect.x, rect.y + (rect.height - icon_sz.GetHeight()) / 2);
|
||||
xoffset = icon_sz.GetWidth() + 4;
|
||||
|
||||
if (rect.height==0)
|
||||
rect.height= icon.GetHeight();
|
||||
rect.height= icon_sz.GetHeight();
|
||||
}
|
||||
|
||||
#ifdef _WIN32
|
||||
@ -297,7 +304,7 @@ wxWindow* BitmapChoiceRenderer::CreateEditorCtrl(wxWindow* parent, wxRect labelR
|
||||
if (can_create_editor_ctrl && !can_create_editor_ctrl())
|
||||
return nullptr;
|
||||
|
||||
std::vector<wxBitmap*> icons = get_extruder_color_icons();
|
||||
std::vector<wxBitmapBundle*> icons = get_extruder_color_icons();
|
||||
if (icons.empty())
|
||||
return nullptr;
|
||||
|
||||
|
@ -264,9 +264,6 @@ void ExtruderSequenceDialog::on_dpi_changed(const wxRect& suggested_rect)
|
||||
{
|
||||
SetFont(wxGetApp().normal_font());
|
||||
|
||||
m_bmp_add.msw_rescale();
|
||||
m_bmp_del.msw_rescale();
|
||||
|
||||
const int em = em_unit();
|
||||
|
||||
m_intervals_grid_sizer->SetHGap(em);
|
||||
|
@ -106,14 +106,14 @@ public:
|
||||
bool set_undo_to_sys_tooltip(const wxString* tip) { return m_undo_ui.set_undo_to_sys_tooltip(tip); }
|
||||
|
||||
// ui items used for revert line value
|
||||
bool has_undo_ui() const { return m_undo_ui.undo_bitmap != nullptr; }
|
||||
const wxBitmap& undo_bitmap() const { return m_undo_ui.undo_bitmap->bmp(); }
|
||||
const wxString* undo_tooltip() const { return m_undo_ui.undo_tooltip; }
|
||||
const wxBitmap& undo_to_sys_bitmap() const { return m_undo_ui.undo_to_sys_bitmap->bmp(); }
|
||||
const wxString* undo_to_sys_tooltip() const { return m_undo_ui.undo_to_sys_tooltip; }
|
||||
const wxColour* label_color() const { return m_undo_ui.label_color; }
|
||||
const bool blink() const { return m_undo_ui.blink; }
|
||||
bool* get_blink_ptr() { return &m_undo_ui.blink; }
|
||||
bool has_undo_ui() const { return m_undo_ui.undo_bitmap != nullptr; }
|
||||
const wxBitmapBundle& undo_bitmap() const { return m_undo_ui.undo_bitmap->bmp(); }
|
||||
const wxString* undo_tooltip() const { return m_undo_ui.undo_tooltip; }
|
||||
const wxBitmapBundle& undo_to_sys_bitmap() const { return m_undo_ui.undo_to_sys_bitmap->bmp(); }
|
||||
const wxString* undo_to_sys_tooltip() const { return m_undo_ui.undo_to_sys_tooltip; }
|
||||
const wxColour* label_color() const { return m_undo_ui.label_color; }
|
||||
const bool blink() const { return m_undo_ui.blink; }
|
||||
bool* get_blink_ptr() { return &m_undo_ui.blink; }
|
||||
};
|
||||
|
||||
|
||||
|
@ -386,14 +386,14 @@ void GCodeViewer::SequentialView::Marker::render()
|
||||
ImGui::PopStyleVar();
|
||||
}
|
||||
|
||||
void GCodeViewer::SequentialView::GCodeWindow::load_gcode(const std::string& filename, std::vector<size_t> &&lines_ends)
|
||||
void GCodeViewer::SequentialView::GCodeWindow::load_gcode(const std::string& filename, const std::vector<size_t>& lines_ends)
|
||||
{
|
||||
assert(! m_file.is_open());
|
||||
if (m_file.is_open())
|
||||
return;
|
||||
|
||||
m_filename = filename;
|
||||
m_lines_ends = std::move(lines_ends);
|
||||
m_lines_ends = lines_ends;
|
||||
|
||||
m_selected_line_id = 0;
|
||||
m_last_lines_size = 0;
|
||||
@ -771,9 +771,7 @@ void GCodeViewer::load(const GCodeProcessorResult& gcode_result, const Print& pr
|
||||
// release gpu memory, if used
|
||||
reset();
|
||||
|
||||
m_sequential_view.gcode_window.load_gcode(gcode_result.filename,
|
||||
// Stealing out lines_ends should be safe because this gcode_result is processed only once (see the 1st if in this function).
|
||||
std::move(const_cast<std::vector<size_t>&>(gcode_result.lines_ends)));
|
||||
m_sequential_view.gcode_window.load_gcode(gcode_result.filename, gcode_result.lines_ends);
|
||||
|
||||
if (wxGetApp().is_gcode_viewer())
|
||||
m_custom_gcode_per_print_z = gcode_result.custom_gcode_per_print_z;
|
||||
@ -993,11 +991,13 @@ void GCodeViewer::render()
|
||||
render_toolpaths();
|
||||
render_shells();
|
||||
float legend_height = 0.0f;
|
||||
render_legend(legend_height);
|
||||
if (m_sequential_view.current.last != m_sequential_view.endpoints.last) {
|
||||
m_sequential_view.marker.set_world_position(m_sequential_view.current_position);
|
||||
m_sequential_view.marker.set_world_offset(m_sequential_view.current_offset);
|
||||
m_sequential_view.render(legend_height);
|
||||
if (!m_layers.empty()) {
|
||||
render_legend(legend_height);
|
||||
if (m_sequential_view.current.last != m_sequential_view.endpoints.last) {
|
||||
m_sequential_view.marker.set_world_position(m_sequential_view.current_position);
|
||||
m_sequential_view.marker.set_world_offset(m_sequential_view.current_offset);
|
||||
m_sequential_view.render(legend_height);
|
||||
}
|
||||
}
|
||||
#if ENABLE_GCODE_VIEWER_STATISTICS
|
||||
render_statistics();
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -1101,6 +1101,9 @@ wxDEFINE_EVENT(EVT_GLCANVAS_QUESTION_MARK, SimpleEvent);
|
||||
wxDEFINE_EVENT(EVT_GLCANVAS_INCREASE_INSTANCES, Event<int>);
|
||||
wxDEFINE_EVENT(EVT_GLCANVAS_INSTANCE_MOVED, SimpleEvent);
|
||||
wxDEFINE_EVENT(EVT_GLCANVAS_INSTANCE_ROTATED, SimpleEvent);
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
wxDEFINE_EVENT(EVT_GLCANVAS_RESET_SKEW, SimpleEvent);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
wxDEFINE_EVENT(EVT_GLCANVAS_INSTANCE_SCALED, SimpleEvent);
|
||||
wxDEFINE_EVENT(EVT_GLCANVAS_FORCE_UPDATE, SimpleEvent);
|
||||
wxDEFINE_EVENT(EVT_GLCANVAS_WIPETOWER_MOVED, Vec3dEvent);
|
||||
@ -2914,7 +2917,13 @@ void GLCanvas3D::on_key(wxKeyEvent& evt)
|
||||
else
|
||||
displacement = multiplier * direction;
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
TransformationType trafo_type;
|
||||
trafo_type.set_relative();
|
||||
m_selection.translate(displacement, trafo_type);
|
||||
#else
|
||||
m_selection.translate(displacement);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
m_dirty = true;
|
||||
}
|
||||
);
|
||||
@ -3584,7 +3593,13 @@ void GLCanvas3D::on_mouse(wxMouseEvent& evt)
|
||||
}
|
||||
}
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
TransformationType trafo_type;
|
||||
trafo_type.set_relative();
|
||||
m_selection.translate(cur_pos - m_mouse.drag.start_position_3D, trafo_type);
|
||||
#else
|
||||
m_selection.translate(cur_pos - m_mouse.drag.start_position_3D);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
if (current_printer_technology() == ptFFF && fff_print()->config().complete_objects)
|
||||
update_sequential_clearance();
|
||||
wxGetApp().obj_manipul()->set_dirty();
|
||||
@ -3830,9 +3845,17 @@ void GLCanvas3D::do_move(const std::string& snapshot_type)
|
||||
ModelObject* model_object = m_model->objects[object_idx];
|
||||
if (model_object != nullptr) {
|
||||
if (selection_mode == Selection::Instance)
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
model_object->instances[instance_idx]->set_transformation(v->get_instance_transformation());
|
||||
#else
|
||||
model_object->instances[instance_idx]->set_offset(v->get_instance_offset());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
else if (selection_mode == Selection::Volume)
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
model_object->volumes[volume_idx]->set_transformation(v->get_volume_transformation());
|
||||
#else
|
||||
model_object->volumes[volume_idx]->set_offset(v->get_volume_offset());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
object_moved = true;
|
||||
model_object->invalidate_bounding_box();
|
||||
@ -3912,8 +3935,8 @@ void GLCanvas3D::do_rotate(const std::string& snapshot_type)
|
||||
int object_idx = v->object_idx();
|
||||
if (object_idx == 1000) { // the wipe tower
|
||||
#endif // ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL
|
||||
Vec3d offset = v->get_volume_offset();
|
||||
post_event(Vec3dEvent(EVT_GLCANVAS_WIPETOWER_ROTATED, Vec3d(offset(0), offset(1), v->get_volume_rotation()(2))));
|
||||
const Vec3d offset = v->get_volume_offset();
|
||||
post_event(Vec3dEvent(EVT_GLCANVAS_WIPETOWER_ROTATED, Vec3d(offset.x(), offset.y(), v->get_volume_rotation().z())));
|
||||
}
|
||||
#if ENABLE_WIPETOWER_OBJECTID_1000_REMOVAL
|
||||
int object_idx = v->object_idx();
|
||||
@ -3921,8 +3944,8 @@ void GLCanvas3D::do_rotate(const std::string& snapshot_type)
|
||||
if (object_idx < 0 || (int)m_model->objects.size() <= object_idx)
|
||||
continue;
|
||||
|
||||
int instance_idx = v->instance_idx();
|
||||
int volume_idx = v->volume_idx();
|
||||
const int instance_idx = v->instance_idx();
|
||||
const int volume_idx = v->volume_idx();
|
||||
|
||||
done.insert(std::pair<int, int>(object_idx, instance_idx));
|
||||
|
||||
@ -3930,12 +3953,20 @@ void GLCanvas3D::do_rotate(const std::string& snapshot_type)
|
||||
ModelObject* model_object = m_model->objects[object_idx];
|
||||
if (model_object != nullptr) {
|
||||
if (selection_mode == Selection::Instance) {
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
model_object->instances[instance_idx]->set_transformation(v->get_instance_transformation());
|
||||
#else
|
||||
model_object->instances[instance_idx]->set_rotation(v->get_instance_rotation());
|
||||
model_object->instances[instance_idx]->set_offset(v->get_instance_offset());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
else if (selection_mode == Selection::Volume) {
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
model_object->volumes[volume_idx]->set_transformation(v->get_volume_transformation());
|
||||
#else
|
||||
model_object->volumes[volume_idx]->set_rotation(v->get_volume_rotation());
|
||||
model_object->volumes[volume_idx]->set_offset(v->get_volume_offset());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
model_object->invalidate_bounding_box();
|
||||
}
|
||||
@ -3985,12 +4016,12 @@ void GLCanvas3D::do_scale(const std::string& snapshot_type)
|
||||
Selection::EMode selection_mode = m_selection.get_mode();
|
||||
|
||||
for (const GLVolume* v : m_volumes.volumes) {
|
||||
int object_idx = v->object_idx();
|
||||
const int object_idx = v->object_idx();
|
||||
if (object_idx < 0 || (int)m_model->objects.size() <= object_idx)
|
||||
continue;
|
||||
|
||||
int instance_idx = v->instance_idx();
|
||||
int volume_idx = v->volume_idx();
|
||||
const int instance_idx = v->instance_idx();
|
||||
const int volume_idx = v->volume_idx();
|
||||
|
||||
done.insert(std::pair<int, int>(object_idx, instance_idx));
|
||||
|
||||
@ -3998,13 +4029,22 @@ void GLCanvas3D::do_scale(const std::string& snapshot_type)
|
||||
ModelObject* model_object = m_model->objects[object_idx];
|
||||
if (model_object != nullptr) {
|
||||
if (selection_mode == Selection::Instance) {
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
model_object->instances[instance_idx]->set_transformation(v->get_instance_transformation());
|
||||
#else
|
||||
model_object->instances[instance_idx]->set_scaling_factor(v->get_instance_scaling_factor());
|
||||
model_object->instances[instance_idx]->set_offset(v->get_instance_offset());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
else if (selection_mode == Selection::Volume) {
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
model_object->instances[instance_idx]->set_transformation(v->get_instance_transformation());
|
||||
model_object->volumes[volume_idx]->set_transformation(v->get_volume_transformation());
|
||||
#else
|
||||
model_object->instances[instance_idx]->set_offset(v->get_instance_offset());
|
||||
model_object->volumes[volume_idx]->set_scaling_factor(v->get_volume_scaling_factor());
|
||||
model_object->volumes[volume_idx]->set_offset(v->get_volume_offset());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
model_object->invalidate_bounding_box();
|
||||
}
|
||||
@ -4013,10 +4053,10 @@ void GLCanvas3D::do_scale(const std::string& snapshot_type)
|
||||
// Fixes sinking/flying instances
|
||||
for (const std::pair<int, int>& i : done) {
|
||||
ModelObject* m = m_model->objects[i.first];
|
||||
double shift_z = m->get_instance_min_z(i.second);
|
||||
const double shift_z = m->get_instance_min_z(i.second);
|
||||
// leave sinking instances as sinking
|
||||
if (min_zs.empty() || min_zs.find({ i.first, i.second })->second >= SINKING_Z_THRESHOLD || shift_z > SINKING_Z_THRESHOLD) {
|
||||
Vec3d shift(0.0, 0.0, -shift_z);
|
||||
const Vec3d shift(0.0, 0.0, -shift_z);
|
||||
m_selection.translate(i.first, i.second, shift);
|
||||
m->translate_instance(i.second, shift);
|
||||
}
|
||||
@ -4066,9 +4106,17 @@ void GLCanvas3D::do_mirror(const std::string& snapshot_type)
|
||||
ModelObject* model_object = m_model->objects[object_idx];
|
||||
if (model_object != nullptr) {
|
||||
if (selection_mode == Selection::Instance)
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
model_object->instances[instance_idx]->set_transformation(v->get_instance_transformation());
|
||||
#else
|
||||
model_object->instances[instance_idx]->set_mirror(v->get_instance_mirror());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
else if (selection_mode == Selection::Volume)
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
model_object->volumes[volume_idx]->set_transformation(v->get_volume_transformation());
|
||||
#else
|
||||
model_object->volumes[volume_idx]->set_mirror(v->get_volume_mirror());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
model_object->invalidate_bounding_box();
|
||||
}
|
||||
@ -4092,6 +4140,44 @@ void GLCanvas3D::do_mirror(const std::string& snapshot_type)
|
||||
m_dirty = true;
|
||||
}
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
void GLCanvas3D::do_reset_skew(const std::string& snapshot_type)
|
||||
{
|
||||
if (m_model == nullptr)
|
||||
return;
|
||||
|
||||
if (!snapshot_type.empty())
|
||||
wxGetApp().plater()->take_snapshot(_(snapshot_type));
|
||||
|
||||
std::set<std::pair<int, int>> done; // keeps track of modified instances
|
||||
|
||||
const Selection::IndicesList& idxs = m_selection.get_volume_idxs();
|
||||
|
||||
for (unsigned int id : idxs) {
|
||||
const GLVolume* v = m_volumes.volumes[id];
|
||||
int object_idx = v->object_idx();
|
||||
if (object_idx < 0 || (int)m_model->objects.size() <= object_idx)
|
||||
continue;
|
||||
|
||||
int instance_idx = v->instance_idx();
|
||||
int volume_idx = v->volume_idx();
|
||||
|
||||
done.insert(std::pair<int, int>(object_idx, instance_idx));
|
||||
|
||||
ModelObject* model_object = m_model->objects[object_idx];
|
||||
if (model_object != nullptr) {
|
||||
model_object->instances[instance_idx]->set_transformation(v->get_instance_transformation());
|
||||
model_object->volumes[volume_idx]->set_transformation(v->get_volume_transformation());
|
||||
model_object->invalidate_bounding_box();
|
||||
}
|
||||
}
|
||||
|
||||
post_event(SimpleEvent(EVT_GLCANVAS_RESET_SKEW));
|
||||
|
||||
m_dirty = true;
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void GLCanvas3D::update_gizmos_on_off_state()
|
||||
{
|
||||
set_as_dirty();
|
||||
@ -5339,7 +5425,7 @@ void GLCanvas3D::_refresh_if_shown_on_screen()
|
||||
|
||||
void GLCanvas3D::_picking_pass()
|
||||
{
|
||||
if (m_picking_enabled && !m_mouse.dragging && m_mouse.position != Vec2d(DBL_MAX, DBL_MAX)) {
|
||||
if (m_picking_enabled && !m_mouse.dragging && m_mouse.position != Vec2d(DBL_MAX, DBL_MAX) && !m_gizmos.is_dragging()) {
|
||||
m_hover_volume_idxs.clear();
|
||||
|
||||
// Render the object for picking.
|
||||
@ -7352,12 +7438,13 @@ bool GLCanvas3D::_is_any_volume_outside() const
|
||||
void GLCanvas3D::_update_selection_from_hover()
|
||||
{
|
||||
bool ctrl_pressed = wxGetKeyState(WXK_CONTROL);
|
||||
bool selection_changed = false;
|
||||
|
||||
if (m_hover_volume_idxs.empty()) {
|
||||
if (!ctrl_pressed && m_rectangle_selection.get_state() == GLSelectionRectangle::EState::Select)
|
||||
if (!ctrl_pressed && m_rectangle_selection.get_state() == GLSelectionRectangle::EState::Select) {
|
||||
selection_changed = ! m_selection.is_empty();
|
||||
m_selection.remove_all();
|
||||
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
GLSelectionRectangle::EState state = m_rectangle_selection.get_state();
|
||||
@ -7370,7 +7457,6 @@ void GLCanvas3D::_update_selection_from_hover()
|
||||
}
|
||||
}
|
||||
|
||||
bool selection_changed = false;
|
||||
#if ENABLE_NEW_RECTANGLE_SELECTION
|
||||
if (!m_rectangle_selection.is_empty()) {
|
||||
#endif // ENABLE_NEW_RECTANGLE_SELECTION
|
||||
|
@ -156,6 +156,9 @@ wxDECLARE_EVENT(EVT_GLCANVAS_INSTANCE_MOVED, SimpleEvent);
|
||||
wxDECLARE_EVENT(EVT_GLCANVAS_FORCE_UPDATE, SimpleEvent);
|
||||
wxDECLARE_EVENT(EVT_GLCANVAS_WIPETOWER_MOVED, Vec3dEvent);
|
||||
wxDECLARE_EVENT(EVT_GLCANVAS_INSTANCE_ROTATED, SimpleEvent);
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
wxDECLARE_EVENT(EVT_GLCANVAS_RESET_SKEW, SimpleEvent);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
wxDECLARE_EVENT(EVT_GLCANVAS_INSTANCE_SCALED, SimpleEvent);
|
||||
wxDECLARE_EVENT(EVT_GLCANVAS_WIPETOWER_ROTATED, Vec3dEvent);
|
||||
wxDECLARE_EVENT(EVT_GLCANVAS_ENABLE_ACTION_BUTTONS, Event<bool>);
|
||||
@ -739,7 +742,11 @@ public:
|
||||
|
||||
void update_volumes_colors_by_extruder();
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
bool is_dragging() const { return m_gizmos.is_dragging() || (m_moving && !m_mouse.scene_position.isApprox(m_mouse.drag.start_position_3D)); }
|
||||
#else
|
||||
bool is_dragging() const { return m_gizmos.is_dragging() || m_moving; }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void render();
|
||||
// printable_only == false -> render also non printable volumes as grayed
|
||||
@ -807,6 +814,9 @@ public:
|
||||
void do_rotate(const std::string& snapshot_type);
|
||||
void do_scale(const std::string& snapshot_type);
|
||||
void do_mirror(const std::string& snapshot_type);
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
void do_reset_skew(const std::string& snapshot_type);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void update_gizmos_on_off_state();
|
||||
void reset_all_gizmos() { m_gizmos.reset_all_states(); }
|
||||
@ -844,7 +854,6 @@ public:
|
||||
// Returns the view ray line, in world coordinate, at the given mouse position.
|
||||
Linef3 mouse_ray(const Point& mouse_pos);
|
||||
|
||||
void set_mouse_as_dragging() { m_mouse.dragging = true; }
|
||||
bool is_mouse_dragging() const { return m_mouse.dragging; }
|
||||
|
||||
double get_size_proportional_to_max_bed_size(double factor) const;
|
||||
|
@ -7,6 +7,7 @@
|
||||
#include "GUI_App.hpp"
|
||||
#include "GLModel.hpp"
|
||||
#endif // ENABLE_LEGACY_OPENGL_REMOVAL
|
||||
#include "BitmapCache.hpp"
|
||||
|
||||
#include <GL/glew.h>
|
||||
|
||||
@ -22,8 +23,8 @@
|
||||
#define STB_DXT_IMPLEMENTATION
|
||||
#include "stb_dxt/stb_dxt.h"
|
||||
|
||||
#include "nanosvg/nanosvg.h"
|
||||
#include "nanosvg/nanosvgrast.h"
|
||||
#include <nanosvg/nanosvg.h>
|
||||
#include <nanosvg/nanosvgrast.h>
|
||||
|
||||
#include "libslic3r/Utils.hpp"
|
||||
|
||||
@ -204,7 +205,7 @@ bool GLTexture::load_from_svg_files_as_sprites_array(const std::vector<std::stri
|
||||
if (!boost::algorithm::iends_with(filename, ".svg"))
|
||||
continue;
|
||||
|
||||
NSVGimage* image = nsvgParseFromFile(filename.c_str(), "px", 96.0f);
|
||||
NSVGimage* image = BitmapCache::nsvgParseFromFileWithReplace(filename.c_str(), "px", 96.0f, {});
|
||||
if (image == nullptr)
|
||||
continue;
|
||||
|
||||
@ -536,7 +537,7 @@ bool GLTexture::load_from_svg(const std::string& filename, bool use_mipmaps, boo
|
||||
{
|
||||
bool compression_enabled = compress && GLEW_EXT_texture_compression_s3tc;
|
||||
|
||||
NSVGimage* image = nsvgParseFromFile(filename.c_str(), "px", 96.0f);
|
||||
NSVGimage* image = BitmapCache::nsvgParseFromFileWithReplace(filename.c_str(), "px", 96.0f, {});
|
||||
if (image == nullptr) {
|
||||
reset();
|
||||
return false;
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -142,14 +142,13 @@ std::map<std::string, std::string> SettingsFactory::CATEGORY_ICON =
|
||||
{ L("Hollowing") , "hollowing" }
|
||||
};
|
||||
|
||||
wxBitmap SettingsFactory::get_category_bitmap(const std::string& category_name, bool menu_bmp /*= true*/)
|
||||
wxBitmapBundle* SettingsFactory::get_category_bitmap(const std::string& category_name)
|
||||
{
|
||||
if (CATEGORY_ICON.find(category_name) == CATEGORY_ICON.end())
|
||||
return wxNullBitmap;
|
||||
return menu_bmp ? create_menu_bitmap(CATEGORY_ICON.at(category_name)) : create_scaled_bitmap(CATEGORY_ICON.at(category_name));
|
||||
return get_bmp_bundle("empty");
|
||||
return get_bmp_bundle(CATEGORY_ICON.at(category_name));
|
||||
}
|
||||
|
||||
|
||||
//-------------------------------------
|
||||
// MenuFactory
|
||||
//-------------------------------------
|
||||
@ -430,12 +429,12 @@ static void create_freq_settings_popupmenu(wxMenu* menu, const bool is_object_se
|
||||
#endif
|
||||
}
|
||||
|
||||
std::vector<wxBitmap> MenuFactory::get_volume_bitmaps()
|
||||
std::vector<wxBitmapBundle*> MenuFactory::get_volume_bitmaps()
|
||||
{
|
||||
std::vector<wxBitmap> volume_bmps;
|
||||
std::vector<wxBitmapBundle*> volume_bmps;
|
||||
volume_bmps.reserve(ADD_VOLUME_MENU_ITEMS.size());
|
||||
for (auto item : ADD_VOLUME_MENU_ITEMS)
|
||||
volume_bmps.push_back(create_menu_bitmap(item.second));
|
||||
volume_bmps.push_back(get_bmp_bundle(item.second));
|
||||
return volume_bmps;
|
||||
}
|
||||
|
||||
@ -620,7 +619,7 @@ wxMenuItem* MenuFactory::append_menu_item_settings(wxMenu* menu_)
|
||||
|
||||
// Add full settings list
|
||||
auto menu_item = new wxMenuItem(menu, wxID_ANY, menu_name);
|
||||
menu_item->SetBitmap(create_menu_bitmap("cog"));
|
||||
menu_item->SetBitmap(*get_bmp_bundle("cog"));
|
||||
menu_item->SetSubMenu(create_settings_popupmenu(menu, is_object_settings, item));
|
||||
|
||||
return menu->Append(menu_item);
|
||||
@ -765,7 +764,7 @@ void MenuFactory::append_menu_item_change_extruder(wxMenu* menu)
|
||||
return;
|
||||
}
|
||||
|
||||
std::vector<wxBitmap*> icons = get_extruder_color_icons(true);
|
||||
std::vector<wxBitmapBundle*> icons = get_extruder_color_icons(true);
|
||||
wxMenu* extruder_selection_menu = new wxMenu();
|
||||
const wxString& name = sels.Count() == 1 ? names[0] : names[1];
|
||||
|
||||
@ -784,7 +783,7 @@ void MenuFactory::append_menu_item_change_extruder(wxMenu* menu)
|
||||
(is_active_extruder ? " (" + _L("active") + ")" : "");
|
||||
|
||||
append_menu_item(extruder_selection_menu, wxID_ANY, item_name, "",
|
||||
[i](wxCommandEvent&) { obj_list()->set_extruder_for_selected_items(i); }, *icons[icon_idx], menu,
|
||||
[i](wxCommandEvent&) { obj_list()->set_extruder_for_selected_items(i); }, icons[icon_idx], menu,
|
||||
[is_active_extruder]() { return !is_active_extruder; }, m_parent);
|
||||
|
||||
}
|
||||
@ -1144,12 +1143,6 @@ void MenuFactory::update_default_menu()
|
||||
create_default_menu();
|
||||
}
|
||||
|
||||
void MenuFactory::msw_rescale()
|
||||
{
|
||||
for (MenuWithSeparators* menu : { &m_object_menu, &m_sla_object_menu, &m_part_menu, &m_default_menu })
|
||||
msw_rescale_menu(dynamic_cast<wxMenu*>(menu));
|
||||
}
|
||||
|
||||
#ifdef _WIN32
|
||||
// For this class is used code from stackoverflow:
|
||||
// https://stackoverflow.com/questions/257288/is-it-possible-to-write-a-template-to-check-for-a-functions-existence
|
||||
@ -1179,7 +1172,7 @@ static void update_menu_item_def_colors(T* item)
|
||||
void MenuFactory::sys_color_changed()
|
||||
{
|
||||
for (MenuWithSeparators* menu : { &m_object_menu, &m_sla_object_menu, &m_part_menu, &m_default_menu }) {
|
||||
msw_rescale_menu(dynamic_cast<wxMenu*>(menu));// msw_rescale_menu updates just icons, so use it
|
||||
sys_color_changed_menu(dynamic_cast<wxMenu*>(menu));// msw_rescale_menu updates just icons, so use it
|
||||
#ifdef _WIN32
|
||||
// but under MSW we have to update item's bachground color
|
||||
for (wxMenuItem* item : menu->GetMenuItems())
|
||||
@ -1192,14 +1185,17 @@ void MenuFactory::sys_color_changed(wxMenuBar* menubar)
|
||||
{
|
||||
for (size_t id = 0; id < menubar->GetMenuCount(); id++) {
|
||||
wxMenu* menu = menubar->GetMenu(id);
|
||||
msw_rescale_menu(menu);
|
||||
sys_color_changed_menu(menu);
|
||||
#ifndef __linux__
|
||||
menu->SetupBitmaps();
|
||||
#ifdef _WIN32
|
||||
// but under MSW we have to update item's bachground color
|
||||
for (wxMenuItem* item : menu->GetMenuItems())
|
||||
update_menu_item_def_colors(item);
|
||||
#endif
|
||||
#endif
|
||||
}
|
||||
menubar->Refresh();
|
||||
// menubar->Refresh();
|
||||
}
|
||||
|
||||
|
||||
|
@ -25,7 +25,7 @@ struct SettingsFactory
|
||||
typedef std::map<std::string, std::vector<std::string>> Bundle;
|
||||
static std::map<std::string, std::string> CATEGORY_ICON;
|
||||
|
||||
static wxBitmap get_category_bitmap(const std::string& category_name, bool menu_bmp = true);
|
||||
static wxBitmapBundle* get_category_bitmap(const std::string& category_name);
|
||||
static Bundle get_bundle(const DynamicPrintConfig* config, bool is_object_settings);
|
||||
static std::vector<std::string> get_options(bool is_part);
|
||||
};
|
||||
@ -34,7 +34,7 @@ class MenuFactory
|
||||
{
|
||||
public:
|
||||
static const std::vector<std::pair<std::string, std::string>> ADD_VOLUME_MENU_ITEMS;
|
||||
static std::vector<wxBitmap> get_volume_bitmaps();
|
||||
static std::vector<wxBitmapBundle*> get_volume_bitmaps();
|
||||
|
||||
MenuFactory();
|
||||
~MenuFactory() = default;
|
||||
@ -43,7 +43,6 @@ public:
|
||||
void update();
|
||||
void update_object_menu();
|
||||
void update_default_menu();
|
||||
void msw_rescale();
|
||||
void sys_color_changed();
|
||||
|
||||
static void sys_color_changed(wxMenuBar* menu_bar);
|
||||
|
9
src/slic3r/GUI/GUI_Geometry.cpp
Normal file
9
src/slic3r/GUI/GUI_Geometry.cpp
Normal file
@ -0,0 +1,9 @@
|
||||
#include "libslic3r/libslic3r.h"
|
||||
#include "GUI_Geometry.hpp"
|
||||
|
||||
namespace Slic3r {
|
||||
namespace GUI {
|
||||
|
||||
|
||||
} // namespace Slic3r
|
||||
} // namespace GUI
|
81
src/slic3r/GUI/GUI_Geometry.hpp
Normal file
81
src/slic3r/GUI/GUI_Geometry.hpp
Normal file
@ -0,0 +1,81 @@
|
||||
#ifndef slic3r_GUI_Geometry_hpp_
|
||||
#define slic3r_GUI_Geometry_hpp_
|
||||
|
||||
namespace Slic3r {
|
||||
namespace GUI {
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
enum class ECoordinatesType : unsigned char
|
||||
{
|
||||
World,
|
||||
Instance,
|
||||
Local
|
||||
};
|
||||
|
||||
class TransformationType
|
||||
{
|
||||
public:
|
||||
enum Enum {
|
||||
// Transforming in a world coordinate system
|
||||
World = 0,
|
||||
// Transforming in a instance coordinate system
|
||||
Instance = 1,
|
||||
// Transforming in a local coordinate system
|
||||
Local = 2,
|
||||
// Absolute transformations, allowed in local coordinate system only.
|
||||
Absolute = 0,
|
||||
// Relative transformations, allowed in both local and world coordinate system.
|
||||
Relative = 4,
|
||||
// For group selection, the transformation is performed as if the group made a single solid body.
|
||||
Joint = 0,
|
||||
// For group selection, the transformation is performed on each object independently.
|
||||
Independent = 8,
|
||||
|
||||
World_Relative_Joint = World | Relative | Joint,
|
||||
World_Relative_Independent = World | Relative | Independent,
|
||||
Instance_Absolute_Joint = Instance | Absolute | Joint,
|
||||
Instance_Absolute_Independent = Instance | Absolute | Independent,
|
||||
Instance_Relative_Joint = Instance | Relative | Joint,
|
||||
Instance_Relative_Independent = Instance | Relative | Independent,
|
||||
Local_Absolute_Joint = Local | Absolute | Joint,
|
||||
Local_Absolute_Independent = Local | Absolute | Independent,
|
||||
Local_Relative_Joint = Local | Relative | Joint,
|
||||
Local_Relative_Independent = Local | Relative | Independent,
|
||||
};
|
||||
|
||||
TransformationType() : m_value(World) {}
|
||||
TransformationType(Enum value) : m_value(value) {}
|
||||
TransformationType& operator=(Enum value) { m_value = value; return *this; }
|
||||
|
||||
Enum operator()() const { return m_value; }
|
||||
bool has(Enum v) const { return ((unsigned int)m_value & (unsigned int)v) != 0; }
|
||||
|
||||
void set_world() { this->remove(Instance); this->remove(Local); }
|
||||
void set_instance() { this->remove(Local); this->add(Instance); }
|
||||
void set_local() { this->remove(Instance); this->add(Local); }
|
||||
void set_absolute() { this->remove(Relative); }
|
||||
void set_relative() { this->add(Relative); }
|
||||
void set_joint() { this->remove(Independent); }
|
||||
void set_independent() { this->add(Independent); }
|
||||
|
||||
bool world() const { return !this->has(Instance) && !this->has(Local); }
|
||||
bool instance() const { return this->has(Instance); }
|
||||
bool local() const { return this->has(Local); }
|
||||
bool absolute() const { return !this->has(Relative); }
|
||||
bool relative() const { return this->has(Relative); }
|
||||
bool joint() const { return !this->has(Independent); }
|
||||
bool independent() const { return this->has(Independent); }
|
||||
|
||||
private:
|
||||
void add(Enum v) { m_value = Enum((unsigned int)m_value | (unsigned int)v); }
|
||||
void remove(Enum v) { m_value = Enum((unsigned int)m_value & (~(unsigned int)v)); }
|
||||
|
||||
Enum m_value;
|
||||
};
|
||||
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
} // namespace Slic3r
|
||||
} // namespace GUI
|
||||
|
||||
#endif // slic3r_GUI_Geometry_hpp_
|
@ -234,47 +234,47 @@ void ObjectLayers::UpdateAndShow(const bool show)
|
||||
|
||||
void ObjectLayers::msw_rescale()
|
||||
{
|
||||
m_bmp_delete.msw_rescale();
|
||||
m_bmp_add.msw_rescale();
|
||||
//m_bmp_delete.msw_rescale();
|
||||
//m_bmp_add.msw_rescale();
|
||||
|
||||
m_grid_sizer->SetHGap(wxGetApp().em_unit());
|
||||
//m_grid_sizer->SetHGap(wxGetApp().em_unit());
|
||||
|
||||
// rescale edit-boxes
|
||||
const int cells_cnt = m_grid_sizer->GetCols() * m_grid_sizer->GetEffectiveRowsCount();
|
||||
for (int i = 0; i < cells_cnt; ++i) {
|
||||
const wxSizerItem* item = m_grid_sizer->GetItem(i);
|
||||
if (item->IsWindow()) {
|
||||
LayerRangeEditor* editor = dynamic_cast<LayerRangeEditor*>(item->GetWindow());
|
||||
if (editor != nullptr)
|
||||
editor->msw_rescale();
|
||||
}
|
||||
else if (item->IsSizer()) // case when we have editor with buttons
|
||||
{
|
||||
wxSizerItem* e_item = item->GetSizer()->GetItem(size_t(0)); // editor
|
||||
if (e_item->IsWindow()) {
|
||||
LayerRangeEditor* editor = dynamic_cast<LayerRangeEditor*>(e_item->GetWindow());
|
||||
if (editor != nullptr)
|
||||
editor->msw_rescale();
|
||||
}
|
||||
//// rescale edit-boxes
|
||||
//const int cells_cnt = m_grid_sizer->GetCols() * m_grid_sizer->GetEffectiveRowsCount();
|
||||
//for (int i = 0; i < cells_cnt; ++i) {
|
||||
// const wxSizerItem* item = m_grid_sizer->GetItem(i);
|
||||
// if (item->IsWindow()) {
|
||||
// LayerRangeEditor* editor = dynamic_cast<LayerRangeEditor*>(item->GetWindow());
|
||||
// if (editor != nullptr)
|
||||
// editor->msw_rescale();
|
||||
// }
|
||||
// else if (item->IsSizer()) // case when we have editor with buttons
|
||||
// {
|
||||
// wxSizerItem* e_item = item->GetSizer()->GetItem(size_t(0)); // editor
|
||||
// if (e_item->IsWindow()) {
|
||||
// LayerRangeEditor* editor = dynamic_cast<LayerRangeEditor*>(e_item->GetWindow());
|
||||
// if (editor != nullptr)
|
||||
// editor->msw_rescale();
|
||||
// }
|
||||
|
||||
if (item->GetSizer()->GetItemCount() > 2) // if there are Add/Del buttons
|
||||
for (size_t btn : {2, 3}) { // del_btn, add_btn
|
||||
wxSizerItem* b_item = item->GetSizer()->GetItem(btn);
|
||||
if (b_item->IsWindow()) {
|
||||
auto button = dynamic_cast<PlusMinusButton*>(b_item->GetWindow());
|
||||
if (button != nullptr)
|
||||
button->msw_rescale();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
// if (item->GetSizer()->GetItemCount() > 2) // if there are Add/Del buttons
|
||||
// for (size_t btn : {2, 3}) { // del_btn, add_btn
|
||||
// wxSizerItem* b_item = item->GetSizer()->GetItem(btn);
|
||||
// if (b_item->IsWindow()) {
|
||||
// auto button = dynamic_cast<PlusMinusButton*>(b_item->GetWindow());
|
||||
// if (button != nullptr)
|
||||
// button->msw_rescale();
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
//}
|
||||
m_grid_sizer->Layout();
|
||||
}
|
||||
|
||||
void ObjectLayers::sys_color_changed()
|
||||
{
|
||||
m_bmp_delete.msw_rescale();
|
||||
m_bmp_add.msw_rescale();
|
||||
m_bmp_delete.sys_color_changed();
|
||||
m_bmp_add.sys_color_changed();
|
||||
|
||||
// rescale edit-boxes
|
||||
const int cells_cnt = m_grid_sizer->GetCols() * m_grid_sizer->GetEffectiveRowsCount();
|
||||
@ -286,7 +286,7 @@ void ObjectLayers::sys_color_changed()
|
||||
if (b_item->IsWindow()) {
|
||||
auto button = dynamic_cast<PlusMinusButton*>(b_item->GetWindow());
|
||||
if (button != nullptr)
|
||||
button->msw_rescale();
|
||||
button->sys_color_changed();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -973,12 +973,11 @@ void ObjectList::extruder_editing()
|
||||
if (!item || !(m_objects_model->GetItemType(item) & (itVolume | itObject)))
|
||||
return;
|
||||
|
||||
const int column_width = GetColumn(colExtruder)->GetWidth() + wxSystemSettings::GetMetric(wxSYS_VSCROLL_X) + 5;
|
||||
|
||||
wxPoint pos = this->get_mouse_position_in_control();
|
||||
wxSize size = wxSize(column_width, -1);
|
||||
pos.x = GetColumn(colName)->GetWidth() + GetColumn(colPrint)->GetWidth() + 5;
|
||||
pos.y -= GetTextExtent("m").y;
|
||||
wxRect rect = this->GetItemRect(item, GetColumn(colExtruder));
|
||||
wxPoint pos = rect.GetPosition();
|
||||
pos.y -= 4;
|
||||
wxSize size = rect.GetSize();
|
||||
size.SetWidth(size.GetWidth() + 8);
|
||||
|
||||
apply_extruder_selector(&m_extruder_editor, this, L("default"), pos, size);
|
||||
|
||||
@ -1541,9 +1540,13 @@ void ObjectList::load_modifier(const wxArrayString& input_files, ModelObject& mo
|
||||
const BoundingBoxf3 instance_bb = model_object.instance_bounding_box(instance_idx);
|
||||
|
||||
// First (any) GLVolume of the selected instance. They all share the same instance matrix.
|
||||
const GLVolume* v = selection.get_volume(*selection.get_volume_idxs().begin());
|
||||
const GLVolume* v = selection.get_first_volume();
|
||||
const Geometry::Transformation inst_transform = v->get_instance_transformation();
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const Transform3d inv_inst_transform = inst_transform.get_matrix_no_offset().inverse();
|
||||
#else
|
||||
const Transform3d inv_inst_transform = inst_transform.get_matrix(true).inverse();
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
const Vec3d instance_offset = v->get_instance_offset();
|
||||
|
||||
for (size_t i = 0; i < input_files.size(); ++i) {
|
||||
@ -1591,9 +1594,15 @@ void ObjectList::load_modifier(const wxArrayString& input_files, ModelObject& mo
|
||||
new_volume->source.mesh_offset = model.objects.front()->volumes.front()->source.mesh_offset;
|
||||
|
||||
if (from_galery) {
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
// Transform the new modifier to be aligned with the print bed.
|
||||
new_volume->set_transformation(v->get_instance_transformation().get_matrix_no_offset().inverse());
|
||||
const BoundingBoxf3 mesh_bb = new_volume->mesh().bounding_box();
|
||||
#else
|
||||
// Transform the new modifier to be aligned with the print bed.
|
||||
const BoundingBoxf3 mesh_bb = new_volume->mesh().bounding_box();
|
||||
new_volume->set_transformation(Geometry::Transformation::volume_to_bed_transformation(inst_transform, mesh_bb));
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
// Set the modifier position.
|
||||
// Translate the new modifier to be pickable: move to the left front corner of the instance's bounding box, lift to print bed.
|
||||
const Vec3d offset = Vec3d(instance_bb.max.x(), instance_bb.min.y(), instance_bb.min.z()) + 0.5 * mesh_bb.size() - instance_offset;
|
||||
@ -1661,17 +1670,27 @@ void ObjectList::load_generic_subobject(const std::string& type_name, const Mode
|
||||
ModelVolume *new_volume = model_object.add_volume(std::move(mesh), type);
|
||||
|
||||
// First (any) GLVolume of the selected instance. They all share the same instance matrix.
|
||||
const GLVolume* v = selection.get_volume(*selection.get_volume_idxs().begin());
|
||||
const GLVolume* v = selection.get_first_volume();
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
// Transform the new modifier to be aligned with the print bed.
|
||||
const BoundingBoxf3 mesh_bb = new_volume->mesh().bounding_box();
|
||||
new_volume->set_transformation(v->get_instance_transformation().get_matrix_no_offset().inverse());
|
||||
const BoundingBoxf3 mesh_bb = new_volume->mesh().bounding_box();
|
||||
#else
|
||||
// Transform the new modifier to be aligned with the print bed.
|
||||
const BoundingBoxf3 mesh_bb = new_volume->mesh().bounding_box();
|
||||
new_volume->set_transformation(Geometry::Transformation::volume_to_bed_transformation(v->get_instance_transformation(), mesh_bb));
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
// Set the modifier position.
|
||||
auto offset = (type_name == "Slab") ?
|
||||
// Slab: Lift to print bed
|
||||
Vec3d(0., 0., 0.5 * mesh_bb.size().z() + instance_bb.min.z() - v->get_instance_offset().z()) :
|
||||
// Translate the new modifier to be pickable: move to the left front corner of the instance's bounding box, lift to print bed.
|
||||
Vec3d(instance_bb.max.x(), instance_bb.min.y(), instance_bb.min.z()) + 0.5 * mesh_bb.size() - v->get_instance_offset();
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
new_volume->set_offset(v->get_instance_transformation().get_matrix_no_offset().inverse() * offset);
|
||||
#else
|
||||
new_volume->set_offset(v->get_instance_transformation().get_matrix(true).inverse() * offset);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
const wxString name = _L("Generic") + "-" + _(type_name);
|
||||
new_volume->name = into_u8(name);
|
||||
@ -2444,6 +2463,21 @@ bool ObjectList::can_merge_to_single_object() const
|
||||
return (*m_objects)[obj_idx]->volumes.size() > 1;
|
||||
}
|
||||
|
||||
wxPoint ObjectList::get_mouse_position_in_control() const
|
||||
{
|
||||
wxPoint pt = wxGetMousePosition() - this->GetScreenPosition();
|
||||
|
||||
#ifdef __APPLE__
|
||||
// Workaround for OSX. From wxWidgets 3.1.6 Hittest doesn't respect to the header of wxDataViewCtrl
|
||||
if (wxDataViewItem top_item = this->GetTopItem(); top_item.IsOk()) {
|
||||
auto rect = this->GetItemRect(top_item, this->GetColumn(0));
|
||||
pt.y -= rect.y;
|
||||
}
|
||||
#endif // __APPLE__
|
||||
|
||||
return pt;
|
||||
}
|
||||
|
||||
// NO_PARAMETERS function call means that changed object index will be determine from Selection()
|
||||
void ObjectList::changed_object(const int obj_idx/* = -1*/) const
|
||||
{
|
||||
@ -2627,8 +2661,14 @@ void ObjectList::part_selection_changed()
|
||||
Sidebar& panel = wxGetApp().sidebar();
|
||||
panel.Freeze();
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const ManipulationEditor* const editor = wxGetApp().obj_manipul()->get_focused_editor();
|
||||
const std::string opt_key = (editor != nullptr) ? editor->get_full_opt_name() : "";
|
||||
wxGetApp().plater()->canvas3D()->handle_sidebar_focus_event(opt_key, !opt_key.empty());
|
||||
#else
|
||||
wxGetApp().plater()->canvas3D()->handle_sidebar_focus_event("", false);
|
||||
wxGetApp().plater()->canvas3D()->enable_moving(enable_manipulation);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
wxGetApp().plater()->canvas3D()->enable_moving(enable_manipulation); // ysFIXME
|
||||
wxGetApp().obj_manipul() ->UpdateAndShow(update_and_show_manipulations);
|
||||
wxGetApp().obj_settings()->UpdateAndShow(update_and_show_settings);
|
||||
wxGetApp().obj_layers() ->UpdateAndShow(update_and_show_layers);
|
||||
@ -3373,8 +3413,12 @@ void ObjectList::update_selections()
|
||||
return;
|
||||
sels.Add(m_objects_model->GetItemById(selection.get_object_idx()));
|
||||
}
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
else if (selection.is_single_volume_or_modifier()) {
|
||||
#else
|
||||
else if (selection.is_single_volume() || selection.is_any_modifier()) {
|
||||
const auto gl_vol = selection.get_volume(*selection.get_volume_idxs().begin());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
const auto gl_vol = selection.get_first_volume();
|
||||
if (m_objects_model->GetVolumeIdByItem(m_objects_model->GetParent(item)) == gl_vol->volume_idx())
|
||||
return;
|
||||
}
|
||||
@ -4388,9 +4432,6 @@ void ObjectList::msw_rescale()
|
||||
GetColumn(colExtruder)->SetWidth( 8 * em);
|
||||
GetColumn(colEditing )->SetWidth( 3 * em);
|
||||
|
||||
// rescale/update existing items with bitmaps
|
||||
m_objects_model->Rescale();
|
||||
|
||||
Layout();
|
||||
}
|
||||
|
||||
@ -4398,7 +4439,10 @@ void ObjectList::sys_color_changed()
|
||||
{
|
||||
wxGetApp().UpdateDVCDarkUI(this, true);
|
||||
|
||||
msw_rescale();
|
||||
// update existing items with bitmaps
|
||||
m_objects_model->UpdateBitmaps();
|
||||
|
||||
Layout();
|
||||
}
|
||||
|
||||
void ObjectList::ItemValueChanged(wxDataViewEvent &event)
|
||||
|
@ -280,7 +280,7 @@ public:
|
||||
bool can_merge_to_multipart_object() const;
|
||||
bool can_merge_to_single_object() const;
|
||||
|
||||
wxPoint get_mouse_position_in_control() const { return wxGetMousePosition() - this->GetScreenPosition(); }
|
||||
wxPoint get_mouse_position_in_control() const;
|
||||
wxBoxSizer* get_sizer() {return m_sizer;}
|
||||
int get_selected_obj_idx() const;
|
||||
ModelConfig& get_item_config(const wxDataViewItem& item) const;
|
||||
|
@ -52,10 +52,17 @@ static choice_ctrl* create_word_local_combo(wxWindow *parent)
|
||||
temp->SetFont(Slic3r::GUI::wxGetApp().normal_font());
|
||||
if (!wxOSX) temp->SetBackgroundStyle(wxBG_STYLE_PAINT);
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
temp->Append(ObjectManipulation::coordinate_type_str(ECoordinatesType::World));
|
||||
temp->Append(ObjectManipulation::coordinate_type_str(ECoordinatesType::Instance));
|
||||
temp->Append(ObjectManipulation::coordinate_type_str(ECoordinatesType::Local));
|
||||
temp->Select((int)ECoordinatesType::World);
|
||||
#else
|
||||
temp->Append(_L("World coordinates"));
|
||||
temp->Append(_L("Local coordinates"));
|
||||
temp->SetSelection(0);
|
||||
temp->SetValue(temp->GetString(0));
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
temp->SetToolTip(_L("Select coordinate space, in which the transformation will be performed."));
|
||||
return temp;
|
||||
@ -81,8 +88,14 @@ void msw_rescale_word_local_combo(choice_ctrl* combo)
|
||||
// Set rescaled size
|
||||
combo->SetSize(size);
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
combo->Append(ObjectManipulation::coordinate_type_str(ECoordinatesType::World));
|
||||
combo->Append(ObjectManipulation::coordinate_type_str(ECoordinatesType::Instance));
|
||||
combo->Append(ObjectManipulation::coordinate_type_str(ECoordinatesType::Local));
|
||||
#else
|
||||
combo->Append(_L("World coordinates"));
|
||||
combo->Append(_L("Local coordinates"));
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
combo->SetValue(selection);
|
||||
#else
|
||||
@ -101,6 +114,7 @@ static void set_font_and_background_style(wxWindow* win, const wxFont& font)
|
||||
|
||||
static const wxString axes_color_text[] = { "#990000", "#009900", "#000099" };
|
||||
static const wxString axes_color_back[] = { "#f5dcdc", "#dcf5dc", "#dcdcf5" };
|
||||
|
||||
ObjectManipulation::ObjectManipulation(wxWindow* parent) :
|
||||
OG_Settings(parent, true)
|
||||
{
|
||||
@ -112,7 +126,7 @@ ObjectManipulation::ObjectManipulation(wxWindow* parent) :
|
||||
// Load bitmaps to be used for the mirroring buttons:
|
||||
m_mirror_bitmap_on = ScalableBitmap(parent, "mirroring_on");
|
||||
m_mirror_bitmap_off = ScalableBitmap(parent, "mirroring_off");
|
||||
m_mirror_bitmap_hidden = ScalableBitmap(parent, "mirroring_transparent.png");
|
||||
m_mirror_bitmap_hidden = ScalableBitmap(parent, "mirroring_transparent");
|
||||
|
||||
const int border = wxOSX ? 0 : 4;
|
||||
const int em = wxGetApp().em_unit();
|
||||
@ -157,8 +171,12 @@ ObjectManipulation::ObjectManipulation(wxWindow* parent) :
|
||||
// Add world local combobox
|
||||
m_word_local_combo = create_word_local_combo(parent);
|
||||
m_word_local_combo->Bind(wxEVT_COMBOBOX, ([this](wxCommandEvent& evt) {
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
this->set_coordinates_type(evt.GetString());
|
||||
#else
|
||||
this->set_world_coordinates(evt.GetSelection() != 1);
|
||||
}), m_word_local_combo->GetId());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}), m_word_local_combo->GetId());
|
||||
|
||||
// Small trick to correct layouting in different view_mode :
|
||||
// Show empty string of a same height as a m_word_local_combo, when m_word_local_combo is hidden
|
||||
@ -264,8 +282,12 @@ ObjectManipulation::ObjectManipulation(wxWindow* parent) :
|
||||
GLCanvas3D* canvas = wxGetApp().plater()->canvas3D();
|
||||
Selection& selection = canvas->get_selection();
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
if (selection.is_single_volume_or_modifier()) {
|
||||
#else
|
||||
if (selection.is_single_volume() || selection.is_single_modifier()) {
|
||||
GLVolume* volume = const_cast<GLVolume*>(selection.get_volume(*selection.get_volume_idxs().begin()));
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
GLVolume* volume = const_cast<GLVolume*>(selection.get_first_volume());
|
||||
volume->set_volume_mirror(axis, -volume->get_volume_mirror(axis));
|
||||
}
|
||||
else if (selection.is_single_full_instance()) {
|
||||
@ -278,7 +300,7 @@ ObjectManipulation::ObjectManipulation(wxWindow* parent) :
|
||||
return;
|
||||
|
||||
// Update mirroring at the GLVolumes.
|
||||
selection.synchronize_unselected_instances(Selection::SYNC_ROTATION_GENERAL);
|
||||
selection.synchronize_unselected_instances(Selection::SyncRotationType::GENERAL);
|
||||
selection.synchronize_unselected_volumes();
|
||||
// Copy mirroring values from GLVolumes into Model (ModelInstance / ModelVolume), trigger background processing.
|
||||
canvas->do_mirror(L("Set Mirror"));
|
||||
@ -327,28 +349,60 @@ ObjectManipulation::ObjectManipulation(wxWindow* parent) :
|
||||
GLCanvas3D* canvas = wxGetApp().plater()->canvas3D();
|
||||
Selection& selection = canvas->get_selection();
|
||||
|
||||
if (selection.is_single_volume() || selection.is_single_modifier()) {
|
||||
const GLVolume* volume = selection.get_volume(*selection.get_volume_idxs().begin());
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
if (selection.is_single_volume_or_modifier()) {
|
||||
const GLVolume* volume = selection.get_first_volume();
|
||||
const double min_z = get_volume_min_z(*volume);
|
||||
if (!is_world_coordinates()) {
|
||||
const Vec3d diff = m_cache.position - volume->get_instance_transformation().get_matrix_no_offset().inverse() * (min_z * Vec3d::UnitZ());
|
||||
|
||||
const Geometry::Transformation& instance_trafo = volume->get_instance_transformation();
|
||||
const Vec3d diff = m_cache.position - instance_trafo.get_matrix(true).inverse() * Vec3d(0., 0., get_volume_min_z(*volume));
|
||||
Plater::TakeSnapshot snapshot(wxGetApp().plater(), _L("Drop to bed"));
|
||||
change_position_value(0, diff.x());
|
||||
change_position_value(1, diff.y());
|
||||
change_position_value(2, diff.z());
|
||||
}
|
||||
else {
|
||||
Plater::TakeSnapshot snapshot(wxGetApp().plater(), _L("Drop to bed"));
|
||||
change_position_value(2, m_cache.position.z() - min_z);
|
||||
}
|
||||
#else
|
||||
if (selection.is_single_volume() || selection.is_single_modifier()) {
|
||||
const GLVolume* volume = selection.get_first_volume();
|
||||
const Vec3d diff = m_cache.position - volume->get_instance_transformation().get_matrix(true).inverse() * (get_volume_min_z(*volume) * Vec3d::UnitZ());
|
||||
|
||||
Plater::TakeSnapshot snapshot(wxGetApp().plater(), _L("Drop to bed"));
|
||||
change_position_value(0, diff.x());
|
||||
change_position_value(1, diff.y());
|
||||
change_position_value(2, diff.z());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
else if (selection.is_single_full_instance()) {
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const double min_z = selection.get_scaled_instance_bounding_box().min.z();
|
||||
if (!is_world_coordinates()) {
|
||||
const GLVolume* volume = selection.get_first_volume();
|
||||
const Vec3d diff = m_cache.position - volume->get_instance_transformation().get_matrix_no_offset().inverse() * (min_z * Vec3d::UnitZ());
|
||||
|
||||
Plater::TakeSnapshot snapshot(wxGetApp().plater(), _L("Drop to bed"));
|
||||
change_position_value(0, diff.x());
|
||||
change_position_value(1, diff.y());
|
||||
change_position_value(2, diff.z());
|
||||
}
|
||||
else {
|
||||
#else
|
||||
const ModelObjectPtrs& objects = wxGetApp().model().objects;
|
||||
const int idx = selection.get_object_idx();
|
||||
if (0 <= idx && idx < static_cast<int>(objects.size())) {
|
||||
const ModelObject* mo = wxGetApp().model().objects[idx];
|
||||
const double min_z = mo->bounding_box().min.z();
|
||||
if (std::abs(min_z) > SINKING_Z_THRESHOLD) {
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
Plater::TakeSnapshot snapshot(wxGetApp().plater(), _L("Drop to bed"));
|
||||
change_position_value(2, m_cache.position.z() - min_z);
|
||||
}
|
||||
#if !ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
#endif // !ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
});
|
||||
editors_grid_sizer->Add(m_drop_to_bed_button);
|
||||
@ -365,21 +419,22 @@ ObjectManipulation::ObjectManipulation(wxWindow* parent) :
|
||||
GLCanvas3D* canvas = wxGetApp().plater()->canvas3D();
|
||||
Selection& selection = canvas->get_selection();
|
||||
|
||||
if (selection.is_single_volume() || selection.is_single_modifier()) {
|
||||
GLVolume* volume = const_cast<GLVolume*>(selection.get_volume(*selection.get_volume_idxs().begin()));
|
||||
volume->set_volume_rotation(Vec3d::Zero());
|
||||
}
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
if (selection.is_single_volume_or_modifier())
|
||||
#else
|
||||
if (selection.is_single_volume() || selection.is_single_modifier())
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
const_cast<GLVolume*>(selection.get_first_volume())->set_volume_rotation(Vec3d::Zero());
|
||||
else if (selection.is_single_full_instance()) {
|
||||
for (unsigned int idx : selection.get_volume_idxs()) {
|
||||
GLVolume* volume = const_cast<GLVolume*>(selection.get_volume(idx));
|
||||
volume->set_instance_rotation(Vec3d::Zero());
|
||||
const_cast<GLVolume*>(selection.get_volume(idx))->set_instance_rotation(Vec3d::Zero());
|
||||
}
|
||||
}
|
||||
else
|
||||
return;
|
||||
|
||||
// Update rotation at the GLVolumes.
|
||||
selection.synchronize_unselected_instances(Selection::SYNC_ROTATION_GENERAL);
|
||||
selection.synchronize_unselected_instances(Selection::SyncRotationType::GENERAL);
|
||||
selection.synchronize_unselected_volumes();
|
||||
// Copy rotation values from GLVolumes into Model (ModelInstance / ModelVolume), trigger background processing.
|
||||
canvas->do_rotate(L("Reset Rotation"));
|
||||
@ -397,11 +452,29 @@ ObjectManipulation::ObjectManipulation(wxWindow* parent) :
|
||||
m_reset_scale_button = new ScalableButton(parent, wxID_ANY, ScalableBitmap(parent, "undo"));
|
||||
m_reset_scale_button->SetToolTip(_L("Reset scale"));
|
||||
m_reset_scale_button->Bind(wxEVT_BUTTON, [this](wxCommandEvent& e) {
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
GLCanvas3D* canvas = wxGetApp().plater()->canvas3D();
|
||||
Selection& selection = canvas->get_selection();
|
||||
if (selection.is_single_volume_or_modifier())
|
||||
const_cast<GLVolume*>(selection.get_first_volume())->set_volume_scaling_factor(Vec3d::Ones());
|
||||
else if (selection.is_single_full_instance()) {
|
||||
for (unsigned int idx : selection.get_volume_idxs()) {
|
||||
const_cast<GLVolume*>(selection.get_volume(idx))->set_instance_scaling_factor(Vec3d::Ones());
|
||||
}
|
||||
}
|
||||
else
|
||||
return;
|
||||
|
||||
canvas->do_scale(L("Reset scale"));
|
||||
|
||||
UpdateAndShow(true);
|
||||
#else
|
||||
Plater::TakeSnapshot snapshot(wxGetApp().plater(), _L("Reset scale"));
|
||||
change_scale_value(0, 100.);
|
||||
change_scale_value(1, 100.);
|
||||
change_scale_value(2, 100.);
|
||||
});
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
});
|
||||
editors_grid_sizer->Add(m_reset_scale_button);
|
||||
|
||||
for (size_t axis_idx = 0; axis_idx < sizeof(axes); axis_idx++)
|
||||
@ -411,6 +484,25 @@ ObjectManipulation::ObjectManipulation(wxWindow* parent) :
|
||||
|
||||
m_main_grid_sizer->Add(editors_grid_sizer, 1, wxEXPAND);
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
m_skew_label = new wxStaticText(parent, wxID_ANY, _L("Skew"));
|
||||
m_main_grid_sizer->Add(m_skew_label, 1, wxEXPAND);
|
||||
|
||||
m_reset_skew_button = new ScalableButton(parent, wxID_ANY, ScalableBitmap(parent, "undo"));
|
||||
m_reset_skew_button->SetToolTip(_L("Reset skew"));
|
||||
m_reset_skew_button->Bind(wxEVT_BUTTON, [this](wxCommandEvent& e) {
|
||||
GLCanvas3D* canvas = wxGetApp().plater()->canvas3D();
|
||||
Selection& selection = canvas->get_selection();
|
||||
if (selection.is_single_full_instance() || selection.is_single_volume_or_modifier()) {
|
||||
selection.setup_cache();
|
||||
selection.reset_skew();
|
||||
canvas->do_reset_skew(L("Reset skew"));
|
||||
UpdateAndShow(true);
|
||||
}
|
||||
});
|
||||
m_main_grid_sizer->Add(m_reset_skew_button);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
m_check_inch = new wxCheckBox(parent, wxID_ANY, _L("Inches"));
|
||||
m_check_inch->SetFont(wxGetApp().normal_font());
|
||||
|
||||
@ -444,8 +536,27 @@ void ObjectManipulation::Show(const bool show)
|
||||
|
||||
if (show) {
|
||||
// Show the "World Coordinates" / "Local Coordintes" Combo in Advanced / Expert mode only.
|
||||
bool show_world_local_combo = wxGetApp().plater()->canvas3D()->get_selection().is_single_full_instance() && wxGetApp().get_mode() != comSimple;
|
||||
m_word_local_combo->Show(show_world_local_combo);
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const Selection& selection = wxGetApp().plater()->canvas3D()->get_selection();
|
||||
bool show_world_local_combo = wxGetApp().get_mode() != comSimple && (selection.is_single_full_instance() || selection.is_single_volume_or_modifier());
|
||||
if (selection.is_single_volume_or_modifier() && m_word_local_combo->GetCount() < 3) {
|
||||
#ifdef __linux__
|
||||
m_word_local_combo->Insert(coordinate_type_str(ECoordinatesType::Instance), 1);
|
||||
#else
|
||||
m_word_local_combo->Insert(coordinate_type_str(ECoordinatesType::Instance), wxNullBitmap, 1);
|
||||
#endif // __linux__
|
||||
m_word_local_combo->Select((int)ECoordinatesType::World);
|
||||
this->set_coordinates_type(m_word_local_combo->GetString(m_word_local_combo->GetSelection()));
|
||||
}
|
||||
else if (selection.is_single_full_instance() && m_word_local_combo->GetCount() > 2) {
|
||||
m_word_local_combo->Delete(1);
|
||||
m_word_local_combo->Select((int)ECoordinatesType::World);
|
||||
this->set_coordinates_type(m_word_local_combo->GetString(m_word_local_combo->GetSelection()));
|
||||
}
|
||||
#else
|
||||
bool show_world_local_combo = wxGetApp().plater()->canvas3D()->get_selection().is_single_full_instance() && wxGetApp().get_mode() != comSimple;
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
m_word_local_combo->Show(show_world_local_combo);
|
||||
m_empty_str->Show(!show_world_local_combo);
|
||||
}
|
||||
}
|
||||
@ -505,8 +616,7 @@ void ObjectManipulation::update_ui_from_settings()
|
||||
}
|
||||
m_check_inch->SetValue(m_imperial_units);
|
||||
|
||||
if (m_use_colors != (wxGetApp().app_config->get("color_mapinulation_panel") == "1"))
|
||||
{
|
||||
if (m_use_colors != (wxGetApp().app_config->get("color_mapinulation_panel") == "1")) {
|
||||
m_use_colors = wxGetApp().app_config->get("color_mapinulation_panel") == "1";
|
||||
// update colors for edit-boxes
|
||||
int axis_id = 0;
|
||||
@ -538,33 +648,49 @@ void ObjectManipulation::update_settings_value(const Selection& selection)
|
||||
m_new_rotate_label_string = L("Rotation");
|
||||
m_new_scale_label_string = L("Scale factors");
|
||||
|
||||
#if !ENABLE_WORLD_COORDINATE
|
||||
if (wxGetApp().get_mode() == comSimple)
|
||||
m_world_coordinates = true;
|
||||
#endif // !ENABLE_WORLD_COORDINATE
|
||||
|
||||
ObjectList* obj_list = wxGetApp().obj_list();
|
||||
if (selection.is_single_full_instance()) {
|
||||
// all volumes in the selection belongs to the same instance, any of them contains the needed instance data, so we take the first one
|
||||
const GLVolume* volume = selection.get_volume(*selection.get_volume_idxs().begin());
|
||||
const GLVolume* volume = selection.get_first_volume();
|
||||
#if !ENABLE_WORLD_COORDINATE
|
||||
m_new_position = volume->get_instance_offset();
|
||||
|
||||
// Verify whether the instance rotation is multiples of 90 degrees, so that the scaling in world coordinates is possible.
|
||||
if (m_world_coordinates && ! m_uniform_scale &&
|
||||
if (m_world_coordinates && ! m_uniform_scale &&
|
||||
! Geometry::is_rotation_ninety_degrees(volume->get_instance_rotation())) {
|
||||
// Manipulating an instance in the world coordinate system, rotation is not multiples of ninety degrees, therefore enforce uniform scaling.
|
||||
m_uniform_scale = true;
|
||||
m_lock_bnt->SetLock(true);
|
||||
}
|
||||
#endif // !ENABLE_WORLD_COORDINATE
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
if (is_world_coordinates()) {
|
||||
m_new_position = volume->get_instance_offset();
|
||||
#else
|
||||
if (m_world_coordinates) {
|
||||
m_new_rotate_label_string = L("Rotate");
|
||||
m_new_rotation = Vec3d::Zero();
|
||||
m_new_size = selection.get_scaled_instance_bounding_box().size();
|
||||
m_new_scale = m_new_size.cwiseProduct(selection.get_unscaled_instance_bounding_box().size().cwiseInverse()) * 100.;
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
m_new_rotate_label_string = L("Rotate");
|
||||
m_new_rotation = Vec3d::Zero();
|
||||
m_new_size = selection.get_scaled_instance_bounding_box().size();
|
||||
m_new_scale = m_new_size.cwiseQuotient(selection.get_unscaled_instance_bounding_box().size()) * 100.0;
|
||||
}
|
||||
else {
|
||||
m_new_rotation = volume->get_instance_rotation() * (180. / M_PI);
|
||||
m_new_size = volume->get_instance_scaling_factor().cwiseProduct(wxGetApp().model().objects[volume->object_idx()]->raw_mesh_bounding_box().size());
|
||||
m_new_scale = volume->get_instance_scaling_factor() * 100.;
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
m_new_move_label_string = L("Translate");
|
||||
m_new_rotate_label_string = L("Rotate");
|
||||
m_new_position = Vec3d::Zero();
|
||||
m_new_rotation = Vec3d::Zero();
|
||||
#else
|
||||
m_new_rotation = volume->get_instance_rotation() * (180.0 / M_PI);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
m_new_size = volume->get_instance_scaling_factor().cwiseProduct(wxGetApp().model().objects[volume->object_idx()]->raw_mesh_bounding_box().size());
|
||||
m_new_scale = volume->get_instance_scaling_factor() * 100.0;
|
||||
}
|
||||
|
||||
m_new_enabled = true;
|
||||
@ -573,19 +699,52 @@ void ObjectManipulation::update_settings_value(const Selection& selection)
|
||||
const BoundingBoxf3& box = selection.get_bounding_box();
|
||||
m_new_position = box.center();
|
||||
m_new_rotation = Vec3d::Zero();
|
||||
m_new_scale = Vec3d(100., 100., 100.);
|
||||
m_new_scale = Vec3d(100.0, 100.0, 100.0);
|
||||
m_new_size = box.size();
|
||||
m_new_rotate_label_string = L("Rotate");
|
||||
m_new_scale_label_string = L("Scale");
|
||||
m_new_enabled = true;
|
||||
}
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
else if (selection.is_single_volume_or_modifier()) {
|
||||
#else
|
||||
else if (selection.is_single_modifier() || selection.is_single_volume()) {
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
// the selection contains a single volume
|
||||
const GLVolume* volume = selection.get_volume(*selection.get_volume_idxs().begin());
|
||||
const GLVolume* volume = selection.get_first_volume();
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
if (is_world_coordinates()) {
|
||||
const Geometry::Transformation trafo(volume->world_matrix());
|
||||
|
||||
const Vec3d& offset = trafo.get_offset();
|
||||
|
||||
m_new_position = offset;
|
||||
m_new_rotate_label_string = L("Rotate");
|
||||
m_new_rotation = Vec3d::Zero();
|
||||
m_new_size = volume->transformed_convex_hull_bounding_box(trafo.get_matrix()).size();
|
||||
m_new_scale = m_new_size.cwiseQuotient(volume->transformed_convex_hull_bounding_box(volume->get_instance_transformation().get_matrix() * volume->get_volume_transformation().get_matrix_no_scaling_factor()).size()) * 100.0;
|
||||
}
|
||||
else if (is_local_coordinates()) {
|
||||
m_new_move_label_string = L("Translate");
|
||||
m_new_rotate_label_string = L("Rotate");
|
||||
m_new_position = Vec3d::Zero();
|
||||
m_new_rotation = Vec3d::Zero();
|
||||
m_new_scale = volume->get_volume_scaling_factor() * 100.0;
|
||||
m_new_size = volume->get_volume_scaling_factor().cwiseProduct(volume->bounding_box().size());
|
||||
}
|
||||
else {
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
m_new_position = volume->get_volume_offset();
|
||||
m_new_rotation = volume->get_volume_rotation() * (180. / M_PI);
|
||||
m_new_scale = volume->get_volume_scaling_factor() * 100.;
|
||||
m_new_size = volume->get_instance_scaling_factor().cwiseProduct(volume->get_volume_scaling_factor().cwiseProduct(volume->bounding_box().size()));
|
||||
m_new_rotate_label_string = L("Rotate");
|
||||
m_new_rotation = Vec3d::Zero();
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
m_new_size = volume->transformed_convex_hull_bounding_box(volume->get_volume_transformation().get_matrix()).size();
|
||||
m_new_scale = m_new_size.cwiseQuotient(volume->transformed_convex_hull_bounding_box(volume->get_volume_transformation().get_matrix_no_scaling_factor()).size()) * 100.0;
|
||||
}
|
||||
#else
|
||||
m_new_scale = volume->get_volume_scaling_factor() * 100.0;
|
||||
m_new_size = volume->get_instance_scaling_factor().cwiseProduct(volume->get_volume_scaling_factor().cwiseProduct(volume->bounding_box().size()));
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
m_new_enabled = true;
|
||||
}
|
||||
else if (obj_list->multiple_selection() || obj_list->is_selected(itInstanceRoot)) {
|
||||
@ -651,22 +810,26 @@ void ObjectManipulation::update_if_dirty()
|
||||
update(m_cache.rotation, m_cache.rotation_rounded, meRotation, m_new_rotation);
|
||||
}
|
||||
|
||||
#if !ENABLE_WORLD_COORDINATE
|
||||
if (selection.requires_uniform_scale()) {
|
||||
m_lock_bnt->SetLock(true);
|
||||
m_lock_bnt->SetToolTip(_L("You cannot use non-uniform scaling mode for multiple objects/parts selection"));
|
||||
m_lock_bnt->disable();
|
||||
}
|
||||
else {
|
||||
#endif // !ENABLE_WORLD_COORDINATE
|
||||
m_lock_bnt->SetLock(m_uniform_scale);
|
||||
m_lock_bnt->SetToolTip(wxEmptyString);
|
||||
m_lock_bnt->enable();
|
||||
#if !ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
{
|
||||
{
|
||||
int new_selection = m_world_coordinates ? 0 : 1;
|
||||
if (m_word_local_combo->GetSelection() != new_selection)
|
||||
m_word_local_combo->SetSelection(new_selection);
|
||||
}
|
||||
#endif // !ENABLE_WORLD_COORDINATE
|
||||
|
||||
if (m_new_enabled)
|
||||
m_og->enable();
|
||||
@ -693,29 +856,75 @@ void ObjectManipulation::update_reset_buttons_visibility()
|
||||
bool show_rotation = false;
|
||||
bool show_scale = false;
|
||||
bool show_drop_to_bed = false;
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
bool show_skew = false;
|
||||
|
||||
if (selection.is_single_full_instance() || selection.is_single_volume_or_modifier()) {
|
||||
const double min_z = selection.is_single_full_instance() ? selection.get_scaled_instance_bounding_box().min.z() :
|
||||
get_volume_min_z(*selection.get_first_volume());
|
||||
|
||||
show_drop_to_bed = std::abs(min_z) > EPSILON;
|
||||
const GLVolume* volume = selection.get_first_volume();
|
||||
Transform3d rotation = Transform3d::Identity();
|
||||
Transform3d scale = Transform3d::Identity();
|
||||
Geometry::Transformation skew;
|
||||
#else
|
||||
if (selection.is_single_full_instance() || selection.is_single_modifier() || selection.is_single_volume()) {
|
||||
const GLVolume* volume = selection.get_volume(*selection.get_volume_idxs().begin());
|
||||
const GLVolume* volume = selection.get_first_volume();
|
||||
Vec3d rotation;
|
||||
Vec3d scale;
|
||||
double min_z = 0.;
|
||||
double min_z = 0.0;
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
if (selection.is_single_full_instance()) {
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const Geometry::Transformation& trafo = volume->get_instance_transformation();
|
||||
rotation = trafo.get_rotation_matrix();
|
||||
scale = trafo.get_scaling_factor_matrix();
|
||||
const Selection::IndicesList& idxs = selection.get_volume_idxs();
|
||||
for (unsigned int id : idxs) {
|
||||
const Geometry::Transformation world_trafo(selection.get_volume(id)->world_matrix());
|
||||
if (world_trafo.has_skew()) {
|
||||
skew = world_trafo;
|
||||
break;
|
||||
}
|
||||
}
|
||||
#else
|
||||
rotation = volume->get_instance_rotation();
|
||||
scale = volume->get_instance_scaling_factor();
|
||||
min_z = wxGetApp().model().objects[volume->composite_id.object_id]->bounding_box().min.z();
|
||||
min_z = selection.get_scaled_instance_bounding_box().min.z();
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
else {
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const Geometry::Transformation& trafo = volume->get_volume_transformation();
|
||||
rotation = trafo.get_rotation_matrix();
|
||||
scale = trafo.get_scaling_factor_matrix();
|
||||
const Geometry::Transformation world_trafo(volume->world_matrix());
|
||||
if (world_trafo.has_skew())
|
||||
skew = world_trafo;
|
||||
#else
|
||||
rotation = volume->get_volume_rotation();
|
||||
scale = volume->get_volume_scaling_factor();
|
||||
min_z = get_volume_min_z(*volume);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
show_rotation = !rotation.isApprox(Transform3d::Identity());
|
||||
show_scale = !scale.isApprox(Transform3d::Identity());
|
||||
show_skew = skew.has_skew();
|
||||
#else
|
||||
show_rotation = !rotation.isApprox(Vec3d::Zero());
|
||||
show_scale = !scale.isApprox(Vec3d::Ones());
|
||||
show_drop_to_bed = std::abs(min_z) > SINKING_Z_THRESHOLD;
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
wxGetApp().CallAfter([this, show_rotation, show_scale, show_drop_to_bed, show_skew] {
|
||||
#else
|
||||
wxGetApp().CallAfter([this, show_rotation, show_scale, show_drop_to_bed] {
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
// There is a case (under OSX), when this function is called after the Manipulation panel is hidden
|
||||
// So, let check if Manipulation panel is still shown for this moment
|
||||
if (!this->IsShown())
|
||||
@ -723,6 +932,10 @@ void ObjectManipulation::update_reset_buttons_visibility()
|
||||
m_reset_rotation_button->Show(show_rotation);
|
||||
m_reset_scale_button->Show(show_scale);
|
||||
m_drop_to_bed_button->Show(show_drop_to_bed);
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
m_reset_skew_button->Show(show_skew);
|
||||
m_skew_label->Show(show_skew);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
// Because of CallAfter we need to layout sidebar after Show/hide of reset buttons one more time
|
||||
Sidebar& panel = wxGetApp().sidebar();
|
||||
@ -742,9 +955,17 @@ void ObjectManipulation::update_mirror_buttons_visibility()
|
||||
Selection& selection = canvas->get_selection();
|
||||
std::array<MirrorButtonState, 3> new_states = {mbHidden, mbHidden, mbHidden};
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
if (is_local_coordinates()) {
|
||||
#else
|
||||
if (!m_world_coordinates) {
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
if (selection.is_single_full_instance() || selection.is_single_volume_or_modifier()) {
|
||||
#else
|
||||
if (selection.is_single_full_instance() || selection.is_single_modifier() || selection.is_single_volume()) {
|
||||
const GLVolume* volume = selection.get_volume(*selection.get_volume_idxs().begin());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
const GLVolume* volume = selection.get_first_volume();
|
||||
Vec3d mirror;
|
||||
|
||||
if (selection.is_single_full_instance())
|
||||
@ -804,10 +1025,23 @@ void ObjectManipulation::update_warning_icon_state(const MeshErrorsInfo& warning
|
||||
m_manifold_warning_bmp = ScalableBitmap(m_parent, warning_icon_name);
|
||||
const wxString& tooltip = warning.tooltip;
|
||||
m_fix_throught_netfab_bitmap->SetBitmap(tooltip.IsEmpty() ? wxNullBitmap : m_manifold_warning_bmp.bmp());
|
||||
m_fix_throught_netfab_bitmap->SetMinSize(tooltip.IsEmpty() ? wxSize(0,0) : m_manifold_warning_bmp.bmp().GetSize());
|
||||
m_fix_throught_netfab_bitmap->SetMinSize(tooltip.IsEmpty() ? wxSize(0,0) : m_manifold_warning_bmp.GetSize());
|
||||
m_fix_throught_netfab_bitmap->SetToolTip(tooltip);
|
||||
}
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
wxString ObjectManipulation::coordinate_type_str(ECoordinatesType type)
|
||||
{
|
||||
switch (type)
|
||||
{
|
||||
case ECoordinatesType::World: { return _L("World coordinates"); }
|
||||
case ECoordinatesType::Instance: { return _L("Instance coordinates"); }
|
||||
case ECoordinatesType::Local: { return _L("Local coordinates"); }
|
||||
default: { assert(false); return _L("Unknown"); }
|
||||
}
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void ObjectManipulation::reset_settings_value()
|
||||
{
|
||||
m_new_position = Vec3d::Zero();
|
||||
@ -831,7 +1065,19 @@ void ObjectManipulation::change_position_value(int axis, double value)
|
||||
auto canvas = wxGetApp().plater()->canvas3D();
|
||||
Selection& selection = canvas->get_selection();
|
||||
selection.setup_cache();
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
TransformationType trafo_type;
|
||||
trafo_type.set_relative();
|
||||
switch (get_coordinates_type())
|
||||
{
|
||||
case ECoordinatesType::Instance: { trafo_type.set_instance(); break; }
|
||||
case ECoordinatesType::Local: { trafo_type.set_local(); break; }
|
||||
default: { break; }
|
||||
}
|
||||
selection.translate(position - m_cache.position, trafo_type);
|
||||
#else
|
||||
selection.translate(position - m_cache.position, selection.requires_local_axes());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
canvas->do_move(L("Set Position"));
|
||||
|
||||
m_cache.position = position;
|
||||
@ -850,6 +1096,18 @@ void ObjectManipulation::change_rotation_value(int axis, double value)
|
||||
GLCanvas3D* canvas = wxGetApp().plater()->canvas3D();
|
||||
Selection& selection = canvas->get_selection();
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
TransformationType transformation_type;
|
||||
transformation_type.set_relative();
|
||||
if (selection.is_single_full_instance())
|
||||
transformation_type.set_independent();
|
||||
|
||||
if (is_local_coordinates())
|
||||
transformation_type.set_local();
|
||||
|
||||
if (is_instance_coordinates())
|
||||
transformation_type.set_instance();
|
||||
#else
|
||||
TransformationType transformation_type(TransformationType::World_Relative_Joint);
|
||||
if (selection.is_single_full_instance() || selection.requires_local_axes())
|
||||
transformation_type.set_independent();
|
||||
@ -858,6 +1116,7 @@ void ObjectManipulation::change_rotation_value(int axis, double value)
|
||||
// transformation_type.set_absolute();
|
||||
transformation_type.set_local();
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
selection.setup_cache();
|
||||
selection.rotate(
|
||||
@ -903,8 +1162,12 @@ void ObjectManipulation::change_size_value(int axis, double value)
|
||||
const Selection& selection = wxGetApp().plater()->canvas3D()->get_selection();
|
||||
|
||||
Vec3d ref_size = m_cache.size;
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
if (selection.is_single_volume_or_modifier()) {
|
||||
#else
|
||||
if (selection.is_single_volume() || selection.is_single_modifier()) {
|
||||
const GLVolume* v = selection.get_volume(*selection.get_volume_idxs().begin());
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
const GLVolume* v = selection.get_first_volume();
|
||||
const Vec3d local_size = size.cwiseQuotient(v->get_instance_scaling_factor());
|
||||
const Vec3d local_ref_size = v->bounding_box().size().cwiseProduct(v->get_volume_scaling_factor());
|
||||
const Vec3d local_change = local_size.cwiseQuotient(local_ref_size);
|
||||
@ -913,11 +1176,19 @@ void ObjectManipulation::change_size_value(int axis, double value)
|
||||
ref_size = Vec3d::Ones();
|
||||
}
|
||||
else if (selection.is_single_full_instance())
|
||||
ref_size = m_world_coordinates ?
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
ref_size = is_world_coordinates() ?
|
||||
#else
|
||||
ref_size = m_world_coordinates ?
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
selection.get_unscaled_instance_bounding_box().size() :
|
||||
wxGetApp().model().objects[selection.get_volume(*selection.get_volume_idxs().begin())->object_idx()]->raw_mesh_bounding_box().size();
|
||||
wxGetApp().model().objects[selection.get_first_volume()->object_idx()]->raw_mesh_bounding_box().size();
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
this->do_size(axis, size.cwiseQuotient(ref_size));
|
||||
#else
|
||||
this->do_scale(axis, size.cwiseQuotient(ref_size));
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
m_cache.size = size;
|
||||
m_cache.size_rounded(axis) = DBL_MAX;
|
||||
@ -927,8 +1198,22 @@ void ObjectManipulation::change_size_value(int axis, double value)
|
||||
void ObjectManipulation::do_scale(int axis, const Vec3d &scale) const
|
||||
{
|
||||
Selection& selection = wxGetApp().plater()->canvas3D()->get_selection();
|
||||
#if !ENABLE_WORLD_COORDINATE
|
||||
Vec3d scaling_factor = scale;
|
||||
#endif // !ENABLE_WORLD_COORDINATE
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
TransformationType transformation_type;
|
||||
if (is_local_coordinates())
|
||||
transformation_type.set_local();
|
||||
else if (is_instance_coordinates())
|
||||
transformation_type.set_instance();
|
||||
|
||||
if (!selection.is_single_full_instance() && !selection.is_single_volume_or_modifier())
|
||||
transformation_type.set_relative();
|
||||
|
||||
const Vec3d scaling_factor = m_uniform_scale ? scale(axis) * Vec3d::Ones() : scale;
|
||||
#else
|
||||
TransformationType transformation_type(TransformationType::World_Relative_Joint);
|
||||
if (selection.is_single_full_instance()) {
|
||||
transformation_type.set_absolute();
|
||||
@ -938,12 +1223,31 @@ void ObjectManipulation::do_scale(int axis, const Vec3d &scale) const
|
||||
|
||||
if (m_uniform_scale || selection.requires_uniform_scale())
|
||||
scaling_factor = scale(axis) * Vec3d::Ones();
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
selection.setup_cache();
|
||||
selection.scale(scaling_factor, transformation_type);
|
||||
wxGetApp().plater()->canvas3D()->do_scale(L("Set Scale"));
|
||||
}
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
void ObjectManipulation::do_size(int axis, const Vec3d& scale) const
|
||||
{
|
||||
Selection& selection = wxGetApp().plater()->canvas3D()->get_selection();
|
||||
|
||||
TransformationType transformation_type;
|
||||
if (is_local_coordinates())
|
||||
transformation_type.set_local();
|
||||
else if (is_instance_coordinates())
|
||||
transformation_type.set_instance();
|
||||
|
||||
const Vec3d scaling_factor = m_uniform_scale ? scale(axis) * Vec3d::Ones() : scale;
|
||||
selection.setup_cache();
|
||||
selection.scale(scaling_factor, transformation_type);
|
||||
wxGetApp().plater()->canvas3D()->do_scale(L("Set Size"));
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void ObjectManipulation::on_change(const std::string& opt_key, int axis, double new_value)
|
||||
{
|
||||
if (!m_cache.is_valid())
|
||||
@ -978,17 +1282,26 @@ void ObjectManipulation::on_change(const std::string& opt_key, int axis, double
|
||||
}
|
||||
}
|
||||
|
||||
void ObjectManipulation::set_uniform_scaling(const bool new_value)
|
||||
void ObjectManipulation::set_uniform_scaling(const bool use_uniform_scale)
|
||||
{
|
||||
const Selection &selection = wxGetApp().plater()->canvas3D()->get_selection();
|
||||
if (selection.is_single_full_instance() && m_world_coordinates && !new_value) {
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
if (!use_uniform_scale)
|
||||
// Recalculate cached values at this panel, refresh the screen.
|
||||
this->UpdateAndShow(true);
|
||||
|
||||
m_uniform_scale = use_uniform_scale;
|
||||
|
||||
set_dirty();
|
||||
#else
|
||||
const Selection& selection = wxGetApp().plater()->canvas3D()->get_selection();
|
||||
if (selection.is_single_full_instance() && m_world_coordinates && !use_uniform_scale) {
|
||||
// Verify whether the instance rotation is multiples of 90 degrees, so that the scaling in world coordinates is possible.
|
||||
// all volumes in the selection belongs to the same instance, any of them contains the needed instance data, so we take the first one
|
||||
const GLVolume* volume = selection.get_volume(*selection.get_volume_idxs().begin());
|
||||
const GLVolume* volume = selection.get_first_volume();
|
||||
// Is the angle close to a multiple of 90 degrees?
|
||||
if (! Geometry::is_rotation_ninety_degrees(volume->get_instance_rotation())) {
|
||||
if (!Geometry::is_rotation_ninety_degrees(volume->get_instance_rotation())) {
|
||||
// Cannot apply scaling in the world coordinate system.
|
||||
//wxMessageDialog dlg(GUI::wxGetApp().mainframe,
|
||||
//wxMessageDialog dlg(GUI::wxGetApp().mainframe,
|
||||
MessageDialog dlg(GUI::wxGetApp().mainframe,
|
||||
_L("The currently manipulated object is tilted (rotation angles are not multiples of 90°).\n"
|
||||
"Non-uniform scaling of tilted objects is only possible in the World coordinate system,\n"
|
||||
@ -996,7 +1309,7 @@ void ObjectManipulation::set_uniform_scaling(const bool new_value)
|
||||
_L("This operation is irreversible.\n"
|
||||
"Do you want to proceed?"),
|
||||
SLIC3R_APP_NAME,
|
||||
wxYES_NO | wxCANCEL | wxCANCEL_DEFAULT | wxICON_QUESTION);
|
||||
wxYES_NO | wxCANCEL | wxCANCEL_DEFAULT | wxICON_QUESTION);
|
||||
if (dlg.ShowModal() != wxID_YES) {
|
||||
// Enforce uniform scaling.
|
||||
m_lock_bnt->SetLock(true);
|
||||
@ -1010,31 +1323,39 @@ void ObjectManipulation::set_uniform_scaling(const bool new_value)
|
||||
this->UpdateAndShow(true);
|
||||
}
|
||||
}
|
||||
m_uniform_scale = new_value;
|
||||
|
||||
m_uniform_scale = use_uniform_scale;
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
void ObjectManipulation::set_coordinates_type(ECoordinatesType type)
|
||||
{
|
||||
if (wxGetApp().get_mode() == comSimple)
|
||||
type = ECoordinatesType::World;
|
||||
|
||||
if (m_coordinates_type == type)
|
||||
return;
|
||||
|
||||
m_coordinates_type = type;
|
||||
this->UpdateAndShow(true);
|
||||
GLCanvas3D* canvas = wxGetApp().plater()->canvas3D();
|
||||
canvas->get_gizmos_manager().update_data();
|
||||
canvas->set_as_dirty();
|
||||
canvas->request_extra_frame();
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void ObjectManipulation::msw_rescale()
|
||||
{
|
||||
const int em = wxGetApp().em_unit();
|
||||
m_item_name->SetMinSize(wxSize(20*em, wxDefaultCoord));
|
||||
msw_rescale_word_local_combo(m_word_local_combo);
|
||||
m_word_local_combo_sizer->SetMinSize(wxSize(-1, m_word_local_combo->GetBestHeight(-1)));
|
||||
m_manifold_warning_bmp.msw_rescale();
|
||||
|
||||
const wxString& tooltip = m_fix_throught_netfab_bitmap->GetToolTipText();
|
||||
m_fix_throught_netfab_bitmap->SetBitmap(tooltip.IsEmpty() ? wxNullBitmap : m_manifold_warning_bmp.bmp());
|
||||
m_fix_throught_netfab_bitmap->SetMinSize(tooltip.IsEmpty() ? wxSize(0, 0) : m_manifold_warning_bmp.bmp().GetSize());
|
||||
|
||||
m_mirror_bitmap_on.msw_rescale();
|
||||
m_mirror_bitmap_off.msw_rescale();
|
||||
m_mirror_bitmap_hidden.msw_rescale();
|
||||
m_reset_scale_button->msw_rescale();
|
||||
m_reset_rotation_button->msw_rescale();
|
||||
m_drop_to_bed_button->msw_rescale();
|
||||
m_lock_bnt->msw_rescale();
|
||||
|
||||
for (int id = 0; id < 3; ++id)
|
||||
m_mirror_buttons[id].first->msw_rescale();
|
||||
m_fix_throught_netfab_bitmap->SetMinSize(tooltip.IsEmpty() ? wxSize(0, 0) : m_manifold_warning_bmp.GetSize());
|
||||
|
||||
// rescale label-heights
|
||||
// Text trick to grid sizer layout:
|
||||
@ -1063,19 +1384,31 @@ void ObjectManipulation::sys_color_changed()
|
||||
for (ManipulationEditor* editor : m_editors)
|
||||
editor->sys_color_changed(this);
|
||||
|
||||
// btn...->msw_rescale() updates icon on button, so use it
|
||||
m_mirror_bitmap_on.msw_rescale();
|
||||
m_mirror_bitmap_off.msw_rescale();
|
||||
m_mirror_bitmap_hidden.msw_rescale();
|
||||
m_reset_scale_button->msw_rescale();
|
||||
m_reset_rotation_button->msw_rescale();
|
||||
m_drop_to_bed_button->msw_rescale();
|
||||
m_lock_bnt->msw_rescale();
|
||||
m_mirror_bitmap_on.sys_color_changed();
|
||||
m_mirror_bitmap_off.sys_color_changed();
|
||||
m_mirror_bitmap_hidden.sys_color_changed();
|
||||
m_reset_scale_button->sys_color_changed();
|
||||
m_reset_rotation_button->sys_color_changed();
|
||||
m_drop_to_bed_button->sys_color_changed();
|
||||
m_lock_bnt->sys_color_changed();
|
||||
|
||||
for (int id = 0; id < 3; ++id)
|
||||
m_mirror_buttons[id].first->msw_rescale();
|
||||
m_mirror_buttons[id].first->sys_color_changed();
|
||||
}
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
void ObjectManipulation::set_coordinates_type(const wxString& type_string)
|
||||
{
|
||||
ECoordinatesType type = ECoordinatesType::World;
|
||||
if (type_string == coordinate_type_str(ECoordinatesType::Instance))
|
||||
type = ECoordinatesType::Instance;
|
||||
else if (type_string == coordinate_type_str(ECoordinatesType::Local))
|
||||
type = ECoordinatesType::Local;
|
||||
|
||||
this->set_coordinates_type(type);
|
||||
}
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
static const char axes[] = { 'x', 'y', 'z' };
|
||||
ManipulationEditor::ManipulationEditor(ObjectManipulation* parent,
|
||||
const std::string& opt_key,
|
||||
@ -1117,8 +1450,8 @@ ManipulationEditor::ManipulationEditor(ObjectManipulation* parent,
|
||||
parent->set_focused_editor(nullptr);
|
||||
|
||||
#if ENABLE_OBJECT_MANIPULATOR_FOCUS
|
||||
// if the widgets exchanging focus are both manipulator fields, call kill_focus
|
||||
if (dynamic_cast<ManipulationEditor*>(e.GetEventObject()) != nullptr && dynamic_cast<ManipulationEditor*>(e.GetWindow()) != nullptr)
|
||||
// if the widgets loosing focus is a manipulator field, call kill_focus
|
||||
if (dynamic_cast<ManipulationEditor*>(e.GetEventObject()) != nullptr)
|
||||
#else
|
||||
if (!m_enter_pressed)
|
||||
#endif // ENABLE_OBJECT_MANIPULATOR_FOCUS
|
||||
|
@ -5,6 +5,9 @@
|
||||
|
||||
#include "GUI_ObjectSettings.hpp"
|
||||
#include "GUI_ObjectList.hpp"
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
#include "GUI_Geometry.hpp"
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
#include "libslic3r/Point.hpp"
|
||||
#include <float.h>
|
||||
|
||||
@ -57,6 +60,10 @@ public:
|
||||
void set_value(const wxString& new_value);
|
||||
void kill_focus(ObjectManipulation *parent);
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
const std::string& get_full_opt_name() const { return m_full_opt_name; }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
bool has_opt_key(const std::string& key) { return m_opt_key == key; }
|
||||
|
||||
private:
|
||||
@ -115,9 +122,12 @@ private:
|
||||
wxStaticText* m_empty_str = nullptr;
|
||||
|
||||
// Non-owning pointers to the reset buttons, so we can hide and show them.
|
||||
ScalableButton* m_reset_scale_button = nullptr;
|
||||
ScalableButton* m_reset_rotation_button = nullptr;
|
||||
ScalableButton* m_drop_to_bed_button = nullptr;
|
||||
ScalableButton* m_reset_scale_button{ nullptr };
|
||||
ScalableButton* m_reset_rotation_button{ nullptr };
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
ScalableButton* m_reset_skew_button{ nullptr };
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
ScalableButton* m_drop_to_bed_button{ nullptr };
|
||||
|
||||
wxCheckBox* m_check_inch {nullptr};
|
||||
|
||||
@ -146,22 +156,35 @@ private:
|
||||
Vec3d m_new_size;
|
||||
bool m_new_enabled {true};
|
||||
bool m_uniform_scale {true};
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
ECoordinatesType m_coordinates_type{ ECoordinatesType::World };
|
||||
#else
|
||||
// Does the object manipulation panel work in World or Local coordinates?
|
||||
bool m_world_coordinates = true;
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
LockButton* m_lock_bnt{ nullptr };
|
||||
choice_ctrl* m_word_local_combo { nullptr };
|
||||
|
||||
ScalableBitmap m_manifold_warning_bmp;
|
||||
wxStaticBitmap* m_fix_throught_netfab_bitmap;
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
// Currently focused editor (nullptr if none)
|
||||
ManipulationEditor* m_focused_editor{ nullptr };
|
||||
#else
|
||||
#ifndef __APPLE__
|
||||
// Currently focused editor (nullptr if none)
|
||||
ManipulationEditor* m_focused_editor {nullptr};
|
||||
#endif // __APPLE__
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
wxFlexGridSizer* m_main_grid_sizer;
|
||||
wxFlexGridSizer* m_labels_grid_sizer;
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
wxStaticText* m_skew_label{ nullptr };
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
// sizers, used for msw_rescale
|
||||
wxBoxSizer* m_word_local_combo_sizer;
|
||||
std::vector<wxBoxSizer*> m_rescalable_sizers;
|
||||
@ -185,11 +208,19 @@ public:
|
||||
// Called from the App to update the UI if dirty.
|
||||
void update_if_dirty();
|
||||
|
||||
void set_uniform_scaling(const bool uniform_scale);
|
||||
void set_uniform_scaling(const bool use_uniform_scale);
|
||||
bool get_uniform_scaling() const { return m_uniform_scale; }
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
void set_coordinates_type(ECoordinatesType type);
|
||||
ECoordinatesType get_coordinates_type() const { return m_coordinates_type; }
|
||||
bool is_world_coordinates() const { return m_coordinates_type == ECoordinatesType::World; }
|
||||
bool is_instance_coordinates() const { return m_coordinates_type == ECoordinatesType::Instance; }
|
||||
bool is_local_coordinates() const { return m_coordinates_type == ECoordinatesType::Local; }
|
||||
#else
|
||||
// Does the object manipulation panel work in World or Local coordinates?
|
||||
void set_world_coordinates(const bool world_coordinates) { m_world_coordinates = world_coordinates; this->UpdateAndShow(true); }
|
||||
bool get_world_coordinates() const { return m_world_coordinates; }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
void reset_cache() { m_cache.reset(); }
|
||||
#ifndef __APPLE__
|
||||
@ -205,11 +236,23 @@ public:
|
||||
void sys_color_changed();
|
||||
void on_change(const std::string& opt_key, int axis, double new_value);
|
||||
void set_focused_editor(ManipulationEditor* focused_editor) {
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
m_focused_editor = focused_editor;
|
||||
#else
|
||||
#ifndef __APPLE__
|
||||
m_focused_editor = focused_editor;
|
||||
#endif // __APPLE__
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
}
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
ManipulationEditor* get_focused_editor() { return m_focused_editor; }
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
static wxString coordinate_type_str(ECoordinatesType type);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
|
||||
private:
|
||||
void reset_settings_value();
|
||||
void update_settings_value(const Selection& selection);
|
||||
@ -225,6 +268,11 @@ private:
|
||||
void change_scale_value(int axis, double value);
|
||||
void change_size_value(int axis, double value);
|
||||
void do_scale(int axis, const Vec3d &scale) const;
|
||||
#if ENABLE_WORLD_COORDINATE
|
||||
void do_size(int axis, const Vec3d& scale) const;
|
||||
|
||||
void set_coordinates_type(const wxString& type_string);
|
||||
#endif // ENABLE_WORLD_COORDINATE
|
||||
};
|
||||
|
||||
}}
|
||||
|
@ -99,7 +99,7 @@ bool ObjectSettings::update_settings_list()
|
||||
btn->SetToolTip(_(L("Remove parameter")));
|
||||
|
||||
btn->SetBitmapFocus(m_bmp_delete_focus.bmp());
|
||||
btn->SetBitmapHover(m_bmp_delete_focus.bmp());
|
||||
btn->SetBitmapCurrent(m_bmp_delete_focus.bmp());
|
||||
|
||||
btn->Bind(wxEVT_BUTTON, [opt_key, config, this](wxEvent &event) {
|
||||
wxGetApp().plater()->take_snapshot(from_u8((boost::format(_utf8(L("Delete Option %s"))) % opt_key).str()));
|
||||
@ -133,7 +133,7 @@ bool ObjectSettings::update_settings_list()
|
||||
return;
|
||||
ctrl->SetBitmap_(m_bmp_delete);
|
||||
ctrl->SetBitmapFocus(m_bmp_delete_focus.bmp());
|
||||
ctrl->SetBitmapHover(m_bmp_delete_focus.bmp());
|
||||
ctrl->SetBitmapCurrent(m_bmp_delete_focus.bmp());
|
||||
};
|
||||
|
||||
const bool is_extruders_cat = cat.first == "Extruders";
|
||||
@ -268,15 +268,6 @@ void ObjectSettings::UpdateAndShow(const bool show)
|
||||
OG_Settings::UpdateAndShow(show ? update_settings_list() : false);
|
||||
}
|
||||
|
||||
void ObjectSettings::msw_rescale()
|
||||
{
|
||||
m_bmp_delete.msw_rescale();
|
||||
m_bmp_delete_focus.msw_rescale();
|
||||
|
||||
for (auto group : m_og_settings)
|
||||
group->msw_rescale();
|
||||
}
|
||||
|
||||
void ObjectSettings::sys_color_changed()
|
||||
{
|
||||
m_og->sys_color_changed();
|
||||
|
@ -56,7 +56,6 @@ public:
|
||||
bool add_missed_options(ModelConfig *config_to, const DynamicPrintConfig &config_from);
|
||||
void update_config_values(ModelConfig *config);
|
||||
void UpdateAndShow(const bool show) override;
|
||||
void msw_rescale();
|
||||
void sys_color_changed();
|
||||
};
|
||||
|
||||
|
@ -983,10 +983,11 @@ void Preview::load_print_as_fff(bool keep_z_range)
|
||||
if (gcode_preview_data_valid) {
|
||||
// Load the real G-code preview.
|
||||
m_canvas->load_gcode_preview(*m_gcode_result, colors);
|
||||
m_left_sizer->Show(m_bottom_toolbar_panel);
|
||||
m_left_sizer->Layout();
|
||||
Refresh();
|
||||
zs = m_canvas->get_gcode_layers_zs();
|
||||
if (!zs.empty())
|
||||
m_left_sizer->Show(m_bottom_toolbar_panel);
|
||||
m_loaded = true;
|
||||
}
|
||||
else if (wxGetApp().is_editor()) {
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user