WIP: Brush assets project #106303
|
@ -25,9 +25,14 @@ vendor,product,version,cve_number,remarks,comment
|
|||
@TIFF_ID@,CVE-2022-3599,Ignored,issue in tiff command line tool not used by blender
|
||||
@TIFF_ID@,CVE-2022-3626,Ignored,issue in tiff command line tool not used by blender
|
||||
@TIFF_ID@,CVE-2022-3627,Ignored,issue in tiff command line tool not used by blender
|
||||
@TIFF_ID@,CVE-2023-40745,Ignored,issue in tiff command line tool not used by blender
|
||||
@TIFF_ID@,CVE-2023-41175,Ignored,issue in tiff command line tool not used by blender
|
||||
@XML2_ID@,CVE-2016-3709,Ignored,not affecting blender and not considered a security issue upstream
|
||||
@XML2_ID@,CVE-2023-39615,Ignored,not affecting blender and not considered a security issue upstream
|
||||
@XML2_ID@,CVE-2020-7595,Ignored,already fixed in the libxml2 version used
|
||||
@GMP_ID@,CVE-2021-43618,Mitigated,patched using upstream commit 561a9c25298e
|
||||
@SQLITE_ID@,CVE-2022-35737,Ignored,only affects SQLITE_ENABLE_STAT4 compile option not used by blender or python
|
||||
@SQLITE_ID@,CVE-2023-7104,Ignored,does not affect blender use of sqlite
|
||||
@SQLITE_ID@,CVE-2024-0232,Ignored,does not affect blender use of sqlite
|
||||
@ZLIB_ID@,CVE-2023-45853,Ignored,only affects minizip not used by blender
|
||||
@SBOMCONTENTS@
|
||||
|
|
|
@ -9,7 +9,12 @@ set(OIDN_EXTRA_ARGS
|
|||
-DOIDN_FILTER_RTLIGHTMAP=OFF
|
||||
-DPython_EXECUTABLE=${PYTHON_BINARY}
|
||||
)
|
||||
if(NOT APPLE)
|
||||
if(APPLE)
|
||||
set(OIDN_EXTRA_ARGS
|
||||
${OIDN_EXTRA_ARGS}
|
||||
-DOIDN_DEVICE_METAL=ON
|
||||
)
|
||||
else()
|
||||
set(OIDN_EXTRA_ARGS
|
||||
${OIDN_EXTRA_ARGS}
|
||||
-DOIDN_DEVICE_SYCL=ON
|
||||
|
|
|
@ -111,9 +111,9 @@ endif()
|
|||
|
||||
message("Checking for perl")
|
||||
# download perl for libvpx
|
||||
if(NOT EXISTS "${DOWNLOAD_DIR}/strawberry-perl-5.22.1.3-64bit-portable.zip")
|
||||
if(NOT EXISTS "${DOWNLOAD_DIR}/strawberry-perl-5.38.0.1-64bit-portable.zip")
|
||||
message("Downloading perl")
|
||||
file(DOWNLOAD "http://strawberryperl.com/download/5.22.1.3/strawberry-perl-5.22.1.3-64bit-portable.zip" "${DOWNLOAD_DIR}/strawberry-perl-5.22.1.3-64bit-portable.zip")
|
||||
file(DOWNLOAD "https://github.com/StrawberryPerl/Perl-Dist-Strawberry/releases/download/SP_5380_5361/strawberry-perl-5.38.0.1-64bit-portable.zip" "${DOWNLOAD_DIR}/strawberry-perl-5.38.0.1-64bit-portable.zip")
|
||||
endif()
|
||||
|
||||
# make perl root directory
|
||||
|
@ -125,10 +125,10 @@ if(NOT EXISTS "${DOWNLOAD_DIR}/perl")
|
|||
endif()
|
||||
|
||||
# extract perl
|
||||
if((NOT EXISTS "${DOWNLOAD_DIR}/perl/portable.perl") AND (EXISTS "${DOWNLOAD_DIR}/strawberry-perl-5.22.1.3-64bit-portable.zip"))
|
||||
if((NOT EXISTS "${DOWNLOAD_DIR}/perl/portable.perl") AND (EXISTS "${DOWNLOAD_DIR}/strawberry-perl-5.38.0.1-64bit-portable.zip"))
|
||||
message("Extracting perl")
|
||||
execute_process(
|
||||
COMMAND ${CMAKE_COMMAND} -E tar jxf ${DOWNLOAD_DIR}/strawberry-perl-5.22.1.3-64bit-portable.zip
|
||||
COMMAND ${CMAKE_COMMAND} -E tar jxf ${DOWNLOAD_DIR}/strawberry-perl-5.38.0.1-64bit-portable.zip
|
||||
WORKING_DIRECTORY ${DOWNLOAD_DIR}/perl
|
||||
)
|
||||
endif()
|
||||
|
|
|
@ -56,7 +56,7 @@ set(BLOSC_URI https://github.com/Blosc/c-blosc/archive/v${BLOSC_VERSION}.tar.gz)
|
|||
set(BLOSC_HASH 134b55813b1dca57019d2a2dc1f7a923)
|
||||
set(BLOSC_HASH_TYPE MD5)
|
||||
set(BLOSC_FILE blosc-${BLOSC_VERSION}.tar.gz)
|
||||
set(BLOSC_CPE "cpe:2.3:a:c-blosc2_project:c-blosc2:${BLOSC_VERSION}:*:*:*:*:*:*:*")
|
||||
set(BLOSC_CPE "cpe:2.3:a:c-blosc_project:c-blosc:${BLOSC_VERSION}:*:*:*:*:*:*:*")
|
||||
|
||||
set(PTHREADS_VERSION 3.0.0)
|
||||
set(PTHREADS_URI http://prdownloads.sourceforge.net/pthreads4w/pthreads4w-code-v${PTHREADS_VERSION}.zip)
|
||||
|
@ -218,11 +218,11 @@ set(OSL_FILE OpenShadingLanguage-${OSL_VERSION}.tar.gz)
|
|||
# BZIP2, FFI, SQLITE and change the versions in this file as well. For compliance
|
||||
# reasons there can be no exceptions to this.
|
||||
|
||||
set(PYTHON_VERSION 3.11.6)
|
||||
set(PYTHON_VERSION 3.11.7)
|
||||
set(PYTHON_SHORT_VERSION 3.11)
|
||||
set(PYTHON_SHORT_VERSION_NO_DOTS 311)
|
||||
set(PYTHON_URI https://www.python.org/ftp/python/${PYTHON_VERSION}/Python-${PYTHON_VERSION}.tar.xz)
|
||||
set(PYTHON_HASH d0c5a1a31efe879723e51addf56dd206)
|
||||
set(PYTHON_HASH d96c7e134c35a8c46236f8a0e566b69c)
|
||||
set(PYTHON_HASH_TYPE MD5)
|
||||
set(PYTHON_FILE Python-${PYTHON_VERSION}.tar.xz)
|
||||
set(PYTHON_CPE "cpe:2.3:a:python:python:${PYTHON_VERSION}:-:*:*:*:*:*:*")
|
||||
|
@ -318,9 +318,9 @@ set(FLAC_FILE flac-${FLAC_VERSION}.tar.xz)
|
|||
set(FLAC_CPE "cpe:2.3:a:flac_project:flac:${FLAC_VERSION}:*:*:*:*:*:*:*")
|
||||
set(FLAC_HOMEPAGE https://xiph.org/flac/)
|
||||
|
||||
set(VPX_VERSION 1.11.0)
|
||||
set(VPX_VERSION 1.14.0)
|
||||
set(VPX_URI https://github.com/webmproject/libvpx/archive/v${VPX_VERSION}/libvpx-v${VPX_VERSION}.tar.gz)
|
||||
set(VPX_HASH 965e51c91ad9851e2337aebcc0f517440c637c506f3a03948062e3d5ea129a83)
|
||||
set(VPX_HASH 5f21d2db27071c8a46f1725928a10227ae45c5cd1cad3727e4aafbe476e321fa)
|
||||
set(VPX_HASH_TYPE SHA256)
|
||||
set(VPX_FILE libvpx-v${VPX_VERSION}.tar.gz)
|
||||
set(VPX_CPE "cpe:2.3:a:webmproject:libvpx:${VPX_VERSION}:*:*:*:*:*:*:*")
|
||||
|
@ -347,9 +347,9 @@ set(OPENJPEG_HASH_TYPE SHA256)
|
|||
set(OPENJPEG_FILE openjpeg-v${OPENJPEG_VERSION}.tar.gz)
|
||||
set(OPENJPEG_CPE "cpe:2.3:a:uclouvain:openjpeg:${OPENJPEG_VERSION}:*:*:*:*:*:*:*")
|
||||
|
||||
set(FFMPEG_VERSION 6.0)
|
||||
set(FFMPEG_VERSION 6.1.1)
|
||||
set(FFMPEG_URI http://ffmpeg.org/releases/ffmpeg-${FFMPEG_VERSION}.tar.bz2)
|
||||
set(FFMPEG_HASH 47d062731c9f66a78380e35a19aac77cebceccd1c7cc309b9c82343ffc430c3d)
|
||||
set(FFMPEG_HASH 5e3133939a61ef64ac9b47ffd29a5ea6e337a4023ef0ad972094b4da844e3a20)
|
||||
set(FFMPEG_HASH_TYPE SHA256)
|
||||
set(FFMPEG_FILE ffmpeg-${FFMPEG_VERSION}.tar.bz2)
|
||||
set(FFMPEG_CPE "cpe:2.3:a:ffmpeg:ffmpeg:${FFMPEG_VERSION}:*:*:*:*:*:*:*")
|
||||
|
@ -479,9 +479,9 @@ set(LZMA_FILE xz-${LZMA_VERSION}.tar.bz2)
|
|||
set(LZMA_HOMEPAGE https://tukaani.org/lzma/)
|
||||
|
||||
# NOTE: Python's build has been modified to use our ssl version.
|
||||
set(SSL_VERSION 3.1.2)
|
||||
set(SSL_VERSION 3.1.5)
|
||||
set(SSL_URI https://www.openssl.org/source/openssl-${SSL_VERSION}.tar.gz)
|
||||
set(SSL_HASH a0ce69b8b97ea6a35b96875235aa453b966ba3cba8af2de23657d8b6767d6539)
|
||||
set(SSL_HASH 6ae015467dabf0469b139ada93319327be24b98251ffaeceda0221848dc09262)
|
||||
set(SSL_HASH_TYPE SHA256)
|
||||
set(SSL_FILE openssl-${SSL_VERSION}.tar.gz)
|
||||
set(SSL_CPE "cpe:2.3:a:openssl:openssl:${SSL_VERSION}:*:*:*:*:*:*:*")
|
||||
|
@ -490,10 +490,10 @@ set(SSL_HOMEPAGE https://www.openssl.org)
|
|||
# Note: This will *HAVE* to match the version python ships on windows which
|
||||
# is hardcoded in pythons PCbuild/get_externals.bat for compliance reasons there
|
||||
# can be no exceptions to this.
|
||||
set(SQLITE_VERSION 3.42.0)
|
||||
set(SQLLITE_LONG_VERSION 3420000)
|
||||
set(SQLITE_URI https://www.sqlite.org/2023/sqlite-autoconf-${SQLLITE_LONG_VERSION}.tar.gz)
|
||||
set(SQLITE_HASH 036575929b174c1b829769255491ba2b32bda9ee)
|
||||
set(SQLITE_VERSION 3.45.1)
|
||||
set(SQLLITE_LONG_VERSION 3450100)
|
||||
set(SQLITE_URI https://www.sqlite.org/2024/sqlite-autoconf-${SQLLITE_LONG_VERSION}.tar.gz)
|
||||
set(SQLITE_HASH 650305e234add12fc1e6bef0b365d86a087b3d38)
|
||||
set(SQLITE_HASH_TYPE SHA1)
|
||||
set(SQLITE_FILE sqlite-autoconf-${SQLLITE_LONG_VERSION}.tar.gz)
|
||||
set(SQLITE_CPE "cpe:2.3:a:sqlite:sqlite:${SQLITE_VERSION}:*:*:*:*:*:*:*")
|
||||
|
@ -517,9 +517,9 @@ set(MATERIALX_HASH fad8f4e19305fb2ee920cbff638f3560)
|
|||
set(MATERIALX_HASH_TYPE MD5)
|
||||
set(MATERIALX_FILE materialx-v${MATERIALX_VERSION}.tar.gz)
|
||||
|
||||
set(OIDN_VERSION 2.2.0-rc)
|
||||
set(OIDN_VERSION 2.2.0-rc2)
|
||||
set(OIDN_URI https://github.com/OpenImageDenoise/oidn/releases/download/v${OIDN_VERSION}/oidn-${OIDN_VERSION}.src.tar.gz)
|
||||
set(OIDN_HASH 896d43b65c3fe71144914a1d6b8a5bfb)
|
||||
set(OIDN_HASH 14b261af3a719c49ab10e71583f1a61a)
|
||||
set(OIDN_HASH_TYPE MD5)
|
||||
set(OIDN_FILE oidn-${OIDN_VERSION}.src.tar.gz)
|
||||
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
diff -Naur ffmpeg-clean/configure ffmpeg-dirty/configure
|
||||
--- ffmpeg-clean/configure 2023-02-27 20:43:45.000000000 +0000
|
||||
+++ ffmpeg-dirty/configure 2023-05-25 09:49:24.949566500 +0100
|
||||
@@ -6563,7 +6563,7 @@
|
||||
@@ -6675,7 +6675,7 @@
|
||||
enabled jni && { [ $target_os = "android" ] && check_headers jni.h && enabled pthreads || die "ERROR: jni not found"; }
|
||||
enabled ladspa && require_headers "ladspa.h dlfcn.h"
|
||||
enabled lcms2 && require_pkg_config lcms2 "lcms2 >= 2.13" lcms2.h cmsCreateContext
|
||||
|
@ -10,7 +10,7 @@ diff -Naur ffmpeg-clean/configure ffmpeg-dirty/configure
|
|||
enabled libaribb24 && { check_pkg_config libaribb24 "aribb24 > 1.0.3" "aribb24/aribb24.h" arib_instance_new ||
|
||||
{ enabled gpl && require_pkg_config libaribb24 aribb24 "aribb24/aribb24.h" arib_instance_new; } ||
|
||||
die "ERROR: libaribb24 requires version higher than 1.0.3 or --enable-gpl."; }
|
||||
@@ -6654,16 +6654,15 @@
|
||||
@@ -6767,18 +6767,17 @@
|
||||
require libopencv opencv2/core/core_c.h cvCreateImageHeader -lopencv_core -lopencv_imgproc; } ||
|
||||
require_pkg_config libopencv opencv opencv/cxcore.h cvCreateImageHeader; }
|
||||
enabled libopenh264 && require_pkg_config libopenh264 openh264 wels/codec_api.h WelsGetCodecVersion
|
||||
|
@ -18,7 +18,9 @@ diff -Naur ffmpeg-clean/configure ffmpeg-dirty/configure
|
|||
- { require_pkg_config libopenjpeg "libopenjp2 >= 2.1.0" openjpeg.h opj_version -DOPJ_STATIC && add_cppflags -DOPJ_STATIC; } }
|
||||
+enabled libopenjpeg && require libopenjpeg openjpeg.h opj_version "-DOPJ_STATIC" -lopenjp2
|
||||
enabled libopenmpt && require_pkg_config libopenmpt "libopenmpt >= 0.2.6557" libopenmpt/libopenmpt.h openmpt_module_create -lstdc++ && append libopenmpt_extralibs "-lstdc++"
|
||||
enabled libopenvino && require libopenvino c_api/ie_c_api.h ie_c_api_version -linference_engine_c_api
|
||||
enabled libopenvino && { { check_pkg_config libopenvino openvino openvino/c/openvino.h ov_core_create && enable openvino2; } ||
|
||||
{ check_pkg_config libopenvino openvino c_api/ie_c_api.h ie_c_api_version ||
|
||||
require libopenvino c_api/ie_c_api.h ie_c_api_version -linference_engine_c_api; } }
|
||||
enabled libopus && {
|
||||
enabled libopus_decoder && {
|
||||
- require_pkg_config libopus opus opus_multistream.h opus_multistream_decoder_create
|
||||
|
@ -30,9 +32,9 @@ diff -Naur ffmpeg-clean/configure ffmpeg-dirty/configure
|
|||
}
|
||||
}
|
||||
enabled libplacebo && require_pkg_config libplacebo "libplacebo >= 4.192.0" libplacebo/vulkan.h pl_vulkan_create
|
||||
@@ -6696,8 +6695,8 @@
|
||||
enabled libvidstab && require_pkg_config libvidstab "vidstab >= 0.98" vid.stab/libvidstab.h vsMotionDetectInit
|
||||
@@ -6812,8 +6811,8 @@
|
||||
enabled libvmaf && require_pkg_config libvmaf "libvmaf >= 2.0.0" libvmaf.h vmaf_init
|
||||
enabled libvmaf && check_pkg_config libvmaf_cuda "libvmaf >= 2.0.0" libvmaf_cuda.h vmaf_cuda_state_init
|
||||
enabled libvo_amrwbenc && require libvo_amrwbenc vo-amrwbenc/enc_if.h E_IF_init -lvo-amrwbenc
|
||||
-enabled libvorbis && require_pkg_config libvorbis vorbis vorbis/codec.h vorbis_info_init &&
|
||||
- require_pkg_config libvorbisenc vorbisenc vorbis/vorbisenc.h vorbis_encode_init
|
||||
|
@ -41,7 +43,7 @@ diff -Naur ffmpeg-clean/configure ffmpeg-dirty/configure
|
|||
|
||||
enabled libvpx && {
|
||||
enabled libvpx_vp8_decoder && {
|
||||
@@ -6724,7 +6723,7 @@
|
||||
@@ -6840,7 +6839,7 @@
|
||||
enabled libwebp && {
|
||||
enabled libwebp_encoder && require_pkg_config libwebp "libwebp >= 0.2.0" webp/encode.h WebPGetEncoderVersion
|
||||
enabled libwebp_anim_encoder && check_pkg_config libwebp_anim_encoder "libwebpmux >= 0.4.0" webp/mux.h WebPAnimEncoderOptionsInit; }
|
||||
|
|
|
@ -2,6 +2,6 @@
|
|||
|
||||
@echo Setting up environment for MSYS2 MSVC 64-bit...
|
||||
|
||||
@set PATH=%CD%\usr\bin;%cd%\..\..\perl\site\bin;%cd%\..\..\perl\bin;%cd%\..\..\c\bin;%PATH%
|
||||
@set PATH=%CD%\usr\bin;%cd%\..\..\perl\site\bin;%cd%\..\..\perl\perl\bin;%cd%\..\..\c\bin;%PATH%
|
||||
|
||||
|
||||
|
|
|
@ -1,49 +1,27 @@
|
|||
diff -Naur oidn-2.0.1/core/CMakeLists.txt external_openimagedenoise/core/CMakeLists.txt
|
||||
--- oidn-2.0.1/core/CMakeLists.txt 2023-06-26 09:06:31.000000000 -0600
|
||||
+++ external_openimagedenoise/core/CMakeLists.txt 2023-07-01 10:54:06.347161100 -0600
|
||||
@@ -76,7 +76,7 @@
|
||||
|
||||
add_library(OpenImageDenoise_core SHARED ${OIDN_CORE_SOURCES} ${OIDN_RESOURCE_FILE})
|
||||
diff -Naur oidn-2.2.0/core/CMakeLists.txt external_openimagedenoise/core/CMakeLists.txt
|
||||
--- oidn-2.2.0/core/CMakeLists.txt 2024-02-01 17:52:16 -0700
|
||||
+++ external_openimagedenoise/core/CMakeLists.txt 2024-02-03 12:41:34 -0700
|
||||
@@ -87,7 +87,7 @@
|
||||
|
||||
add_library(OpenImageDenoise_core ${OIDN_CORE_LIB_TYPE} ${OIDN_CORE_SOURCES} ${OIDN_RESOURCE_FILE})
|
||||
set_property(TARGET OpenImageDenoise_core PROPERTY VERSION ${PROJECT_VERSION})
|
||||
-
|
||||
+target_compile_definitions(OpenImageDenoise_core PRIVATE SHARED_POSTFIX=\"$<$<CONFIG:Debug>:$<TARGET_PROPERTY:OpenImageDenoise_core,DEBUG_POSTFIX>>\")
|
||||
target_link_libraries(OpenImageDenoise_core
|
||||
PUBLIC
|
||||
OpenImageDenoise_common
|
||||
diff -Naur oidn-2.0.1/core/module.cpp external_openimagedenoise/core/module.cpp
|
||||
--- oidn-2.0.1/core/module.cpp 2023-06-26 09:06:31.000000000 -0600
|
||||
+++ external_openimagedenoise/core/module.cpp 2023-07-01 10:49:59.924876500 -0600
|
||||
diff -Naur oidn-2.2.0/core/module.cpp external_openimagedenoise/core/module.cpp
|
||||
--- oidn-2.2.0/core/module.cpp 2024-02-01 17:52:16 -0700
|
||||
+++ external_openimagedenoise/core/module.cpp 2024-02-03 12:41:34 -0700
|
||||
@@ -29,7 +29,7 @@
|
||||
return true; // module already loaded
|
||||
|
||||
|
||||
// Get the path of the module to load
|
||||
- std::string filename = "OpenImageDenoise_" + name;
|
||||
+ std::string filename = "OpenImageDenoise_" + name + SHARED_POSTFIX;
|
||||
#if defined(_WIN32)
|
||||
filename += ".dll";
|
||||
#else
|
||||
diff -Naur oidn-2.1.0/devices/CMakeLists.txt external_openimagedenoise/devices/CMakeLists.txt
|
||||
--- oidn-2.1.0/devices/CMakeLists.txt 2023-10-11 14:04:08 -0600
|
||||
+++ external_openimagedenoise/devices/CMakeLists.txt 2023-12-23 09:34:17 -0700
|
||||
@@ -59,6 +59,8 @@
|
||||
-DOIDN_API_NAMESPACE:STRING=${OIDN_API_NAMESPACE}
|
||||
-DOIDN_WARN_AS_ERRORS:BOOL=${OIDN_WARN_AS_ERRORS}
|
||||
-DOIDN_SANITIZER:STRING=${OIDN_SANITIZER}
|
||||
+ -DPython_EXECUTABLE:STRING=${Python_EXECUTABLE}
|
||||
+ -DCMAKE_DEBUG_POSTFIX:STRING=${CMAKE_DEBUG_POSTFIX}
|
||||
BUILD_ALWAYS TRUE
|
||||
DEPENDS
|
||||
OpenImageDenoise_core
|
||||
@@ -149,6 +151,7 @@
|
||||
-DOIDN_API_NAMESPACE:STRING=${OIDN_API_NAMESPACE}
|
||||
-DOIDN_WARN_AS_ERRORS:BOOL=${OIDN_WARN_AS_ERRORS}
|
||||
-DOIDN_SANITIZER:STRING=${OIDN_SANITIZER}
|
||||
+ -DPython_EXECUTABLE:STRING=${Python_EXECUTABLE}
|
||||
BUILD_ALWAYS TRUE
|
||||
DEPENDS
|
||||
OpenImageDenoise_core
|
||||
--- a/core/module.cpp 2023-11-16 19:07:32
|
||||
+++ b/core/module.cpp 2023-11-16 19:08:01
|
||||
@@ -37,7 +37,8 @@
|
||||
"." + toString(OIDN_VERSION_MINOR) +
|
||||
"." + toString(OIDN_VERSION_PATCH);
|
||||
|
@ -54,3 +32,23 @@ diff -Naur oidn-2.1.0/devices/CMakeLists.txt external_openimagedenoise/devices/C
|
|||
#else
|
||||
filename = "lib" + filename + ".so" + versionStr;
|
||||
#endif
|
||||
diff -Naur oidn-2.2.0/devices/CMakeLists.txt external_openimagedenoise/devices/CMakeLists.txt
|
||||
--- oidn-2.2.0/devices/CMakeLists.txt 2024-02-01 17:52:16 -0700
|
||||
+++ external_openimagedenoise/devices/CMakeLists.txt 2024-02-03 13:10:31 -0700
|
||||
@@ -65,6 +65,7 @@
|
||||
-DOIDN_WARN_AS_ERRORS:BOOL=${OIDN_WARN_AS_ERRORS}
|
||||
-DOIDN_SANITIZER:STRING=${OIDN_SANITIZER}
|
||||
-DOIDN_DEVICE_CUDA_API:STRING=${OIDN_DEVICE_CUDA_API}
|
||||
+ -DPython_EXECUTABLE:STRING=${Python_EXECUTABLE}
|
||||
BUILD_ALWAYS TRUE
|
||||
DEPENDS
|
||||
OpenImageDenoise_core
|
||||
@@ -155,6 +156,8 @@
|
||||
-DOIDN_API_NAMESPACE:STRING=${OIDN_API_NAMESPACE}
|
||||
-DOIDN_WARN_AS_ERRORS:BOOL=${OIDN_WARN_AS_ERRORS}
|
||||
-DOIDN_SANITIZER:STRING=${OIDN_SANITIZER}
|
||||
+ -DPython_EXECUTABLE:STRING=${Python_EXECUTABLE}
|
||||
+ -DCMAKE_DEBUG_POSTFIX:STRING=${CMAKE_DEBUG_POSTFIX}
|
||||
BUILD_ALWAYS TRUE
|
||||
DEPENDS
|
||||
OpenImageDenoise_core
|
||||
|
|
|
@ -38,7 +38,7 @@ PROJECT_NAME = Blender
|
|||
# could be handy for archiving the generated documentation or if some version
|
||||
# control system is used.
|
||||
|
||||
PROJECT_NUMBER = V4.1
|
||||
PROJECT_NUMBER = V4.2
|
||||
|
||||
# Using the PROJECT_BRIEF tag one can provide an optional one line description
|
||||
# for a project that appears at the top of each page and should give viewer a
|
||||
|
|
|
@ -352,6 +352,11 @@ class CyclesRenderSettings(bpy.types.PropertyGroup):
|
|||
items=enum_denoising_input_passes,
|
||||
default='RGB_ALBEDO_NORMAL',
|
||||
)
|
||||
denoising_use_gpu: BoolProperty(
|
||||
name="Denoise on GPU",
|
||||
description="Perform denoising on GPU devices, if available. This is significantly faster than on CPU, but requires additional GPU memory. When large scenes need more GPU memory, this option can be disabled",
|
||||
default=False,
|
||||
)
|
||||
|
||||
use_preview_denoising: BoolProperty(
|
||||
name="Use Viewport Denoising",
|
||||
|
@ -382,6 +387,11 @@ class CyclesRenderSettings(bpy.types.PropertyGroup):
|
|||
min=0, max=(1 << 24),
|
||||
default=1,
|
||||
)
|
||||
preview_denoising_use_gpu: BoolProperty(
|
||||
name="Denoise Preview on GPU",
|
||||
description="Perform denoising on GPU devices, if available. This is significantly faster than on CPU, but requires additional GPU memory. When large scenes need more GPU memory, this option can be disabled",
|
||||
default=True,
|
||||
)
|
||||
|
||||
samples: IntProperty(
|
||||
name="Samples",
|
||||
|
@ -1591,6 +1601,22 @@ class CyclesPreferences(bpy.types.AddonPreferences):
|
|||
def has_active_device(self):
|
||||
return self.get_num_gpu_devices() > 0
|
||||
|
||||
def has_oidn_gpu_devices(self):
|
||||
import _cycles
|
||||
compute_device_type = self.get_compute_device_type()
|
||||
|
||||
# We need non-CPU devices, used for rendering and supporting OIDN GPU denoising
|
||||
for device in _cycles.available_devices(compute_device_type):
|
||||
device_type = device[1]
|
||||
if device_type == 'CPU':
|
||||
continue
|
||||
|
||||
has_device_oidn_support = device[5]
|
||||
if has_device_oidn_support and self.find_existing_device_entry(device).use:
|
||||
return True
|
||||
|
||||
return False
|
||||
|
||||
def _draw_devices(self, layout, device_type, devices):
|
||||
box = layout.box()
|
||||
|
||||
|
@ -1685,12 +1711,13 @@ class CyclesPreferences(bpy.types.AddonPreferences):
|
|||
|
||||
import _cycles
|
||||
has_peer_memory = 0
|
||||
has_rt_api_support = False
|
||||
has_rt_api_support = {'METAL': False, 'HIP': False, 'ONEAPI': False}
|
||||
for device in _cycles.available_devices(compute_device_type):
|
||||
if device[3] and self.find_existing_device_entry(device).use:
|
||||
has_peer_memory += 1
|
||||
if device[4] and self.find_existing_device_entry(device).use:
|
||||
has_rt_api_support = True
|
||||
device_type = device[1]
|
||||
has_rt_api_support[device_type] = True
|
||||
|
||||
if has_peer_memory > 1:
|
||||
row = layout.row()
|
||||
|
@ -1708,25 +1735,25 @@ class CyclesPreferences(bpy.types.AddonPreferences):
|
|||
|
||||
# MetalRT only works on Apple Silicon and Navi2.
|
||||
is_arm64 = platform.machine() == 'arm64'
|
||||
if is_arm64 or (is_navi_2 and has_rt_api_support):
|
||||
if is_arm64 or (is_navi_2 and has_rt_api_support['METAL']):
|
||||
col = layout.column()
|
||||
col.use_property_split = True
|
||||
# Kernel specialization is only supported on Apple Silicon
|
||||
if is_arm64:
|
||||
col.prop(self, "kernel_optimization_level")
|
||||
if has_rt_api_support:
|
||||
if has_rt_api_support['METAL']:
|
||||
col.prop(self, "metalrt")
|
||||
|
||||
if compute_device_type == 'HIP':
|
||||
import platform
|
||||
if platform.system() == "Windows": # HIP-RT is currently only supported on Windows
|
||||
has_cuda, has_optix, has_hip, has_metal, has_oneapi, has_hiprt = _cycles.get_device_types()
|
||||
row = layout.row()
|
||||
row.enabled = has_hiprt
|
||||
row.active = has_rt_api_support['HIP']
|
||||
row.prop(self, "use_hiprt")
|
||||
|
||||
elif compute_device_type == 'ONEAPI' and _cycles.with_embree_gpu:
|
||||
row = layout.row()
|
||||
row.active = has_rt_api_support['ONEAPI']
|
||||
row.prop(self, "use_oneapirt")
|
||||
|
||||
def draw(self, context):
|
||||
|
|
|
@ -157,6 +157,10 @@ def get_effective_preview_denoiser(context):
|
|||
return 'OIDN'
|
||||
|
||||
|
||||
def has_oidn_gpu_devices(context):
|
||||
return context.preferences.addons[__package__].preferences.has_oidn_gpu_devices()
|
||||
|
||||
|
||||
def use_mnee(context):
|
||||
# The MNEE kernel doesn't compile on macOS < 13.
|
||||
if use_metal(context):
|
||||
|
@ -236,6 +240,11 @@ class CYCLES_RENDER_PT_sampling_viewport_denoise(CyclesButtonsPanel, Panel):
|
|||
|
||||
col.prop(cscene, "preview_denoising_start_sample", text="Start Sample")
|
||||
|
||||
if effective_preview_denoiser == 'OPENIMAGEDENOISE':
|
||||
row = col.row()
|
||||
row.active = not use_cpu(context) and has_oidn_gpu_devices(context)
|
||||
row.prop(cscene, "preview_denoising_use_gpu", text="Use GPU")
|
||||
|
||||
|
||||
class CYCLES_RENDER_PT_sampling_render(CyclesButtonsPanel, Panel):
|
||||
bl_label = "Render"
|
||||
|
@ -295,6 +304,11 @@ class CYCLES_RENDER_PT_sampling_render_denoise(CyclesButtonsPanel, Panel):
|
|||
if cscene.denoiser == 'OPENIMAGEDENOISE':
|
||||
col.prop(cscene, "denoising_prefilter", text="Prefilter")
|
||||
|
||||
if cscene.denoiser == 'OPENIMAGEDENOISE':
|
||||
row = col.row()
|
||||
row.active = not use_cpu(context) and has_oidn_gpu_devices(context)
|
||||
row.prop(cscene, "denoising_use_gpu", text="Use GPU")
|
||||
|
||||
|
||||
class CYCLES_RENDER_PT_sampling_path_guiding(CyclesButtonsPanel, Panel):
|
||||
bl_label = "Path Guiding"
|
||||
|
|
|
@ -417,12 +417,14 @@ static PyObject *available_devices_func(PyObject * /*self*/, PyObject *args)
|
|||
for (size_t i = 0; i < devices.size(); i++) {
|
||||
DeviceInfo &device = devices[i];
|
||||
string type_name = Device::string_from_type(device.type);
|
||||
PyObject *device_tuple = PyTuple_New(5);
|
||||
PyObject *device_tuple = PyTuple_New(6);
|
||||
PyTuple_SET_ITEM(device_tuple, 0, pyunicode_from_string(device.description.c_str()));
|
||||
PyTuple_SET_ITEM(device_tuple, 1, pyunicode_from_string(type_name.c_str()));
|
||||
PyTuple_SET_ITEM(device_tuple, 2, pyunicode_from_string(device.id.c_str()));
|
||||
PyTuple_SET_ITEM(device_tuple, 3, PyBool_FromLong(device.has_peer_memory));
|
||||
PyTuple_SET_ITEM(device_tuple, 4, PyBool_FromLong(device.use_hardware_raytracing));
|
||||
PyTuple_SET_ITEM(
|
||||
device_tuple, 5, PyBool_FromLong(device.denoisers & DENOISER_OPENIMAGEDENOISE));
|
||||
PyTuple_SET_ITEM(ret, i, device_tuple);
|
||||
}
|
||||
|
||||
|
|
|
@ -474,10 +474,12 @@ void BlenderSync::sync_integrator(BL::ViewLayer &b_view_layer, bool background)
|
|||
* is that the interface and the integrator are technically out of sync. */
|
||||
if (denoise_params.use) {
|
||||
integrator->set_denoiser_type(denoise_params.type);
|
||||
integrator->set_denoise_use_gpu(denoise_params.use_gpu);
|
||||
integrator->set_denoise_start_sample(denoise_params.start_sample);
|
||||
integrator->set_use_denoise_pass_albedo(denoise_params.use_pass_albedo);
|
||||
integrator->set_use_denoise_pass_normal(denoise_params.use_pass_normal);
|
||||
integrator->set_denoiser_prefilter(denoise_params.prefilter);
|
||||
integrator->set_denoiser_quality(denoise_params.quality);
|
||||
}
|
||||
|
||||
/* UPDATE_NONE as we don't want to tag the integrator as modified (this was done by the
|
||||
|
@ -970,8 +972,12 @@ DenoiseParams BlenderSync::get_denoise_params(BL::Scene &b_scene,
|
|||
/* Final Render Denoising */
|
||||
denoising.use = get_boolean(cscene, "use_denoising");
|
||||
denoising.type = (DenoiserType)get_enum(cscene, "denoiser", DENOISER_NUM, DENOISER_NONE);
|
||||
denoising.use_gpu = get_boolean(cscene, "denoising_use_gpu");
|
||||
denoising.prefilter = (DenoiserPrefilter)get_enum(
|
||||
cscene, "denoising_prefilter", DENOISER_PREFILTER_NUM, DENOISER_PREFILTER_NONE);
|
||||
/* This currently only affects NVIDIA and the difference in quality is too small to justify
|
||||
* exposing a setting to the user. */
|
||||
denoising.quality = DENOISER_QUALITY_HIGH;
|
||||
|
||||
input_passes = (DenoiserInput)get_enum(
|
||||
cscene, "denoising_input_passes", DENOISER_INPUT_NUM, DENOISER_INPUT_RGB_ALBEDO_NORMAL);
|
||||
|
@ -988,8 +994,12 @@ DenoiseParams BlenderSync::get_denoise_params(BL::Scene &b_scene,
|
|||
denoising.use = get_boolean(cscene, "use_preview_denoising");
|
||||
denoising.type = (DenoiserType)get_enum(
|
||||
cscene, "preview_denoiser", DENOISER_NUM, DENOISER_NONE);
|
||||
denoising.use_gpu = get_boolean(cscene, "preview_denoising_use_gpu");
|
||||
denoising.prefilter = (DenoiserPrefilter)get_enum(
|
||||
cscene, "preview_denoising_prefilter", DENOISER_PREFILTER_NUM, DENOISER_PREFILTER_FAST);
|
||||
/* This currently only affects NVIDIA and the difference in quality is too small to justify
|
||||
* exposing a setting to the user. */
|
||||
denoising.quality = DENOISER_QUALITY_BALANCED;
|
||||
denoising.start_sample = get_int(cscene, "preview_denoising_start_sample");
|
||||
|
||||
input_passes = (DenoiserInput)get_enum(
|
||||
|
|
|
@ -195,7 +195,11 @@ void device_cuda_info(vector<DeviceInfo> &devices)
|
|||
VLOG_INFO << "Device has compute preemption or is not used for display.";
|
||||
devices.push_back(info);
|
||||
}
|
||||
VLOG_INFO << "Added device \"" << name << "\" with id \"" << info.id << "\".";
|
||||
VLOG_INFO << "Added device \"" << info.description << "\" with id \"" << info.id << "\".";
|
||||
|
||||
if (info.denoisers & DENOISER_OPENIMAGEDENOISE)
|
||||
VLOG_INFO << "Device with id \"" << info.id << "\" is supporting "
|
||||
<< denoiserTypeToHumanReadable(DENOISER_OPENIMAGEDENOISE) << ".";
|
||||
}
|
||||
|
||||
if (!display_devices.empty()) {
|
||||
|
|
|
@ -48,12 +48,25 @@ const NodeEnum *DenoiseParams::get_prefilter_enum()
|
|||
return &prefilter_enum;
|
||||
}
|
||||
|
||||
const NodeEnum *DenoiseParams::get_quality_enum()
|
||||
{
|
||||
static NodeEnum quality_enum;
|
||||
|
||||
if (quality_enum.empty()) {
|
||||
quality_enum.insert("high", DENOISER_QUALITY_HIGH);
|
||||
quality_enum.insert("balanced", DENOISER_QUALITY_BALANCED);
|
||||
}
|
||||
|
||||
return &quality_enum;
|
||||
}
|
||||
|
||||
NODE_DEFINE(DenoiseParams)
|
||||
{
|
||||
NodeType *type = NodeType::add("denoise_params", create);
|
||||
|
||||
const NodeEnum *type_enum = get_type_enum();
|
||||
const NodeEnum *prefilter_enum = get_prefilter_enum();
|
||||
const NodeEnum *quality_enum = get_quality_enum();
|
||||
|
||||
SOCKET_BOOLEAN(use, "Use", false);
|
||||
|
||||
|
@ -67,6 +80,7 @@ NODE_DEFINE(DenoiseParams)
|
|||
SOCKET_BOOLEAN(temporally_stable, "Temporally Stable", false);
|
||||
|
||||
SOCKET_ENUM(prefilter, "Prefilter", *prefilter_enum, DENOISER_PREFILTER_FAST);
|
||||
SOCKET_ENUM(quality, "Quality", *quality_enum, DENOISER_QUALITY_HIGH);
|
||||
|
||||
return type;
|
||||
}
|
||||
|
|
|
@ -40,6 +40,12 @@ enum DenoiserPrefilter {
|
|||
DENOISER_PREFILTER_NUM,
|
||||
};
|
||||
|
||||
enum DenoiserQuality {
|
||||
DENOISER_QUALITY_HIGH = 1,
|
||||
DENOISER_QUALITY_BALANCED = 2,
|
||||
DENOISER_QUALITY_NUM,
|
||||
};
|
||||
|
||||
/* NOTE: Is not a real scene node. Using Node API for ease of (de)serialization.
|
||||
* The default values here do not really matter as they are always initialized from the
|
||||
* Integrator node. */
|
||||
|
@ -63,20 +69,19 @@ class DenoiseParams : public Node {
|
|||
/* Configure the denoiser to use motion vectors, previous image and a temporally stable model. */
|
||||
bool temporally_stable = false;
|
||||
|
||||
/* If true, then allow, if supported, OpenImageDenoise to use GPU device.
|
||||
* If false, then OpenImageDenoise will always use CPU regardless of GPU device
|
||||
* precense. */
|
||||
bool use_gpu = true;
|
||||
|
||||
DenoiserPrefilter prefilter = DENOISER_PREFILTER_FAST;
|
||||
DenoiserQuality quality = DENOISER_QUALITY_HIGH;
|
||||
|
||||
static const NodeEnum *get_type_enum();
|
||||
static const NodeEnum *get_prefilter_enum();
|
||||
static const NodeEnum *get_quality_enum();
|
||||
|
||||
DenoiseParams();
|
||||
|
||||
bool modified(const DenoiseParams &other) const
|
||||
{
|
||||
return !(use == other.use && type == other.type && start_sample == other.start_sample &&
|
||||
use_pass_albedo == other.use_pass_albedo &&
|
||||
use_pass_normal == other.use_pass_normal &&
|
||||
temporally_stable == other.temporally_stable && prefilter == other.prefilter);
|
||||
}
|
||||
};
|
||||
|
||||
CCL_NAMESPACE_END
|
||||
|
|
|
@ -257,6 +257,12 @@ class Device {
|
|||
return false;
|
||||
}
|
||||
|
||||
/* Returns native buffer handle for device pointer. */
|
||||
virtual void *get_native_buffer(device_ptr /*ptr*/)
|
||||
{
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
/* Guiding */
|
||||
|
||||
/* Returns path guiding device handle. */
|
||||
|
|
|
@ -206,7 +206,11 @@ void device_hip_info(vector<DeviceInfo> &devices)
|
|||
devices.push_back(info);
|
||||
}
|
||||
|
||||
VLOG_INFO << "Added device \"" << name << "\" with id \"" << info.id << "\".";
|
||||
VLOG_INFO << "Added device \"" << info.description << "\" with id \"" << info.id << "\".";
|
||||
|
||||
if (info.denoisers & DENOISER_OPENIMAGEDENOISE)
|
||||
VLOG_INFO << "Device with id \"" << info.id << "\" is supporting "
|
||||
<< denoiserTypeToHumanReadable(DENOISER_OPENIMAGEDENOISE) << ".";
|
||||
}
|
||||
|
||||
if (!display_devices.empty())
|
||||
|
|
|
@ -6,6 +6,7 @@
|
|||
|
||||
# include "device/metal/device.h"
|
||||
# include "device/metal/device_impl.h"
|
||||
# include "integrator/denoiser_oidn_gpu.h"
|
||||
|
||||
#endif
|
||||
|
||||
|
@ -55,6 +56,11 @@ void device_metal_info(vector<DeviceInfo> &devices)
|
|||
info.display_device = true;
|
||||
info.denoisers = DENOISER_NONE;
|
||||
info.id = id;
|
||||
# if defined(WITH_OPENIMAGEDENOISE)
|
||||
if (OIDNDenoiserGPU::is_device_supported(info)) {
|
||||
info.denoisers |= DENOISER_OPENIMAGEDENOISE;
|
||||
}
|
||||
# endif
|
||||
|
||||
MetalGPUVendor vendor = MetalInfo::get_device_vendor(device);
|
||||
|
||||
|
@ -79,6 +85,12 @@ void device_metal_info(vector<DeviceInfo> &devices)
|
|||
|
||||
devices.push_back(info);
|
||||
device_index++;
|
||||
|
||||
VLOG_INFO << "Added device \"" << info.description << "\" with id \"" << info.id << "\".";
|
||||
|
||||
if (info.denoisers & DENOISER_OPENIMAGEDENOISE)
|
||||
VLOG_INFO << "Device with id \"" << info.id << "\" is supporting "
|
||||
<< denoiserTypeToHumanReadable(DENOISER_OPENIMAGEDENOISE) << ".";
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -134,6 +134,8 @@ class MetalDevice : public Device {
|
|||
|
||||
virtual bool should_use_graphics_interop() override;
|
||||
|
||||
virtual void *get_native_buffer(device_ptr ptr) override;
|
||||
|
||||
virtual unique_ptr<DeviceQueue> gpu_queue_create() override;
|
||||
|
||||
virtual void build_bvh(BVH *bvh, Progress &progress, bool refit) override;
|
||||
|
|
|
@ -1389,6 +1389,11 @@ bool MetalDevice::should_use_graphics_interop()
|
|||
return false;
|
||||
}
|
||||
|
||||
void *MetalDevice::get_native_buffer(device_ptr ptr)
|
||||
{
|
||||
return ((MetalMem *)ptr)->mtlBuffer;
|
||||
}
|
||||
|
||||
void MetalDevice::flush_delayed_free_list()
|
||||
{
|
||||
/* free any Metal buffers that may have been freed by host while a command
|
||||
|
|
|
@ -40,6 +40,8 @@ class MetalDeviceQueue : public DeviceQueue {
|
|||
virtual void copy_to_device(device_memory &mem) override;
|
||||
virtual void copy_from_device(device_memory &mem) override;
|
||||
|
||||
virtual void *native_queue() override;
|
||||
|
||||
protected:
|
||||
void setup_capture();
|
||||
void update_capture(DeviceKernel kernel);
|
||||
|
|
|
@ -979,6 +979,11 @@ void MetalDeviceQueue::close_blit_encoder()
|
|||
}
|
||||
}
|
||||
|
||||
void *MetalDeviceQueue::native_queue()
|
||||
{
|
||||
return mtlCommandQueue_;
|
||||
}
|
||||
|
||||
CCL_NAMESPACE_END
|
||||
|
||||
#endif /* WITH_METAL */
|
||||
|
|
|
@ -131,7 +131,11 @@ static void device_iterator_cb(
|
|||
# endif
|
||||
|
||||
devices->push_back(info);
|
||||
VLOG_INFO << "Added device \"" << name << "\" with id \"" << info.id << "\".";
|
||||
VLOG_INFO << "Added device \"" << info.description << "\" with id \"" << info.id << "\".";
|
||||
|
||||
if (info.denoisers & DENOISER_OPENIMAGEDENOISE)
|
||||
VLOG_INFO << "Device with id \"" << info.id << "\" is supporting "
|
||||
<< denoiserTypeToHumanReadable(DENOISER_OPENIMAGEDENOISE) << ".";
|
||||
}
|
||||
#endif
|
||||
|
||||
|
|
|
@ -157,6 +157,11 @@ class DeviceQueue {
|
|||
/* Device this queue has been created for. */
|
||||
Device *device;
|
||||
|
||||
virtual void *native_queue()
|
||||
{
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
protected:
|
||||
/* Hide construction so that allocation via `Device` API is enforced. */
|
||||
explicit DeviceQueue(Device *device);
|
||||
|
|
|
@ -27,7 +27,9 @@ unique_ptr<Denoiser> Denoiser::create(Device *path_trace_device, const DenoisePa
|
|||
#endif
|
||||
|
||||
#ifdef WITH_OPENIMAGEDENOISE
|
||||
if (params.type == DENOISER_OPENIMAGEDENOISE && path_trace_device->info.type != DEVICE_CPU &&
|
||||
/* If available and allowed, then we will use OpenImageDenoise on GPU, otherwise on CPU. */
|
||||
if (params.type == DENOISER_OPENIMAGEDENOISE && params.use_gpu &&
|
||||
path_trace_device->info.type != DEVICE_CPU &&
|
||||
OIDNDenoiserGPU::is_device_supported(path_trace_device->info))
|
||||
{
|
||||
return make_unique<OIDNDenoiserGPU>(path_trace_device, params);
|
||||
|
|
|
@ -324,9 +324,9 @@ void DenoiserGPU::denoise_color_read(const DenoiseContext &context, const Denois
|
|||
denoiser_queue_.get(), pass_access_info, 1.0f, context.num_samples);
|
||||
|
||||
PassAccessor::Destination destination(pass_access_info.type);
|
||||
destination.d_pixels = context.render_buffers->buffer.device_pointer +
|
||||
pass.denoised_offset * sizeof(float);
|
||||
destination.d_pixels = context.render_buffers->buffer.device_pointer;
|
||||
destination.num_components = 3;
|
||||
destination.pixel_offset = pass.denoised_offset;
|
||||
destination.pixel_stride = context.buffer_params.pass_stride;
|
||||
|
||||
BufferParams buffer_params = context.buffer_params;
|
||||
|
|
|
@ -164,6 +164,18 @@ class OIDNDenoiseContext {
|
|||
oidn_filter.setProgressMonitorFunction(oidn_progress_monitor_function, denoiser_);
|
||||
oidn_filter.set("hdr", true);
|
||||
oidn_filter.set("srgb", false);
|
||||
|
||||
# if OIDN_VERSION_MAJOR >= 2
|
||||
switch (denoise_params_.quality) {
|
||||
case DENOISER_QUALITY_BALANCED:
|
||||
oidn_filter.set("quality", OIDN_QUALITY_BALANCED);
|
||||
break;
|
||||
case DENOISER_QUALITY_HIGH:
|
||||
default:
|
||||
oidn_filter.set("quality", OIDN_QUALITY_HIGH);
|
||||
}
|
||||
# endif
|
||||
|
||||
if (denoise_params_.prefilter == DENOISER_PREFILTER_NONE ||
|
||||
denoise_params_.prefilter == DENOISER_PREFILTER_ACCURATE)
|
||||
{
|
||||
|
|
|
@ -47,6 +47,20 @@ bool OIDNDenoiserGPU::is_device_supported(const DeviceInfo &device)
|
|||
case DEVICE_OPTIX:
|
||||
device_type = OIDN_DEVICE_TYPE_CUDA;
|
||||
break;
|
||||
# endif
|
||||
# ifdef OIDN_DEVICE_METAL
|
||||
case DEVICE_METAL: {
|
||||
int num_devices = oidnGetNumPhysicalDevices();
|
||||
for (int i = 0; i < num_devices; i++) {
|
||||
if (oidnGetPhysicalDeviceUInt(i, "type") == OIDN_DEVICE_TYPE_METAL) {
|
||||
const char *name = oidnGetPhysicalDeviceString(i, "name");
|
||||
if (device.id.find(name) != std::string::npos) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
# endif
|
||||
case DEVICE_CPU:
|
||||
/* This is the GPU denoiser - CPU devices shouldn't end up here. */
|
||||
|
@ -111,6 +125,9 @@ uint OIDNDenoiserGPU::get_device_type_mask() const
|
|||
# ifdef OIDN_DEVICE_SYCL
|
||||
device_mask |= DEVICE_MASK_ONEAPI;
|
||||
# endif
|
||||
# ifdef OIDN_DEVICE_METAL
|
||||
device_mask |= DEVICE_MASK_METAL;
|
||||
# endif
|
||||
# ifdef OIDN_DEVICE_CUDA
|
||||
device_mask |= DEVICE_MASK_CUDA;
|
||||
device_mask |= DEVICE_MASK_OPTIX;
|
||||
|
@ -132,14 +149,61 @@ OIDNFilter OIDNDenoiserGPU::create_filter()
|
|||
denoiser_device_->set_error(error_message);
|
||||
}
|
||||
}
|
||||
|
||||
# if OIDN_VERSION_MAJOR >= 2
|
||||
switch (quality_) {
|
||||
case DENOISER_QUALITY_BALANCED:
|
||||
oidnSetFilterInt(filter, "quality", OIDN_QUALITY_BALANCED);
|
||||
break;
|
||||
case DENOISER_QUALITY_HIGH:
|
||||
default:
|
||||
oidnSetFilterInt(filter, "quality", OIDN_QUALITY_HIGH);
|
||||
}
|
||||
# endif
|
||||
|
||||
return filter;
|
||||
}
|
||||
|
||||
bool OIDNDenoiserGPU::commit_and_execute_filter(OIDNFilter filter, ExecMode mode)
|
||||
{
|
||||
const char *error_message = nullptr;
|
||||
OIDNError err = OIDN_ERROR_NONE;
|
||||
|
||||
for (;;) {
|
||||
oidnCommitFilter(filter);
|
||||
if (mode == ExecMode::ASYNC) {
|
||||
oidnExecuteFilterAsync(filter);
|
||||
}
|
||||
else {
|
||||
oidnExecuteFilter(filter);
|
||||
}
|
||||
|
||||
/* If OIDN runs out of memory, reduce mem limit and retry */
|
||||
err = oidnGetDeviceError(oidn_device_, (const char **)&error_message);
|
||||
if (err != OIDN_ERROR_OUT_OF_MEMORY || max_mem_ < 200) {
|
||||
break;
|
||||
}
|
||||
max_mem_ = max_mem_ / 2;
|
||||
oidnSetFilterInt(oidn_filter_, "maxMemoryMB", max_mem_);
|
||||
}
|
||||
|
||||
if (err != OIDN_ERROR_NONE) {
|
||||
if (error_message == nullptr) {
|
||||
error_message = "Unspecified OIDN error";
|
||||
}
|
||||
LOG(ERROR) << "OIDN error: " << error_message;
|
||||
denoiser_device_->set_error(error_message);
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
bool OIDNDenoiserGPU::denoise_create_if_needed(DenoiseContext &context)
|
||||
{
|
||||
const bool recreate_denoiser = (oidn_device_ == nullptr) || (oidn_filter_ == nullptr) ||
|
||||
(use_pass_albedo_ != context.use_pass_albedo) ||
|
||||
(use_pass_normal_ != context.use_pass_normal);
|
||||
(use_pass_normal_ != context.use_pass_normal) ||
|
||||
(quality_ != params_.quality);
|
||||
if (!recreate_denoiser) {
|
||||
return true;
|
||||
}
|
||||
|
@ -161,6 +225,13 @@ bool OIDNDenoiserGPU::denoise_create_if_needed(DenoiseContext &context)
|
|||
1);
|
||||
break;
|
||||
# endif
|
||||
# if defined(OIDN_DEVICE_METAL) && defined(WITH_METAL)
|
||||
case DEVICE_METAL: {
|
||||
denoiser_queue_->init_execution();
|
||||
const MTLCommandQueue_id queue = (const MTLCommandQueue_id)denoiser_queue_->native_queue();
|
||||
oidn_device_ = oidnNewMetalDevice(&queue, 1);
|
||||
} break;
|
||||
# endif
|
||||
# if defined(OIDN_DEVICE_CUDA) && defined(WITH_CUDA)
|
||||
case DEVICE_CUDA:
|
||||
case DEVICE_OPTIX: {
|
||||
|
@ -192,6 +263,8 @@ bool OIDNDenoiserGPU::denoise_create_if_needed(DenoiseContext &context)
|
|||
|
||||
oidnCommitDevice(oidn_device_);
|
||||
|
||||
quality_ = params_.quality;
|
||||
|
||||
oidn_filter_ = create_filter();
|
||||
if (oidn_filter_ == nullptr) {
|
||||
return false;
|
||||
|
@ -199,12 +272,6 @@ bool OIDNDenoiserGPU::denoise_create_if_needed(DenoiseContext &context)
|
|||
|
||||
oidnSetFilterBool(oidn_filter_, "hdr", true);
|
||||
oidnSetFilterBool(oidn_filter_, "srgb", false);
|
||||
oidnSetFilterInt(oidn_filter_, "maxMemoryMB", max_mem_);
|
||||
if (params_.prefilter == DENOISER_PREFILTER_NONE ||
|
||||
params_.prefilter == DENOISER_PREFILTER_ACCURATE)
|
||||
{
|
||||
oidnSetFilterInt(oidn_filter_, "cleanAux", true);
|
||||
}
|
||||
|
||||
if (context.use_pass_albedo) {
|
||||
albedo_filter_ = create_filter();
|
||||
|
@ -249,24 +316,25 @@ bool OIDNDenoiserGPU::denoise_run(const DenoiseContext &context, const DenoisePa
|
|||
/* Color pass. */
|
||||
const int64_t pass_stride_in_bytes = context.buffer_params.pass_stride * sizeof(float);
|
||||
|
||||
oidnSetSharedFilterImage(oidn_filter_,
|
||||
"color",
|
||||
(void *)context.render_buffers->buffer.device_pointer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
pass.denoised_offset * sizeof(float),
|
||||
pass_stride_in_bytes,
|
||||
pass_stride_in_bytes * context.buffer_params.stride);
|
||||
oidnSetSharedFilterImage(oidn_filter_,
|
||||
"output",
|
||||
(void *)context.render_buffers->buffer.device_pointer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
pass.denoised_offset * sizeof(float),
|
||||
pass_stride_in_bytes,
|
||||
pass_stride_in_bytes * context.buffer_params.stride);
|
||||
set_filter_pass(oidn_filter_,
|
||||
"color",
|
||||
context.render_buffers->buffer.device_pointer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
pass.denoised_offset * sizeof(float),
|
||||
pass_stride_in_bytes,
|
||||
pass_stride_in_bytes * context.buffer_params.stride);
|
||||
|
||||
set_filter_pass(oidn_filter_,
|
||||
"output",
|
||||
context.render_buffers->buffer.device_pointer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
pass.denoised_offset * sizeof(float),
|
||||
pass_stride_in_bytes,
|
||||
pass_stride_in_bytes * context.buffer_params.stride);
|
||||
|
||||
/* Optional albedo and color passes. */
|
||||
if (context.num_input_passes > 1) {
|
||||
|
@ -275,125 +343,126 @@ bool OIDNDenoiserGPU::denoise_run(const DenoiseContext &context, const DenoisePa
|
|||
const int64_t row_stride_in_bytes = context.guiding_params.stride * pixel_stride_in_bytes;
|
||||
|
||||
if (context.use_pass_albedo) {
|
||||
if (params_.prefilter == DENOISER_PREFILTER_NONE) {
|
||||
oidnSetSharedFilterImage(oidn_filter_,
|
||||
"albedo",
|
||||
(void *)d_guiding_buffer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
context.guiding_params.pass_albedo * sizeof(float),
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
}
|
||||
else {
|
||||
oidnSetSharedFilterImage(albedo_filter_,
|
||||
"color",
|
||||
(void *)d_guiding_buffer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
context.guiding_params.pass_albedo * sizeof(float),
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
oidnSetSharedFilterImage(albedo_filter_,
|
||||
"output",
|
||||
(void *)d_guiding_buffer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
context.guiding_params.pass_albedo * sizeof(float),
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
oidnCommitFilter(albedo_filter_);
|
||||
oidnExecuteFilterAsync(albedo_filter_);
|
||||
set_filter_pass(oidn_filter_,
|
||||
"albedo",
|
||||
d_guiding_buffer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
context.guiding_params.pass_albedo * sizeof(float),
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
|
||||
oidnSetSharedFilterImage(oidn_filter_,
|
||||
"albedo",
|
||||
(void *)d_guiding_buffer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
context.guiding_params.pass_albedo * sizeof(float),
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
if (params_.prefilter == DENOISER_PREFILTER_ACCURATE) {
|
||||
set_filter_pass(albedo_filter_,
|
||||
"albedo",
|
||||
d_guiding_buffer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
context.guiding_params.pass_albedo * sizeof(float),
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
|
||||
set_filter_pass(albedo_filter_,
|
||||
"output",
|
||||
d_guiding_buffer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
context.guiding_params.pass_albedo * sizeof(float),
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
|
||||
if (!commit_and_execute_filter(albedo_filter_, ExecMode::ASYNC)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (context.use_pass_normal) {
|
||||
if (params_.prefilter == DENOISER_PREFILTER_NONE) {
|
||||
oidnSetSharedFilterImage(oidn_filter_,
|
||||
"normal",
|
||||
(void *)d_guiding_buffer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
context.guiding_params.pass_normal * sizeof(float),
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
}
|
||||
else {
|
||||
oidnSetSharedFilterImage(normal_filter_,
|
||||
"color",
|
||||
(void *)d_guiding_buffer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
context.guiding_params.pass_normal * sizeof(float),
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
set_filter_pass(oidn_filter_,
|
||||
"normal",
|
||||
d_guiding_buffer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
context.guiding_params.pass_normal * sizeof(float),
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
|
||||
oidnSetSharedFilterImage(normal_filter_,
|
||||
"output",
|
||||
(void *)d_guiding_buffer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
context.guiding_params.pass_normal * sizeof(float),
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
if (params_.prefilter == DENOISER_PREFILTER_ACCURATE) {
|
||||
set_filter_pass(normal_filter_,
|
||||
"normal",
|
||||
d_guiding_buffer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
context.guiding_params.pass_normal * sizeof(float),
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
|
||||
oidnCommitFilter(normal_filter_);
|
||||
oidnExecuteFilterAsync(normal_filter_);
|
||||
set_filter_pass(normal_filter_,
|
||||
"output",
|
||||
d_guiding_buffer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
context.guiding_params.pass_normal * sizeof(float),
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
|
||||
oidnSetSharedFilterImage(oidn_filter_,
|
||||
"normal",
|
||||
(void *)d_guiding_buffer,
|
||||
OIDN_FORMAT_FLOAT3,
|
||||
context.buffer_params.width,
|
||||
context.buffer_params.height,
|
||||
context.guiding_params.pass_normal * sizeof(float),
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
if (!commit_and_execute_filter(normal_filter_, ExecMode::ASYNC)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
oidnCommitFilter(oidn_filter_);
|
||||
oidnExecuteFilter(oidn_filter_);
|
||||
oidnSetFilterInt(oidn_filter_, "cleanAux", params_.prefilter != DENOISER_PREFILTER_FAST);
|
||||
return commit_and_execute_filter(oidn_filter_);
|
||||
}
|
||||
|
||||
const char *out_message = nullptr;
|
||||
OIDNError err = oidnGetDeviceError(oidn_device_, (const char **)&out_message);
|
||||
if (OIDN_ERROR_NONE != err) {
|
||||
/* If OIDN runs out of memory, reduce mem limit and retry */
|
||||
while (err == OIDN_ERROR_OUT_OF_MEMORY && max_mem_ > 200) {
|
||||
max_mem_ = max_mem_ / 2;
|
||||
oidnSetFilterInt(oidn_filter_, "maxMemoryMB", max_mem_);
|
||||
oidnCommitFilter(oidn_filter_);
|
||||
oidnExecuteFilter(oidn_filter_);
|
||||
err = oidnGetDeviceError(oidn_device_, &out_message);
|
||||
}
|
||||
if (out_message) {
|
||||
LOG(ERROR) << "OIDN error: " << out_message;
|
||||
denoiser_device_->set_error(out_message);
|
||||
}
|
||||
else {
|
||||
LOG(ERROR) << "OIDN error: unspecified";
|
||||
denoiser_device_->set_error("Unspecified OIDN error");
|
||||
}
|
||||
return false;
|
||||
void OIDNDenoiserGPU::set_filter_pass(OIDNFilter filter,
|
||||
const char *name,
|
||||
device_ptr ptr,
|
||||
int format,
|
||||
int width,
|
||||
int height,
|
||||
size_t offset_in_bytes,
|
||||
size_t pixel_stride_in_bytes,
|
||||
size_t row_stride_in_bytes)
|
||||
{
|
||||
# if defined(OIDN_DEVICE_METAL) && defined(WITH_METAL)
|
||||
if (denoiser_device_->info.type == DEVICE_METAL) {
|
||||
void *mtl_buffer = denoiser_device_->get_native_buffer(ptr);
|
||||
OIDNBuffer oidn_buffer = oidnNewSharedBufferFromMetal(oidn_device_, mtl_buffer);
|
||||
|
||||
oidnSetFilterImage(filter,
|
||||
name,
|
||||
oidn_buffer,
|
||||
(OIDNFormat)format,
|
||||
width,
|
||||
height,
|
||||
offset_in_bytes,
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
|
||||
oidnReleaseBuffer(oidn_buffer);
|
||||
}
|
||||
else
|
||||
# endif
|
||||
{
|
||||
oidnSetSharedFilterImage(filter,
|
||||
name,
|
||||
(void *)ptr,
|
||||
(OIDNFormat)format,
|
||||
width,
|
||||
height,
|
||||
offset_in_bytes,
|
||||
pixel_stride_in_bytes,
|
||||
row_stride_in_bytes);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
CCL_NAMESPACE_END
|
||||
|
|
|
@ -36,6 +36,11 @@ class OIDNDenoiserGPU : public DenoiserGPU {
|
|||
static bool is_device_supported(const DeviceInfo &device);
|
||||
|
||||
protected:
|
||||
enum class ExecMode {
|
||||
SYNC,
|
||||
ASYNC,
|
||||
};
|
||||
|
||||
virtual uint get_device_type_mask() const override;
|
||||
|
||||
/* Create OIDN denoiser descriptor if needed.
|
||||
|
@ -50,6 +55,17 @@ class OIDNDenoiserGPU : public DenoiserGPU {
|
|||
virtual bool denoise_run(const DenoiseContext &context, const DenoisePass &pass) override;
|
||||
|
||||
OIDNFilter create_filter();
|
||||
bool commit_and_execute_filter(OIDNFilter filter, ExecMode mode = ExecMode::SYNC);
|
||||
|
||||
void set_filter_pass(OIDNFilter filter,
|
||||
const char *name,
|
||||
device_ptr ptr,
|
||||
int format,
|
||||
int width,
|
||||
int height,
|
||||
size_t offset_in_bytes,
|
||||
size_t pixel_stride_in_bytes,
|
||||
size_t row_stride_in_bytes);
|
||||
|
||||
OIDNDevice oidn_device_ = nullptr;
|
||||
OIDNFilter oidn_filter_ = nullptr;
|
||||
|
@ -61,8 +77,10 @@ class OIDNDenoiserGPU : public DenoiserGPU {
|
|||
|
||||
bool use_pass_albedo_ = false;
|
||||
bool use_pass_normal_ = false;
|
||||
DenoiserQuality quality_ = DENOISER_QUALITY_HIGH;
|
||||
|
||||
int max_mem_ = 3000;
|
||||
/* Filter memory usage limit if we ran out of memory with OIDN's default limit. */
|
||||
int max_mem_ = 768;
|
||||
};
|
||||
|
||||
CCL_NAMESPACE_END
|
||||
|
|
|
@ -69,6 +69,10 @@ class PassAccessor {
|
|||
* Allows to get pixels of render buffer into a partial slice of the destination. */
|
||||
int offset = 0;
|
||||
|
||||
/* Offset in floats from the beginning of pixels storage.
|
||||
* Is ignored for half4 destination. */
|
||||
int pixel_offset = 0;
|
||||
|
||||
/* Number of floats per pixel. When zero is the same as `num_components`.
|
||||
*
|
||||
* NOTE: Is ignored for half4 destination, as the half4 pixels are always 4-component
|
||||
|
|
|
@ -47,7 +47,7 @@ inline void PassAccessorCPU::run_get_pass_kernel_processor_float(
|
|||
|
||||
parallel_for(0, buffer_params.window_height, [&](int64_t y) {
|
||||
const float *buffer = window_data + y * buffer_row_stride;
|
||||
float *pixel = destination.pixels +
|
||||
float *pixel = destination.pixels + destination.pixel_offset +
|
||||
(y * buffer_params.width + destination.offset) * pixel_stride;
|
||||
func(kfilm_convert, buffer, pixel, buffer_params.window_width, pass_stride, pixel_stride);
|
||||
});
|
||||
|
|
|
@ -48,6 +48,7 @@ void PassAccessorGPU::run_film_convert_kernels(DeviceKernel kernel,
|
|||
&buffer_params.window_width,
|
||||
&offset,
|
||||
&buffer_params.stride,
|
||||
&destination.pixel_offset,
|
||||
&destination.offset,
|
||||
&destination_stride);
|
||||
|
||||
|
|
|
@ -809,6 +809,7 @@ ccl_device_inline void kernel_gpu_film_convert_half_write(ccl_global uchar4 *rgb
|
|||
int width, \
|
||||
int offset, \
|
||||
int stride, \
|
||||
int channel_offset, \
|
||||
int rgba_offset, \
|
||||
int rgba_stride) \
|
||||
{ \
|
||||
|
@ -824,7 +825,7 @@ ccl_device_inline void kernel_gpu_film_convert_half_write(ccl_global uchar4 *rgb
|
|||
ccl_global const float *buffer = render_buffer + offset + \
|
||||
buffer_pixel_index * kfilm_convert.pass_stride; \
|
||||
\
|
||||
ccl_global float *pixel = pixels + \
|
||||
ccl_global float *pixel = pixels + channel_offset + \
|
||||
(render_pixel_index + rgba_offset) * kfilm_convert.pixel_stride; \
|
||||
\
|
||||
FILM_GET_PASS_PIXEL_F32(variant, input_channel_count); \
|
||||
|
|
|
@ -136,6 +136,10 @@ NODE_DEFINE(Integrator)
|
|||
denoiser_prefilter_enum.insert("fast", DENOISER_PREFILTER_FAST);
|
||||
denoiser_prefilter_enum.insert("accurate", DENOISER_PREFILTER_ACCURATE);
|
||||
|
||||
static NodeEnum denoiser_quality_enum;
|
||||
denoiser_quality_enum.insert("high", DENOISER_QUALITY_HIGH);
|
||||
denoiser_quality_enum.insert("balanced", DENOISER_QUALITY_BALANCED);
|
||||
|
||||
/* Default to accurate denoising with OpenImageDenoise. For interactive viewport
|
||||
* it's best use OptiX and disable the normal pass since it does not always have
|
||||
* the desired effect for that denoiser. */
|
||||
|
@ -148,6 +152,8 @@ NODE_DEFINE(Integrator)
|
|||
"Denoiser Prefilter",
|
||||
denoiser_prefilter_enum,
|
||||
DENOISER_PREFILTER_ACCURATE);
|
||||
SOCKET_BOOLEAN(denoise_use_gpu, "Denoise on GPU", true);
|
||||
SOCKET_ENUM(denoiser_quality, "Denoiser Quality", denoiser_quality_enum, DENOISER_QUALITY_HIGH);
|
||||
|
||||
return type;
|
||||
}
|
||||
|
@ -393,12 +399,15 @@ DenoiseParams Integrator::get_denoise_params() const
|
|||
|
||||
denoise_params.type = denoiser_type;
|
||||
|
||||
denoise_params.use_gpu = denoise_use_gpu;
|
||||
|
||||
denoise_params.start_sample = denoise_start_sample;
|
||||
|
||||
denoise_params.use_pass_albedo = use_denoise_pass_albedo;
|
||||
denoise_params.use_pass_normal = use_denoise_pass_normal;
|
||||
|
||||
denoise_params.prefilter = denoiser_prefilter;
|
||||
denoise_params.quality = denoiser_quality;
|
||||
|
||||
return denoise_params;
|
||||
}
|
||||
|
|
|
@ -98,6 +98,8 @@ class Integrator : public Node {
|
|||
NODE_SOCKET_API(bool, use_denoise_pass_albedo);
|
||||
NODE_SOCKET_API(bool, use_denoise_pass_normal);
|
||||
NODE_SOCKET_API(DenoiserPrefilter, denoiser_prefilter);
|
||||
NODE_SOCKET_API(bool, denoise_use_gpu);
|
||||
NODE_SOCKET_API(DenoiserQuality, denoiser_quality);
|
||||
|
||||
enum : uint32_t {
|
||||
AO_PASS_MODIFIED = (1 << 0),
|
||||
|
|
|
@ -8,9 +8,13 @@ echo by dragging them into the text area of your bug report, please include both
|
|||
echo blender_debug_output.txt and blender_system_info.txt in your report.
|
||||
echo.
|
||||
pause
|
||||
mkdir "%temp%\blender\debug_logs" > NUL 2>&1
|
||||
echo.
|
||||
echo Starting blender and waiting for it to exit....
|
||||
setlocal
|
||||
|
||||
set PYTHONPATH=
|
||||
"%~dp0\blender" --debug --debug-gpu --debug-cycles --python-expr "import bpy; bpy.ops.wm.sysinfo(filepath=r'%temp%\blender\debug_logs\blender_system_info.txt')" > "%temp%\blender\debug_logs\blender_debug_output.txt" 2>&1 < %0
|
||||
explorer "%temp%\blender\debug_logs"
|
||||
set DEBUGLOGS="%temp%\blender\debug_logs"
|
||||
mkdir "%DEBUGLOGS%" > NUL 2>&1
|
||||
|
||||
"%~dp0\blender" --debug --debug-gpu --debug-cycles --python-expr "import bpy; bpy.context.preferences.filepaths.temporary_directory=r'%DEBUGLOGS%'; bpy.ops.wm.sysinfo(filepath=r'%DEBUGLOGS%\blender_system_info.txt')" > "%DEBUGLOGS%\blender_debug_output.txt" 2>&1 < %0
|
||||
explorer "%DEBUGLOGS%"
|
||||
|
|
|
@ -8,9 +8,13 @@ echo by dragging them into the text area of your bug report, please include both
|
|||
echo blender_debug_output.txt and blender_system_info.txt in your report.
|
||||
echo.
|
||||
pause
|
||||
mkdir "%temp%\blender\debug_logs" > NUL 2>&1
|
||||
echo.
|
||||
echo Starting blender and waiting for it to exit....
|
||||
setlocal
|
||||
|
||||
set PYTHONPATH=
|
||||
"%~dp0\blender" --debug --debug-gpu --debug-gpu-force-workarounds --python-expr "import bpy; bpy.ops.wm.sysinfo(filepath=r'%temp%\blender\debug_logs\blender_system_info.txt')" > "%temp%\blender\debug_logs\blender_debug_output.txt" 2>&1 < %0
|
||||
explorer "%temp%\blender\debug_logs"
|
||||
set DEBUGLOGS="%temp%\blender\debug_logs"
|
||||
mkdir "%DEBUGLOGS%" > NUL 2>&1
|
||||
|
||||
"%~dp0\blender" --debug --debug-gpu --debug-gpu-force-workarounds --python-expr "import bpy; bpy.context.preferences.filepaths.temporary_directory=r'%DEBUGLOGS%'; bpy.ops.wm.sysinfo(filepath=r'%DEBUGLOGS%\blender_system_info.txt')" > "%DEBUGLOGS%\blender_debug_output.txt" 2>&1 < %0
|
||||
explorer "%DEBUGLOGS%"
|
||||
|
|
|
@ -8,9 +8,13 @@ echo by dragging them into the text area of your bug report, please include both
|
|||
echo blender_debug_output.txt and blender_system_info.txt in your report.
|
||||
echo.
|
||||
pause
|
||||
mkdir "%temp%\blender\debug_logs" > NUL 2>&1
|
||||
echo.
|
||||
echo Starting blender and waiting for it to exit....
|
||||
setlocal
|
||||
|
||||
set PYTHONPATH=
|
||||
"%~dp0\blender" --debug --debug-cycles --python-expr "import bpy; bpy.ops.wm.sysinfo(filepath=r'%temp%\blender\debug_logs\blender_system_info.txt')" > "%temp%\blender\debug_logs\blender_debug_output.txt" 2>&1 < %0
|
||||
explorer "%temp%\blender\debug_logs"
|
||||
set DEBUGLOGS="%temp%\blender\debug_logs"
|
||||
mkdir "%DEBUGLOGS%" > NUL 2>&1
|
||||
|
||||
"%~dp0\blender" --debug --debug-cycles --python-expr "import bpy; bpy.context.preferences.filepaths.temporary_directory=r'%DEBUGLOGS%'; bpy.ops.wm.sysinfo(filepath=r'%DEBUGLOGS%\blender_system_info.txt')" > "%DEBUGLOGS%\blender_debug_output.txt" 2>&1 < %0
|
||||
explorer "%DEBUGLOGS%"
|
||||
|
|
|
@ -8,9 +8,13 @@ echo by dragging them into the text area of your bug report, please include both
|
|||
echo blender_debug_output.txt and blender_system_info.txt in your report.
|
||||
echo.
|
||||
pause
|
||||
mkdir "%temp%\blender\debug_logs" > NUL 2>&1
|
||||
echo.
|
||||
echo Starting blender and waiting for it to exit....
|
||||
setlocal
|
||||
|
||||
set PYTHONPATH=
|
||||
"%~dp0\blender" --factory-startup --python-expr "import bpy; bpy.ops.wm.sysinfo(filepath=r'%temp%\blender\debug_logs\blender_system_info.txt')" > "%temp%\blender\debug_logs\blender_debug_output.txt" 2>&1
|
||||
explorer "%temp%\blender\debug_logs"
|
||||
set DEBUGLOGS="%temp%\blender\debug_logs"
|
||||
mkdir "%DEBUGLOGS%" > NUL 2>&1
|
||||
|
||||
"%~dp0\blender" --factory-startup --python-expr "import bpy; bpy.context.preferences.filepaths.temporary_directory=r'%DEBUGLOGS%'; bpy.ops.wm.sysinfo(filepath=r'%DEBUGLOGS%\blender_system_info.txt')" > "%DEBUGLOGS%\blender_debug_output.txt" 2>&1 < %0
|
||||
explorer "%DEBUGLOGS%"
|
||||
|
|
|
@ -11,6 +11,7 @@ import os
|
|||
import re
|
||||
import sys
|
||||
import glob
|
||||
from pathlib import PurePath
|
||||
|
||||
# XXX Relative import does not work here when used from Blender...
|
||||
from bl_i18n_utils import settings as settings_i18n, utils
|
||||
|
@ -575,6 +576,7 @@ def dump_py_messages_from_files(msgs, reports, files, settings):
|
|||
("pgettext_tip", ("tip_",)),
|
||||
("pgettext_rpt", ("rpt_",)),
|
||||
("pgettext_data", ("data_",)),
|
||||
("poll_message_set", ()),
|
||||
)
|
||||
pgettext_variants_args = {"msgid": (0, {"msgctxt": 1})}
|
||||
|
||||
|
@ -664,6 +666,7 @@ def dump_py_messages_from_files(msgs, reports, files, settings):
|
|||
root_node = ast.parse(filedata.read(), fp, 'exec')
|
||||
|
||||
fp_rel = make_rel(fp)
|
||||
fp_rel = PurePath(fp_rel).as_posix()
|
||||
|
||||
for node in ast.walk(root_node):
|
||||
if type(node) == ast.Call:
|
||||
|
|
|
@ -15,6 +15,7 @@ from bl_i18n_utils import (
|
|||
settings,
|
||||
utils_rtl,
|
||||
)
|
||||
from typing import Dict
|
||||
|
||||
|
||||
##### Misc Utils #####
|
||||
|
@ -737,6 +738,7 @@ class I18nMessages:
|
|||
self._reverse_cache = None
|
||||
if rebuild_now:
|
||||
src_to_msg, ctxt_to_msg, msgid_to_msg, msgstr_to_msg = {}, {}, {}, {}
|
||||
ctxt_to_msg.setdefault(self.settings.DEFAULT_CONTEXT, set())
|
||||
for key, msg in self.msgs.items():
|
||||
if msg.is_commented:
|
||||
continue
|
||||
|
@ -799,7 +801,7 @@ class I18nMessages:
|
|||
rlbl = getattr(msgs, msgmap["rna_label"]["msgstr"])
|
||||
# print("rna label: " + rlbl, rlbl in msgid_to_msg, rlbl in msgstr_to_msg)
|
||||
if rlbl:
|
||||
k = ctxt_to_msg[rna_ctxt].copy()
|
||||
k = ctxt_to_msg.get(rna_ctxt, set()).copy()
|
||||
if k and rlbl in msgid_to_msg:
|
||||
k &= msgid_to_msg[rlbl]
|
||||
elif k and rlbl in msgstr_to_msg:
|
||||
|
@ -1253,7 +1255,7 @@ class I18n:
|
|||
|
||||
def __init__(self, kind=None, src=None, langs=set(), settings=settings):
|
||||
self.settings = settings
|
||||
self.trans = {}
|
||||
self.trans: Dict[str, I18nMessages] = {}
|
||||
self.src = {} # Should have the same keys as self.trans (plus PARSER_PY_ID for py file)!
|
||||
self.dst = self._dst # A callable that transforms src_path into dst_path!
|
||||
if kind and src:
|
||||
|
@ -1485,6 +1487,7 @@ class I18n:
|
|||
if langs:
|
||||
translations &= langs
|
||||
translations = [('"' + lng + '"', " " * (len(lng) + 6), self.trans[lng]) for lng in sorted(translations)]
|
||||
print("Translated keys saved to .py file:")
|
||||
print(*(k for k in keys.keys()))
|
||||
for key in keys.keys():
|
||||
if ref.msgs[key].is_commented:
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
# SPDX-FileCopyrightText: 2019-2023 Blender Authors
|
||||
# SPDX-FileCopyrightText: 2019-2024 Blender Authors
|
||||
#
|
||||
# SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
|
@ -73,6 +73,7 @@ url_manual_mapping = (
|
|||
("bpy.ops.object.simulation_nodes_cache_calculate_to_frame*", "physics/simulation_nodes.html#bpy-ops-object-simulation-nodes-cache-calculate-to-frame"),
|
||||
("bpy.types.brushcurvessculptsettings.density_add_attempts*", "sculpt_paint/curves_sculpting/tools/density_curves.html#bpy-types-brushcurvessculptsettings-density-add-attempts"),
|
||||
("bpy.types.brushgpencilsettings.use_random_press_strength*", "grease_pencil/modes/draw/tools/draw.html#bpy-types-brushgpencilsettings-use-random-press-strength"),
|
||||
("bpy.types.cyclesmaterialsettings.use_bump_map_correction*", "render/cycles/material_settings.html#bpy-types-cyclesmaterialsettings-use-bump-map-correction"),
|
||||
("bpy.types.fluiddomainsettings.use_collision_border_front*", "physics/fluid/type/domain/settings.html#bpy-types-fluiddomainsettings-use-collision-border-front"),
|
||||
("bpy.types.fluiddomainsettings.use_collision_border_right*", "physics/fluid/type/domain/settings.html#bpy-types-fluiddomainsettings-use-collision-border-right"),
|
||||
("bpy.types.lineartgpencilmodifier.shadow_region_filtering*", "grease_pencil/modifiers/generate/line_art.html#bpy-types-lineartgpencilmodifier-shadow-region-filtering"),
|
||||
|
@ -94,6 +95,7 @@ url_manual_mapping = (
|
|||
("bpy.types.fluiddomainsettings.use_collision_border_left*", "physics/fluid/type/domain/settings.html#bpy-types-fluiddomainsettings-use-collision-border-left"),
|
||||
("bpy.types.lineartgpencilmodifier.use_intersection_match*", "grease_pencil/modifiers/generate/line_art.html#bpy-types-lineartgpencilmodifier-use-intersection-match"),
|
||||
("bpy.types.rendersettings_simplify_gpencil_view_modifier*", "render/cycles/render_settings/simplify.html#bpy-types-rendersettings-simplify-gpencil-view-modifier"),
|
||||
("bpy.types.sequencertimelineoverlay.show_strip_tag_color*", "editors/video_sequencer/sequencer/display.html#bpy-types-sequencertimelineoverlay-show-strip-tag-color"),
|
||||
("bpy.types.spaceoutliner.use_filter_object_grease_pencil*", "editors/outliner/interface.html#bpy-types-spaceoutliner-use-filter-object-grease-pencil"),
|
||||
("bpy.types.brushcurvessculptsettings.interpolate_length*", "sculpt_paint/curves_sculpting/tools/add_curves.html#bpy-types-brushcurvessculptsettings-interpolate-length"),
|
||||
("bpy.types.brushgpencilsettings.eraser_thickness_factor*", "grease_pencil/modes/draw/tools/erase.html#bpy-types-brushgpencilsettings-eraser-thickness-factor"),
|
||||
|
@ -243,6 +245,7 @@ url_manual_mapping = (
|
|||
("bpy.types.linestylegeometrymodifier_simplification*", "render/freestyle/view_layer/line_style/modifiers/geometry/simplification.html#bpy-types-linestylegeometrymodifier-simplification"),
|
||||
("bpy.types.materialgpencilstyle.use_overlap_strokes*", "grease_pencil/materials/properties.html#bpy-types-materialgpencilstyle-use-overlap-strokes"),
|
||||
("bpy.types.movietrackingtrack.use_grayscale_preview*", "movie_clip/tracking/clip/sidebar/track/track.html#bpy-types-movietrackingtrack-use-grayscale-preview"),
|
||||
("bpy.types.nodetreeinterfacesocket.hide_in_modifier*", "interface/controls/nodes/groups.html#bpy-types-nodetreeinterfacesocket-hide-in-modifier"),
|
||||
("bpy.types.sequencertimelineoverlay.show_strip_name*", "editors/video_sequencer/sequencer/display.html#bpy-types-sequencertimelineoverlay-show-strip-name"),
|
||||
("bpy.types.sequencertimelineoverlay.show_thumbnails*", "editors/video_sequencer/sequencer/display.html#bpy-types-sequencertimelineoverlay-show-thumbnails"),
|
||||
("bpy.types.spacespreadsheet.geometry_component_type*", "editors/spreadsheet.html#bpy-types-spacespreadsheet-geometry-component-type"),
|
||||
|
@ -259,6 +262,7 @@ url_manual_mapping = (
|
|||
("bpy.types.clothsettings.compression_stiffness_max*", "physics/cloth/settings/property_weights.html#bpy-types-clothsettings-compression-stiffness-max"),
|
||||
("bpy.types.colormanagedsequencercolorspacesettings*", "render/color_management.html#bpy-types-colormanagedsequencercolorspacesettings"),
|
||||
("bpy.types.colormanagedviewsettings.view_transform*", "render/color_management.html#bpy-types-colormanagedviewsettings-view-transform"),
|
||||
("bpy.types.compositornodetree.use_groupnode_buffer*", "compositing/sidebar.html#bpy-types-compositornodetree-use-groupnode-buffer"),
|
||||
("bpy.types.cyclesmaterialsettings.volume_step_rate*", "render/cycles/material_settings.html#bpy-types-cyclesmaterialsettings-volume-step-rate"),
|
||||
("bpy.types.cyclesobjectsettings.is_caustics_caster*", "render/cycles/object_settings/object_data.html#bpy-types-cyclesobjectsettings-is-caustics-caster"),
|
||||
("bpy.types.cyclesrendersettings.adaptive_threshold*", "render/cycles/render_settings/sampling.html#bpy-types-cyclesrendersettings-adaptive-threshold"),
|
||||
|
@ -287,6 +291,7 @@ url_manual_mapping = (
|
|||
("bpy.types.movietrackingplanetrack.use_auto_keying*", "movie_clip/tracking/clip/sidebar/track/plane_track.html#bpy-types-movietrackingplanetrack-use-auto-keying"),
|
||||
("bpy.types.movietrackingsettings.use_tripod_solver*", "movie_clip/tracking/clip/toolbar/solve.html#bpy-types-movietrackingsettings-use-tripod-solver"),
|
||||
("bpy.types.nodesmodifier.simulation_bake_directory*", "modeling/modifiers/generate/geometry_nodes.html#bpy-types-nodesmodifier-simulation-bake-directory"),
|
||||
("bpy.types.nodetreeinterfacesocket.force_non_field*", "interface/controls/nodes/groups.html#bpy-types-nodetreeinterfacesocket-force-non-field"),
|
||||
("bpy.types.rendersettings.simplify_child_particles*", "render/cycles/render_settings/simplify.html#bpy-types-rendersettings-simplify-child-particles"),
|
||||
("bpy.types.rendersettings.use_high_quality_normals*", "render/eevee/render_settings/performance.html#bpy-types-rendersettings-use-high-quality-normals"),
|
||||
("bpy.types.sculpt.automasking_start_normal_falloff*", "sculpt_paint/sculpting/controls.html#bpy-types-sculpt-automasking-start-normal-falloff"),
|
||||
|
@ -337,6 +342,7 @@ url_manual_mapping = (
|
|||
("bpy.types.linestylethicknessmodifier_calligraphy*", "render/freestyle/view_layer/line_style/modifiers/thickness/calligraphy.html#bpy-types-linestylethicknessmodifier-calligraphy"),
|
||||
("bpy.types.materiallineart.use_material_mask_bits*", "render/materials/line_art.html#bpy-types-materiallineart-use-material-mask-bits"),
|
||||
("bpy.types.movietrackingdopesheet.use_invert_sort*", "movie_clip/tracking/dope_sheet.html#bpy-types-movietrackingdopesheet-use-invert-sort"),
|
||||
("bpy.types.nodetreeinterfacesocket*.default_value*", "interface/controls/nodes/groups.html#bpy-types-nodetreeinterfacesocket-default-value"),
|
||||
("bpy.types.rendersettings_simplify_gpencil_onplay*", "render/cycles/render_settings/simplify.html#bpy-types-rendersettings-simplify-gpencil-onplay"),
|
||||
("bpy.types.rigidbodyconstraint.breaking_threshold*", "physics/rigid_body/constraints/introduction.html#bpy-types-rigidbodyconstraint-breaking-threshold"),
|
||||
("bpy.types.sculpt.use_automasking_cavity_inverted*", "sculpt_paint/sculpting/controls.html#bpy-types-sculpt-use-automasking-cavity-inverted"),
|
||||
|
@ -428,6 +434,7 @@ url_manual_mapping = (
|
|||
("bpy.types.clothcollisionsettings.use_collision*", "physics/cloth/settings/collisions.html#bpy-types-clothcollisionsettings-use-collision"),
|
||||
("bpy.types.clothsettings.uniform_pressure_force*", "physics/cloth/settings/physical_properties.html#bpy-types-clothsettings-uniform-pressure-force"),
|
||||
("bpy.types.collection.lineart_intersection_mask*", "scene_layout/collections/collections.html#bpy-types-collection-lineart-intersection-mask"),
|
||||
("bpy.types.compositornodetree.use_viewer_border*", "compositing/sidebar.html#bpy-types-compositornodetree-use-viewer-border"),
|
||||
("bpy.types.cyclesobjectsettings.use_camera_cull*", "render/cycles/object_settings/object_data.html#bpy-types-cyclesobjectsettings-use-camera-cull"),
|
||||
("bpy.types.cyclesobjectsettings.use_motion_blur*", "render/cycles/object_settings/object_data.html#bpy-types-cyclesobjectsettings-use-motion-blur"),
|
||||
("bpy.types.cyclesrendersettings.diffuse_bounces*", "render/cycles/render_settings/light_paths.html#bpy-types-cyclesrendersettings-diffuse-bounces"),
|
||||
|
@ -459,7 +466,6 @@ url_manual_mapping = (
|
|||
("bpy.types.movietrackingcamera.distortion_model*", "movie_clip/tracking/clip/sidebar/track/camera.html#bpy-types-movietrackingcamera-distortion-model"),
|
||||
("bpy.types.movietrackingtrack.use_alpha_preview*", "movie_clip/tracking/clip/sidebar/track/track.html#bpy-types-movietrackingtrack-use-alpha-preview"),
|
||||
("bpy.types.movietrackingtrack.use_green_channel*", "movie_clip/tracking/clip/sidebar/track/track.html#bpy-types-movietrackingtrack-use-green-channel"),
|
||||
("bpy.types.nodesocketinterface.hide_in_modifier*", "interface/controls/nodes/groups.html#bpy-types-nodesocketinterface-hide-in-modifier"),
|
||||
("bpy.types.rendersettings.resolution_percentage*", "render/output/properties/format.html#bpy-types-rendersettings-resolution-percentage"),
|
||||
("bpy.types.rendersettings_simplify_gpencil_tint*", "render/cycles/render_settings/simplify.html#bpy-types-rendersettings-simplify-gpencil-tint"),
|
||||
("bpy.types.softbodysettings.use_estimate_matrix*", "physics/soft_body/settings/solver.html#bpy-types-softbodysettings-use-estimate-matrix"),
|
||||
|
@ -490,7 +496,6 @@ url_manual_mapping = (
|
|||
("bpy.types.clothsettings.compression_stiffness*", "physics/cloth/settings/physical_properties.html#bpy-types-clothsettings-compression-stiffness"),
|
||||
("bpy.types.clothsettings.tension_stiffness_max*", "physics/cloth/settings/property_weights.html#bpy-types-clothsettings-tension-stiffness-max"),
|
||||
("bpy.types.clothsettings.vertex_group_pressure*", "physics/cloth/settings/physical_properties.html#bpy-types-clothsettings-vertex-group-pressure"),
|
||||
("bpy.types.cyclesmaterialsettings.displacement*", "render/cycles/material_settings.html#bpy-types-cyclesmaterialsettings-displacement"),
|
||||
("bpy.types.cyclesrendersettings.fast_gi_method*", "render/cycles/render_settings/light_paths.html#bpy-types-cyclesrendersettings-fast-gi-method"),
|
||||
("bpy.types.cyclesrendersettings.glossy_bounces*", "render/cycles/render_settings/light_paths.html#bpy-types-cyclesrendersettings-glossy-bounces"),
|
||||
("bpy.types.cyclesrendersettings.use_light_tree*", "render/cycles/render_settings/sampling.html#bpy-types-cyclesrendersettings-use-light-tree"),
|
||||
|
@ -512,7 +517,7 @@ url_manual_mapping = (
|
|||
("bpy.types.fluiddomainsettings.particle_radius*", "physics/fluid/type/domain/settings.html#bpy-types-fluiddomainsettings-particle-radius"),
|
||||
("bpy.types.fluiddomainsettings.slice_per_voxel*", "physics/fluid/type/domain/gas/viewport_display.html#bpy-types-fluiddomainsettings-slice-per-voxel"),
|
||||
("bpy.types.fluiddomainsettings.surface_tension*", "physics/fluid/type/domain/liquid/diffusion.html#bpy-types-fluiddomainsettings-surface-tension"),
|
||||
("bpy.types.fluiddomainsettings.viscosity_value*", "physics/fluid/type/domain/liquid/viscosity.html#bpy-types-fluiddomainsettings-viscosity-value"),
|
||||
("bpy.types.fluiddomainsettings.viscosity_value*", "physics/fluid/type/domain/liquid/diffusion.html#bpy-types-fluiddomainsettings-viscosity-value"),
|
||||
("bpy.types.fluideffectorsettings.effector_type*", "physics/fluid/type/effector.html#bpy-types-fluideffectorsettings-effector-type"),
|
||||
("bpy.types.fluidflowsettings.use_particle_size*", "physics/fluid/type/flow.html#bpy-types-fluidflowsettings-use-particle-size"),
|
||||
("bpy.types.freestylelineset.face_mark_negation*", "render/freestyle/view_layer/line_set.html#bpy-types-freestylelineset-face-mark-negation"),
|
||||
|
@ -526,10 +531,12 @@ url_manual_mapping = (
|
|||
("bpy.types.materialgpencilstyle.alignment_mode*", "grease_pencil/materials/properties.html#bpy-types-materialgpencilstyle-alignment-mode"),
|
||||
("bpy.types.movietrackingtrack.use_blue_channel*", "movie_clip/tracking/clip/sidebar/track/track.html#bpy-types-movietrackingtrack-use-blue-channel"),
|
||||
("bpy.types.movietrackingtrack.use_custom_color*", "movie_clip/tracking/clip/sidebar/track/track.html#bpy-types-movietrackingtrack-use-custom-color"),
|
||||
("bpy.types.nodetreeinterfacesocket.description*", "interface/controls/nodes/groups.html#bpy-types-nodetreeinterfacesocket-description"),
|
||||
("bpy.types.objectlineart.intersection_priority*", "scene_layout/object/properties/line_art.html#bpy-types-objectlineart-intersection-priority"),
|
||||
("bpy.types.particlesettings.use_modifier_stack*", "physics/particles/emitter/emission.html#bpy-types-particlesettings-use-modifier-stack"),
|
||||
("bpy.types.rendersettings.sequencer_gl_preview*", "editors/video_sequencer/preview/sidebar.html#bpy-types-rendersettings-sequencer-gl-preview"),
|
||||
("bpy.types.rendersettings.simplify_subdivision*", "render/cycles/render_settings/simplify.html#bpy-types-rendersettings-simplify-subdivision"),
|
||||
("bpy.types.rendersettings.use_simplify_normals*", "render/cycles/render_settings/simplify.html#bpy-types-rendersettings-use-simplify-normals"),
|
||||
("bpy.types.sculpt.use_automasking_start_normal*", "sculpt_paint/sculpting/controls.html#bpy-types-sculpt-use-automasking-start-normal"),
|
||||
("bpy.types.sequencerpreviewoverlay.show_cursor*", "editors/video_sequencer/preview/display/overlays.html#bpy-types-sequencerpreviewoverlay-show-cursor"),
|
||||
("bpy.types.softbodysettings.use_edge_collision*", "physics/soft_body/settings/edges.html#bpy-types-softbodysettings-use-edge-collision"),
|
||||
|
@ -606,7 +613,9 @@ url_manual_mapping = (
|
|||
("bpy.types.moviesequence.animation_offset_end*", "editors/video_sequencer/sequencer/sidebar/strip.html#bpy-types-moviesequence-animation-offset-end"),
|
||||
("bpy.types.movietrackingdopesheet.sort_method*", "movie_clip/tracking/dope_sheet.html#bpy-types-movietrackingdopesheet-sort-method"),
|
||||
("bpy.types.movietrackingtrack.use_red_channel*", "movie_clip/tracking/clip/sidebar/track/track.html#bpy-types-movietrackingtrack-use-red-channel"),
|
||||
("bpy.types.nodesocketinterface*.default_value*", "interface/controls/nodes/groups.html#bpy-types-nodesocketinterface-default-value"),
|
||||
("bpy.types.nodetreeinterfacesocket*.max_value*", "interface/controls/nodes/groups.html#bpy-types-nodetreeinterfacesocket-max-value"),
|
||||
("bpy.types.nodetreeinterfacesocket*.min_value*", "interface/controls/nodes/groups.html#bpy-types-nodetreeinterfacesocket-min-value"),
|
||||
("bpy.types.nodetreeinterfacesocket.hide_value*", "interface/controls/nodes/groups.html#bpy-types-nodetreeinterfacesocket-hide-value"),
|
||||
("bpy.types.object.add_rest_position_attribute*", "animation/shape_keys/shape_keys_panel.html#bpy-types-object-add-rest-position-attribute"),
|
||||
("bpy.types.rendersettings.line_thickness_mode*", "render/freestyle/render.html#bpy-types-rendersettings-line-thickness-mode"),
|
||||
("bpy.types.rendersettings.motion_blur_shutter*", "render/cycles/render_settings/motion_blur.html#bpy-types-rendersettings-motion-blur-shutter"),
|
||||
|
@ -646,6 +655,7 @@ url_manual_mapping = (
|
|||
("bpy.types.clothsettings.vertex_group_intern*", "physics/cloth/settings/physical_properties.html#bpy-types-clothsettings-vertex-group-intern"),
|
||||
("bpy.types.clothsettings.vertex_group_shrink*", "physics/cloth/settings/property_weights.html#bpy-types-clothsettings-vertex-group-shrink"),
|
||||
("bpy.types.colormanagedviewsettings.exposure*", "render/color_management.html#bpy-types-colormanagedviewsettings-exposure"),
|
||||
("bpy.types.compositornodetree.render_quality*", "compositing/sidebar.html#bpy-types-compositornodetree-render-quality"),
|
||||
("bpy.types.cyclesobjectsettings.motion_steps*", "render/cycles/object_settings/object_data.html#bpy-types-cyclesobjectsettings-motion-steps"),
|
||||
("bpy.types.cyclesrendersettings.filter_width*", "render/cycles/render_settings/film.html#bpy-types-cyclesrendersettings-filter-width"),
|
||||
("bpy.types.fluiddomainsettings.cfl_condition*", "physics/fluid/type/domain/settings.html#bpy-types-fluiddomainsettings-cfl-condition"),
|
||||
|
@ -654,7 +664,7 @@ url_manual_mapping = (
|
|||
("bpy.types.fluiddomainsettings.timesteps_min*", "physics/fluid/type/domain/settings.html#bpy-types-fluiddomainsettings-timesteps-min"),
|
||||
("bpy.types.fluiddomainsettings.use_diffusion*", "physics/fluid/type/domain/liquid/diffusion.html#bpy-types-fluiddomainsettings-use-diffusion"),
|
||||
("bpy.types.fluiddomainsettings.use_fractions*", "physics/fluid/type/domain/settings.html#bpy-types-fluiddomainsettings-use-fractions"),
|
||||
("bpy.types.fluiddomainsettings.use_viscosity*", "physics/fluid/type/domain/liquid/viscosity.html#bpy-types-fluiddomainsettings-use-viscosity"),
|
||||
("bpy.types.fluiddomainsettings.use_viscosity*", "physics/fluid/type/domain/liquid/diffusion.html#bpy-types-fluiddomainsettings-use-viscosity"),
|
||||
("bpy.types.fluidflowsettings.particle_system*", "physics/fluid/type/flow.html#bpy-types-fluidflowsettings-particle-system"),
|
||||
("bpy.types.fluidflowsettings.velocity_factor*", "physics/fluid/type/flow.html#bpy-types-fluidflowsettings-velocity-factor"),
|
||||
("bpy.types.fluidflowsettings.velocity_normal*", "physics/fluid/type/flow.html#bpy-types-fluidflowsettings-velocity-normal"),
|
||||
|
@ -677,6 +687,7 @@ url_manual_mapping = (
|
|||
("bpy.types.rendersettings.preview_pixel_size*", "render/cycles/render_settings/performance.html#bpy-types-rendersettings-preview-pixel-size"),
|
||||
("bpy.types.rendersettings.use_crop_to_border*", "render/output/properties/format.html#bpy-types-rendersettings-use-crop-to-border"),
|
||||
("bpy.types.rendersettings.use_file_extension*", "render/output/properties/output.html#bpy-types-rendersettings-use-file-extension"),
|
||||
("bpy.types.scene.use_custom_simulation_range*", "scene_layout/scene/properties.html#bpy-types-scene-use-custom-simulation-range"),
|
||||
("bpy.types.sculpt.constant_detail_resolution*", "sculpt_paint/sculpting/tool_settings/dyntopo.html#bpy-types-sculpt-constant-detail-resolution"),
|
||||
("bpy.types.sequencemodifier.input_mask_strip*", "editors/video_sequencer/sequencer/sidebar/modifiers.html#bpy-types-sequencemodifier-input-mask-strip"),
|
||||
("bpy.types.sequencertoolsettings.pivot_point*", "editors/video_sequencer/preview/controls/pivot_point.html#bpy-types-sequencertoolsettings-pivot-point"),
|
||||
|
@ -725,6 +736,7 @@ url_manual_mapping = (
|
|||
("bpy.types.cyclesrendersettings.max_bounces*", "render/cycles/render_settings/light_paths.html#bpy-types-cyclesrendersettings-max-bounces"),
|
||||
("bpy.types.cyclesrendersettings.use_fast_gi*", "render/cycles/render_settings/light_paths.html#bpy-types-cyclesrendersettings-use-fast-gi"),
|
||||
("bpy.types.cyclesrendersettings.use_guiding*", "render/cycles/render_settings/sampling.html#bpy-types-cyclesrendersettings-use-guiding"),
|
||||
("bpy.types.drivervariable.type.context_prop*", "animation/drivers/drivers_panel.html#bpy-types-drivervariable-type-context-prop"),
|
||||
("bpy.types.editbone.bbone_custom_handle_end*", "animation/armatures/bones/properties/bendy_bones.html#bpy-types-editbone-bbone-custom-handle-end"),
|
||||
("bpy.types.editbone.bbone_handle_type_start*", "animation/armatures/bones/properties/bendy_bones.html#bpy-types-editbone-bbone-handle-type-start"),
|
||||
("bpy.types.fieldsettings.guide_clump_amount*", "physics/forces/force_fields/types/curve_guide.html#bpy-types-fieldsettings-guide-clump-amount"),
|
||||
|
@ -792,7 +804,6 @@ url_manual_mapping = (
|
|||
("bpy.ops.outliner.collection_exclude_clear*", "editors/outliner/editing.html#bpy-ops-outliner-collection-exclude-clear"),
|
||||
("bpy.ops.outliner.collection_holdout_clear*", "render/layers/introduction.html#bpy-ops-outliner-collection-holdout-clear"),
|
||||
("bpy.ops.sculpt.face_set_change_visibility*", "sculpt_paint/sculpting/editing/sculpt.html#bpy-ops-sculpt-face-set-change-visibility"),
|
||||
("bpy.ops.sculpt.face_set_invert_visibility*", "sculpt_paint/sculpting/editing/face_sets.html#bpy-ops-sculpt-face-set-invert-visibility"),
|
||||
("bpy.ops.sculpt.face_sets_randomize_colors*", "sculpt_paint/sculpting/editing/face_sets.html#bpy-ops-sculpt-face-sets-randomize-colors"),
|
||||
("bpy.ops.sequencer.retiming_transition_add*", "video_editing/edit/montage/editing.html#bpy-ops-sequencer-retiming-transition-add"),
|
||||
("bpy.types.animvizmotionpaths.frame_before*", "animation/motion_paths.html#bpy-types-animvizmotionpaths-frame-before"),
|
||||
|
@ -806,6 +817,8 @@ url_manual_mapping = (
|
|||
("bpy.types.clothsettings.tension_stiffness*", "physics/cloth/settings/physical_properties.html#bpy-types-clothsettings-tension-stiffness"),
|
||||
("bpy.types.clothsettings.vertex_group_mass*", "physics/cloth/settings/shape.html#bpy-types-clothsettings-vertex-group-mass"),
|
||||
("bpy.types.compositornodeconvertcolorspace*", "compositing/types/color/convert_colorspace.html#bpy-types-compositornodeconvertcolorspace"),
|
||||
("bpy.types.compositornodetree.edit_quality*", "compositing/sidebar.html#bpy-types-compositornodetree-edit-quality"),
|
||||
("bpy.types.compositornodetree.use_two_pass*", "compositing/sidebar.html#bpy-types-compositornodetree-use-two-pass"),
|
||||
("bpy.types.cyclescurverendersettings.shape*", "render/cycles/render_settings/hair.html#bpy-types-cyclescurverendersettings-shape"),
|
||||
("bpy.types.cycleslightsettings.cast_shadow*", "render/cycles/light_settings.html#bpy-types-cycleslightsettings-cast-shadow"),
|
||||
("bpy.types.cycleslightsettings.max_bounces*", "render/cycles/light_settings.html#bpy-types-cycleslightsettings-max-bounces"),
|
||||
|
@ -850,7 +863,6 @@ url_manual_mapping = (
|
|||
("bpy.types.materialgpencilstyle.fill_style*", "grease_pencil/materials/properties.html#bpy-types-materialgpencilstyle-fill-style"),
|
||||
("bpy.types.materialgpencilstyle.mix_factor*", "grease_pencil/materials/properties.html#bpy-types-materialgpencilstyle-mix-factor"),
|
||||
("bpy.types.materialgpencilstyle.pass_index*", "grease_pencil/materials/properties.html#bpy-types-materialgpencilstyle-pass-index"),
|
||||
("bpy.types.nodesocketinterface.description*", "interface/controls/nodes/groups.html#bpy-types-nodesocketinterface-description"),
|
||||
("bpy.types.rendersettings.dither_intensity*", "render/output/properties/post_processing.html#bpy-types-rendersettings-dither-intensity"),
|
||||
("bpy.types.rendersettings.film_transparent*", "render/cycles/render_settings/film.html#bpy-types-rendersettings-film-transparent"),
|
||||
("bpy.types.rendersettings.simplify_volumes*", "render/cycles/render_settings/simplify.html#bpy-types-rendersettings-simplify-volumes"),
|
||||
|
@ -864,6 +876,7 @@ url_manual_mapping = (
|
|||
("bpy.types.spacefilebrowser.recent_folders*", "editors/file_browser.html#bpy-types-spacefilebrowser-recent-folders"),
|
||||
("bpy.types.spacefilebrowser.system_folders*", "editors/file_browser.html#bpy-types-spacefilebrowser-system-folders"),
|
||||
("bpy.types.spacenodeeditor.show_annotation*", "interface/controls/nodes/introduction.html#bpy-types-spacenodeeditor-show-annotation"),
|
||||
("bpy.types.spacenodeeditor.use_auto_render*", "compositing/sidebar.html#bpy-types-spacenodeeditor-use-auto-render"),
|
||||
("bpy.types.spaceoutliner.use_filter_object*", "editors/outliner/interface.html#bpy-types-spaceoutliner-use-filter-object"),
|
||||
("bpy.types.spacesequenceeditor.use_proxies*", "editors/video_sequencer/preview/sidebar.html#bpy-types-spacesequenceeditor-use-proxies"),
|
||||
("bpy.types.spaceuveditor.edge_display_type*", "editors/uv/overlays.html#bpy-types-spaceuveditor-edge-display-type"),
|
||||
|
@ -952,9 +965,6 @@ url_manual_mapping = (
|
|||
("bpy.types.movietrackingobject.keyframe_a*", "movie_clip/tracking/clip/toolbar/solve.html#bpy-types-movietrackingobject-keyframe-a"),
|
||||
("bpy.types.movietrackingobject.keyframe_b*", "movie_clip/tracking/clip/toolbar/solve.html#bpy-types-movietrackingobject-keyframe-b"),
|
||||
("bpy.types.movietrackingtrack.weight_stab*", "movie_clip/tracking/clip/sidebar/track/track.html#bpy-types-movietrackingtrack-weight-stab"),
|
||||
("bpy.types.nodesocketinterface*.max_value*", "interface/controls/nodes/groups.html#bpy-types-nodesocketinterface-max-value"),
|
||||
("bpy.types.nodesocketinterface*.min_value*", "interface/controls/nodes/groups.html#bpy-types-nodesocketinterface-min-value"),
|
||||
("bpy.types.nodesocketinterface.hide_value*", "interface/controls/nodes/groups.html#bpy-types-nodesocketinterface-hide-value"),
|
||||
("bpy.types.object.use_shape_key_edit_mode*", "animation/shape_keys/shape_keys_panel.html#bpy-types-object-use-shape-key-edit-mode"),
|
||||
("bpy.types.objectlineart.crease_threshold*", "scene_layout/object/properties/line_art.html#bpy-types-objectlineart-crease-threshold"),
|
||||
("bpy.types.rendersettings.use_compositing*", "render/output/properties/post_processing.html#bpy-types-rendersettings-use-compositing"),
|
||||
|
@ -1012,6 +1022,8 @@ url_manual_mapping = (
|
|||
("bpy.types.colormanagedviewsettings.look*", "render/color_management.html#bpy-types-colormanagedviewsettings-look"),
|
||||
("bpy.types.compositornodecolorcorrection*", "compositing/types/color/adjust/color_correction.html#bpy-types-compositornodecolorcorrection"),
|
||||
("bpy.types.compositornodemoviedistortion*", "compositing/types/transform/movie_distortion.html#bpy-types-compositornodemoviedistortion"),
|
||||
("bpy.types.compositornodetree.chunk_size*", "compositing/sidebar.html#bpy-types-compositornodetree-chunk-size"),
|
||||
("bpy.types.compositornodetree.use_opencl*", "compositing/sidebar.html#bpy-types-compositornodetree-use-opencl"),
|
||||
("bpy.types.cyclesrendersettings.caustics*", "render/cycles/render_settings/light_paths.html#bpy-types-cyclesrendersettings-caustics"),
|
||||
("bpy.types.cyclesrendersettings.denoiser*", "render/cycles/render_settings/sampling.html#bpy-types-cyclesrendersettings-denoiser"),
|
||||
("bpy.types.editbone.use_inherit_rotation*", "animation/armatures/bones/properties/relations.html#bpy-types-editbone-use-inherit-rotation"),
|
||||
|
@ -1113,6 +1125,7 @@ url_manual_mapping = (
|
|||
("bpy.types.clothsettings.rest_shape_key*", "physics/cloth/settings/shape.html#bpy-types-clothsettings-rest-shape-key"),
|
||||
("bpy.types.compositornodebrightcontrast*", "compositing/types/color/adjust/bright_contrast.html#bpy-types-compositornodebrightcontrast"),
|
||||
("bpy.types.compositornodedoubleedgemask*", "compositing/types/mask/double_edge_mask.html#bpy-types-compositornodedoubleedgemask"),
|
||||
("bpy.types.compositornodetree.precision*", "compositing/sidebar.html#bpy-types-compositornodetree-precision"),
|
||||
("bpy.types.cyclesrendersettings.samples*", "render/cycles/render_settings/sampling.html#bpy-types-cyclesrendersettings-samples"),
|
||||
("bpy.types.dopesheet.show_only_selected*", "editors/dope_sheet/introduction.html#bpy-types-dopesheet-show-only-selected"),
|
||||
("bpy.types.ffmpegsettings.audio_bitrate*", "render/output/properties/output.html#bpy-types-ffmpegsettings-audio-bitrate"),
|
||||
|
@ -1140,11 +1153,13 @@ url_manual_mapping = (
|
|||
("bpy.types.geometrynodetoolsetselection*", "modeling/geometry_nodes/geometry/write/set_selection.html#bpy-types-geometrynodetoolsetselection"),
|
||||
("bpy.types.geometrynodetree.is_modifier*", "editors/geometry_node.html#bpy-types-geometrynodetree-is-modifier"),
|
||||
("bpy.types.greasepencil.edit_line_color*", "grease_pencil/properties/display.html#bpy-types-greasepencil-edit-line-color"),
|
||||
("bpy.types.material.displacement_method*", "render/cycles/material_settings.html#bpy-types-material-displacement-method"),
|
||||
("bpy.types.material.preview_render_type*", "render/materials/preview.html#bpy-types-material-preview-render-type"),
|
||||
("bpy.types.materialgpencilstyle.pattern*", "grease_pencil/materials/properties.html#bpy-types-materialgpencilstyle-pattern"),
|
||||
("bpy.types.materialgpencilstyle.texture*", "grease_pencil/materials/properties.html#bpy-types-materialgpencilstyle-texture"),
|
||||
("bpy.types.modifier.use_apply_on_spline*", "modeling/modifiers/introduction.html#bpy-types-modifier-use-apply-on-spline"),
|
||||
("bpy.types.movietrackingplanetrack.name*", "movie_clip/tracking/clip/sidebar/track/plane_track.html#bpy-types-movietrackingplanetrack-name"),
|
||||
("bpy.types.nodetreeinterfacesocket.name*", "interface/controls/nodes/groups.html#bpy-types-nodetreeinterfacesocket-name"),
|
||||
("bpy.types.object.use_empty_image_alpha*", "modeling/empties.html#bpy-types-object-use-empty-image-alpha"),
|
||||
("bpy.types.rendersettings.frame_map_new*", "render/output/properties/frame_range.html#bpy-types-rendersettings-frame-map-new"),
|
||||
("bpy.types.rendersettings.frame_map_old*", "render/output/properties/frame_range.html#bpy-types-rendersettings-frame-map-old"),
|
||||
|
@ -1153,6 +1168,7 @@ url_manual_mapping = (
|
|||
("bpy.types.rendersettings.use_sequencer*", "render/output/properties/post_processing.html#bpy-types-rendersettings-use-sequencer"),
|
||||
("bpy.types.sceneeevee.volumetric_shadow*", "render/eevee/render_settings/volumetrics.html#bpy-types-sceneeevee-volumetric-shadow"),
|
||||
("bpy.types.sequenceeditor.overlay_frame*", "editors/video_sequencer/preview/sidebar.html#bpy-types-sequenceeditor-overlay-frame"),
|
||||
("bpy.types.sequenceeditor.proxy_storage*", "editors/video_sequencer/sequencer/sidebar/proxy.html#bpy-types-sequenceeditor-proxy-storage"),
|
||||
("bpy.types.sequencetimelinechannel.lock*", "editors/video_sequencer/sequencer/channels.html#bpy-types-sequencetimelinechannel-lock"),
|
||||
("bpy.types.sequencetimelinechannel.mute*", "editors/video_sequencer/sequencer/channels.html#bpy-types-sequencetimelinechannel-mute"),
|
||||
("bpy.types.sequencetimelinechannel.name*", "editors/video_sequencer/sequencer/channels.html#bpy-types-sequencetimelinechannel-name"),
|
||||
|
@ -1227,6 +1243,7 @@ url_manual_mapping = (
|
|||
("bpy.types.compositornodedistancematte*", "compositing/types/keying/distance_key.html#bpy-types-compositornodedistancematte"),
|
||||
("bpy.types.compositornodeseparatecolor*", "compositing/types/color/mix/separate_color.html#bpy-types-compositornodeseparatecolor"),
|
||||
("bpy.types.compositornodesetalpha.mode*", "compositing/types/color/set_alpha.html#bpy-types-compositornodesetalpha-mode"),
|
||||
("bpy.types.compositornodeviewer.center*", "compositing/types/output/viewer.html#bpy-types-compositornodeviewer-center"),
|
||||
("bpy.types.curves.use_sculpt_collision*", "sculpt_paint/curves_sculpting/introduction.html#bpy-types-curves-use-sculpt-collision"),
|
||||
("bpy.types.dopesheet.use_filter_invert*", "editors/graph_editor/channels/introduction.html#bpy-types-dopesheet-use-filter-invert"),
|
||||
("bpy.types.editbone.bbone_mapping_mode*", "animation/armatures/bones/properties/bendy_bones.html#bpy-types-editbone-bbone-mapping-mode"),
|
||||
|
@ -1289,6 +1306,7 @@ url_manual_mapping = (
|
|||
("bpy.types.sequence.show_retiming_keys*", "editors/video_sequencer/sequencer/sidebar/strip.html#bpy-types-sequence-show-retiming-keys"),
|
||||
("bpy.types.sequenceeditor.show_overlay*", "editors/video_sequencer/preview/sidebar.html#bpy-types-sequenceeditor-show-overlay"),
|
||||
("bpy.types.sequenceeditor.use_prefetch*", "editors/video_sequencer/preview/sidebar.html#bpy-types-sequenceeditor-use-prefetch"),
|
||||
("bpy.types.sequenceproxy.use_overwrite*", "editors/video_sequencer/sequencer/sidebar/proxy.html#bpy-types-sequenceproxy-use-overwrite"),
|
||||
("bpy.types.softbodysettings.ball_stiff*", "physics/soft_body/settings/self_collision.html#bpy-types-softbodysettings-ball-stiff"),
|
||||
("bpy.types.soundsequence.show_waveform*", "editors/video_sequencer/sequencer/sidebar/strip.html#bpy-types-soundsequence-show-waveform"),
|
||||
("bpy.types.spaceclipeditor.show_stable*", "editors/clip/display/clip_display.html#bpy-types-spaceclipeditor-show-stable"),
|
||||
|
@ -1467,7 +1485,6 @@ url_manual_mapping = (
|
|||
("bpy.types.compositornodedilateerode*", "compositing/types/filter/dilate_erode.html#bpy-types-compositornodedilateerode"),
|
||||
("bpy.types.compositornodeellipsemask*", "compositing/types/mask/ellipse_mask.html#bpy-types-compositornodeellipsemask"),
|
||||
("bpy.types.compositornodeseparatexyz*", "compositing/types/vector/separate_xyz.html#bpy-types-compositornodeseparatexyz"),
|
||||
("bpy.types.compositornodesplitviewer*", "compositing/types/output/split_viewer.html#bpy-types-compositornodesplitviewer"),
|
||||
("bpy.types.curve.render_resolution_u*", "modeling/curves/properties/shape.html#bpy-types-curve-render-resolution-u"),
|
||||
("bpy.types.cyclesrendersettings.seed*", "render/cycles/render_settings/sampling.html#bpy-types-cyclesrendersettings-seed"),
|
||||
("bpy.types.dynamicpaintbrushsettings*", "physics/dynamic_paint/brush.html#bpy-types-dynamicpaintbrushsettings"),
|
||||
|
@ -1580,6 +1597,7 @@ url_manual_mapping = (
|
|||
("bpy.ops.sculpt.set_persistent_base*", "sculpt_paint/sculpting/tools/layer.html#bpy-ops-sculpt-set-persistent-base"),
|
||||
("bpy.ops.sequencer.crossfade_sounds*", "video_editing/edit/montage/strips/transitions/sound_crossfade.html#bpy-ops-sequencer-crossfade-sounds"),
|
||||
("bpy.ops.sequencer.export_subtitles*", "editors/video_sequencer/preview/header.html#bpy-ops-sequencer-export-subtitles"),
|
||||
("bpy.ops.sequencer.previewrange_set*", "editors/video_sequencer/sequencer/navigating.html#bpy-ops-sequencer-previewrange-set"),
|
||||
("bpy.ops.sequencer.retiming_key_add*", "video_editing/edit/montage/editing.html#bpy-ops-sequencer-retiming-key-add"),
|
||||
("bpy.ops.text.jump_to_file_at_point*", "editors/text_editor.html#bpy-ops-text-jump-to-file-at-point"),
|
||||
("bpy.ops.transform.edge_bevelweight*", "modeling/meshes/editing/edge/edge_data.html#bpy-ops-transform-edge-bevelweight"),
|
||||
|
@ -1653,13 +1671,13 @@ url_manual_mapping = (
|
|||
("bpy.types.mesh.use_mirror_topology*", "modeling/meshes/tools/tool_settings.html#bpy-types-mesh-use-mirror-topology"),
|
||||
("bpy.types.movieclip.display_aspect*", "editors/clip/display/clip_display.html#bpy-types-movieclip-display-aspect"),
|
||||
("bpy.types.movietrackingtrack.color*", "movie_clip/tracking/clip/sidebar/track/track.html#bpy-types-movietrackingtrack-color"),
|
||||
("bpy.types.nodesocketinterface.name*", "interface/controls/nodes/groups.html#bpy-types-nodesocketinterface-name"),
|
||||
("bpy.types.object.is_shadow_catcher*", "render/cycles/object_settings/object_data.html#bpy-types-object-is-shadow-catcher"),
|
||||
("bpy.types.particleinstancemodifier*", "modeling/modifiers/physics/particle_instance.html#bpy-types-particleinstancemodifier"),
|
||||
("bpy.types.rendersettings.hair_type*", "render/eevee/render_settings/hair.html#bpy-types-rendersettings-hair-type"),
|
||||
("bpy.types.rendersettings.tile_size*", "render/cycles/render_settings/performance.html#bpy-types-rendersettings-tile-size"),
|
||||
("bpy.types.rigidbodyobject.friction*", "physics/rigid_body/properties/collisions.html#bpy-types-rigidbodyobject-friction"),
|
||||
("bpy.types.scenedisplay.viewport_aa*", "render/workbench/sampling.html#bpy-types-scenedisplay-viewport-aa"),
|
||||
("bpy.types.sequenceeditor.proxy_dir*", "editors/video_sequencer/sequencer/sidebar/proxy.html#bpy-types-sequenceeditor-proxy-dir"),
|
||||
("bpy.types.sequencertimelineoverlay*", "editors/video_sequencer/sequencer/display.html#bpy-types-sequencertimelineoverlay"),
|
||||
("bpy.types.sequencetransform.filter*", "editors/video_sequencer/sequencer/sidebar/strip.html#bpy-types-sequencetransform-filter"),
|
||||
("bpy.types.sequencetransform.offset*", "editors/video_sequencer/sequencer/sidebar/strip.html#bpy-types-sequencetransform-offset"),
|
||||
|
@ -1697,6 +1715,7 @@ url_manual_mapping = (
|
|||
("bpy.ops.geometry.attribute_remove*", "modeling/geometry_nodes/attributes_reference.html#bpy-ops-geometry-attribute-remove"),
|
||||
("bpy.ops.gpencil.frame_clean_loose*", "grease_pencil/modes/edit/grease_pencil_menu.html#bpy-ops-gpencil-frame-clean-loose"),
|
||||
("bpy.ops.gpencil.selectmode_toggle*", "grease_pencil/selecting.html#bpy-ops-gpencil-selectmode-toggle"),
|
||||
("bpy.ops.graph.scale_from_neighbor*", "editors/graph_editor/fcurves/editing.html#bpy-ops-graph-scale-from-neighbor"),
|
||||
("bpy.ops.mask.feather_weight_clear*", "movie_clip/masking/editing.html#bpy-ops-mask-feather-weight-clear"),
|
||||
("bpy.ops.mask.primitive_circle_add*", "movie_clip/masking/scurve.html#bpy-ops-mask-primitive-circle-add"),
|
||||
("bpy.ops.mask.primitive_square_add*", "movie_clip/masking/scurve.html#bpy-ops-mask-primitive-square-add"),
|
||||
|
@ -1719,6 +1738,7 @@ url_manual_mapping = (
|
|||
("bpy.ops.render.play_rendered_anim*", "render/output/animation_player.html#bpy-ops-render-play-rendered-anim"),
|
||||
("bpy.ops.sculpt.set_pivot_position*", "sculpt_paint/sculpting/editing/sculpt.html#bpy-ops-sculpt-set-pivot-position"),
|
||||
("bpy.ops.sculpt.trim_lasso_gesture*", "sculpt_paint/sculpting/editing/sculpt.html#bpy-ops-sculpt-trim-lasso-gesture"),
|
||||
("bpy.ops.sculpt_curves.select_ends*", "sculpt_paint/curves_sculpting/introduction.html#bpy-ops-sculpt-curves-select-ends"),
|
||||
("bpy.ops.sculpt_curves.select_grow*", "sculpt_paint/curves_sculpting/introduction.html#bpy-ops-sculpt-curves-select-grow"),
|
||||
("bpy.ops.sequencer.image_strip_add*", "video_editing/edit/montage/strips/image.html#bpy-ops-sequencer-image-strip-add"),
|
||||
("bpy.ops.sequencer.images_separate*", "video_editing/edit/montage/editing.html#bpy-ops-sequencer-images-separate"),
|
||||
|
@ -1802,6 +1822,7 @@ url_manual_mapping = (
|
|||
("bpy.types.limitdistanceconstraint*", "animation/constraints/transform/limit_distance.html#bpy-types-limitdistanceconstraint"),
|
||||
("bpy.types.limitlocationconstraint*", "animation/constraints/transform/limit_location.html#bpy-types-limitlocationconstraint"),
|
||||
("bpy.types.limitrotationconstraint*", "animation/constraints/transform/limit_rotation.html#bpy-types-limitrotationconstraint"),
|
||||
("bpy.types.moviesequence.use_proxy*", "editors/video_sequencer/sequencer/sidebar/proxy.html#bpy-types-moviesequence-use-proxy"),
|
||||
("bpy.types.movietrackingtrack.lock*", "movie_clip/tracking/clip/sidebar/track/track.html#bpy-types-movietrackingtrack-lock"),
|
||||
("bpy.types.movietrackingtrack.name*", "movie_clip/tracking/clip/sidebar/track/track.html#bpy-types-movietrackingtrack-name"),
|
||||
("bpy.types.multiplygpencilmodifier*", "grease_pencil/modifiers/generate/multiple_strokes.html#bpy-types-multiplygpencilmodifier"),
|
||||
|
@ -1844,6 +1865,7 @@ url_manual_mapping = (
|
|||
("bpy.ops.gpencil.vertex_color_set*", "grease_pencil/modes/vertex_paint/editing.html#bpy-ops-gpencil-vertex-color-set"),
|
||||
("bpy.ops.graph.extrapolation_type*", "editors/graph_editor/channels/editing.html#bpy-ops-graph-extrapolation-type"),
|
||||
("bpy.ops.graph.interpolation_type*", "editors/graph_editor/fcurves/editing.html#bpy-ops-graph-interpolation-type"),
|
||||
("bpy.ops.graph.select_key_handles*", "editors/graph_editor/introduction.html#bpy-ops-graph-select-key-handles"),
|
||||
("bpy.ops.image.match_movie_length*", "editors/image/image_settings.html#bpy-ops-image-match-movie-length"),
|
||||
("bpy.ops.mesh.customdata_skin_add*", "modeling/meshes/properties/custom_data.html#bpy-ops-mesh-customdata-skin-add"),
|
||||
("bpy.ops.mesh.dissolve_degenerate*", "modeling/meshes/editing/mesh/cleanup.html#bpy-ops-mesh-dissolve-degenerate"),
|
||||
|
@ -1851,6 +1873,7 @@ url_manual_mapping = (
|
|||
("bpy.ops.mesh.mark_freestyle_face*", "modeling/meshes/editing/face/face_data.html#bpy-ops-mesh-mark-freestyle-face"),
|
||||
("bpy.ops.mesh.primitive_plane_add*", "modeling/meshes/primitives.html#bpy-ops-mesh-primitive-plane-add"),
|
||||
("bpy.ops.mesh.primitive_torus_add*", "modeling/meshes/primitives.html#bpy-ops-mesh-primitive-torus-add"),
|
||||
("bpy.ops.mesh.select_by_attribute*", "modeling/meshes/selecting/by_attribute.html#bpy-ops-mesh-select-by-attribute"),
|
||||
("bpy.ops.mesh.select_non_manifold*", "modeling/meshes/selecting/all_by_trait.html#bpy-ops-mesh-select-non-manifold"),
|
||||
("bpy.ops.nla.selected_objects_add*", "editors/nla/introduction.html#bpy-ops-nla-selected-objects-add"),
|
||||
("bpy.ops.object.constraints_clear*", "animation/constraints/interface/adding_removing.html#bpy-ops-object-constraints-clear"),
|
||||
|
@ -1870,14 +1893,15 @@ url_manual_mapping = (
|
|||
("bpy.ops.scene.view_layer_add_aov*", "render/layers/passes.html#bpy-ops-scene-view-layer-add-aov"),
|
||||
("bpy.ops.screen.spacedata_cleanup*", "advanced/operators.html#bpy-ops-screen-spacedata-cleanup"),
|
||||
("bpy.ops.sculpt.detail_flood_fill*", "sculpt_paint/sculpting/tool_settings/dyntopo.html#bpy-ops-sculpt-detail-flood-fill"),
|
||||
("bpy.ops.sculpt_curves.select_end*", "sculpt_paint/curves_sculpting/introduction.html#bpy-ops-sculpt-curves-select-end"),
|
||||
("bpy.ops.sequencer.duplicate_move*", "video_editing/edit/montage/editing.html#bpy-ops-sequencer-duplicate-move"),
|
||||
("bpy.ops.sequencer.enable_proxies*", "editors/video_sequencer/sequencer/sidebar/proxy.html#bpy-ops-sequencer-enable-proxies"),
|
||||
("bpy.ops.sequencer.retiming_reset*", "video_editing/edit/montage/editing.html#bpy-ops-sequencer-retiming-reset"),
|
||||
("bpy.ops.sequencer.select_grouped*", "video_editing/edit/montage/selecting.html#bpy-ops-sequencer-select-grouped"),
|
||||
("bpy.ops.sequencer.select_handles*", "video_editing/edit/montage/selecting.html#bpy-ops-sequencer-select-handles"),
|
||||
("bpy.ops.ui.copy_data_path_button*", "interface/controls/buttons/menus.html#bpy-ops-ui-copy-data-path-button"),
|
||||
("bpy.ops.uv.average_islands_scale*", "modeling/meshes/uv/editing.html#bpy-ops-uv-average-islands-scale"),
|
||||
("bpy.ops.wm.read_factory_settings*", "interface/window_system/topbar.html#bpy-ops-wm-read-factory-settings"),
|
||||
("bpy.ops.wm.read_factory_userpref*", "editors/preferences/introduction.html#bpy-ops-wm-read-factory-userpref"),
|
||||
("bpy.types.action.use_frame_range*", "animation/actions.html#bpy-types-action-use-frame-range"),
|
||||
("bpy.types.armature.axes_position*", "animation/armatures/properties/display.html#bpy-types-armature-axes-position"),
|
||||
("bpy.types.armature.pose_position*", "animation/armatures/properties/introduction.html#bpy-types-armature-pose-position"),
|
||||
|
@ -1934,6 +1958,7 @@ url_manual_mapping = (
|
|||
("bpy.types.geometrynodeinputimage*", "modeling/geometry_nodes/input/constant/image.html#bpy-types-geometrynodeinputimage"),
|
||||
("bpy.types.geometrynodeinputindex*", "modeling/geometry_nodes/geometry/read/input_index.html#bpy-types-geometrynodeinputindex"),
|
||||
("bpy.types.geometrynodeisviewport*", "modeling/geometry_nodes/input/scene/is_viewport.html#bpy-types-geometrynodeisviewport"),
|
||||
("bpy.types.geometrynodemenuswitch*", "modeling/geometry_nodes/utilities/menu_switch.html#bpy-types-geometrynodemenuswitch"),
|
||||
("bpy.types.geometrynodemeshcircle*", "modeling/geometry_nodes/mesh/primitives/mesh_circle.html#bpy-types-geometrynodemeshcircle"),
|
||||
("bpy.types.geometrynodeobjectinfo*", "modeling/geometry_nodes/input/scene/object_info.html#bpy-types-geometrynodeobjectinfo"),
|
||||
("bpy.types.geometrynodeselfobject*", "modeling/geometry_nodes/input/scene/self_object.html#bpy-types-geometrynodeselfobject"),
|
||||
|
@ -1966,6 +1991,7 @@ url_manual_mapping = (
|
|||
("bpy.types.sceneeevee.motion_blur*", "render/eevee/render_settings/motion_blur.html#bpy-types-sceneeevee-motion-blur"),
|
||||
("bpy.types.sceneeevee.taa_samples*", "render/eevee/render_settings/sampling.html#bpy-types-sceneeevee-taa-samples"),
|
||||
("bpy.types.sculpt.radial_symmetry*", "sculpt_paint/sculpting/tool_settings/symmetry.html#bpy-types-sculpt-radial-symmetry"),
|
||||
("bpy.types.sequenceproxy.timecode*", "editors/video_sequencer/sequencer/sidebar/proxy.html#bpy-types-sequenceproxy-timecode"),
|
||||
("bpy.types.shadernodecombinecolor*", "render/shader_nodes/converter/combine_color.html#bpy-types-shadernodecombinecolor"),
|
||||
("bpy.types.shadernodedisplacement*", "render/shader_nodes/vector/displacement.html#bpy-types-shadernodedisplacement"),
|
||||
("bpy.types.shadernodelightfalloff*", "render/shader_nodes/color/light_falloff.html#bpy-types-shadernodelightfalloff"),
|
||||
|
@ -2038,6 +2064,7 @@ url_manual_mapping = (
|
|||
("bpy.ops.outliner.show_one_level*", "editors/outliner/editing.html#bpy-ops-outliner-show-one-level"),
|
||||
("bpy.ops.paint.brush_colors_flip*", "sculpt_paint/brush/brush_settings.html#bpy-ops-paint-brush-colors-flip"),
|
||||
("bpy.ops.paint.vertex_color_dirt*", "sculpt_paint/vertex_paint/editing.html#bpy-ops-paint-vertex-color-dirt"),
|
||||
("bpy.ops.paint.visibility_invert*", "sculpt_paint/sculpting/editing/sculpt.html#bpy-ops-paint-visibility-invert"),
|
||||
("bpy.ops.paint.weight_from_bones*", "sculpt_paint/weight_paint/editing.html#bpy-ops-paint-weight-from-bones"),
|
||||
("bpy.ops.paintcurve.delete_point*", "sculpt_paint/brush/stroke.html#bpy-ops-paintcurve-delete-point"),
|
||||
("bpy.ops.pose.paths_range_update*", "animation/motion_paths.html#bpy-ops-pose-paths-range-update"),
|
||||
|
@ -2046,6 +2073,7 @@ url_manual_mapping = (
|
|||
("bpy.ops.screen.screen_full_area*", "interface/window_system/areas.html#bpy-ops-screen-screen-full-area"),
|
||||
("bpy.ops.sculpt.face_sets_create*", "sculpt_paint/sculpting/editing/face_sets.html#bpy-ops-sculpt-face-sets-create"),
|
||||
("bpy.ops.sculpt.trim_box_gesture*", "sculpt_paint/sculpting/editing/sculpt.html#bpy-ops-sculpt-trim-box-gesture"),
|
||||
("bpy.ops.sequencer.rebuild_proxy*", "editors/video_sequencer/sequencer/sidebar/proxy.html#bpy-ops-sequencer-rebuild-proxy"),
|
||||
("bpy.ops.sequencer.retiming_show*", "video_editing/edit/montage/editing.html#bpy-ops-sequencer-retiming-show"),
|
||||
("bpy.ops.sequencer.select_linked*", "video_editing/edit/montage/selecting.html#bpy-ops-sequencer-select-linked"),
|
||||
("bpy.ops.transform.rotate_normal*", "modeling/meshes/editing/mesh/normals.html#bpy-ops-transform-rotate-normal"),
|
||||
|
@ -2122,6 +2150,7 @@ url_manual_mapping = (
|
|||
("bpy.types.sculpt.detail_percent*", "sculpt_paint/sculpting/tool_settings/dyntopo.html#bpy-types-sculpt-detail-percent"),
|
||||
("bpy.types.sculpt.gravity_object*", "sculpt_paint/sculpting/tool_settings/options.html#bpy-types-sculpt-gravity-object"),
|
||||
("bpy.types.sculpt.show_face_sets*", "sculpt_paint/sculpting/editing/face_sets.html#bpy-types-sculpt-show-face-sets"),
|
||||
("bpy.types.sequenceproxy.quality*", "editors/video_sequencer/sequencer/sidebar/proxy.html#bpy-types-sequenceproxy-quality"),
|
||||
("bpy.types.shadernodebsdfdiffuse*", "render/shader_nodes/shader/diffuse.html#bpy-types-shadernodebsdfdiffuse"),
|
||||
("bpy.types.shadernodelayerweight*", "render/shader_nodes/input/layer_weight.html#bpy-types-shadernodelayerweight"),
|
||||
("bpy.types.shadernodenewgeometry*", "render/shader_nodes/input/geometry.html#bpy-types-shadernodenewgeometry"),
|
||||
|
@ -2163,6 +2192,7 @@ url_manual_mapping = (
|
|||
("bpy.ops.gpencil.stroke_outline*", "grease_pencil/modes/edit/stroke_menu.html#bpy-ops-gpencil-stroke-outline"),
|
||||
("bpy.ops.graph.blend_to_default*", "editors/graph_editor/fcurves/editing.html#bpy-ops-graph-blend-to-default"),
|
||||
("bpy.ops.graph.equalize_handles*", "editors/graph_editor/fcurves/editing.html#bpy-ops-graph-equalize-handles"),
|
||||
("bpy.ops.graph.select_leftright*", "editors/graph_editor/introduction.html#bpy-ops-graph-select-leftright"),
|
||||
("bpy.ops.graph.sound_to_samples*", "editors/graph_editor/channels/editing.html#bpy-ops-graph-sound-to-samples"),
|
||||
("bpy.ops.mball.delete_metaelems*", "modeling/metas/editing.html#bpy-ops-mball-delete-metaelems"),
|
||||
("bpy.ops.mball.reveal_metaelems*", "modeling/metas/properties.html#bpy-ops-mball-reveal-metaelems"),
|
||||
|
@ -2370,6 +2400,7 @@ url_manual_mapping = (
|
|||
("bpy.types.compositornodeimage*", "compositing/types/input/image.html#bpy-types-compositornodeimage"),
|
||||
("bpy.types.compositornodemapuv*", "compositing/types/transform/map_uv.html#bpy-types-compositornodemapuv"),
|
||||
("bpy.types.compositornodescale*", "compositing/types/transform/scale.html#bpy-types-compositornodescale"),
|
||||
("bpy.types.compositornodesplit*", "compositing/types/utilities/split.html#bpy-types-compositornodesplit"),
|
||||
("bpy.types.compositornodevalue*", "compositing/types/input/constant/value.html#bpy-types-compositornodevalue"),
|
||||
("bpy.types.copyscaleconstraint*", "animation/constraints/transform/copy_scale.html#bpy-types-copyscaleconstraint"),
|
||||
("bpy.types.curve.path_duration*", "modeling/curves/properties/path_animation.html#bpy-types-curve-path-duration"),
|
||||
|
@ -2401,6 +2432,7 @@ url_manual_mapping = (
|
|||
("bpy.types.rigidbodyconstraint*", "physics/rigid_body/constraints/index.html#bpy-types-rigidbodyconstraint"),
|
||||
("bpy.types.rigifyarmaturelayer*", "addons/rigging/rigify/metarigs.html#bpy-types-rigifyarmaturelayer"),
|
||||
("bpy.types.scene.show_subframe*", "editors/timeline.html#bpy-types-scene-show-subframe"),
|
||||
("bpy.types.sequenceproxy.build*", "editors/video_sequencer/sequencer/sidebar/proxy.html#bpy-types-sequenceproxy-build"),
|
||||
("bpy.types.shadernodeaddshader*", "render/shader_nodes/shader/add.html#bpy-types-shadernodeaddshader"),
|
||||
("bpy.types.shadernodeattribute*", "render/shader_nodes/input/attribute.html#bpy-types-shadernodeattribute"),
|
||||
("bpy.types.shadernodeblackbody*", "render/shader_nodes/converter/blackbody.html#bpy-types-shadernodeblackbody"),
|
||||
|
@ -2412,6 +2444,7 @@ url_manual_mapping = (
|
|||
("bpy.types.shadernodeoutputaov*", "render/shader_nodes/output/aov.html#bpy-types-shadernodeoutputaov"),
|
||||
("bpy.types.shadernodepointinfo*", "render/shader_nodes/input/point_info.html#bpy-types-shadernodepointinfo"),
|
||||
("bpy.types.shadernodewireframe*", "render/shader_nodes/input/wireframe.html#bpy-types-shadernodewireframe"),
|
||||
("bpy.types.shapekey.lock_shape*", "animation/shape_keys/shape_keys_panel.html#bpy-types-shapekey-lock-shape"),
|
||||
("bpy.types.shapekey.slider_max*", "animation/shape_keys/shape_keys_panel.html#bpy-types-shapekey-slider-max"),
|
||||
("bpy.types.shapekey.slider_min*", "animation/shape_keys/shape_keys_panel.html#bpy-types-shapekey-slider-min"),
|
||||
("bpy.types.spacesequenceeditor*", "editors/video_sequencer/index.html#bpy-types-spacesequenceeditor"),
|
||||
|
@ -2491,6 +2524,7 @@ url_manual_mapping = (
|
|||
("bpy.ops.sculpt.face_set_edit*", "sculpt_paint/sculpting/editing/face_sets.html#bpy-ops-sculpt-face-set-edit"),
|
||||
("bpy.ops.sequencer.gap_insert*", "video_editing/edit/montage/editing.html#bpy-ops-sequencer-gap-insert"),
|
||||
("bpy.ops.sequencer.gap_remove*", "video_editing/edit/montage/editing.html#bpy-ops-sequencer-gap-remove"),
|
||||
("bpy.ops.sequencer.hold_split*", "video_editing/edit/montage/editing.html#bpy-ops-sequencer-hold-split"),
|
||||
("bpy.ops.sequencer.rendersize*", "video_editing/edit/montage/editing.html#bpy-ops-sequencer-rendersize"),
|
||||
("bpy.ops.sequencer.select_all*", "video_editing/edit/montage/selecting.html#bpy-ops-sequencer-select-all"),
|
||||
("bpy.ops.sequencer.select_box*", "video_editing/edit/montage/selecting.html#bpy-ops-sequencer-select-box"),
|
||||
|
@ -2609,8 +2643,11 @@ url_manual_mapping = (
|
|||
("bpy.ops.gpencil.stroke_trim*", "grease_pencil/modes/edit/stroke_menu.html#bpy-ops-gpencil-stroke-trim"),
|
||||
("bpy.ops.gpencil.trace_image*", "grease_pencil/modes/object/trace_image.html#bpy-ops-gpencil-trace-image"),
|
||||
("bpy.ops.graph.blend_to_ease*", "editors/graph_editor/fcurves/editing.html#bpy-ops-graph-blend-to-ease"),
|
||||
("bpy.ops.graph.channels_bake*", "editors/graph_editor/channels/editing.html#bpy-ops-graph-channels-bake"),
|
||||
("bpy.ops.graph.fmodifier_add*", "editors/graph_editor/channels/editing.html#bpy-ops-graph-fmodifier-add"),
|
||||
("bpy.ops.graph.scale_average*", "editors/graph_editor/fcurves/editing.html#bpy-ops-graph-scale-average"),
|
||||
("bpy.ops.graph.select_column*", "editors/graph_editor/introduction.html#bpy-ops-graph-select-column"),
|
||||
("bpy.ops.graph.select_linked*", "editors/graph_editor/introduction.html#bpy-ops-graph-select-linked"),
|
||||
("bpy.ops.image.external_edit*", "editors/image/editing.html#bpy-ops-image-external-edit"),
|
||||
("bpy.ops.mesh.colors_reverse*", "modeling/meshes/editing/face/face_data.html#bpy-ops-mesh-colors-reverse"),
|
||||
("bpy.ops.mesh.dissolve_edges*", "modeling/meshes/editing/mesh/delete.html#bpy-ops-mesh-dissolve-edges"),
|
||||
|
@ -2889,6 +2926,8 @@ url_manual_mapping = (
|
|||
("bpy.ops.graph.easing_type*", "editors/graph_editor/fcurves/editing.html#bpy-ops-graph-easing-type"),
|
||||
("bpy.ops.graph.handle_type*", "editors/graph_editor/fcurves/editing.html#bpy-ops-graph-handle-type"),
|
||||
("bpy.ops.graph.match_slope*", "editors/graph_editor/fcurves/editing.html#bpy-ops-graph-match-slope"),
|
||||
("bpy.ops.graph.select_less*", "editors/graph_editor/introduction.html#bpy-ops-graph-select-less"),
|
||||
("bpy.ops.graph.select_more*", "editors/graph_editor/introduction.html#bpy-ops-graph-select-more"),
|
||||
("bpy.ops.graph.time_offset*", "editors/graph_editor/fcurves/editing.html#bpy-ops-graph-time-offset"),
|
||||
("bpy.ops.marker.select_all*", "animation/markers.html#bpy-ops-marker-select-all"),
|
||||
("bpy.ops.mask.copy_splines*", "movie_clip/masking/editing.html#bpy-ops-mask-copy-splines"),
|
||||
|
@ -2919,7 +2958,6 @@ url_manual_mapping = (
|
|||
("bpy.ops.screen.area_split*", "interface/window_system/areas.html#bpy-ops-screen-area-split"),
|
||||
("bpy.ops.screen.screenshot*", "interface/window_system/topbar.html#bpy-ops-screen-screenshot"),
|
||||
("bpy.ops.sculpt.dirty_mask*", "sculpt_paint/sculpting/editing/mask.html#bpy-ops-sculpt-dirty-mask"),
|
||||
("bpy.ops.sculpt.reveal_all*", "sculpt_paint/sculpting/editing/face_sets.html#bpy-ops-sculpt-reveal-all"),
|
||||
("bpy.ops.sculpt.symmetrize*", "sculpt_paint/sculpting/tool_settings/symmetry.html#bpy-ops-sculpt-symmetrize"),
|
||||
("bpy.ops.uv.align_rotation*", "modeling/meshes/uv/editing.html#bpy-ops-uv-align-rotation"),
|
||||
("bpy.ops.uv.remove_doubles*", "modeling/meshes/uv/editing.html#bpy-ops-uv-remove-doubles"),
|
||||
|
@ -2988,6 +3026,8 @@ url_manual_mapping = (
|
|||
("bpy.ops.font.textbox_add*", "modeling/texts/properties.html#bpy-ops-font-textbox-add"),
|
||||
("bpy.ops.gpencil.dissolve*", "grease_pencil/modes/edit/grease_pencil_menu.html#bpy-ops-gpencil-dissolve"),
|
||||
("bpy.ops.graph.frame_jump*", "editors/graph_editor/fcurves/editing.html#bpy-ops-graph-frame-jump"),
|
||||
("bpy.ops.graph.select_all*", "editors/graph_editor/introduction.html#bpy-ops-graph-select-all"),
|
||||
("bpy.ops.graph.select_box*", "editors/graph_editor/introduction.html#bpy-ops-graph-select-box"),
|
||||
("bpy.ops.marker.duplicate*", "animation/markers.html#bpy-ops-marker-duplicate"),
|
||||
("bpy.ops.mask.select_less*", "movie_clip/masking/selecting.html#bpy-ops-mask-select-less"),
|
||||
("bpy.ops.mask.select_more*", "movie_clip/masking/selecting.html#bpy-ops-mask-select-more"),
|
||||
|
@ -3028,8 +3068,10 @@ url_manual_mapping = (
|
|||
("bpy.ops.view3d.view_roll*", "editors/3dview/navigate/navigation.html#bpy-ops-view3d-view-roll"),
|
||||
("bpy.ops.wm.open_mainfile*", "files/blend/open_save.html#bpy-ops-wm-open-mainfile"),
|
||||
("bpy.ops.wm.owner_disable*", "interface/window_system/workspaces.html#bpy-ops-wm-owner-disable"),
|
||||
("bpy.ops.wm.read_userpref*", "editors/preferences/introduction.html#bpy-ops-wm-read-userpref"),
|
||||
("bpy.ops.wm.save_homefile*", "interface/window_system/topbar.html#bpy-ops-wm-save-homefile"),
|
||||
("bpy.ops.wm.save_mainfile*", "files/blend/open_save.html#bpy-ops-wm-save-mainfile"),
|
||||
("bpy.ops.wm.save_userpref*", "editors/preferences/introduction.html#bpy-ops-wm-save-userpref"),
|
||||
("bpy.types.arealight.size*", "render/lights/light_object.html#bpy-types-arealight-size"),
|
||||
("bpy.types.attributegroup*", "modeling/meshes/properties/object_data.html#bpy-types-attributegroup"),
|
||||
("bpy.types.bone.show_wire*", "animation/armatures/bones/properties/display.html#bpy-types-bone-show-wire"),
|
||||
|
@ -3115,6 +3157,7 @@ url_manual_mapping = (
|
|||
("bpy.ops.object.join_uvs*", "scene_layout/object/editing/link_transfer/copy_uvmaps.html#bpy-ops-object-join-uvs"),
|
||||
("bpy.ops.object.mode_set*", "editors/3dview/modes.html#bpy-ops-object-mode-set"),
|
||||
("bpy.ops.outliner.delete*", "editors/outliner/editing.html#bpy-ops-outliner-delete"),
|
||||
("bpy.ops.paint.hide_show*", "sculpt_paint/sculpting/editing/sculpt.html#bpy-ops-paint-hide-show"),
|
||||
("bpy.ops.paintcurve.draw*", "sculpt_paint/brush/stroke.html#bpy-ops-paintcurve-draw"),
|
||||
("bpy.ops.pose.relax_rest*", "animation/armatures/posing/editing/in_betweens.html#bpy-ops-pose-relax-rest"),
|
||||
("bpy.ops.pose.select_all*", "animation/armatures/posing/selecting.html#bpy-ops-pose-select-all"),
|
||||
|
|
|
@ -1299,7 +1299,6 @@ def km_outliner(params):
|
|||
("outliner.show_one_level", {"type": 'NUMPAD_MINUS', "value": 'PRESS'},
|
||||
{"properties": [("open", False)]}),
|
||||
*_template_items_select_actions(params, "outliner.select_all"),
|
||||
("outliner.expanded_toggle", {"type": 'A', "value": 'PRESS', "shift": True}, None),
|
||||
("outliner.keyingset_add_selected", {"type": 'K', "value": 'PRESS'}, None),
|
||||
("outliner.keyingset_remove_selected", {"type": 'K', "value": 'PRESS', "alt": True}, None),
|
||||
("anim.keyframe_insert", {"type": 'I', "value": 'PRESS'}, None),
|
||||
|
@ -1318,6 +1317,11 @@ def km_outliner(params):
|
|||
# Copy/paste.
|
||||
("outliner.id_copy", {"type": 'C', "value": 'PRESS', "ctrl": True}, None),
|
||||
("outliner.id_paste", {"type": 'V', "value": 'PRESS', "ctrl": True}, None),
|
||||
|
||||
op_menu("VIEW3D_MT_add", {"type": 'A', "value": 'PRESS', "shift": True}),
|
||||
("object.duplicate", {"type": 'D', "value": 'PRESS', "shift": True}, None),
|
||||
("object.duplicate", {"type": 'D', "value": 'PRESS', "alt": True},
|
||||
{"properties": [("linked", True)]}),
|
||||
])
|
||||
|
||||
return keymap
|
||||
|
@ -4612,6 +4616,8 @@ def km_grease_pencil_edit_mode(params):
|
|||
# Dissolve
|
||||
("grease_pencil.dissolve", {"type": 'X', "value": 'PRESS', "ctrl": True}, None),
|
||||
("grease_pencil.dissolve", {"type": 'DEL', "value": 'PRESS', "ctrl": True}, None),
|
||||
# Separate
|
||||
("grease_pencil.separate", {"type": 'P', "value": 'PRESS'}, None),
|
||||
# Delete all active frames
|
||||
("grease_pencil.delete_frame", {"type": 'DEL', "value": 'PRESS', "shift": True},
|
||||
{"properties": [("type", "ALL_FRAMES")]}),
|
||||
|
|
|
@ -557,6 +557,8 @@ def km_outliner(params):
|
|||
# Copy/paste.
|
||||
("outliner.id_copy", {"type": 'C', "value": 'PRESS', "ctrl": True}, None),
|
||||
("outliner.id_paste", {"type": 'V', "value": 'PRESS', "ctrl": True}, None),
|
||||
|
||||
("object.duplicate", {"type": 'D', "value": 'PRESS', "ctrl": True}, None),
|
||||
])
|
||||
|
||||
return keymap
|
||||
|
|
|
@ -6,10 +6,12 @@ import bpy
|
|||
from bpy.types import (
|
||||
Menu,
|
||||
Operator,
|
||||
OperatorFileListElement,
|
||||
WindowManager,
|
||||
)
|
||||
from bpy.props import (
|
||||
BoolProperty,
|
||||
CollectionProperty,
|
||||
StringProperty,
|
||||
)
|
||||
from bpy.app.translations import (
|
||||
|
@ -622,7 +624,7 @@ class AddPresetOperator(AddPresetBase, Operator):
|
|||
|
||||
ret = []
|
||||
for prop_id, prop in operator_rna.properties.items():
|
||||
if not (prop.is_hidden or prop.is_skip_save):
|
||||
if not prop.is_skip_preset:
|
||||
if prop_id not in properties_blacklist:
|
||||
ret.append("op.%s" % prop_id)
|
||||
|
||||
|
@ -655,6 +657,74 @@ class WM_MT_operator_presets(Menu):
|
|||
preset_operator = "script.execute_preset"
|
||||
|
||||
|
||||
class WM_OT_operator_presets_cleanup(Operator):
|
||||
bl_idname = "wm.operator_presets_cleanup"
|
||||
bl_label = "Clean Up Operator Presets"
|
||||
bl_description = "Remove outdated operator properties from presets that may cause problems"
|
||||
|
||||
operator: StringProperty(name="operator")
|
||||
properties: CollectionProperty(name="properties", type=OperatorFileListElement)
|
||||
|
||||
def cleanup_preset(self, filepath, properties):
|
||||
from pathlib import Path
|
||||
file = Path(filepath)
|
||||
if not (file.is_file() and filepath.suffix == ".py"):
|
||||
return
|
||||
lines = file.read_text().splitlines(True)
|
||||
if len(lines) == 0:
|
||||
return
|
||||
new_lines = []
|
||||
for line in lines:
|
||||
if not any(line.startswith(("op.%s" % prop)) for prop in properties):
|
||||
new_lines.append(line)
|
||||
file.write_text("".join(new_lines))
|
||||
|
||||
def cleanup_operators_presets(self, operators, properties):
|
||||
base_preset_directory = bpy.utils.user_resource(
|
||||
'SCRIPTS', path="presets", create=False)
|
||||
for operator in operators:
|
||||
from pathlib import Path
|
||||
operator_path = AddPresetOperator.operator_path(operator)
|
||||
directory = Path(base_preset_directory, operator_path)
|
||||
|
||||
if not directory.is_dir():
|
||||
continue
|
||||
|
||||
for filepath in directory.iterdir():
|
||||
self.cleanup_preset(filepath, properties)
|
||||
|
||||
def execute(self, context):
|
||||
properties = []
|
||||
operators = []
|
||||
if self.operator:
|
||||
operators.append(self.operator)
|
||||
for prop in self.properties:
|
||||
properties.append(prop.name)
|
||||
else:
|
||||
# Cleanup by default I/O Operators Presets
|
||||
operators = ['WM_OT_alembic_export',
|
||||
'WM_OT_alembic_import',
|
||||
'WM_OT_collada_export',
|
||||
'WM_OT_collada_import',
|
||||
'WM_OT_gpencil_export_svg',
|
||||
'WM_OT_gpencil_export_pdf',
|
||||
'WM_OT_gpencil_export_svg',
|
||||
'WM_OT_gpencil_import_svg',
|
||||
'WM_OT_obj_export',
|
||||
'WM_OT_obj_import',
|
||||
'WM_OT_ply_export',
|
||||
'WM_OT_ply_import',
|
||||
'WM_OT_stl_export',
|
||||
'WM_OT_stl_import',
|
||||
'WM_OT_usd_export',
|
||||
'WM_OT_usd_import',
|
||||
]
|
||||
properties = ["filepath", "directory", "files", "filename"]
|
||||
|
||||
self.cleanup_operators_presets(operators, properties)
|
||||
return {'FINISHED'}
|
||||
|
||||
|
||||
class AddPresetGpencilBrush(AddPresetBase, Operator):
|
||||
"""Add or remove grease pencil brush preset"""
|
||||
bl_idname = "scene.gpencil_brush_preset_add"
|
||||
|
@ -748,4 +818,5 @@ classes = (
|
|||
AddPresetEEVEERaytracing,
|
||||
ExecutePreset,
|
||||
WM_MT_operator_presets,
|
||||
WM_OT_operator_presets_cleanup,
|
||||
)
|
||||
|
|
|
@ -148,6 +148,8 @@ class PREFERENCES_OT_copy_prev(Operator):
|
|||
# Reload preferences and `recent-files.txt`.
|
||||
bpy.ops.wm.read_userpref()
|
||||
bpy.ops.wm.read_history()
|
||||
# Fix operator presets that have unwanted filepath properties
|
||||
bpy.ops.wm.operator_presets_cleanup()
|
||||
|
||||
# don't loose users work if they open the splash later.
|
||||
if bpy.data.is_saved is bpy.data.is_dirty is False:
|
||||
|
|
|
@ -3487,7 +3487,8 @@ class WM_MT_region_toggle_pie(Menu):
|
|||
text = enum_items[region_type].name
|
||||
attr = cls._region_info[region_type]
|
||||
value = getattr(space_data, attr)
|
||||
props = pie.operator("wm.context_toggle", text=text, icon='CHECKBOX_HLT' if value else 'CHECKBOX_DEHLT')
|
||||
props = pie.operator("wm.context_toggle", text=text, text_ctxt=i18n_contexts.default,
|
||||
icon='CHECKBOX_HLT' if value else 'CHECKBOX_DEHLT')
|
||||
props.data_path = "space_data." + attr
|
||||
|
||||
def draw(self, context):
|
||||
|
|
|
@ -7,6 +7,7 @@ from bpy.types import Menu
|
|||
from bl_ui import node_add_menu
|
||||
from bpy.app.translations import (
|
||||
pgettext_iface as iface_,
|
||||
contexts as i18n_contexts,
|
||||
)
|
||||
|
||||
|
||||
|
@ -231,6 +232,7 @@ class NODE_MT_category_compositor_mask(Menu):
|
|||
class NODE_MT_category_compositor_tracking(Menu):
|
||||
bl_idname = "NODE_MT_category_compositor_tracking"
|
||||
bl_label = "Tracking"
|
||||
bl_translation_context = i18n_contexts.id_movieclip
|
||||
|
||||
def draw(self, _context):
|
||||
layout = self.layout
|
||||
|
|
|
@ -542,6 +542,7 @@ class NODE_MT_category_GEO_UTILITIES(Menu):
|
|||
layout.menu("NODE_MT_category_GEO_UTILITIES_FIELD")
|
||||
layout.menu("NODE_MT_category_GEO_UTILITIES_MATH")
|
||||
layout.menu("NODE_MT_category_GEO_UTILITIES_ROTATION")
|
||||
layout.menu("NODE_MT_category_GEO_UTILITIES_DEPRECATED")
|
||||
layout.separator()
|
||||
node_add_menu.add_node_type(layout, "GeometryNodeIndexSwitch")
|
||||
node_add_menu.add_node_type(layout, "GeometryNodeMenuSwitch")
|
||||
|
@ -551,6 +552,15 @@ class NODE_MT_category_GEO_UTILITIES(Menu):
|
|||
node_add_menu.draw_assets_for_catalog(layout, self.bl_label)
|
||||
|
||||
|
||||
class NODE_MT_category_GEO_UTILITIES_DEPRECATED(Menu):
|
||||
bl_idname = "NODE_MT_category_GEO_UTILITIES_DEPRECATED"
|
||||
bl_label = "Deprecated"
|
||||
|
||||
def draw(self, context):
|
||||
layout = self.layout
|
||||
node_add_menu.add_node_type(layout, "FunctionNodeRotateEuler")
|
||||
|
||||
|
||||
class NODE_MT_category_GEO_UTILITIES_FIELD(Menu):
|
||||
bl_idname = "NODE_MT_category_GEO_UTILITIES_FIELD"
|
||||
bl_label = "Field"
|
||||
|
@ -769,6 +779,7 @@ classes = (
|
|||
NODE_MT_category_GEO_UTILITIES_FIELD,
|
||||
NODE_MT_category_GEO_UTILITIES_MATH,
|
||||
NODE_MT_category_GEO_UTILITIES_ROTATION,
|
||||
NODE_MT_category_GEO_UTILITIES_DEPRECATED,
|
||||
NODE_MT_category_GEO_GROUP,
|
||||
)
|
||||
|
||||
|
|
|
@ -42,6 +42,9 @@ class MotionPathButtonsPanel:
|
|||
start_end_group.prop(mps, "frame_end", text="End")
|
||||
col.prop(mps, "frame_step", text="Step")
|
||||
|
||||
row = col.row()
|
||||
row.prop(mps, "bake_in_camera_space", text="Bake to Active Camera")
|
||||
|
||||
if bones:
|
||||
op_category = "pose"
|
||||
icon = 'BONE_DATA'
|
||||
|
|
|
@ -118,13 +118,15 @@ class DATA_PT_bone_collections(ArmatureButtonsPanel, Panel):
|
|||
col = row.column(align=True)
|
||||
col.operator("armature.collection_add", icon='ADD', text="")
|
||||
col.operator("armature.collection_remove", icon='REMOVE', text="")
|
||||
|
||||
col.separator()
|
||||
|
||||
col.menu("ARMATURE_MT_collection_context_menu", icon='DOWNARROW_HLT', text="")
|
||||
|
||||
if active_bcoll:
|
||||
col.separator()
|
||||
col.operator("armature.collection_move", icon='TRIA_UP', text="").direction = 'UP'
|
||||
col.operator("armature.collection_move", icon='TRIA_DOWN', text="").direction = 'DOWN'
|
||||
col.separator()
|
||||
|
||||
col.menu("ARMATURE_MT_collection_context_menu", icon='DOWNARROW_HLT', text="")
|
||||
|
||||
row = layout.row()
|
||||
|
||||
|
|
|
@ -380,7 +380,7 @@ class DATA_PT_camera_background_image(CameraButtonsPanel, Panel):
|
|||
col = box.column()
|
||||
if bg.image is not None:
|
||||
col.prop(bg.image, "use_view_as_render")
|
||||
col.prop(bg, "alpha", slider=True)
|
||||
col.prop(bg, "alpha")
|
||||
col.row().prop(bg, "display_depth", expand=True)
|
||||
|
||||
col.row().prop(bg, "frame_method", expand=True)
|
||||
|
|
|
@ -15,6 +15,17 @@ class DataButtonsPanel:
|
|||
return hasattr(context, "grease_pencil") and context.grease_pencil
|
||||
|
||||
|
||||
class LayerDataButtonsPanel:
|
||||
bl_space_type = 'PROPERTIES'
|
||||
bl_region_type = 'WINDOW'
|
||||
bl_context = "data"
|
||||
|
||||
@classmethod
|
||||
def poll(cls, context):
|
||||
grease_pencil = context.grease_pencil
|
||||
return grease_pencil and grease_pencil.layers.active
|
||||
|
||||
|
||||
class DATA_PT_context_grease_pencil(DataButtonsPanel, Panel):
|
||||
bl_label = ""
|
||||
bl_options = {'HIDE_HEADER'}
|
||||
|
@ -67,13 +78,59 @@ class DATA_PT_grease_pencil_layers(DataButtonsPanel, Panel):
|
|||
layout.use_property_decorate = True
|
||||
col = layout.column(align=True)
|
||||
|
||||
col = layout.row(align=True)
|
||||
col.prop(layer, "opacity", text="Opacity", slider=True)
|
||||
row = layout.row(align=True)
|
||||
row.prop(layer, "opacity", text="Opacity", slider=True)
|
||||
|
||||
|
||||
class DATA_PT_grease_pencil_layer_transform(LayerDataButtonsPanel, Panel):
|
||||
bl_label = "Transform"
|
||||
bl_parent_id = "DATA_PT_grease_pencil_layers"
|
||||
bl_options = {'DEFAULT_CLOSED'}
|
||||
|
||||
def draw(self, context):
|
||||
layout = self.layout
|
||||
layout.use_property_split = True
|
||||
|
||||
grease_pencil = context.grease_pencil
|
||||
layer = grease_pencil.layers.active
|
||||
layout.active = not layer.lock
|
||||
|
||||
row = layout.row(align=True)
|
||||
row.prop(layer, "translation")
|
||||
|
||||
row = layout.row(align=True)
|
||||
row.prop(layer, "rotation")
|
||||
|
||||
row = layout.row(align=True)
|
||||
row.prop(layer, "scale")
|
||||
|
||||
|
||||
class DATA_PT_grease_pencil_layer_relations(LayerDataButtonsPanel, Panel):
|
||||
bl_label = "Relations"
|
||||
bl_parent_id = "DATA_PT_grease_pencil_layers"
|
||||
bl_options = {'DEFAULT_CLOSED'}
|
||||
|
||||
def draw(self, context):
|
||||
layout = self.layout
|
||||
layout.use_property_split = True
|
||||
|
||||
grease_pencil = context.grease_pencil
|
||||
layer = grease_pencil.layers.active
|
||||
layout.active = not layer.lock
|
||||
|
||||
row = layout.row(align=True)
|
||||
row.prop(layer, "parent", text="Parent")
|
||||
|
||||
if layer.parent and layer.parent.type == 'ARMATURE':
|
||||
row = layout.row(align=True)
|
||||
row.prop_search(layer, "parent_bone", layer.parent.data, "bones", text="Bone")
|
||||
|
||||
|
||||
classes = (
|
||||
DATA_PT_context_grease_pencil,
|
||||
DATA_PT_grease_pencil_layers,
|
||||
DATA_PT_grease_pencil_layer_transform,
|
||||
DATA_PT_grease_pencil_layer_relations,
|
||||
GREASE_PENCIL_MT_grease_pencil_add_layer_extra,
|
||||
)
|
||||
|
||||
|
|
|
@ -608,7 +608,7 @@ class GreasePencilMaterialsPanel:
|
|||
row.operator("grease_pencil.stroke_material_set", text="Assign")
|
||||
elif not is_grease_pencil_version3 and ob.data.use_stroke_edit_mode:
|
||||
row = layout.row(align=True)
|
||||
row.operator("gpencil.stroke_material_set", text="Assign")
|
||||
row.operator("gpencil.stroke_change_color", text="Assign")
|
||||
row.operator("gpencil.material_select", text="Select").deselect = False
|
||||
row.operator("gpencil.material_select", text="Deselect").deselect = True
|
||||
# stroke color
|
||||
|
|
|
@ -212,10 +212,10 @@ class MASK_PT_point:
|
|||
if parent.parent in tracking.objects:
|
||||
ob = tracking.objects[parent.parent]
|
||||
col.prop_search(parent, "sub_parent", ob,
|
||||
tracks_list, icon='ANIM_DATA', text="Track")
|
||||
tracks_list, icon='ANIM_DATA', text="Track", text_ctxt=i18n_contexts.id_movieclip)
|
||||
else:
|
||||
col.prop_search(parent, "sub_parent", tracking,
|
||||
tracks_list, icon='ANIM_DATA', text="Track")
|
||||
tracks_list, icon='ANIM_DATA', text="Track", text_ctxt=i18n_contexts.id_movieclip)
|
||||
|
||||
|
||||
class MASK_PT_display:
|
||||
|
|
|
@ -395,7 +395,7 @@ class OBJECT_PT_visibility(ObjectButtonsPanel, Panel):
|
|||
col = layout.column(heading="Ray Visibility")
|
||||
col.prop(ob, "visible_shadow", text="Shadow", toggle=False)
|
||||
|
||||
if ob.type in {'MESH', 'CURVE', 'SURFACE', 'META', 'FONT', 'CURVES', 'POINTCLOUD', 'VOLUME', 'LIGHT'}:
|
||||
if ob.type in {'MESH', 'CURVE', 'SURFACE', 'META', 'FONT', 'CURVES', 'POINTCLOUD', 'VOLUME'}:
|
||||
layout.separator()
|
||||
col = layout.column(heading="Light Probes")
|
||||
col.prop(ob, "hide_probe_volume", text="Volume", toggle=False, invert_checkbox=True)
|
||||
|
|
|
@ -319,6 +319,32 @@ class VIEWLAYER_PT_layer_passes_lightgroups(ViewLayerLightgroupsPanel):
|
|||
COMPAT_ENGINES = {'CYCLES'}
|
||||
|
||||
|
||||
class VIEWLAYER_PT_filter(ViewLayerButtonsPanel, Panel):
|
||||
bl_label = "Filter"
|
||||
bl_options = {'DEFAULT_CLOSED'}
|
||||
COMPAT_ENGINES = {'BLENDER_EEVEE_NEXT'}
|
||||
|
||||
def draw(self, context):
|
||||
layout = self.layout
|
||||
layout.use_property_split = True
|
||||
layout.use_property_decorate = False
|
||||
|
||||
scene = context.scene
|
||||
rd = scene.render
|
||||
view_layer = context.view_layer
|
||||
|
||||
col = layout.column(heading="Include")
|
||||
col.prop(view_layer, "use_sky", text="Environment")
|
||||
col.prop(view_layer, "use_solid", text="Surfaces")
|
||||
col.prop(view_layer, "use_strand", text="Curves")
|
||||
col.prop(view_layer, "use_volumes", text="Volumes")
|
||||
|
||||
col = layout.column(heading="Use")
|
||||
sub = col.row()
|
||||
sub.prop(view_layer, "use_motion_blur", text="Motion Blur")
|
||||
sub.active = scene.eevee.use_motion_blur
|
||||
|
||||
|
||||
class VIEWLAYER_PT_layer_custom_props(PropertyPanel, Panel):
|
||||
bl_space_type = 'PROPERTIES'
|
||||
bl_region_type = 'WINDOW'
|
||||
|
@ -340,6 +366,7 @@ classes = (
|
|||
VIEWLAYER_PT_layer_passes_cryptomatte,
|
||||
VIEWLAYER_PT_layer_passes_aov,
|
||||
VIEWLAYER_PT_layer_passes_lightgroups,
|
||||
VIEWLAYER_PT_filter,
|
||||
VIEWLAYER_PT_layer_custom_props,
|
||||
VIEWLAYER_UL_aov,
|
||||
)
|
||||
|
|
|
@ -363,7 +363,7 @@ class CLIP_PT_tools_clip(Panel):
|
|||
bl_space_type = 'CLIP_EDITOR'
|
||||
bl_region_type = 'TOOLS'
|
||||
bl_label = "Clip"
|
||||
bl_translation_context = bpy.app.translations.contexts.id_movieclip
|
||||
bl_translation_context = i18n_contexts.id_movieclip
|
||||
bl_category = "Track"
|
||||
|
||||
@classmethod
|
||||
|
@ -473,6 +473,7 @@ class CLIP_PT_tools_tracking(CLIP_PT_tracking_panel, Panel):
|
|||
bl_space_type = 'CLIP_EDITOR'
|
||||
bl_region_type = 'TOOLS'
|
||||
bl_label = "Track"
|
||||
bl_translation_context = i18n_contexts.id_movieclip
|
||||
bl_category = "Track"
|
||||
bl_options = {'DEFAULT_CLOSED'}
|
||||
|
||||
|
@ -725,6 +726,7 @@ class CLIP_PT_track(CLIP_PT_tracking_panel, Panel):
|
|||
bl_region_type = 'UI'
|
||||
bl_category = "Track"
|
||||
bl_label = "Track"
|
||||
bl_translation_context = i18n_contexts.id_movieclip
|
||||
|
||||
def draw(self, context):
|
||||
layout = self.layout
|
||||
|
@ -1265,7 +1267,6 @@ class CLIP_PT_tools_scenesetup(Panel):
|
|||
bl_space_type = 'CLIP_EDITOR'
|
||||
bl_region_type = 'TOOLS'
|
||||
bl_label = "Scene Setup"
|
||||
bl_translation_context = bpy.app.translations.contexts.id_movieclip
|
||||
bl_category = "Solve"
|
||||
|
||||
@classmethod
|
||||
|
@ -1364,7 +1365,7 @@ class CLIP_MT_view(Menu):
|
|||
|
||||
class CLIP_MT_clip(Menu):
|
||||
bl_label = "Clip"
|
||||
bl_translation_context = bpy.app.translations.contexts.id_movieclip
|
||||
bl_translation_context = i18n_contexts.id_movieclip
|
||||
|
||||
def draw(self, context):
|
||||
layout = self.layout
|
||||
|
|
|
@ -159,6 +159,7 @@ class GRAPH_MT_view(Menu):
|
|||
layout.prop(st, "use_realtime_update")
|
||||
layout.prop(st, "show_sliders")
|
||||
layout.prop(st, "use_auto_merge_keyframes")
|
||||
layout.prop(st, "autolock_translation_axis")
|
||||
layout.separator()
|
||||
|
||||
if st.mode != 'DRIVERS':
|
||||
|
|
|
@ -1431,8 +1431,11 @@ class IMAGE_PT_view_vectorscope(ImageScopesPanel, Panel):
|
|||
layout = self.layout
|
||||
|
||||
sima = context.space_data
|
||||
|
||||
layout.template_vectorscope(sima, "scopes")
|
||||
layout.prop(sima.scopes, "vectorscope_alpha")
|
||||
row = layout.split(factor=0.75)
|
||||
row.prop(sima.scopes, "vectorscope_alpha")
|
||||
row.prop(sima.scopes, "vectorscope_mode", text="")
|
||||
|
||||
|
||||
class IMAGE_PT_sample_line(ImageScopesPanel, Panel):
|
||||
|
|
|
@ -206,6 +206,7 @@ class NLA_MT_add(Menu):
|
|||
|
||||
class NLA_MT_tracks(Menu):
|
||||
bl_label = "Track"
|
||||
bl_translation_context = i18n_contexts.id_action
|
||||
|
||||
def draw(self, _context):
|
||||
layout = self.layout
|
||||
|
|
|
@ -155,6 +155,7 @@ class OUTLINER_MT_view_pie(Menu):
|
|||
pie = layout.menu_pie()
|
||||
pie.operator("outliner.show_hierarchy")
|
||||
pie.operator("outliner.show_active", icon='ZOOM_SELECTED')
|
||||
pie.operator("outliner.expanded_toggle")
|
||||
|
||||
|
||||
class OUTLINER_MT_edit_datablocks(Menu):
|
||||
|
|
|
@ -454,6 +454,7 @@ class TOPBAR_MT_blender_system(Menu):
|
|||
layout.separator()
|
||||
|
||||
layout.operator("screen.spacedata_cleanup")
|
||||
layout.operator("wm.operator_presets_cleanup")
|
||||
|
||||
|
||||
class TOPBAR_MT_templates_more(Menu):
|
||||
|
|
|
@ -1597,12 +1597,12 @@ class USERPREF_UL_asset_libraries(UIList):
|
|||
class USERPREF_UL_extension_repos(UIList):
|
||||
def draw_item(self, _context, layout, _data, item, icon, _active_data, _active_propname, _index):
|
||||
repo = item
|
||||
|
||||
icon = 'WORLD' if repo.use_remote_path else 'DISK_DRIVE'
|
||||
if self.layout_type in {'DEFAULT', 'COMPACT'}:
|
||||
layout.prop(repo, "name", text="", emboss=False)
|
||||
layout.prop(repo, "name", text="", icon=icon, emboss=False)
|
||||
elif self.layout_type == 'GRID':
|
||||
layout.alignment = 'CENTER'
|
||||
layout.prop(repo, "name", text="", emboss=False)
|
||||
layout.prop(repo, "name", text="", icon=icon, emboss=False)
|
||||
|
||||
# Show an error icon if this repository has unusable settings.
|
||||
if repo.enabled:
|
||||
|
@ -2047,7 +2047,7 @@ class USERPREF_PT_extensions_repos(Panel):
|
|||
layout.use_property_decorate = False
|
||||
|
||||
paths = context.preferences.filepaths
|
||||
active_library_index = paths.active_extension_repo
|
||||
active_repo_index = paths.active_extension_repo
|
||||
|
||||
row = layout.row()
|
||||
|
||||
|
@ -2060,10 +2060,14 @@ class USERPREF_PT_extensions_repos(Panel):
|
|||
col = row.column(align=True)
|
||||
col.operator_menu_enum("preferences.extension_repo_add", "type", text="", icon='ADD')
|
||||
props = col.operator_menu_enum("preferences.extension_repo_remove", "type", text="", icon='REMOVE')
|
||||
props.index = active_library_index
|
||||
props.index = active_repo_index
|
||||
|
||||
col.separator()
|
||||
col.operator("preferences.extension_repo_sync", text="", icon='FILE_REFRESH')
|
||||
col.operator("preferences.extension_repo_upgrade", text="", icon='IMPORT')
|
||||
|
||||
try:
|
||||
active_repo = None if active_library_index < 0 else paths.extension_repos[active_library_index]
|
||||
active_repo = None if active_repo_index < 0 else paths.extension_repos[active_repo_index]
|
||||
except IndexError:
|
||||
active_repo = None
|
||||
|
||||
|
@ -2072,14 +2076,16 @@ class USERPREF_PT_extensions_repos(Panel):
|
|||
|
||||
layout.separator()
|
||||
|
||||
layout.prop(active_repo, "use_remote_path", text="Use Remote URL")
|
||||
row = layout.row()
|
||||
# NOTE: changing repositories from remote to local & vice versa could be supported but is obscure enough
|
||||
# that it can be hidden entirely. If there is a some justification to show this, it can be exposed.
|
||||
# For now it can be accessed from Python if someone is.
|
||||
# `layout.prop(active_repo, "use_remote_path", text="Use Remote URL")`
|
||||
|
||||
if active_repo.use_remote_path:
|
||||
row = layout.row()
|
||||
if active_repo.remote_path == "":
|
||||
row.alert = True
|
||||
else:
|
||||
row.active = False
|
||||
row.prop(active_repo, "remote_path", text="")
|
||||
row.prop(active_repo, "remote_path", text="URL")
|
||||
|
||||
if layout_panel := self._panel_layout_kludge(layout, text="Advanced"):
|
||||
|
||||
|
|
|
@ -1134,11 +1134,12 @@ class VIEW3D_MT_editor_menus(Menu):
|
|||
elif mode_string == 'VERTEX_GPENCIL':
|
||||
layout.menu("VIEW3D_MT_select_edit_gpencil")
|
||||
elif mode_string in {'PAINT_WEIGHT', 'PAINT_VERTEX', 'PAINT_TEXTURE'}:
|
||||
mesh = obj.data
|
||||
if mesh.use_paint_mask:
|
||||
layout.menu("VIEW3D_MT_select_paint_mask")
|
||||
elif mesh.use_paint_mask_vertex and mode_string in {'PAINT_WEIGHT', 'PAINT_VERTEX'}:
|
||||
layout.menu("VIEW3D_MT_select_paint_mask_vertex")
|
||||
if obj.type == 'MESH':
|
||||
mesh = obj.data
|
||||
if mesh.use_paint_mask:
|
||||
layout.menu("VIEW3D_MT_select_paint_mask")
|
||||
elif mesh.use_paint_mask_vertex and mode_string in {'PAINT_WEIGHT', 'PAINT_VERTEX'}:
|
||||
layout.menu("VIEW3D_MT_select_paint_mask_vertex")
|
||||
elif mode_string not in {'SCULPT', 'SCULPT_CURVES', 'PAINT_GREASE_PENCIL'}:
|
||||
layout.menu("VIEW3D_MT_select_%s" % mode_string.lower())
|
||||
|
||||
|
@ -3173,6 +3174,7 @@ class VIEW3D_MT_object_parent(Menu):
|
|||
|
||||
class VIEW3D_MT_object_track(Menu):
|
||||
bl_label = "Track"
|
||||
bl_translation_context = i18n_contexts.constraint
|
||||
|
||||
def draw(self, _context):
|
||||
layout = self.layout
|
||||
|
@ -3541,8 +3543,10 @@ class VIEW3D_MT_paint_weight(Menu):
|
|||
|
||||
layout.menu("VIEW3D_MT_paint_weight_lock", text="Locks")
|
||||
|
||||
def draw(self, _context):
|
||||
self.draw_generic(self.layout, is_editmode=False)
|
||||
def draw(self, context):
|
||||
obj = context.active_object
|
||||
if obj.type == 'MESH':
|
||||
self.draw_generic(self.layout, is_editmode=False)
|
||||
|
||||
|
||||
class VIEW3D_MT_sculpt(Menu):
|
||||
|
@ -4448,6 +4452,7 @@ class VIEW3D_MT_edit_mesh_context_menu(Menu):
|
|||
|
||||
col.operator("mesh.mark_sharp")
|
||||
col.operator("mesh.mark_sharp", text="Clear Sharp").clear = True
|
||||
col.operator("mesh.set_sharpness_by_angle")
|
||||
|
||||
if with_freestyle:
|
||||
col.separator()
|
||||
|
@ -5808,6 +5813,10 @@ class VIEW3D_MT_edit_greasepencil(Menu):
|
|||
|
||||
layout.separator()
|
||||
|
||||
layout.operator_menu_enum("grease_pencil.separate", "mode", text="Separate")
|
||||
|
||||
layout.separator()
|
||||
|
||||
layout.menu("GREASE_PENCIL_MT_layer_active", text="Active Layer")
|
||||
|
||||
layout.separator()
|
||||
|
@ -8208,6 +8217,10 @@ class VIEW3D_MT_greasepencil_edit_context_menu(Menu):
|
|||
|
||||
col.menu("VIEW3D_MT_mirror", text="Mirror Points")
|
||||
|
||||
col.separator()
|
||||
|
||||
col.operator("grease_pencil.separate", text="Separate").mode = 'SELECTED'
|
||||
|
||||
# Removal Operators
|
||||
col.separator()
|
||||
|
||||
|
@ -8237,6 +8250,10 @@ class VIEW3D_MT_greasepencil_edit_context_menu(Menu):
|
|||
|
||||
col.menu("VIEW3D_MT_mirror")
|
||||
|
||||
col.separator()
|
||||
|
||||
col.operator("grease_pencil.separate", text="Separate").mode = 'SELECTED'
|
||||
|
||||
|
||||
def draw_gpencil_layer_active(context, layout):
|
||||
gpl = context.active_gpencil_layer
|
||||
|
|
|
@ -65,6 +65,7 @@ class AssetLibrary {
|
|||
*/
|
||||
std::unique_ptr<AssetStorage> asset_storage_;
|
||||
|
||||
protected:
|
||||
std::optional<eAssetImportMethod> import_method_;
|
||||
/** Assets owned by this library may be imported with a different method than set in
|
||||
* #import_method_ above, it's just a default. */
|
||||
|
|
|
@ -15,10 +15,11 @@ set(SRC
|
|||
intern/asset_catalog.cc
|
||||
intern/asset_catalog_path.cc
|
||||
intern/asset_catalog_tree.cc
|
||||
intern/asset_essentials_library.cc
|
||||
intern/asset_identifier.cc
|
||||
intern/asset_library.cc
|
||||
intern/asset_library_all.cc
|
||||
intern/asset_library_essentials.cc
|
||||
intern/asset_library_from_preferences.cc
|
||||
intern/asset_library_on_disk.cc
|
||||
intern/asset_library_runtime.cc
|
||||
intern/asset_library_service.cc
|
||||
|
@ -34,6 +35,8 @@ set(SRC
|
|||
AS_asset_representation.hh
|
||||
AS_essentials_library.hh
|
||||
intern/asset_library_all.hh
|
||||
intern/asset_library_essentials.hh
|
||||
intern/asset_library_from_preferences.hh
|
||||
intern/asset_library_on_disk.hh
|
||||
intern/asset_library_runtime.hh
|
||||
intern/asset_library_service.hh
|
||||
|
|
|
@ -6,14 +6,23 @@
|
|||
* \ingroup asset_system
|
||||
*/
|
||||
|
||||
#include "BLI_path_util.h"
|
||||
|
||||
#include "BKE_appdir.hh"
|
||||
|
||||
#include "utils.hh"
|
||||
|
||||
#include "AS_essentials_library.hh"
|
||||
#include "asset_library_essentials.hh"
|
||||
|
||||
namespace blender::asset_system {
|
||||
|
||||
EssentialsAssetLibrary::EssentialsAssetLibrary()
|
||||
: OnDiskAssetLibrary(ASSET_LIBRARY_ESSENTIALS,
|
||||
{},
|
||||
utils::normalize_directory_path(essentials_directory_path()))
|
||||
{
|
||||
import_method_ = ASSET_IMPORT_APPEND_REUSE;
|
||||
}
|
||||
|
||||
StringRefNull essentials_directory_path()
|
||||
{
|
||||
static std::string path = []() {
|
|
@ -0,0 +1,20 @@
|
|||
/* SPDX-FileCopyrightText: 2024 Blender Authors
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-2.0-or-later */
|
||||
|
||||
/** \file
|
||||
* \ingroup asset_system
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "asset_library_on_disk.hh"
|
||||
|
||||
namespace blender::asset_system {
|
||||
|
||||
class EssentialsAssetLibrary : public OnDiskAssetLibrary {
|
||||
public:
|
||||
EssentialsAssetLibrary();
|
||||
};
|
||||
|
||||
} // namespace blender::asset_system
|
|
@ -0,0 +1,18 @@
|
|||
/* SPDX-FileCopyrightText: 2024 Blender Authors
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-2.0-or-later */
|
||||
|
||||
/** \file
|
||||
* \ingroup asset_system
|
||||
*/
|
||||
|
||||
#include "asset_library_from_preferences.hh"
|
||||
|
||||
namespace blender::asset_system {
|
||||
|
||||
PreferencesOnDiskAssetLibrary::PreferencesOnDiskAssetLibrary(StringRef name, StringRef root_path)
|
||||
: OnDiskAssetLibrary(ASSET_LIBRARY_CUSTOM, name, root_path)
|
||||
{
|
||||
}
|
||||
|
||||
} // namespace blender::asset_system
|
|
@ -0,0 +1,20 @@
|
|||
/* SPDX-FileCopyrightText: 2024 Blender Authors
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-2.0-or-later */
|
||||
|
||||
/** \file
|
||||
* \ingroup asset_system
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "asset_library_on_disk.hh"
|
||||
|
||||
namespace blender::asset_system {
|
||||
|
||||
class PreferencesOnDiskAssetLibrary : public OnDiskAssetLibrary {
|
||||
public:
|
||||
PreferencesOnDiskAssetLibrary(StringRef name = "", StringRef root_path = "");
|
||||
};
|
||||
|
||||
} // namespace blender::asset_system
|
|
@ -20,6 +20,8 @@
|
|||
#include "AS_asset_library.hh"
|
||||
#include "AS_essentials_library.hh"
|
||||
#include "asset_library_all.hh"
|
||||
#include "asset_library_essentials.hh"
|
||||
#include "asset_library_from_preferences.hh"
|
||||
#include "asset_library_on_disk.hh"
|
||||
#include "asset_library_runtime.hh"
|
||||
#include "asset_library_service.hh"
|
||||
|
@ -72,10 +74,7 @@ AssetLibrary *AssetLibraryService::get_asset_library(
|
|||
return nullptr;
|
||||
}
|
||||
|
||||
AssetLibrary *library = get_asset_library_on_disk_builtin(type, root_path);
|
||||
library->import_method_ = ASSET_IMPORT_APPEND_REUSE;
|
||||
|
||||
return library;
|
||||
return get_asset_library_on_disk_builtin(type, root_path);
|
||||
}
|
||||
case ASSET_LIBRARY_LOCAL: {
|
||||
/* For the "Current File" library we get the asset library root path based on main. */
|
||||
|
@ -132,8 +131,19 @@ AssetLibrary *AssetLibraryService::get_asset_library_on_disk(eAssetLibraryType l
|
|||
return lib;
|
||||
}
|
||||
|
||||
std::unique_ptr lib_uptr = std::make_unique<OnDiskAssetLibrary>(
|
||||
library_type, name, normalized_root_path);
|
||||
std::unique_ptr<OnDiskAssetLibrary> lib_uptr;
|
||||
switch (library_type) {
|
||||
case ASSET_LIBRARY_CUSTOM:
|
||||
lib_uptr = std::make_unique<PreferencesOnDiskAssetLibrary>(name, normalized_root_path);
|
||||
break;
|
||||
case ASSET_LIBRARY_ESSENTIALS:
|
||||
lib_uptr = std::make_unique<EssentialsAssetLibrary>();
|
||||
break;
|
||||
default:
|
||||
lib_uptr = std::make_unique<OnDiskAssetLibrary>(library_type, name, normalized_root_path);
|
||||
break;
|
||||
}
|
||||
|
||||
AssetLibrary *lib = lib_uptr.get();
|
||||
|
||||
lib->load_catalogs();
|
||||
|
|
|
@ -21,7 +21,7 @@ extern "C" {
|
|||
*/
|
||||
|
||||
/** Blender major and minor version. */
|
||||
#define BLENDER_VERSION 401
|
||||
#define BLENDER_VERSION 402
|
||||
/** Blender patch version for bug-fix releases. */
|
||||
#define BLENDER_VERSION_PATCH 0
|
||||
/** Blender release cycle stage: alpha/beta/rc/release. */
|
||||
|
@ -29,7 +29,7 @@ extern "C" {
|
|||
|
||||
/* Blender file format version. */
|
||||
#define BLENDER_FILE_VERSION BLENDER_VERSION
|
||||
#define BLENDER_FILE_SUBVERSION 17
|
||||
#define BLENDER_FILE_SUBVERSION 1
|
||||
|
||||
/* Minimum Blender version that supports reading file written with the current
|
||||
* version. Older Blender versions will test this and cancel loading the file, showing a warning to
|
||||
|
|
|
@ -112,6 +112,8 @@ typedef enum {
|
|||
BKE_CB_EVT_TRANSLATION_UPDATE_POST,
|
||||
BKE_CB_EVT_EXTENSION_REPOS_UPDATE_PRE,
|
||||
BKE_CB_EVT_EXTENSION_REPOS_UPDATE_POST,
|
||||
BKE_CB_EVT_EXTENSION_REPOS_SYNC,
|
||||
BKE_CB_EVT_EXTENSION_REPOS_UPGRADE,
|
||||
BKE_CB_EVT_TOT,
|
||||
} eCbEvent;
|
||||
|
||||
|
|
|
@ -93,7 +93,7 @@ void BKE_object_defgroup_unique_name(bDeformGroup *dg, Object *ob);
|
|||
|
||||
MDeformWeight *BKE_defvert_find_index(const MDeformVert *dv, int defgroup);
|
||||
/**
|
||||
* Ensures that `dv` has a deform weight entry for the specified defweight group.
|
||||
* Ensures that `dv` has a deform weight entry for the specified group (`defgroup`).
|
||||
*
|
||||
* \note this function is mirrored in editmesh_tools.cc, for use for edit-vertices.
|
||||
*/
|
||||
|
|
|
@ -34,14 +34,6 @@ namespace blender::bke {
|
|||
|
||||
namespace greasepencil {
|
||||
|
||||
struct DrawingTransforms {
|
||||
float4x4 world_space_to_layer_space;
|
||||
float4x4 layer_space_to_world_space;
|
||||
|
||||
DrawingTransforms() = default;
|
||||
DrawingTransforms(const Object &grease_pencil_ob);
|
||||
};
|
||||
|
||||
class DrawingRuntime {
|
||||
public:
|
||||
/**
|
||||
|
@ -447,6 +439,23 @@ class Layer : public ::GreasePencilLayer {
|
|||
*/
|
||||
void update_from_dna_read();
|
||||
|
||||
/**
|
||||
* Returns the transformation from layer space to object space.
|
||||
*/
|
||||
float4x4 to_object_space(const Object &object) const;
|
||||
|
||||
/**
|
||||
* Returns the transformation from layer space to world space.
|
||||
*/
|
||||
float4x4 to_world_space(const Object &object) const;
|
||||
|
||||
/**
|
||||
* Returns the name of the parent bone. Should only be used in case the parent object is an
|
||||
* armature.
|
||||
*/
|
||||
StringRefNull parent_bone_name() const;
|
||||
void set_parent_bone_name(const char *new_name);
|
||||
|
||||
private:
|
||||
using SortedKeysIterator = const int *;
|
||||
|
||||
|
@ -460,6 +469,16 @@ class Layer : public ::GreasePencilLayer {
|
|||
*/
|
||||
SortedKeysIterator remove_leading_null_frames_in_range(SortedKeysIterator begin,
|
||||
SortedKeysIterator end);
|
||||
|
||||
/**
|
||||
* The local transform of the layer (in layer space, not object space).
|
||||
*/
|
||||
float4x4 local_transform() const;
|
||||
|
||||
/**
|
||||
* Get the parent to world marix for this layer.
|
||||
*/
|
||||
float4x4 parent_to_world(const Object &parent) const;
|
||||
};
|
||||
|
||||
class LayerGroupRuntime {
|
||||
|
@ -706,6 +725,7 @@ TREENODE_COMMON_METHODS_FORWARD_IMPL(LayerGroup);
|
|||
namespace convert {
|
||||
|
||||
void legacy_gpencil_frame_to_grease_pencil_drawing(const bGPDframe &gpf,
|
||||
const ListBase &vertex_group_names,
|
||||
GreasePencilDrawing &r_drawing);
|
||||
void legacy_gpencil_to_grease_pencil(Main &main, GreasePencil &grease_pencil, bGPdata &gpd);
|
||||
|
||||
|
|
|
@ -421,9 +421,6 @@ void BKE_modifier_free(ModifierData *md);
|
|||
*/
|
||||
void BKE_modifier_remove_from_list(Object *ob, ModifierData *md);
|
||||
|
||||
/* Generate new UID for the given modifier. */
|
||||
void BKE_modifier_session_uid_generate(ModifierData *md);
|
||||
|
||||
void BKE_modifier_unique_name(ListBase *modifiers, ModifierData *md);
|
||||
|
||||
ModifierData *BKE_modifier_copy_ex(const ModifierData *md, int flag);
|
||||
|
@ -472,8 +469,20 @@ void BKE_modifiers_foreach_tex_link(Object *ob, TexWalkFunc walk, void *user_dat
|
|||
|
||||
ModifierData *BKE_modifiers_findby_type(const Object *ob, ModifierType type);
|
||||
ModifierData *BKE_modifiers_findby_name(const Object *ob, const char *name);
|
||||
ModifierData *BKE_modifiers_findby_session_uid(const Object *ob, const SessionUID *session_uid);
|
||||
ModifierData *BKE_modifiers_findby_persistent_uid(const Object *ob, int persistent_uid);
|
||||
|
||||
void BKE_modifiers_clear_errors(Object *ob);
|
||||
|
||||
/**
|
||||
* Updates `md.persistent_uid` so that it is a valid identifier (>=1) and is unique in the object.
|
||||
*/
|
||||
void BKE_modifiers_persistent_uid_init(const Object &object, ModifierData &md);
|
||||
/**
|
||||
* Returns true when all the modifier identifiers are positive and unique. This should generally be
|
||||
* true and should only be used by asserts.
|
||||
*/
|
||||
bool BKE_modifiers_persistent_uids_are_valid(const Object &object);
|
||||
|
||||
/**
|
||||
* used for buttons, to find out if the 'draw deformed in edit-mode option is there.
|
||||
*
|
||||
|
@ -584,8 +593,6 @@ void BKE_modifier_deform_vertsEM(ModifierData *md,
|
|||
*/
|
||||
Mesh *BKE_modifier_get_evaluated_mesh_from_evaluated_object(Object *ob_eval);
|
||||
|
||||
void BKE_modifier_check_uids_unique_and_report(const Object *object);
|
||||
|
||||
void BKE_modifier_blend_write(BlendWriter *writer, const ID *id_owner, ListBase *modbase);
|
||||
void BKE_modifier_blend_read_data(BlendDataReader *reader, ListBase *lb, Object *ob);
|
||||
|
||||
|
|
|
@ -396,6 +396,8 @@ typedef struct bNodeType {
|
|||
|
||||
/** True when the node cannot be muted. */
|
||||
bool no_muting;
|
||||
/** True when the node still works but it's usage is discouraged. */
|
||||
const char *deprecation_notice;
|
||||
|
||||
/* RNA integration */
|
||||
ExtensionRNA rna_ext;
|
||||
|
|
|
@ -115,7 +115,8 @@ bool BKE_object_copy_gpencil_modifier(Object *ob_dst, GpencilModifierData *gmd_s
|
|||
* Copy the whole stack of modifiers from one object into another.
|
||||
*
|
||||
* \warning *Does not* clear modifier stack and related data (particle systems, soft-body,
|
||||
* etc.) in `ob_dst`, if needed calling code must do it.
|
||||
* etc.) in `ob_dst`, if needed calling code must do it. The caller is also responsible for
|
||||
* ensuring the modifier identifiers are unique.
|
||||
*
|
||||
* \param do_copy_all: If true, even modifiers that should not support copying (like Hook one)
|
||||
* will be duplicated.
|
||||
|
|
|
@ -149,6 +149,13 @@ bMotionPath *animviz_verify_motionpaths(ReportList *reports,
|
|||
if (*dst != nullptr) {
|
||||
mpath = *dst;
|
||||
|
||||
if (avs->path_bakeflag & MOTIONPATH_BAKE_CAMERA_SPACE) {
|
||||
mpath->flag |= MOTIONPATH_FLAG_BAKE_CAMERA;
|
||||
}
|
||||
else {
|
||||
mpath->flag &= ~MOTIONPATH_FLAG_BAKE_CAMERA;
|
||||
}
|
||||
|
||||
/* Only reuse a path if it was already a valid path, and of the expected length. */
|
||||
if (mpath->start_frame != mpath->end_frame && mpath->length == expected_length) {
|
||||
mpath->start_frame = avs->path_sf;
|
||||
|
@ -176,6 +183,13 @@ bMotionPath *animviz_verify_motionpaths(ReportList *reports,
|
|||
mpath->flag &= ~MOTIONPATH_FLAG_BHEAD;
|
||||
}
|
||||
|
||||
if (avs->path_bakeflag & MOTIONPATH_BAKE_CAMERA_SPACE) {
|
||||
mpath->flag |= MOTIONPATH_FLAG_BAKE_CAMERA;
|
||||
}
|
||||
else {
|
||||
mpath->flag &= ~MOTIONPATH_FLAG_BAKE_CAMERA;
|
||||
}
|
||||
|
||||
/* Set default custom values (RGB). */
|
||||
mpath->color[0] = 1.0;
|
||||
mpath->color[1] = 0.0;
|
||||
|
|
|
@ -22,7 +22,7 @@ BakeDataBlockID::BakeDataBlockID(const ID &id)
|
|||
{
|
||||
this->type = GS(id.name);
|
||||
this->id_name = id.name + 2;
|
||||
if (id.lib) {
|
||||
if (ID_IS_LINKED(&id)) {
|
||||
this->lib_name = id.lib->id.name + 2;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -46,7 +46,7 @@
|
|||
#endif
|
||||
|
||||
#ifdef WITH_USD
|
||||
# include "usd.h"
|
||||
# include "usd.hh"
|
||||
#endif
|
||||
|
||||
static void cachefile_handle_free(CacheFile *cache_file);
|
||||
|
@ -188,7 +188,8 @@ void BKE_cachefile_reader_open(CacheFile *cache_file,
|
|||
case CACHEFILE_TYPE_USD:
|
||||
# ifdef WITH_USD
|
||||
/* Open USD cache reader. */
|
||||
*reader = CacheReader_open_usd_object(cache_file->handle, *reader, object, object_path);
|
||||
*reader = blender::io::usd::CacheReader_open_usd_object(
|
||||
cache_file->handle, *reader, object, object_path);
|
||||
# endif
|
||||
break;
|
||||
case CACHE_FILE_TYPE_INVALID:
|
||||
|
@ -232,7 +233,7 @@ void BKE_cachefile_reader_free(CacheFile *cache_file, CacheReader **reader)
|
|||
break;
|
||||
case CACHEFILE_TYPE_USD:
|
||||
# ifdef WITH_USD
|
||||
USD_CacheReader_free(*reader);
|
||||
blender::io::usd::USD_CacheReader_free(*reader);
|
||||
# endif
|
||||
break;
|
||||
case CACHE_FILE_TYPE_INVALID:
|
||||
|
@ -272,7 +273,7 @@ static void cachefile_handle_free(CacheFile *cache_file)
|
|||
break;
|
||||
case CACHEFILE_TYPE_USD:
|
||||
# ifdef WITH_USD
|
||||
USD_CacheReader_free(*reader);
|
||||
blender::io::usd::USD_CacheReader_free(*reader);
|
||||
# endif
|
||||
break;
|
||||
case CACHE_FILE_TYPE_INVALID:
|
||||
|
@ -299,7 +300,7 @@ static void cachefile_handle_free(CacheFile *cache_file)
|
|||
break;
|
||||
case CACHEFILE_TYPE_USD:
|
||||
# ifdef WITH_USD
|
||||
USD_free_handle(cache_file->handle);
|
||||
blender::io::usd::USD_free_handle(cache_file->handle);
|
||||
# endif
|
||||
break;
|
||||
case CACHE_FILE_TYPE_INVALID:
|
||||
|
@ -365,7 +366,8 @@ void BKE_cachefile_eval(Main *bmain, Depsgraph *depsgraph, CacheFile *cache_file
|
|||
#ifdef WITH_USD
|
||||
if (BLI_path_extension_check_glob(filepath, "*.usd;*.usda;*.usdc;*.usdz")) {
|
||||
cache_file->type = CACHEFILE_TYPE_USD;
|
||||
cache_file->handle = USD_create_handle(bmain, filepath, &cache_file->object_paths);
|
||||
cache_file->handle = blender::io::usd::USD_create_handle(
|
||||
bmain, filepath, &cache_file->object_paths);
|
||||
STRNCPY(cache_file->handle_filepath, filepath);
|
||||
}
|
||||
#endif
|
||||
|
|
|
@ -1359,6 +1359,12 @@ static void save_sample_line(
|
|||
scopes->vecscope[idx + 0] = yuv[1];
|
||||
scopes->vecscope[idx + 1] = yuv[2];
|
||||
|
||||
int color_idx = (idx / 2) * 4;
|
||||
scopes->vecscope_rgb[color_idx + 0] = rgb[0];
|
||||
scopes->vecscope_rgb[color_idx + 1] = rgb[1];
|
||||
scopes->vecscope_rgb[color_idx + 2] = rgb[2];
|
||||
scopes->vecscope_rgb[color_idx + 3] = scopes->vecscope_alpha;
|
||||
|
||||
/* Waveform. */
|
||||
switch (scopes->wavefrm_mode) {
|
||||
case SCOPES_WAVEFRM_RGB:
|
||||
|
@ -1707,6 +1713,7 @@ void BKE_scopes_update(Scopes *scopes,
|
|||
}
|
||||
if (scopes->vecscope) {
|
||||
MEM_freeN(scopes->vecscope);
|
||||
MEM_freeN(scopes->vecscope_rgb);
|
||||
}
|
||||
|
||||
scopes->waveform_1 = static_cast<float *>(
|
||||
|
@ -1717,6 +1724,8 @@ void BKE_scopes_update(Scopes *scopes,
|
|||
MEM_callocN(scopes->waveform_tot * 2 * sizeof(float), "waveform point channel 3"));
|
||||
scopes->vecscope = static_cast<float *>(
|
||||
MEM_callocN(scopes->waveform_tot * 2 * sizeof(float), "vectorscope point channel"));
|
||||
scopes->vecscope_rgb = static_cast<float *>(
|
||||
MEM_callocN(scopes->waveform_tot * 4 * sizeof(float), "vectorscope color channel"));
|
||||
|
||||
if (ibuf->float_buffer.data) {
|
||||
cm_processor = IMB_colormanagement_display_processor_new(view_settings, display_settings);
|
||||
|
@ -1794,6 +1803,7 @@ void BKE_scopes_free(Scopes *scopes)
|
|||
MEM_SAFE_FREE(scopes->waveform_2);
|
||||
MEM_SAFE_FREE(scopes->waveform_3);
|
||||
MEM_SAFE_FREE(scopes->vecscope);
|
||||
MEM_SAFE_FREE(scopes->vecscope_rgb);
|
||||
}
|
||||
|
||||
void BKE_scopes_new(Scopes *scopes)
|
||||
|
@ -1810,6 +1820,7 @@ void BKE_scopes_new(Scopes *scopes)
|
|||
scopes->waveform_2 = nullptr;
|
||||
scopes->waveform_3 = nullptr;
|
||||
scopes->vecscope = nullptr;
|
||||
scopes->vecscope_rgb = nullptr;
|
||||
}
|
||||
|
||||
void BKE_color_managed_display_settings_init(ColorManagedDisplaySettings *settings)
|
||||
|
|
|
@ -88,7 +88,7 @@
|
|||
#endif
|
||||
|
||||
#ifdef WITH_USD
|
||||
# include "usd.h"
|
||||
# include "usd.hh"
|
||||
#endif
|
||||
|
||||
/* ---------------------------------------------------------------------------- */
|
||||
|
@ -5395,7 +5395,8 @@ static void transformcache_evaluate(bConstraint *con, bConstraintOb *cob, ListBa
|
|||
break;
|
||||
case CACHEFILE_TYPE_USD:
|
||||
# ifdef WITH_USD
|
||||
USD_get_transform(data->reader, cob->matrix, time * FPS, cache_file->scale);
|
||||
blender::io::usd::USD_get_transform(
|
||||
data->reader, cob->matrix, time * FPS, cache_file->scale);
|
||||
# endif
|
||||
break;
|
||||
case CACHE_FILE_TYPE_INVALID:
|
||||
|
|
|
@ -89,89 +89,85 @@ CurvesGeometry::CurvesGeometry(const int point_num, const int curve_num)
|
|||
this->runtime->type_counts[CURVE_TYPE_CATMULL_ROM] = curve_num;
|
||||
}
|
||||
|
||||
/**
|
||||
* \note Expects `dst` to be initialized, since the original attributes must be freed.
|
||||
*/
|
||||
static void copy_curves_geometry(CurvesGeometry &dst, const CurvesGeometry &src)
|
||||
CurvesGeometry::CurvesGeometry(const CurvesGeometry &other)
|
||||
{
|
||||
CustomData_free(&dst.point_data, dst.point_num);
|
||||
CustomData_free(&dst.curve_data, dst.curve_num);
|
||||
dst.point_num = src.point_num;
|
||||
dst.curve_num = src.curve_num;
|
||||
CustomData_copy(&src.point_data, &dst.point_data, CD_MASK_ALL, dst.point_num);
|
||||
CustomData_copy(&src.curve_data, &dst.curve_data, CD_MASK_ALL, dst.curve_num);
|
||||
|
||||
dst.vertex_group_active_index = src.vertex_group_active_index;
|
||||
BKE_defgroup_copy_list(&dst.vertex_group_names, &src.vertex_group_names);
|
||||
|
||||
implicit_sharing::copy_shared_pointer(src.curve_offsets,
|
||||
src.runtime->curve_offsets_sharing_info,
|
||||
&dst.curve_offsets,
|
||||
&dst.runtime->curve_offsets_sharing_info);
|
||||
|
||||
dst.tag_topology_changed();
|
||||
|
||||
/* Though type counts are a cache, they must be copied because they are calculated eagerly. */
|
||||
dst.runtime->type_counts = src.runtime->type_counts;
|
||||
dst.runtime->evaluated_offsets_cache = src.runtime->evaluated_offsets_cache;
|
||||
dst.runtime->nurbs_basis_cache = src.runtime->nurbs_basis_cache;
|
||||
dst.runtime->evaluated_position_cache = src.runtime->evaluated_position_cache;
|
||||
dst.runtime->bounds_cache = src.runtime->bounds_cache;
|
||||
dst.runtime->evaluated_length_cache = src.runtime->evaluated_length_cache;
|
||||
dst.runtime->evaluated_tangent_cache = src.runtime->evaluated_tangent_cache;
|
||||
dst.runtime->evaluated_normal_cache = src.runtime->evaluated_normal_cache;
|
||||
|
||||
if (src.runtime->bake_materials) {
|
||||
dst.runtime->bake_materials = std::make_unique<bake::BakeMaterialsList>(
|
||||
*src.runtime->bake_materials);
|
||||
this->curve_offsets = other.curve_offsets;
|
||||
if (other.runtime->curve_offsets_sharing_info) {
|
||||
other.runtime->curve_offsets_sharing_info->add_user();
|
||||
}
|
||||
}
|
||||
|
||||
CurvesGeometry::CurvesGeometry(const CurvesGeometry &other) : CurvesGeometry()
|
||||
{
|
||||
copy_curves_geometry(*this, other);
|
||||
CustomData_copy(&other.point_data, &this->point_data, CD_MASK_ALL, other.point_num);
|
||||
CustomData_copy(&other.curve_data, &this->curve_data, CD_MASK_ALL, other.curve_num);
|
||||
|
||||
this->point_num = other.point_num;
|
||||
this->curve_num = other.curve_num;
|
||||
|
||||
BKE_defgroup_copy_list(&this->vertex_group_names, &other.vertex_group_names);
|
||||
this->vertex_group_active_index = other.vertex_group_active_index;
|
||||
|
||||
this->runtime = MEM_new<CurvesGeometryRuntime>(
|
||||
__func__,
|
||||
CurvesGeometryRuntime{other.runtime->curve_offsets_sharing_info,
|
||||
other.runtime->type_counts,
|
||||
other.runtime->evaluated_offsets_cache,
|
||||
other.runtime->nurbs_basis_cache,
|
||||
other.runtime->evaluated_position_cache,
|
||||
other.runtime->bounds_cache,
|
||||
other.runtime->evaluated_length_cache,
|
||||
other.runtime->evaluated_tangent_cache,
|
||||
other.runtime->evaluated_normal_cache,
|
||||
{}});
|
||||
|
||||
if (other.runtime->bake_materials) {
|
||||
this->runtime->bake_materials = std::make_unique<bake::BakeMaterialsList>(
|
||||
*other.runtime->bake_materials);
|
||||
}
|
||||
}
|
||||
|
||||
CurvesGeometry &CurvesGeometry::operator=(const CurvesGeometry &other)
|
||||
{
|
||||
if (this != &other) {
|
||||
copy_curves_geometry(*this, other);
|
||||
if (this == &other) {
|
||||
return *this;
|
||||
}
|
||||
std::destroy_at(this);
|
||||
new (this) CurvesGeometry(other);
|
||||
return *this;
|
||||
}
|
||||
|
||||
/* The source should be empty, but in a valid state so that using it further will work. */
|
||||
static void move_curves_geometry(CurvesGeometry &dst, CurvesGeometry &src)
|
||||
CurvesGeometry::CurvesGeometry(CurvesGeometry &&other)
|
||||
{
|
||||
dst.point_num = src.point_num;
|
||||
std::swap(dst.point_data, src.point_data);
|
||||
CustomData_free(&src.point_data, src.point_num);
|
||||
src.point_num = 0;
|
||||
this->curve_offsets = other.curve_offsets;
|
||||
other.curve_offsets = nullptr;
|
||||
|
||||
dst.curve_num = src.curve_num;
|
||||
std::swap(dst.curve_data, src.curve_data);
|
||||
CustomData_free(&src.curve_data, src.curve_num);
|
||||
src.curve_num = 0;
|
||||
this->point_data = other.point_data;
|
||||
CustomData_reset(&other.point_data);
|
||||
|
||||
std::swap(dst.curve_offsets, src.curve_offsets);
|
||||
this->curve_data = other.curve_data;
|
||||
CustomData_reset(&other.curve_data);
|
||||
|
||||
std::swap(dst.vertex_group_names.first, src.vertex_group_names.first);
|
||||
std::swap(dst.vertex_group_names.last, src.vertex_group_names.last);
|
||||
std::swap(dst.vertex_group_active_index, src.vertex_group_active_index);
|
||||
this->point_num = other.point_num;
|
||||
other.point_num = 0;
|
||||
|
||||
std::swap(dst.runtime, src.runtime);
|
||||
}
|
||||
this->curve_num = other.curve_num;
|
||||
other.curve_num = 0;
|
||||
|
||||
CurvesGeometry::CurvesGeometry(CurvesGeometry &&other) : CurvesGeometry()
|
||||
{
|
||||
move_curves_geometry(*this, other);
|
||||
this->vertex_group_names = other.vertex_group_names;
|
||||
BLI_listbase_clear(&other.vertex_group_names);
|
||||
|
||||
this->vertex_group_active_index = other.vertex_group_active_index;
|
||||
other.vertex_group_active_index = 0;
|
||||
|
||||
this->runtime = other.runtime;
|
||||
other.runtime = nullptr;
|
||||
}
|
||||
|
||||
CurvesGeometry &CurvesGeometry::operator=(CurvesGeometry &&other)
|
||||
{
|
||||
if (this != &other) {
|
||||
move_curves_geometry(*this, other);
|
||||
if (this == &other) {
|
||||
return *this;
|
||||
}
|
||||
std::destroy_at(this);
|
||||
new (this) CurvesGeometry(std::move(other));
|
||||
return *this;
|
||||
}
|
||||
|
||||
|
@ -179,11 +175,12 @@ CurvesGeometry::~CurvesGeometry()
|
|||
{
|
||||
CustomData_free(&this->point_data, this->point_num);
|
||||
CustomData_free(&this->curve_data, this->curve_num);
|
||||
implicit_sharing::free_shared_data(&this->curve_offsets,
|
||||
&this->runtime->curve_offsets_sharing_info);
|
||||
BLI_freelistN(&this->vertex_group_names);
|
||||
MEM_delete(this->runtime);
|
||||
this->runtime = nullptr;
|
||||
if (this->runtime) {
|
||||
implicit_sharing::free_shared_data(&this->curve_offsets,
|
||||
&this->runtime->curve_offsets_sharing_info);
|
||||
MEM_delete(this->runtime);
|
||||
}
|
||||
}
|
||||
|
||||
/** \} */
|
||||
|
|
|
@ -26,6 +26,8 @@
|
|||
#include "BLI_sort_utils.h"
|
||||
#include "BLI_string_utils.hh"
|
||||
|
||||
#include "BLT_translation.h"
|
||||
|
||||
#include "BKE_anim_data.h"
|
||||
#include "BKE_animsys.h"
|
||||
#include "BKE_context.hh"
|
||||
|
@ -169,7 +171,7 @@ void BKE_fmodifier_name_set(FModifier *fcm, const char *name)
|
|||
* Ensure the name is unique. */
|
||||
const FModifierTypeInfo *fmi = get_fmodifier_typeinfo(fcm->type);
|
||||
ListBase list = BLI_listbase_from_link((Link *)fcm);
|
||||
BLI_uniquename(&list, fcm, fmi->name, '.', offsetof(FModifier, name), sizeof(fcm->name));
|
||||
BLI_uniquename(&list, fcm, DATA_(fmi->name), '.', offsetof(FModifier, name), sizeof(fcm->name));
|
||||
}
|
||||
|
||||
void BKE_fmodifiers_foreach_id(ListBase *fmodifiers, LibraryForeachIDData *data)
|
||||
|
|
|
@ -8,6 +8,7 @@
|
|||
|
||||
#include <iostream>
|
||||
|
||||
#include "BKE_action.h"
|
||||
#include "BKE_anim_data.h"
|
||||
#include "BKE_curves.hh"
|
||||
#include "BKE_customdata.hh"
|
||||
|
@ -25,8 +26,10 @@
|
|||
|
||||
#include "BLI_bounds.hh"
|
||||
#include "BLI_map.hh"
|
||||
#include "BLI_math_euler_types.hh"
|
||||
#include "BLI_math_geom.h"
|
||||
#include "BLI_math_matrix.h"
|
||||
#include "BLI_math_matrix_types.hh"
|
||||
#include "BLI_math_vector_types.hh"
|
||||
#include "BLI_memarena.h"
|
||||
#include "BLI_memory_utils.hh"
|
||||
|
@ -240,14 +243,6 @@ IDTypeInfo IDType_ID_GP = {
|
|||
|
||||
namespace blender::bke::greasepencil {
|
||||
|
||||
DrawingTransforms::DrawingTransforms(const Object &grease_pencil_ob)
|
||||
{
|
||||
/* TODO: For now layer space = object space. This needs to change once the layers have a
|
||||
* transform. */
|
||||
this->layer_space_to_world_space = float4x4_view(grease_pencil_ob.object_to_world);
|
||||
this->world_space_to_layer_space = math::invert(this->layer_space_to_world_space);
|
||||
}
|
||||
|
||||
static const std::string ATTR_RADIUS = "radius";
|
||||
static const std::string ATTR_OPACITY = "opacity";
|
||||
static const std::string ATTR_VERTEX_COLOR = "vertex_color";
|
||||
|
@ -664,6 +659,13 @@ Layer::Layer()
|
|||
|
||||
this->opacity = 1.0f;
|
||||
|
||||
this->parent = nullptr;
|
||||
this->parsubstr = nullptr;
|
||||
|
||||
zero_v3(this->translation);
|
||||
zero_v3(this->rotation);
|
||||
copy_v3_fl(this->scale, 1.0f);
|
||||
|
||||
BLI_listbase_clear(&this->masks);
|
||||
|
||||
this->runtime = MEM_new<LayerRuntime>(__func__);
|
||||
|
@ -680,11 +682,18 @@ Layer::Layer(const Layer &other) : Layer()
|
|||
|
||||
/* TODO: duplicate masks. */
|
||||
|
||||
/* Note: We do not duplicate the frame storage since it is only needed for writing. */
|
||||
/* Note: We do not duplicate the frame storage since it is only needed for writing to file. */
|
||||
|
||||
this->blend_mode = other.blend_mode;
|
||||
this->opacity = other.opacity;
|
||||
|
||||
this->parent = other.parent;
|
||||
this->set_parent_bone_name(other.parsubstr);
|
||||
|
||||
copy_v3_v3(this->translation, other.translation);
|
||||
copy_v3_v3(this->rotation, other.rotation);
|
||||
copy_v3_v3(this->scale, other.scale);
|
||||
|
||||
this->runtime->frames_ = other.runtime->frames_;
|
||||
this->runtime->sorted_keys_cache_ = other.runtime->sorted_keys_cache_;
|
||||
/* TODO: what about masks cache? */
|
||||
|
@ -702,6 +711,8 @@ Layer::~Layer()
|
|||
MEM_freeN(mask);
|
||||
}
|
||||
|
||||
MEM_SAFE_FREE(this->parsubstr);
|
||||
|
||||
MEM_delete(this->runtime);
|
||||
this->runtime = nullptr;
|
||||
}
|
||||
|
@ -946,6 +957,57 @@ void Layer::update_from_dna_read()
|
|||
}
|
||||
}
|
||||
|
||||
float4x4 Layer::to_world_space(const Object &object) const
|
||||
{
|
||||
if (this->parent == nullptr) {
|
||||
return float4x4(object.object_to_world) * this->local_transform();
|
||||
}
|
||||
const Object &parent = *this->parent;
|
||||
return this->parent_to_world(parent) * this->local_transform();
|
||||
}
|
||||
|
||||
float4x4 Layer::to_object_space(const Object &object) const
|
||||
{
|
||||
if (this->parent == nullptr) {
|
||||
return this->local_transform();
|
||||
}
|
||||
const Object &parent = *this->parent;
|
||||
return float4x4(object.world_to_object) * this->parent_to_world(parent) *
|
||||
this->local_transform();
|
||||
}
|
||||
|
||||
StringRefNull Layer::parent_bone_name() const
|
||||
{
|
||||
return (this->parsubstr != nullptr) ? StringRefNull(this->parsubstr) : StringRefNull();
|
||||
}
|
||||
|
||||
void Layer::set_parent_bone_name(const char *new_name)
|
||||
{
|
||||
if (this->parsubstr != nullptr) {
|
||||
MEM_freeN(this->parsubstr);
|
||||
}
|
||||
this->parsubstr = BLI_strdup_null(new_name);
|
||||
}
|
||||
|
||||
float4x4 Layer::parent_to_world(const Object &parent) const
|
||||
{
|
||||
const float4x4 parent_object_to_world(parent.object_to_world);
|
||||
if (parent.type == OB_ARMATURE && !this->parent_bone_name().is_empty()) {
|
||||
if (bPoseChannel *channel = BKE_pose_channel_find_name(parent.pose,
|
||||
this->parent_bone_name().c_str()))
|
||||
{
|
||||
return parent_object_to_world * float4x4_view(channel->pose_mat);
|
||||
}
|
||||
}
|
||||
return parent_object_to_world;
|
||||
}
|
||||
|
||||
float4x4 Layer::local_transform() const
|
||||
{
|
||||
return math::from_loc_rot_scale<float4x4, math::EulerXYZ>(
|
||||
float3(this->translation), float3(this->rotation), float3(this->scale));
|
||||
}
|
||||
|
||||
LayerGroup::LayerGroup()
|
||||
{
|
||||
new (&this->base) TreeNode(GP_LAYER_TREE_GROUP);
|
||||
|
|
|
@ -8,6 +8,7 @@
|
|||
|
||||
#include "BKE_attribute.hh"
|
||||
#include "BKE_curves.hh"
|
||||
#include "BKE_deform.hh"
|
||||
#include "BKE_grease_pencil.hh"
|
||||
#include "BKE_material.h"
|
||||
|
||||
|
@ -19,10 +20,52 @@
|
|||
|
||||
#include "DNA_gpencil_legacy_types.h"
|
||||
#include "DNA_grease_pencil_types.h"
|
||||
#include "DNA_meshdata_types.h"
|
||||
|
||||
namespace blender::bke::greasepencil::convert {
|
||||
|
||||
/**
|
||||
* Find vertex groups that have assigned vertices in this drawing.
|
||||
* Returns:
|
||||
* - ListBase with used vertex group names (bDeformGroup)
|
||||
* - Array of indices in the new vertex group list for remapping
|
||||
*/
|
||||
static void find_used_vertex_groups(const bGPDframe &gpf,
|
||||
const ListBase &all_names,
|
||||
ListBase &r_vertex_group_names,
|
||||
Array<int> &r_indices)
|
||||
{
|
||||
const int num_vertex_groups = BLI_listbase_count(&all_names);
|
||||
Array<int> is_group_used(num_vertex_groups, false);
|
||||
LISTBASE_FOREACH (bGPDstroke *, gps, &gpf.strokes) {
|
||||
if (!gps->dvert) {
|
||||
continue;
|
||||
}
|
||||
Span<MDeformVert> dverts = {gps->dvert, gps->totpoints};
|
||||
for (const MDeformVert &dvert : dverts) {
|
||||
for (const MDeformWeight &weight : Span<MDeformWeight>{dvert.dw, dvert.totweight}) {
|
||||
is_group_used[weight.def_nr] = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
BLI_listbase_clear(&r_vertex_group_names);
|
||||
r_indices.reinitialize(num_vertex_groups);
|
||||
int new_group_i = 0;
|
||||
int old_group_i;
|
||||
LISTBASE_FOREACH_INDEX (const bDeformGroup *, def_group, &all_names, old_group_i) {
|
||||
if (!is_group_used[old_group_i]) {
|
||||
r_indices[old_group_i] = -1;
|
||||
continue;
|
||||
}
|
||||
r_indices[old_group_i] = new_group_i++;
|
||||
|
||||
bDeformGroup *def_group_copy = static_cast<bDeformGroup *>(MEM_dupallocN(def_group));
|
||||
BLI_addtail(&r_vertex_group_names, def_group_copy);
|
||||
}
|
||||
}
|
||||
|
||||
void legacy_gpencil_frame_to_grease_pencil_drawing(const bGPDframe &gpf,
|
||||
const ListBase &vertex_group_names,
|
||||
GreasePencilDrawing &r_drawing)
|
||||
{
|
||||
/* Construct an empty CurvesGeometry in-place. */
|
||||
|
@ -54,6 +97,25 @@ void legacy_gpencil_frame_to_grease_pencil_drawing(const bGPDframe &gpf,
|
|||
/* All strokes are poly curves. */
|
||||
curves.fill_curve_types(CURVE_TYPE_POLY);
|
||||
|
||||
/* Find used vertex groups in this drawing. */
|
||||
ListBase stroke_vertex_group_names;
|
||||
Array<int> stroke_def_nr_map;
|
||||
find_used_vertex_groups(gpf, vertex_group_names, stroke_vertex_group_names, stroke_def_nr_map);
|
||||
BLI_assert(BLI_listbase_is_empty(&curves.vertex_group_names));
|
||||
curves.vertex_group_names = stroke_vertex_group_names;
|
||||
const bool use_dverts = !BLI_listbase_is_empty(&curves.vertex_group_names);
|
||||
|
||||
/* Copy vertex weights and map the vertex group indices. */
|
||||
auto copy_dvert = [&](const MDeformVert &src_dvert, MDeformVert &dst_dvert) {
|
||||
dst_dvert = src_dvert;
|
||||
dst_dvert.dw = static_cast<MDeformWeight *>(MEM_dupallocN(src_dvert.dw));
|
||||
const MutableSpan<MDeformWeight> vertex_weights = {dst_dvert.dw, dst_dvert.totweight};
|
||||
for (MDeformWeight &weight : vertex_weights) {
|
||||
/* Map def_nr to the reduced vertex group list. */
|
||||
weight.def_nr = stroke_def_nr_map[weight.def_nr];
|
||||
}
|
||||
};
|
||||
|
||||
/* Point Attributes. */
|
||||
MutableSpan<float3> positions = curves.positions_for_write();
|
||||
MutableSpan<float> radii = drawing.radii_for_write();
|
||||
|
@ -66,6 +128,8 @@ void legacy_gpencil_frame_to_grease_pencil_drawing(const bGPDframe &gpf,
|
|||
attributes.lookup_or_add_for_write_span<ColorGeometry4f>("vertex_color", AttrDomain::Point);
|
||||
SpanAttributeWriter<bool> selection = attributes.lookup_or_add_for_write_span<bool>(
|
||||
".selection", AttrDomain::Point);
|
||||
MutableSpan<MDeformVert> dverts = use_dverts ? curves.wrap().deform_verts_for_write() :
|
||||
MutableSpan<MDeformVert>();
|
||||
|
||||
/* Curve Attributes. */
|
||||
SpanAttributeWriter<bool> stroke_cyclic = attributes.lookup_or_add_for_write_span<bool>(
|
||||
|
@ -126,6 +190,8 @@ void legacy_gpencil_frame_to_grease_pencil_drawing(const bGPDframe &gpf,
|
|||
MutableSpan<ColorGeometry4f> stroke_vertex_colors = vertex_colors.span.slice(
|
||||
stroke_points_range);
|
||||
MutableSpan<bool> stroke_selections = selection.span.slice(stroke_points_range);
|
||||
MutableSpan<MDeformVert> stroke_dverts = use_dverts ? dverts.slice(stroke_points_range) :
|
||||
MutableSpan<MDeformVert>();
|
||||
|
||||
/* Do first point. */
|
||||
const bGPDspoint &first_pt = stroke_points.first();
|
||||
|
@ -143,6 +209,9 @@ void legacy_gpencil_frame_to_grease_pencil_drawing(const bGPDframe &gpf,
|
|||
stroke_rotations.first() = first_pt.uv_rot;
|
||||
stroke_vertex_colors.first() = ColorGeometry4f(first_pt.vert_color);
|
||||
stroke_selections.first() = (first_pt.flag & GP_SPOINT_SELECT) != 0;
|
||||
if (use_dverts && gps->dvert) {
|
||||
copy_dvert(gps->dvert[0], stroke_dverts.first());
|
||||
}
|
||||
|
||||
/* Do the rest of the points. */
|
||||
for (const int i : stroke_points.index_range().drop_back(1)) {
|
||||
|
@ -156,6 +225,9 @@ void legacy_gpencil_frame_to_grease_pencil_drawing(const bGPDframe &gpf,
|
|||
stroke_rotations[point_i] = pt.uv_rot;
|
||||
stroke_vertex_colors[point_i] = ColorGeometry4f(pt.vert_color);
|
||||
stroke_selections[point_i] = (pt.flag & GP_SPOINT_SELECT) != 0;
|
||||
if (use_dverts && gps->dvert) {
|
||||
copy_dvert(gps->dvert[point_i], stroke_dverts[point_i]);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -210,6 +282,13 @@ void legacy_gpencil_to_grease_pencil(Main &bmain, GreasePencil &grease_pencil, b
|
|||
|
||||
new_layer.blend_mode = int8_t(gpl->blend_mode);
|
||||
|
||||
new_layer.parent = gpl->parent;
|
||||
new_layer.set_parent_bone_name(gpl->parsubstr);
|
||||
|
||||
copy_v3_v3(new_layer.translation, gpl->location);
|
||||
copy_v3_v3(new_layer.rotation, gpl->rotation);
|
||||
copy_v3_v3(new_layer.scale, gpl->scale);
|
||||
|
||||
/* Convert the layer masks. */
|
||||
LISTBASE_FOREACH (bGPDlayer_Mask *, mask, &gpl->mask_layers) {
|
||||
LayerMask *new_mask = new LayerMask(mask->name);
|
||||
|
@ -225,7 +304,7 @@ void legacy_gpencil_to_grease_pencil(Main &bmain, GreasePencil &grease_pencil, b
|
|||
grease_pencil.drawing_array[i]);
|
||||
|
||||
/* Convert the frame to a drawing. */
|
||||
legacy_gpencil_frame_to_grease_pencil_drawing(*gpf, drawing);
|
||||
legacy_gpencil_frame_to_grease_pencil_drawing(*gpf, gpd.vertex_group_names, drawing);
|
||||
|
||||
/* Add the frame to the layer. */
|
||||
if (GreasePencilFrame *new_frame = new_layer.add_frame(gpf->framenum, i)) {
|
||||
|
@ -242,6 +321,10 @@ void legacy_gpencil_to_grease_pencil(Main &bmain, GreasePencil &grease_pencil, b
|
|||
/* TODO: Update drawing user counts. */
|
||||
}
|
||||
|
||||
/* Copy vertex group names and settings. */
|
||||
BKE_defgroup_copy_list(&grease_pencil.vertex_group_names, &gpd.vertex_group_names);
|
||||
grease_pencil.vertex_group_active_index = gpd.vertex_group_active_index;
|
||||
|
||||
/* Convert the onion skinning settings. */
|
||||
grease_pencil.onion_skinning_settings.opacity = gpd.onion_factor;
|
||||
grease_pencil.onion_skinning_settings.mode = gpd.onion_mode;
|
||||
|
|
|
@ -428,7 +428,7 @@ static ImageGPUTextures image_get_gpu_texture(Image *ima,
|
|||
void *lock;
|
||||
ImBuf *ibuf = BKE_image_acquire_ibuf(ima, iuser, (use_viewers) ? &lock : nullptr);
|
||||
if (ibuf == nullptr) {
|
||||
BKE_image_release_ibuf(ima, ibuf, (use_viewers) ? &lock : nullptr);
|
||||
BKE_image_release_ibuf(ima, ibuf, (use_viewers) ? lock : nullptr);
|
||||
*tex = image_gpu_texture_error_create(textarget);
|
||||
result.texture = *tex;
|
||||
|
||||
|
@ -473,7 +473,7 @@ static ImageGPUTextures image_get_gpu_texture(Image *ima,
|
|||
GPU_texture_original_size_set(*tex, ibuf->x, ibuf->y);
|
||||
}
|
||||
|
||||
BKE_image_release_ibuf(ima, ibuf, (use_viewers) ? &lock : nullptr);
|
||||
BKE_image_release_ibuf(ima, ibuf, (use_viewers) ? lock : nullptr);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
|
|
@ -2273,6 +2273,7 @@ void BKE_main_mesh_legacy_convert_auto_smooth(Main &bmain)
|
|||
else {
|
||||
BLI_addtail(&object->modifiers, md);
|
||||
}
|
||||
BKE_modifiers_persistent_uid_init(*object, md->modifier);
|
||||
|
||||
md->settings.properties = bke::idprop::create_group("Nodes Modifier Settings").release();
|
||||
IDProperty *angle_prop =
|
||||
|
|
|
@ -36,6 +36,7 @@
|
|||
#include "BLI_linklist.h"
|
||||
#include "BLI_listbase.h"
|
||||
#include "BLI_path_util.h"
|
||||
#include "BLI_rand.hh"
|
||||
#include "BLI_session_uid.h"
|
||||
#include "BLI_string.h"
|
||||
#include "BLI_string_utf8.h"
|
||||
|
@ -161,9 +162,6 @@ static ModifierData *modifier_allocate_and_init(ModifierType type)
|
|||
ModifierData *BKE_modifier_new(int type)
|
||||
{
|
||||
ModifierData *md = modifier_allocate_and_init(ModifierType(type));
|
||||
|
||||
BKE_modifier_session_uid_generate(md);
|
||||
|
||||
return md;
|
||||
}
|
||||
|
||||
|
@ -220,11 +218,6 @@ void BKE_modifier_remove_from_list(Object *ob, ModifierData *md)
|
|||
BLI_remlink(&ob->modifiers, md);
|
||||
}
|
||||
|
||||
void BKE_modifier_session_uid_generate(ModifierData *md)
|
||||
{
|
||||
md->session_uid = BLI_session_uid_generate();
|
||||
}
|
||||
|
||||
void BKE_modifier_unique_name(ListBase *modifiers, ModifierData *md)
|
||||
{
|
||||
if (modifiers && md) {
|
||||
|
@ -266,10 +259,10 @@ ModifierData *BKE_modifiers_findby_name(const Object *ob, const char *name)
|
|||
BLI_findstring(&(ob->modifiers), name, offsetof(ModifierData, name)));
|
||||
}
|
||||
|
||||
ModifierData *BKE_modifiers_findby_session_uid(const Object *ob, const SessionUID *session_uid)
|
||||
ModifierData *BKE_modifiers_findby_persistent_uid(const Object *ob, const int persistent_uid)
|
||||
{
|
||||
LISTBASE_FOREACH (ModifierData *, md, &ob->modifiers) {
|
||||
if (BLI_session_uid_is_equal(&md->session_uid, session_uid)) {
|
||||
if (md->persistent_uid == persistent_uid) {
|
||||
return md;
|
||||
}
|
||||
}
|
||||
|
@ -358,6 +351,7 @@ void BKE_modifier_copydata_ex(const ModifierData *md, ModifierData *target, cons
|
|||
target->mode = md->mode;
|
||||
target->flag = md->flag;
|
||||
target->ui_expand_flag = md->ui_expand_flag;
|
||||
target->persistent_uid = md->persistent_uid;
|
||||
|
||||
if (mti->copy_data) {
|
||||
mti->copy_data(md, target, flag);
|
||||
|
@ -368,17 +362,6 @@ void BKE_modifier_copydata_ex(const ModifierData *md, ModifierData *target, cons
|
|||
mti->foreach_ID_link(target, nullptr, modifier_copy_data_id_us_cb, nullptr);
|
||||
}
|
||||
}
|
||||
|
||||
if (flag & LIB_ID_CREATE_NO_MAIN) {
|
||||
/* Make sure UID is the same between the source and the target.
|
||||
* This is needed in the cases when UID is to be preserved and when there is no copy_data
|
||||
* callback, or the copy_data does not do full byte copy of the modifier data. */
|
||||
target->session_uid = md->session_uid;
|
||||
}
|
||||
else {
|
||||
/* In the case copy_data made full byte copy force UID to be re-generated. */
|
||||
BKE_modifier_session_uid_generate(target);
|
||||
}
|
||||
}
|
||||
|
||||
void BKE_modifier_copydata(const ModifierData *md, ModifierData *target)
|
||||
|
@ -985,7 +968,7 @@ Mesh *BKE_modifier_get_evaluated_mesh_from_evaluated_object(Object *ob_eval)
|
|||
ModifierData *BKE_modifier_get_original(const Object *object, ModifierData *md)
|
||||
{
|
||||
const Object *object_orig = DEG_get_original_object((Object *)object);
|
||||
return BKE_modifiers_findby_session_uid(object_orig, &md->session_uid);
|
||||
return BKE_modifiers_findby_persistent_uid(object_orig, md->persistent_uid);
|
||||
}
|
||||
|
||||
ModifierData *BKE_modifier_get_evaluated(Depsgraph *depsgraph, Object *object, ModifierData *md)
|
||||
|
@ -994,30 +977,49 @@ ModifierData *BKE_modifier_get_evaluated(Depsgraph *depsgraph, Object *object, M
|
|||
if (object_eval == object) {
|
||||
return md;
|
||||
}
|
||||
return BKE_modifiers_findby_session_uid(object_eval, &md->session_uid);
|
||||
return BKE_modifiers_findby_persistent_uid(object_eval, md->persistent_uid);
|
||||
}
|
||||
|
||||
void BKE_modifier_check_uids_unique_and_report(const Object *object)
|
||||
void BKE_modifiers_persistent_uid_init(const Object &object, ModifierData &md)
|
||||
{
|
||||
GSet *used_uids = BLI_gset_new(
|
||||
BLI_session_uid_ghash_hash, BLI_session_uid_ghash_compare, "modifier used uids");
|
||||
|
||||
LISTBASE_FOREACH (ModifierData *, md, &object->modifiers) {
|
||||
const SessionUID *session_uid = &md->session_uid;
|
||||
if (!BLI_session_uid_is_generated(session_uid)) {
|
||||
printf("Modifier %s -> %s does not have UID generated.\n", object->id.name + 2, md->name);
|
||||
continue;
|
||||
}
|
||||
|
||||
if (BLI_gset_lookup(used_uids, session_uid) != nullptr) {
|
||||
printf("Modifier %s -> %s has duplicate UID generated.\n", object->id.name + 2, md->name);
|
||||
continue;
|
||||
}
|
||||
|
||||
BLI_gset_insert(used_uids, (void *)session_uid);
|
||||
uint64_t hash = blender::get_default_hash(blender::StringRef(md.name));
|
||||
if (ID_IS_LINKED(&object)) {
|
||||
hash = blender::get_default_hash(hash, blender::StringRef(object.id.lib->filepath_abs));
|
||||
}
|
||||
if (ID_IS_OVERRIDE_LIBRARY_REAL(&object)) {
|
||||
BLI_assert(ID_IS_LINKED(object.id.override_library->reference));
|
||||
hash = blender::get_default_hash(
|
||||
hash, blender::StringRef(object.id.override_library->reference->lib->filepath_abs));
|
||||
}
|
||||
blender::RandomNumberGenerator rng{uint32_t(hash)};
|
||||
while (true) {
|
||||
const int new_uid = rng.get_int32();
|
||||
if (new_uid <= 0) {
|
||||
continue;
|
||||
}
|
||||
if (BKE_modifiers_findby_persistent_uid(&object, new_uid) != nullptr) {
|
||||
continue;
|
||||
}
|
||||
md.persistent_uid = new_uid;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
BLI_gset_free(used_uids, nullptr);
|
||||
bool BKE_modifiers_persistent_uids_are_valid(const Object &object)
|
||||
{
|
||||
blender::Set<int> uids;
|
||||
int modifiers_num = 0;
|
||||
LISTBASE_FOREACH (const ModifierData *, md, &object.modifiers) {
|
||||
if (md->persistent_uid <= 0) {
|
||||
return false;
|
||||
}
|
||||
uids.add(md->persistent_uid);
|
||||
modifiers_num++;
|
||||
}
|
||||
if (uids.size() != modifiers_num) {
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void BKE_modifier_blend_write(BlendWriter *writer, const ID *id_owner, ListBase *modbase)
|
||||
|
@ -1245,8 +1247,6 @@ void BKE_modifier_blend_read_data(BlendDataReader *reader, ListBase *lb, Object
|
|||
BLO_read_list(reader, lb);
|
||||
|
||||
LISTBASE_FOREACH (ModifierData *, md, lb) {
|
||||
BKE_modifier_session_uid_generate(md);
|
||||
|
||||
md->error = nullptr;
|
||||
md->runtime = nullptr;
|
||||
|
||||
|
|
|
@ -250,6 +250,7 @@ static void object_copy_data(Main *bmain, ID *id_dst, const ID *id_src, const in
|
|||
BLI_listbase_clear(&ob_dst->greasepencil_modifiers);
|
||||
/* NOTE: Also takes care of soft-body and particle systems copying. */
|
||||
BKE_object_modifier_stack_copy(ob_dst, ob_src, true, flag_subdata);
|
||||
BLI_assert(BKE_modifiers_persistent_uids_are_valid(*ob_dst));
|
||||
|
||||
BLI_listbase_clear((ListBase *)&ob_dst->drawdata);
|
||||
BLI_listbase_clear(&ob_dst->pc_ids);
|
||||
|
@ -766,6 +767,7 @@ static void object_blend_read_data(BlendDataReader *reader, ID *id)
|
|||
wmd->width = wav->width;
|
||||
|
||||
BLI_addtail(&ob->modifiers, wmd);
|
||||
BKE_modifiers_persistent_uid_init(*ob, wmd->modifier);
|
||||
|
||||
BLI_remlink(&ob->effect, paf);
|
||||
MEM_freeN(paf);
|
||||
|
@ -784,6 +786,7 @@ static void object_blend_read_data(BlendDataReader *reader, ID *id)
|
|||
bmd->seed = 1;
|
||||
|
||||
BLI_addtail(&ob->modifiers, bmd);
|
||||
BKE_modifiers_persistent_uid_init(*ob, bmd->modifier);
|
||||
|
||||
BLI_remlink(&ob->effect, paf);
|
||||
MEM_freeN(paf);
|
||||
|
@ -871,6 +874,7 @@ static void object_blend_read_data(BlendDataReader *reader, ID *id)
|
|||
BLI_remlink(&ob->hooks, hook);
|
||||
|
||||
BKE_modifier_unique_name(&ob->modifiers, (ModifierData *)hmd);
|
||||
BKE_modifiers_persistent_uid_init(*ob, hmd->modifier);
|
||||
|
||||
MEM_freeN(hook);
|
||||
}
|
||||
|
@ -1423,6 +1427,7 @@ bool BKE_object_copy_modifier(
|
|||
|
||||
BLI_addtail(&ob_dst->modifiers, md_dst);
|
||||
BKE_modifier_unique_name(&ob_dst->modifiers, md_dst);
|
||||
BKE_modifiers_persistent_uid_init(*ob_dst, *md_dst);
|
||||
}
|
||||
|
||||
BKE_object_modifier_set_active(ob_dst, md_dst);
|
||||
|
@ -5324,7 +5329,6 @@ void BKE_object_to_curve_clear(Object *object)
|
|||
void BKE_object_check_uids_unique_and_report(const Object *object)
|
||||
{
|
||||
BKE_pose_check_uids_unique_and_report(object->pose);
|
||||
BKE_modifier_check_uids_unique_and_report(object);
|
||||
}
|
||||
|
||||
SubsurfModifierData *BKE_object_get_last_subsurf_modifier(const Object *ob)
|
||||
|
|
|
@ -3958,6 +3958,7 @@ static ModifierData *object_add_or_copy_particle_system(
|
|||
psmd->psys = psys;
|
||||
BLI_addtail(&ob->modifiers, md);
|
||||
BKE_object_modifier_set_active(ob, md);
|
||||
BKE_modifiers_persistent_uid_init(*ob, *md);
|
||||
|
||||
psys->totpart = 0;
|
||||
psys->flag = PSYS_CURRENT;
|
||||
|
|
|
@ -500,7 +500,7 @@ MovieTrackingTrack *BKE_tracking_track_add_empty(MovieTracking *tracking, ListBa
|
|||
const MovieTrackingSettings *settings = &tracking->settings;
|
||||
|
||||
MovieTrackingTrack *track = MEM_cnew<MovieTrackingTrack>("add_marker_exec track");
|
||||
STRNCPY(track->name, "Track");
|
||||
STRNCPY(track->name, CTX_DATA_(BLT_I18NCONTEXT_ID_MOVIECLIP, "Track"));
|
||||
|
||||
/* Fill track's settings from default settings. */
|
||||
track->motion_model = settings->default_motion_model;
|
||||
|
|
|
@ -1844,6 +1844,18 @@ static bool ch_is_op(char op)
|
|||
}
|
||||
}
|
||||
|
||||
static bool ch_is_op_unary(char op)
|
||||
{
|
||||
switch (op) {
|
||||
case '+':
|
||||
case '-':
|
||||
case '~':
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Helper function for #unit_distribute_negatives to find the next negative to distribute.
|
||||
*
|
||||
|
@ -1912,6 +1924,18 @@ static char *find_next_op(const char *str, char *remaining_str, int remaining_st
|
|||
return remaining_str + i;
|
||||
}
|
||||
|
||||
/**
|
||||
* Skip over multiple successive unary operators (typically `-`), skipping spaces.
|
||||
* This allows for `--90d` to be handled properly, see: #117783.
|
||||
*/
|
||||
static char *skip_unary_op(char *str)
|
||||
{
|
||||
while (*str == ' ' || ch_is_op_unary(*str)) {
|
||||
str++;
|
||||
}
|
||||
return str;
|
||||
}
|
||||
|
||||
/**
|
||||
* Put parentheses around blocks of values after negative signs to get rid of an implied "+"
|
||||
* between numbers without an operation between them. For example:
|
||||
|
@ -1937,8 +1961,9 @@ static bool unit_distribute_negatives(char *str, const int str_maxncpy)
|
|||
memmove(remaining_str + 1, remaining_str, remaining_str_maxncpy - 2);
|
||||
*remaining_str = '(';
|
||||
|
||||
/* Add the ')' before the next operation or at the end. */
|
||||
remaining_str = find_next_op(str, remaining_str + 1, remaining_str_maxncpy);
|
||||
/* Add the ')' before the next operation or at the end.
|
||||
* Unary operators are skipped to allow `--` to be a supported prefix. */
|
||||
remaining_str = find_next_op(str, skip_unary_op(remaining_str + 1), remaining_str_maxncpy);
|
||||
remaining_str_maxncpy = str_maxncpy - int(remaining_str - str);
|
||||
memmove(remaining_str + 1, remaining_str, remaining_str_maxncpy - 2);
|
||||
*remaining_str = ')';
|
||||
|
|
|
@ -307,8 +307,8 @@ class Any {
|
|||
return buffer_.ptr();
|
||||
}
|
||||
else {
|
||||
/* Using #malloc so that the #unique_ptr can free the memory. */
|
||||
T *value = static_cast<T *>(malloc(sizeof(T)));
|
||||
/* Using raw allocation here. The caller is responsible for constructing the value. */
|
||||
T *value = static_cast<T *>(::operator new(sizeof(T)));
|
||||
new (&buffer_) std::unique_ptr<T>(value);
|
||||
return value;
|
||||
}
|
||||
|
|
|
@ -626,7 +626,7 @@ constexpr bool operator>=(StringRef a, StringRef b)
|
|||
* \{ */
|
||||
|
||||
/**
|
||||
* Support using the fmt library with #StringRef and implicitly also #StringRefNull.
|
||||
* Support using the `fmt` library with #StringRef and implicitly also #StringRefNull.
|
||||
*/
|
||||
inline std::string_view format_as(StringRef str)
|
||||
{
|
||||
|
|
|
@ -34,6 +34,10 @@ struct SearchItem {
|
|||
* number is not based on an actual clock.
|
||||
*/
|
||||
int recent_time;
|
||||
/**
|
||||
* Deprecated items can still be found via search, but are at the bottom of the list.
|
||||
*/
|
||||
bool is_deprecated;
|
||||
};
|
||||
|
||||
struct RecentCache {
|
||||
|
|
|
@ -343,7 +343,7 @@ static std::optional<float> score_query_against_words(Span<StringRef> query_word
|
|||
Array<int, 64> word_match_map(item.normalized_words.size(), unused_word);
|
||||
|
||||
/* Start with some high score, because otherwise the final score might become negative. */
|
||||
float total_match_score = 1000;
|
||||
float total_match_score = item.is_deprecated ? 500 : 1000;
|
||||
|
||||
for (const int query_word_index : query_words.index_range()) {
|
||||
const StringRef query_word = query_words[query_word_index];
|
||||
|
@ -514,6 +514,9 @@ void StringSearchBase::add_impl(const StringRef str, void *user_data, const int
|
|||
}
|
||||
}
|
||||
|
||||
/* Not checking for the "D" to avoid problems with upper/lower-case. */
|
||||
const bool is_deprecated = str.find("eprecated") != StringRef::not_found;
|
||||
|
||||
items_.append({user_data,
|
||||
allocator_.construct_array_copy(words.as_span()),
|
||||
allocator_.construct_array_copy(word_group_ids.as_span()),
|
||||
|
@ -521,7 +524,8 @@ void StringSearchBase::add_impl(const StringRef str, void *user_data, const int
|
|||
main_group_length,
|
||||
int(str.size()),
|
||||
weight,
|
||||
recent_time});
|
||||
recent_time,
|
||||
is_deprecated});
|
||||
}
|
||||
|
||||
Vector<void *> StringSearchBase::query_impl(const StringRef query) const
|
||||
|
|
|
@ -27,6 +27,7 @@
|
|||
#include "DNA_modifier_types.h"
|
||||
#include "DNA_movieclip_types.h"
|
||||
#include "DNA_scene_types.h"
|
||||
#include "DNA_sequence_types.h"
|
||||
#include "DNA_world_types.h"
|
||||
|
||||
#include "DNA_defaults.h"
|
||||
|
@ -61,6 +62,7 @@
|
|||
#include "BKE_scene.h"
|
||||
#include "BKE_tracking.h"
|
||||
|
||||
#include "SEQ_iterator.hh"
|
||||
#include "SEQ_retiming.hh"
|
||||
#include "SEQ_sequencer.hh"
|
||||
|
||||
|
@ -1936,6 +1938,15 @@ static void fix_geometry_nodes_object_info_scale(bNodeTree &ntree)
|
|||
}
|
||||
}
|
||||
|
||||
static bool seq_filter_bilinear_to_auto(Sequence *seq, void * /*user_data*/)
|
||||
{
|
||||
StripTransform *transform = seq->strip->transform;
|
||||
if (transform != nullptr && transform->filter == SEQ_TRANSFORM_FILTER_BILINEAR) {
|
||||
transform->filter = SEQ_TRANSFORM_FILTER_AUTO;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
void blo_do_versions_400(FileData *fd, Library * /*lib*/, Main *bmain)
|
||||
{
|
||||
if (!MAIN_VERSION_FILE_ATLEAST(bmain, 400, 1)) {
|
||||
|
@ -2848,6 +2859,44 @@ void blo_do_versions_400(FileData *fd, Library * /*lib*/, Main *bmain)
|
|||
}
|
||||
}
|
||||
|
||||
if (!MAIN_VERSION_FILE_ATLEAST(bmain, 401, 18)) {
|
||||
LISTBASE_FOREACH (Scene *, scene, &bmain->scenes) {
|
||||
if (scene->ed != nullptr) {
|
||||
SEQ_for_each_callback(&scene->ed->seqbase, seq_filter_bilinear_to_auto, nullptr);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!MAIN_VERSION_FILE_ATLEAST(bmain, 401, 19)) {
|
||||
LISTBASE_FOREACH (bNodeTree *, ntree, &bmain->nodetrees) {
|
||||
if (ntree->type == NTREE_GEOMETRY) {
|
||||
version_node_socket_name(ntree, FN_NODE_ROTATE_ROTATION, "Rotation 1", "Rotation");
|
||||
version_node_socket_name(ntree, FN_NODE_ROTATE_ROTATION, "Rotation 2", "Rotate By");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!MAIN_VERSION_FILE_ATLEAST(bmain, 401, 20)) {
|
||||
LISTBASE_FOREACH (Object *, ob, &bmain->objects) {
|
||||
int uid = 1;
|
||||
LISTBASE_FOREACH (ModifierData *, md, &ob->modifiers) {
|
||||
/* These identifiers are not necessarily stable for linked data. If the linked data has a
|
||||
* new modifier inserted, the identifiers of other modifiers can change. */
|
||||
md->persistent_uid = uid++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!MAIN_VERSION_FILE_ATLEAST(bmain, 402, 1)) {
|
||||
using namespace blender::bke::greasepencil;
|
||||
/* Initialize newly added scale layer transform to one. */
|
||||
LISTBASE_FOREACH (GreasePencil *, grease_pencil, &bmain->grease_pencils) {
|
||||
for (Layer *layer : grease_pencil->layers_for_write()) {
|
||||
copy_v3_fl(layer->scale, 1.0f);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Always bump subversion in BKE_blender_version.h when adding versioning
|
||||
* code here, and wrap it inside a MAIN_VERSION_FILE_ATLEAST check.
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue