WIP: Brush assets project #106303

Draft
Julian Eisel wants to merge 358 commits from brush-assets-project into main

When changing the target branch, be careful to rebase the branch in your fork to match. See documentation.
141 changed files with 2484 additions and 1395 deletions
Showing only changes of commit 0e32443c28 - Show all commits

30
AUTHORS
View File

@ -26,8 +26,10 @@ Aaron Franke <arnfranke@yahoo.com>
Adam Nydahl <Loginer>
Adi Sage <adisage.connect@gmail.com>
Aditya Y Jeppu <quantimoney>
Adrian Bibby Walther <adrianbibbywalther@gmail.com>
Adrian Newton <TFS>
AgAmemnno <kaz380@hotmail.co.jp>
Ahmad Rifai <riff.blend@gmail.com>
Aidan Davey <ShadowDragon>
Aidan Haile <tactical_fluke>
Alan Babu <alanaman>
@ -69,7 +71,7 @@ Andrej730 <azhilenkov@gmail.com>
Andres Stephens <ondraise15@hotmail.com>
Andrew Buttery <axb2035@gmail.com>
Andrew Hale <TrumanBlending@gmail.com>
Andrew Oates <aoates>
Andrew Oates <andrew@andrewoates.com>
Andrew Wiggin <ender79bl@gmail.com>
Andrew Williams <sobakasu>
Andrii Symkin <pembem22>
@ -96,10 +98,12 @@ Arystanbek Dyussenov <arystan.d@gmail.com>
Asad-ullah Khan <kh4n>
Asher <ThatAsherGuy>
Ashley Ruglys <ashley.ruglys@gmail.com>
Attila Afra <attila.t.afra@intel.com>
Aurel Wildfellner <aurel.w@gmail.com>
Aurelien Jarno <aurel32>
Azeem Bande-Ali <azeemba>
Baardaap <blender@aaltjegron.nl>
Bartosz Kosiorek <gang65@poczta.onet.pl>
Bartosz Moniewski <monio>
Bassam Kurdali <bassam@urchn.org>
Bastien Montagne <bastien@blender.org>
@ -197,6 +201,7 @@ Dorian <BD3D>
Doug Hammond <doughammond@hamsterfight.co.uk>
Douglas Paul <douglas.w.paul@gmail.com>
Dyvine57 <dulana57@gmail.com>
ESASHIKA Kaoru <git@pluser.dev>
Ed Halley <ed@halley.cc>
Edgar Roman Cervantes <redvant>
Edmund Kapusniak <edmundmk>
@ -207,6 +212,7 @@ Ejner Fergo <ejnersan@gmail.com>
Elia Sarti <vekoon@gmail.com>
Emanuel Claesson <emanuel.claesson@gmail.com>
Enrico Fracasso <enrico.fracasso@email.it>
Enrique-de-la-Calle <encalle@ucm.es>
Eric Bickle <ShadowChaser>
Eric Cosky <eric_cosky>
Erik Abrahamsson <ecke101@gmail.com>
@ -231,6 +237,7 @@ Fulk33 <spaceshipwars@gmx.de>
Fynn Grotehans <fynngr@noreply.localhost>
Félix <Miadim>
Gaia Clary <gaia.clary@machinimatrix.org>
Gangneron <clementgangneron@gmail.com>
Garry R. Osgood <grosgood>
Gavin Li <gav@developer.blender.org>
Geoffrey Bantle <hairbat@yahoo.com>
@ -323,6 +330,7 @@ John Quillan <jquillan>
Johnny Matthews <johnny.matthews@gmail.com>
Joilnen Leite <joilnen.leite@gmail.com>
Jonas Holzman <jonas@holzman.fr>
JonasDichelle <jonasdichelle@gmail.com>
Jonathan Williamson <jonathan@cgcookie.com>
Jorge Bernal <jbernalmartinez@gmail.com>
Jorijn de Graaf <bonj@noreply.localhost>
@ -345,7 +353,7 @@ Julian Eisel <julian@blender.org>
Julian Plak <julian.plak@live.nl>
Julian Squires <julian@cipht.net>
Julien Kaspar <julien@blender.org>
Jun Mizutani <jmztn@noreply.localhost>
Jun Mizutani <mizutani.jun@nifty.ne.jp>
Jung Jaeyun <cube-c>
Jure Triglav <juretriglav@gmail.com>
Justin Dailey <dail8859@yahoo.com>
@ -356,7 +364,7 @@ Kai Jægersen <kaio>
Karsten Schwenk <macnihilist@gmx.net>
Karthik Rangasai Sivaraman <rangasai>
Kaspian Jakobsson <kaspian.jakobsson@gmail.com>
Kazashi Yoshioka <vnapdv@noreply.localhost>
Kazashi Yoshioka <kaz380@hotmail.co.jp>
Kdaf <Kdaf>
Keir Mierle <mierle@gmail.com>
Keith Boshoff <wahooney>
@ -373,6 +381,7 @@ Kevin Mackay <mackay.ka@gmail.com>
Khanh Ha <khanhhh89@gmail.com>
Konrad Kleine <konrad.wilhelm.kleine@gmail.com>
Konrad Puklicki <puklicki>
Koranir <101683475+Koranir@users.noreply.github.com>
Kris <Metricity>
Krzysztof Recko <yetioszek@gmail.com>
Kévin Dietrich <kevin.dietrich@mailoo.org>
@ -484,6 +493,7 @@ Nick Milios <semaphore>
Nick Samarin <nicks1987@bigmir.net>
Nicola De Mitri <nicolasap>
Nicolas Fauvet <droune2001>
Nika Kutsniashvili <nickberckley@gmail.com>
Nikhil Shringarpurey <Nikhil.Net>
Nikita Sirgienko <nikita.sirgienko@intel.com>
Nikolaus Leopold <nikolaus.leopold@gmail.com>
@ -512,6 +522,7 @@ Paul Golter <paulgolter>
Paul Melis <paulmelis>
PaulKristoffersson <57681017+PaulKristoffersson@users.noreply.github.com>
Pawel Franitza <Rongix>
Pedro A <povmaniac@noreply.localhost>
Pedro Reis <veryprofessionaldodo>
Peng Yan <1105012124@qq.com>
Petar Dosev <pdosev@gmail.com>
@ -532,8 +543,10 @@ Phoenix Katsch <phoenixkatsch>
Pi Lanningham <Quantumplation>
Pierluigi Grassi <pierluigi@tukano.it>
Pierre Risch <prisch>
Pierrick Bouvier <pierrick.bouvier@linaro.org>
Piotr Makal <pmakal>
Piotr Ostrowski <postrowski>
Prakhar Singh Chouhan <tunealso@gmail.com>
Pratik Borhade <pratikborhade302@gmail.com>
Prikshit singh <prikshitsingh79@gmail.com>
Quentin Wenger <matpi@protonmail.ch>
@ -545,6 +558,7 @@ Rajesh Malviya <rajveer0malviya@gmail.com>
Ralf Hölzemer <r.hoelzemer@googlemail.com>
Ramil Roosileht <Limarest>
Rateeb Riyasat <bmollusc>
Raul Fernandez <farsthary84@gmail.com>
Rawalanche <rawalanche@gmail.com>
Ray Molenkamp <github@lazydodo.com>
Rebecca Dengate <beckyd>
@ -573,15 +587,18 @@ Ryan Inch <Imaginer>
S J Bennett (quollism) <quollism@ii.net>
Sahar A. Kashi <sahar.alipourkashi@amd.com>
Sam Miller <samuelmiller>
Samuel Bilek <samuel-bilek-1@noreply.localhost>
Sandy Carter <bwrsandman@gmail.com>
Sayak Biswas <sayakAMD>
Scott Petrovic <scottpetrovic@gmail.com>
Scott Spadea <scottspadea>
Scott Wilson <propersquid>
Scurest <scurest>
Sean Kim <SeanCTKim@protonmail.com>
Sebastian Herholz <sebastian.herholz@intel.com>
Sebastian Koenig <sebastiankoenig@posteo.de>
Sebastian Parborg <darkdefende@gmail.com>
Sebastian Parborg <sebastian@blender.org>
SebastianWitt <w.basti@gmx.de>
Sebastiano Barrera <bars>
Sebastián Barschkis <sebbas@sebbas.org>
Sergej Reich <sergej.reich@googlemail.com>
@ -629,6 +646,7 @@ Thomas Beck <software@plasmasolutions.de>
Thomas Dinges <thomas@blender.org>
Thomas Lachmann <TL>
Thomas Szepe <HG1_public@gmx.net>
Thomas Wilshaw <thomaswilshaw@gmail.com>
Tiago Chaves <laurelkeys>
Tianwei Shen <shentianweipku@gmail.com>
Tim Stullich <tstullich>
@ -677,6 +695,7 @@ Willian Padovani Germano <wpgermano@gmail.com>
Wouter <waterflames>
Wouter van Heyst <larstiq-bforge@larstiq.dyndns.org>
Wybren van Keulen <wybren>
XDzZyq <xiaodouzizyq@gmail.com>
Xavier Cho <mysticfall>
Xavier Hallade <xavier.hallade@intel.com>
Xavier Thomas <xavier.thomas.1980@gmail.com>
@ -697,12 +716,14 @@ Zijun Zhou <eary@noreply.localhost>
andreas atteneder <atti>
ariva00 <ariva00.it@gmail.com>
b-init <b-init>
bartus <bartus@noreply.localhost>
bird_d <bird_d>
brunoT <drehuwann@gmail.com>
cgtinker <Denys.Hsu@gmail.com>
coyo_t <constachugga@gmail.com>
dupoxy <dupoxy@noreply.localhost>
fiord <hyoga_quasar@yahoo.co.jp>
grady <mgradysaunders@gmail.com>
himisa <himisa@noreply.localhost>
jim man <jimman2003>
jon denning <gfxcoder@gmail.com>
@ -718,6 +739,7 @@ nBurn <nbwashburn@gmail.com>
nutti <nutti.metro@gmail.com>
ok_what <ip1149a@gmail.com>
persun <perplexing.sun@gmail.com>
rifai.id <arifai.dev@gmail.com>
swann <slumber>
unclezeiv <davide.vercelli@gmail.com>
yves <valfeur>

View File

@ -129,7 +129,7 @@ elseif(CMAKE_C_COMPILER_ID MATCHES "Clang")
The minimum supported version of CLANG is 8.0, found ${CMAKE_C_COMPILER_VERSION}"
)
endif()
elseif(CMAKE_CXX_COMPILER_ID MATCHES MSVC)
elseif(CMAKE_CXX_COMPILER_ID STREQUAL "MSVC")
if(MSVC_VERSION VERSION_LESS "1928")
# MSVC_VERSION is an internal version number, it doesn't map to something
# the end user would recognize as a version. Because of this, for MSVC we do
@ -645,7 +645,7 @@ mark_as_advanced(WITH_CYCLES_PRECOMPUTE)
mark_as_advanced(CYCLES_TEST_DEVICES)
# NVIDIA CUDA & OptiX
if(NOT APPLE AND NOT (WIN32 AND CMAKE_SYSTEM_PROCESSOR MATCHES ARM64))
if(NOT APPLE AND NOT (WIN32 AND CMAKE_SYSTEM_PROCESSOR STREQUAL "ARM64"))
option(WITH_CYCLES_DEVICE_CUDA "Enable Cycles NVIDIA CUDA compute support" ON)
option(WITH_CYCLES_DEVICE_OPTIX "Enable Cycles NVIDIA OptiX support" ON)
mark_as_advanced(WITH_CYCLES_DEVICE_CUDA)
@ -680,7 +680,7 @@ When set, this path will be used at runtime to compile OptiX kernels."
endif()
# AMD HIP
if(NOT APPLE AND NOT (WIN32 AND CMAKE_SYSTEM_PROCESSOR MATCHES ARM64))
if(NOT APPLE AND NOT (WIN32 AND CMAKE_SYSTEM_PROCESSOR STREQUAL "ARM64"))
option(WITH_CYCLES_DEVICE_HIP "Enable Cycles AMD HIP support" ON)
option(WITH_CYCLES_HIP_BINARIES "Build Cycles AMD HIP binaries" OFF)
# Radeon VII (gfx906) not currently working with HIP SDK, so left out of the list.
@ -707,7 +707,7 @@ if(APPLE)
endif()
# oneAPI
if(NOT APPLE AND NOT (WIN32 AND CMAKE_SYSTEM_PROCESSOR MATCHES ARM64))
if(NOT APPLE AND NOT (WIN32 AND CMAKE_SYSTEM_PROCESSOR STREQUAL "ARM64"))
option(WITH_CYCLES_DEVICE_ONEAPI "Enable Cycles oneAPI compute support" OFF)
option(WITH_CYCLES_ONEAPI_BINARIES "\
Enable Ahead-Of-Time compilation for Cycles oneAPI device"
@ -797,9 +797,19 @@ endif()
# Unit testing
option(WITH_GTESTS "Enable GTest unit testing" OFF)
option(WITH_GPU_RENDER_TESTS "Enable GPU render related unit testing (EEVEE, Workbench and Grease Pencil)" OFF)
option(WITH_GPU_RENDER_TESTS_SILENT "Run GPU render tests silently (finished tests will pass). Generated report will show failing tests" ON)
option(WITH_GPU_DRAW_TESTS "Enable GPU drawing related unit testing (GPU backends and draw manager)" OFF)
option(WITH_GPU_RENDER_TESTS "\
Enable GPU render related unit testing (EEVEE, Workbench and Grease Pencil)"
OFF
)
option(WITH_GPU_RENDER_TESTS_SILENT "\
Run GPU render tests silently (finished tests will pass). \
Generated report will show failing tests"
ON
)
option(WITH_GPU_DRAW_TESTS "\
Enable GPU drawing related unit testing (GPU backends and draw manager)"
OFF
)
option(WITH_COMPOSITOR_REALTIME_TESTS "Enable regression testing for realtime compositor" OFF)
if(UNIX AND NOT (APPLE OR HAIKU))
option(WITH_UI_TESTS "\
@ -816,7 +826,10 @@ endif()
# Enabled by default for typical use cases to speed up development cycles. However, when looking
# into threading or memory related issues (in dependency graph, out-of-bounds, etc) forcing single
# test per Blender instance could give much better clues about the root of the problem.
option(WITH_TESTS_BATCHED "Run multiple tests in a single Blender invocation, for faster test execution" ON)
option(WITH_TESTS_BATCHED "\
Run multiple tests in a single Blender invocation, for faster test execution"
ON
)
mark_as_advanced(WITH_TESTS_BATCHED)
option(WITH_TESTS_SINGLE_BINARY "\
@ -1354,7 +1367,7 @@ if(NOT CMAKE_BUILD_TYPE MATCHES "Release")
# affect on the printed backtrace, and exception handling was correct as well.
#
# Related discussion:
# https://stackoverflow.com/questions/26300819/why-gcc-compiled-c-program-needs-eh-frame-section
# https://stackoverflow.com/questions/26300819
add_compile_options("$<${_is_CONFIG_DEBUG}:-fno-unwind-tables>")
add_compile_options("$<${_is_CONFIG_DEBUG}:-fno-asynchronous-unwind-tables>")
@ -1675,12 +1688,14 @@ if("${CMAKE_GENERATOR}" MATCHES "Ninja" AND WITH_NINJA_POOL_JOBS)
# but this also accounts for the part of the physical RAM being used by other unrelated
# processes on the system, and the part being used by the 'regular' compile and linking jobs.
#
# Also always cap heavy jobs amount to `number of available threads - 1`, to ensure that even if
# there would be enough RAM, the machine never ends up handling only heavy jobs at some point.
# This can have annoying sides effects, like lack of output in the console for several minutes,
# which can lead to a wrong detection of 'unresponsive' state by the buildbots e.g.
# Also always cap heavy jobs amount to `number of available threads - 1`,
# to ensure that even if there would be enough RAM, the machine never ends up
# handling only heavy jobs at some point.
# This can have annoying sides effects, like lack of output in the console for several
# minutes, which can lead to a wrong detection of 'unresponsive' state by the build-bots e.g.
#
# Currently, these settings applied to a 64GB/16threads linux machine will use, for a full build:
# Currently, these settings applied to a 64GB/16threads linux machine will use,
# for a full build:
# - release build:
# * RAM: typically less than 20%, with some peaks at 25%.
# * CPU: over 90% of usage on average over the whole build time.
@ -1927,6 +1942,7 @@ if(CMAKE_COMPILER_IS_GNUCC)
endif()
elseif(CMAKE_C_COMPILER_ID MATCHES "Clang")
# Matches both "Clang" & "AppleClang" on macOS.
add_check_c_compiler_flags(
C_WARNINGS
@ -2034,7 +2050,7 @@ elseif(CMAKE_C_COMPILER_ID MATCHES "Clang")
CXX_WARN_NO_UNDEF_PREFIX -Wno-undef-prefix
)
elseif(CMAKE_C_COMPILER_ID MATCHES "Intel")
elseif(CMAKE_C_COMPILER_ID STREQUAL "Intel")
add_check_c_compiler_flags(
C_WARNINGS
@ -2055,7 +2071,7 @@ elseif(CMAKE_C_COMPILER_ID MATCHES "Intel")
# Disable numbered, false positives.
string(APPEND C_WARNINGS " -wd188,186,144,913,556,858,597,177,1292,167,279,592,94,2722,3199")
string(APPEND CXX_WARNINGS " -wd188,186,144,913,556,858,597,177,1292,167,279,592,94,2722,3199")
elseif(CMAKE_C_COMPILER_ID MATCHES "MSVC")
elseif(CMAKE_C_COMPILER_ID STREQUAL "MSVC")
# most msvc warnings are C & C++
set(_WARNINGS
# warning level:
@ -2149,7 +2165,7 @@ set(CMAKE_CXX_EXTENSIONS OFF)
# This is because sse2neon requires it.
if(MSVC)
string(APPEND CMAKE_CXX_FLAGS " /Zc:__cplusplus")
if(CMAKE_SYSTEM_PROCESSOR MATCHES ARM64)
if(CMAKE_SYSTEM_PROCESSOR STREQUAL "ARM64")
string(APPEND CMAKE_CXX_FLAGS " /Zc:preprocessor")
string(APPEND CMAKE_C_FLAGS " /Zc:preprocessor")
endif()
@ -2160,7 +2176,7 @@ endif()
if(
CMAKE_COMPILER_IS_GNUCC OR
(CMAKE_C_COMPILER_ID MATCHES "Clang" AND (NOT MSVC)) OR
(CMAKE_C_COMPILER_ID MATCHES "Intel")
(CMAKE_C_COMPILER_ID STREQUAL "Intel")
)
# Use C11 + GNU extensions, works with GCC, Clang, ICC
string(APPEND CMAKE_C_FLAGS " -std=gnu11")

View File

@ -116,7 +116,8 @@ if(NOT BLENDER_PLATFORM_WINDOWS_ARM)
endif()
# Embree needs to be included after dpcpp as it uses it for compiling with GPU support
if(BLENDER_PLATFORM_WINDOWS_ARM)
# WoA needs embree to be built with the VS Generator + LLVM, put it in it's own file to avoid clutter
# WoA needs embree to be built with the VS Generator + LLVM,
# put it in it's own file to avoid clutter.
include(cmake/embree_windows_arm.cmake)
else()
include(cmake/embree.cmake)

View File

@ -15,7 +15,8 @@ foreach(_variableName ${_variableNames})
# First see if DEP_HOMEPAGE is set, if it is use that.
set(DEP_HOMEPAGE ${${DEP_NAME}_HOMEPAGE})
if(NOT DEP_HOMEPAGE)
# If the xxx_HOMEPAGE is not set but the URI for the archive is a known github format extract the reprository/project from the URI
# If the xxx_HOMEPAGE is not set but the URI for the archive is a known github format
# extract the repository/project from the URI.
string(REGEX MATCH "https:\/\/(.*)github\.com\/(.+)\/(archive|releases|release|tar.gz)\/(.*)" DEP_PROJECT "${${_variableName}}")
if(CMAKE_MATCH_2)
set(DEP_HOMEPAGE "https://www.github.com/${CMAKE_MATCH_2}")

View File

@ -43,15 +43,18 @@ set(EMBREE_EXTRA_ARGS
# We want the VS2019 tools for embree, as they are stable.
# We cannot use VS2022 easily, unless we specify an older (unsupported) toolset such as 17.35,
# as the newer toolsets mandate LLVM 16, which we cannot use currently, due to lack of support in OSL and ISPC.
# as the newer toolsets mandate LLVM 16, which we cannot use currently,
# due to lack of support in OSL and ISPC.
set(EMBREE_VCTOOLS_REQUIRED_VERSION 14.29)
# Extract the list of installed tools that match the required version from the `VCToolsInstallDir` env var
# Extract the list of installed tools that match the required version from the
# `VCToolsInstallDir` env var
file(TO_CMAKE_PATH $ENV{VCToolsInstallDir} EMBREE_VCTOOLSINSTALLDIR_PATH)
cmake_path(GET EMBREE_VCTOOLSINSTALLDIR_PATH PARENT_PATH EMBREE_VCTOOLSDIR_PATH)
file(GLOB EMBREE_INSTALLED_VCTOOLS RELATIVE ${EMBREE_VCTOOLSDIR_PATH} ${EMBREE_VCTOOLSDIR_PATH}/${EMBREE_VCTOOLS_REQUIRED_VERSION}*)
# Check that at least one the installed tool versions (there may be different subversions) is present
# Check that at least one the installed tool versions
# (there may be different subversions) is present.
if(NOT EMBREE_INSTALLED_VCTOOLS)
message(FATAL_ERROR "When building for Windows ARM64 platforms, embree requires VC Tools ${EMBREE_VCTOOLS_REQUIRED_VERSION} to be installed alongside the current version.")
endif()
@ -60,15 +63,26 @@ endif()
list(SORT EMBREE_INSTALLED_VCTOOLS)
list(GET EMBREE_INSTALLED_VCTOOLS -1 EMBREE_VCTOOLS_VERSION)
# Configure our in file and temporarily store it in the build dir (with modified extension so nothing else picks it up)
# This feels icky, but boost does something similar, and we haven't called ExternalProject_Add yet, so the embree dir does not yet exist
configure_file(${PATCH_DIR}/embree_Directory.Build.Props.in ${BUILD_DIR}/embree_Directory.Build.Props_temp)
# Configure our in file and temporarily store it in the build dir
# (with modified extension so nothing else picks it up)
# This feels icky, but boost does something similar, and we haven't called
# `ExternalProject_Add` yet, so the embree dir does not yet exist.
configure_file(
${PATCH_DIR}/embree_Directory.Build.Props.in
${BUILD_DIR}/embree_Directory.Build.Props_temp
)
# Update the patch command to copy the configured build props file in
set(EMBREE_PATCH_COMMAND COMMAND ${CMAKE_COMMAND} -E copy ${BUILD_DIR}/embree_Directory.Build.Props_temp ${BUILD_DIR}/embree/src/external_embree-build/Directory.Build.Props && ${PATCH_CMD} -p 1 -d ${BUILD_DIR}/embree/src/external_embree < ${PATCH_DIR}/embree.diff)
set(EMBREE_PATCH_COMMAND
COMMAND ${CMAKE_COMMAND} -E copy
${BUILD_DIR}/embree_Directory.Build.Props_temp
${BUILD_DIR}/embree/src/external_embree-build/Directory.Build.Props &&
${PATCH_CMD} -p 1 -d ${BUILD_DIR}/embree/src/external_embree < ${PATCH_DIR}/embree.diff
)
# This all only works if we use the VS generator (with clangcl toolset), so switch back to that
# Note: there is literally no way to get ninja to use a different toolset other than manually overwriting every env var, or calling a nested vcvarsall, both of which are *messy*
# This all only works if we use the VS generator (with `clangcl` toolset), so switch back to that
# Note: there is literally no way to get ninja to use a different toolset other than manually
# overwriting every env var, or calling a nested `vcvarsall`, both of which are *messy*.
set(EMBREE_GENERATOR ${CMAKE_GENERATOR})
set(EMBREE_GENERATOR_TOOLSET ClangCL)
@ -99,16 +113,30 @@ add_dependencies(
if(BUILD_MODE STREQUAL Release)
ExternalProject_Add_Step(external_embree after_install
COMMAND ${CMAKE_COMMAND} -E copy_directory ${LIBDIR}/embree/include ${HARVEST_TARGET}/embree/include
COMMAND ${CMAKE_COMMAND} -E copy_directory ${LIBDIR}/embree/lib ${HARVEST_TARGET}/embree/lib
COMMAND ${CMAKE_COMMAND} -E copy_directory ${LIBDIR}/embree/share ${HARVEST_TARGET}/embree/share
COMMAND ${CMAKE_COMMAND} -E copy ${LIBDIR}/embree/bin/embree4.dll ${HARVEST_TARGET}/embree/bin/embree4.dll
COMMAND ${CMAKE_COMMAND} -E copy_directory
${LIBDIR}/embree/include
${HARVEST_TARGET}/embree/include
COMMAND ${CMAKE_COMMAND} -E copy_directory
${LIBDIR}/embree/lib
${HARVEST_TARGET}/embree/lib
COMMAND ${CMAKE_COMMAND} -E copy_directory
${LIBDIR}/embree/share
${HARVEST_TARGET}/embree/share
COMMAND ${CMAKE_COMMAND} -E copy
${LIBDIR}/embree/bin/embree4.dll
${HARVEST_TARGET}/embree/bin/embree4.dll
DEPENDEES install
)
else()
ExternalProject_Add_Step(external_embree after_install
COMMAND ${CMAKE_COMMAND} -E copy ${LIBDIR}/embree/bin/embree4_d.dll ${HARVEST_TARGET}/embree/bin/embree4_d.dll
COMMAND ${CMAKE_COMMAND} -E copy ${LIBDIR}/embree/lib/embree4_d.lib ${HARVEST_TARGET}/embree/lib/embree4_d.lib
COMMAND ${CMAKE_COMMAND} -E copy
${LIBDIR}/embree/bin/embree4_d.dll
${HARVEST_TARGET}/embree/bin/embree4_d.dll
COMMAND ${CMAKE_COMMAND} -E copy
${LIBDIR}/embree/lib/embree4_d.lib
${HARVEST_TARGET}/embree/lib/embree4_d.lib
DEPENDEES install
)
endif()

View File

@ -3,7 +3,7 @@
# SPDX-License-Identifier: GPL-2.0-or-later
# Generated configuration files use an old `aclocal-1.15` on RockyLinux8.
if(CMAKE_SYSTEM_NAME MATCHES "Linux")
if(CMAKE_SYSTEM_NAME STREQUAL "Linux")
set(_autoconf_cmd_optional ./autogen.sh &&)
else()
set(_autoconf_cmd_optional)

View File

@ -59,6 +59,21 @@ else()
set(OIDN_CMAKE_FLAGS ${DEFAULT_CMAKE_FLAGS})
endif()
set(ODIN_PATCH_COMMAND
${PATCH_CMD} --verbose -p 1 -N -d
${BUILD_DIR}/openimagedenoise/src/external_openimagedenoise <
${PATCH_DIR}/oidn.diff
)
if(CMAKE_SYSTEM_NAME STREQUAL "Linux")
# Replace `attrib.memoryType` with `attrib.type`.
# See: https://github.com/ROCm/HIP/pull/2164
set(ODIN_PATCH_COMMAND ${ODIN_PATCH_COMMAND} &&
sed -i "s/(attrib\\.memoryType)/(attrib.type)/g"
${BUILD_DIR}/openimagedenoise/src/external_openimagedenoise/devices/hip/hip_device.cpp
)
endif()
ExternalProject_Add(external_openimagedenoise
URL file://${PACKAGE_DIR}/${OIDN_FILE}
DOWNLOAD_DIR ${DOWNLOAD_DIR}
@ -71,13 +86,12 @@ ExternalProject_Add(external_openimagedenoise
${OIDN_CMAKE_FLAGS}
${OIDN_EXTRA_ARGS}
PATCH_COMMAND ${PATCH_CMD} --verbose -p 1 -N -d
${BUILD_DIR}/openimagedenoise/src/external_openimagedenoise <
${PATCH_DIR}/oidn.diff
PATCH_COMMAND ${ODIN_PATCH_COMMAND}
INSTALL_DIR ${LIBDIR}/openimagedenoise
)
unset(ODIN_PATCH_COMMAND)
add_dependencies(
external_openimagedenoise
external_tbb

View File

@ -41,7 +41,7 @@ message("PATCH_DIR = ${PATCH_DIR}")
message("BUILD_DIR = ${BUILD_DIR}")
if(WIN32)
if(CMAKE_SYSTEM_PROCESSOR MATCHES ARM64)
if(CMAKE_SYSTEM_PROCESSOR STREQUAL "ARM64")
set(BLENDER_PLATFORM_ARM ON)
set(BLENDER_PLATFORM_WINDOWS_ARM ON)
endif()

View File

@ -116,12 +116,14 @@ else()
endif()
set(PYTHON_BINARY ${LIBDIR}/python/bin/python${PYTHON_SHORT_VERSION})
# Various flags to convince Python to use our own versions of ffi, sqlite, ssl, bzip2, lzma and zlib.
# Various flags to convince Python to use our own versions of:
# `ffi`, `sqlite`, `ssl`, `bzip2`, `lzma` and `zlib`.
# Using pkg-config is only supported for some, and even then we need to work around issues.
set(PYTHON_CONFIGURE_EXTRA_ARGS --with-openssl=${LIBDIR}/ssl)
set(PYTHON_CFLAGS "${PLATFORM_CFLAGS} ")
# Manually specify some library paths. For ffi there is no other way, for sqlite is needed because
# LIBSQLITE3_LIBS does not work, and ssl because it uses the wrong ssl/lib dir instead of ssl/lib64.
# Manually specify some library paths. For ffi there is no other way,
# for sqlite is needed because LIBSQLITE3_LIBS does not work,
# and ssl because it uses the wrong ssl/lib dir instead of ssl/lib64.
set(PYTHON_LDFLAGS "-L${LIBDIR}/ffi/lib -L${LIBDIR}/sqlite/lib -L${LIBDIR}/ssl/lib -L${LIBDIR}/ssl/lib64 ${PLATFORM_LDFLAGS} ")
set(PYTHON_CONFIGURE_EXTRA_ENV
export CFLAGS=${PYTHON_CFLAGS} &&

View File

@ -87,7 +87,8 @@ if(EXISTS "${DOWNLOAD_DIR}/msys2/msys64/usr/bin/perl.exe")
)
endif()
# Strip out the copy of link that comes with some packages if it exists, otherwise meson builds break
# Strip out the copy of link that comes with some packages if it exists,
# otherwise meson builds break.
if(EXISTS "${DOWNLOAD_DIR}/msys2/msys64/usr/bin/link.exe")
execute_process(
COMMAND ${CMAKE_COMMAND} -E rm ${DOWNLOAD_DIR}/msys2/msys64/usr/bin/link.exe

View File

@ -5,7 +5,8 @@
set(SSL_CONFIGURE_COMMAND ./Configure)
if(WIN32)
# Python will build this with its preferred build options and patches. We only need to unpack openssl
# Python will build this with its preferred build options and patches.
# We only need to unpack openssl.
ExternalProject_Add(external_ssl
URL file://${PACKAGE_DIR}/${SSL_FILE}
DOWNLOAD_DIR ${DOWNLOAD_DIR}

View File

@ -41,7 +41,8 @@ if(NOT WIN32)
INSTALL_DIR ${LIBDIR}/theora
)
else()
# We are kind of naughty here and steal vorbis' FindOgg.cmake, but given it's a dependency anyway...
# We are kind of naughty here and steal vorbis' `FindOgg.cmake`,
# but given it's a dependency anyway.
ExternalProject_Add(external_theora
URL file://${PACKAGE_DIR}/${THEORA_FILE}
DOWNLOAD_DIR ${DOWNLOAD_DIR}

View File

@ -554,7 +554,7 @@ macro(TEST_SSE_SUPPORT
set(${_sse_flags} "/arch:SSE")
set(${_sse2_flags} "/arch:SSE2")
endif()
elseif(CMAKE_C_COMPILER_ID MATCHES "Intel")
elseif(CMAKE_C_COMPILER_ID STREQUAL "Intel")
set(${_sse_flags} "") # icc defaults to -msse
set(${_sse2_flags} "") # icc defaults to -msse2
else()
@ -766,7 +766,7 @@ endmacro()
macro(remove_cc_flag_unsigned_char)
if(CMAKE_COMPILER_IS_GNUCC OR
(CMAKE_C_COMPILER_ID MATCHES "Clang") OR
(CMAKE_C_COMPILER_ID MATCHES "Intel"))
(CMAKE_C_COMPILER_ID STREQUAL "Intel"))
remove_cc_flag("-funsigned-char")
elseif(MSVC)
remove_cc_flag("/J")

View File

@ -62,7 +62,7 @@ else()
set(CPACK_PACKAGE_FILE_NAME ${PROJECT_NAME_LOWER}-${MAJOR_VERSION}.${MINOR_VERSION}.${PATCH_VERSION}-git${CPACK_DATE}.${BUILD_REV}-${PACKAGE_ARCH})
endif()
if(CMAKE_SYSTEM_NAME MATCHES "Linux")
if(CMAKE_SYSTEM_NAME STREQUAL "Linux")
# RPM packages
include(build_files/cmake/RpmBuild.cmake)
if(RPMBUILD_FOUND)

View File

@ -649,7 +649,7 @@ if(CMAKE_DL_LIBS)
list(APPEND PLATFORM_LINKLIBS ${CMAKE_DL_LIBS})
endif()
if(CMAKE_SYSTEM_NAME MATCHES "Linux")
if(CMAKE_SYSTEM_NAME STREQUAL "Linux")
if(NOT WITH_PYTHON_MODULE)
# binreloc is linux only
set(BINRELOC_INCLUDE_DIRS ${CMAKE_SOURCE_DIR}/extern/binreloc/include)
@ -1043,7 +1043,7 @@ elseif(CMAKE_C_COMPILER_ID MATCHES "Clang")
endif()
# Intel C++ Compiler
elseif(CMAKE_C_COMPILER_ID MATCHES "Intel")
elseif(CMAKE_C_COMPILER_ID STREQUAL "Intel")
# think these next two are broken
find_program(XIAR xiar)
if(XIAR)
@ -1136,8 +1136,12 @@ if(PLATFORM_BUNDLED_LIBRARIES)
# Environment variables to run precompiled executables that needed libraries.
list(JOIN PLATFORM_BUNDLED_LIBRARY_DIRS ":" _library_paths)
set(PLATFORM_ENV_BUILD "LD_LIBRARY_PATH=\"${_library_paths}:$LD_LIBRARY_PATH\"")
set(PLATFORM_ENV_INSTALL "LD_LIBRARY_PATH=${CMAKE_INSTALL_PREFIX_WITH_CONFIG}/lib/;$LD_LIBRARY_PATH")
set(PLATFORM_ENV_BUILD
"LD_LIBRARY_PATH=\"${_library_paths}:$LD_LIBRARY_PATH\""
)
set(PLATFORM_ENV_INSTALL
"LD_LIBRARY_PATH=${CMAKE_INSTALL_PREFIX_WITH_CONFIG}/lib/;$LD_LIBRARY_PATH"
)
unset(_library_paths)
else()
# Quiet unused variable warnings, unfortunately this can't be empty.

View File

@ -119,7 +119,11 @@ remove_cc_flag("/GR")
add_definitions(-D_WIN32_WINNT=0x603)
# First generate the manifest for tests since it will not need the dependency on the CRT.
configure_file(${CMAKE_SOURCE_DIR}/release/windows/manifest/blender.exe.manifest.in ${CMAKE_CURRENT_BINARY_DIR}/tests.exe.manifest @ONLY)
configure_file(
${CMAKE_SOURCE_DIR}/release/windows/manifest/blender.exe.manifest.in
${CMAKE_CURRENT_BINARY_DIR}/tests.exe.manifest
@ONLY
)
# Always detect CRT paths, but only manually install with WITH_WINDOWS_BUNDLE_CRT.
set(CMAKE_INSTALL_SYSTEM_RUNTIME_LIBS_SKIP TRUE)
@ -152,7 +156,11 @@ endif()
if(NOT WITH_PYTHON_MODULE)
set(BUNDLECRT "${BUNDLECRT}<dependency><dependentAssembly><assemblyIdentity type=\"win32\" name=\"blender.shared\" version=\"1.0.0.0\" /></dependentAssembly></dependency>")
endif()
configure_file(${CMAKE_SOURCE_DIR}/release/windows/manifest/blender.exe.manifest.in ${CMAKE_CURRENT_BINARY_DIR}/blender.exe.manifest @ONLY)
configure_file(
${CMAKE_SOURCE_DIR}/release/windows/manifest/blender.exe.manifest.in
${CMAKE_CURRENT_BINARY_DIR}/blender.exe.manifest
@ONLY
)
remove_cc_flag(
"/MDd"
@ -257,7 +265,7 @@ set(PLATFORM_LINKFLAGS_RELEASE "${PLATFORM_LINKFLAGS} ${PDB_INFO_OVERRIDE_LINKER
string(APPEND CMAKE_STATIC_LINKER_FLAGS " /ignore:4221")
if(CMAKE_CL_64)
if(CMAKE_SYSTEM_PROCESSOR MATCHES ARM64)
if(CMAKE_SYSTEM_PROCESSOR STREQUAL "ARM64")
string(PREPEND PLATFORM_LINKFLAGS "/MACHINE:ARM64 ")
else()
string(PREPEND PLATFORM_LINKFLAGS "/MACHINE:X64 ")
@ -270,7 +278,7 @@ if(NOT DEFINED LIBDIR)
# Setup 64bit and 64bit windows systems
if(CMAKE_CL_64)
message(STATUS "64 bit compiler detected.")
if(CMAKE_SYSTEM_PROCESSOR MATCHES ARM64)
if(CMAKE_SYSTEM_PROCESSOR STREQUAL "ARM64")
set(LIBDIR_BASE "windows_arm64")
else()
set(LIBDIR_BASE "windows_x64")
@ -328,7 +336,10 @@ foreach(child ${children})
endforeach()
if(WITH_PUGIXML)
set(PUGIXML_LIBRARIES optimized ${LIBDIR}/pugixml/lib/pugixml.lib debug ${LIBDIR}/pugixml/lib/pugixml_d.lib)
set(PUGIXML_LIBRARIES
optimized ${LIBDIR}/pugixml/lib/pugixml.lib
debug ${LIBDIR}/pugixml/lib/pugixml_d.lib
)
set(PUGIXML_INCLUDE_DIR ${LIBDIR}/pugixml/include)
endif()
@ -386,7 +397,10 @@ if(WITH_HARFBUZZ)
windows_find_package(Harfbuzz)
if(NOT Harfbuzz_FOUND)
set(LIBHARFBUZZ_INCLUDE_DIRS ${LIBDIR}/harfbuzz/include)
set(LIBHARFBUZZ_LIBRARIES optimized ${LIBDIR}/harfbuzz/lib/libharfbuzz.lib debug ${LIBDIR}/harfbuzz/lib/libharfbuzz_d.lib)
set(LIBHARFBUZZ_LIBRARIES
optimized ${LIBDIR}/harfbuzz/lib/libharfbuzz.lib
debug ${LIBDIR}/harfbuzz/lib/libharfbuzz_d.lib
)
set(Harfbuzz_FOUND ON)
endif()
endif()
@ -522,7 +536,11 @@ if(WITH_IMAGE_OPENEXR)
warn_hardcoded_paths(OpenEXR)
set(OPENEXR ${LIBDIR}/openexr)
set(OPENEXR_INCLUDE_DIR ${OPENEXR}/include)
set(OPENEXR_INCLUDE_DIRS ${OPENEXR_INCLUDE_DIR} ${IMATH_INCLUDE_DIRS} ${OPENEXR_INCLUDE_DIR}/OpenEXR)
set(OPENEXR_INCLUDE_DIRS
${OPENEXR_INCLUDE_DIR}
${IMATH_INCLUDE_DIRS}
${OPENEXR_INCLUDE_DIR}/OpenEXR
)
set(OPENEXR_LIBPATH ${OPENEXR}/lib)
# Check if the blender 3.3 lib static library eixts
# if not assume this is a 3.4+ dynamic version.
@ -558,7 +576,10 @@ if(WITH_JACK)
${LIBDIR}/jack/include/jack
${LIBDIR}/jack/include
)
set(JACK_LIBRARIES optimized ${LIBDIR}/jack/lib/libjack.lib debug ${LIBDIR}/jack/lib/libjack_d.lib)
set(JACK_LIBRARIES
optimized ${LIBDIR}/jack/lib/libjack.lib
debug ${LIBDIR}/jack/lib/libjack_d.lib
)
endif()
set(_PYTHON_VERSION "3.11")
@ -592,7 +613,10 @@ if(WITH_PYTHON)
set(NUMPY_FOUND ON)
# uncached vars
set(PYTHON_INCLUDE_DIRS "${PYTHON_INCLUDE_DIR}")
set(PYTHON_LIBRARIES debug "${PYTHON_LIBRARY_DEBUG}" optimized "${PYTHON_LIBRARY}" )
set(PYTHON_LIBRARIES
debug "${PYTHON_LIBRARY_DEBUG}"
optimized "${PYTHON_LIBRARY}"
)
endif()
if(NOT WITH_WINDOWS_FIND_MODULES)
@ -612,7 +636,7 @@ if(NOT WITH_WINDOWS_FIND_MODULES)
if(NOT BOOST_VERSION)
message(FATAL_ERROR "Unable to determine Boost version")
endif()
if(CMAKE_SYSTEM_PROCESSOR MATCHES ARM64)
if(CMAKE_SYSTEM_PROCESSOR STREQUAL "ARM64")
set(BOOST_POSTFIX "vc143-mt-a64-${BOOST_VERSION}")
set(BOOST_DEBUG_POSTFIX "vc143-mt-gyd-a64-${BOOST_VERSION}")
set(BOOST_PREFIX "")
@ -696,8 +720,14 @@ if(NOT OpenImageIO_FOUND)
set(OPENIMAGEIO_LIBPATH ${OPENIMAGEIO}/lib)
set(OPENIMAGEIO_INCLUDE_DIR ${OPENIMAGEIO}/include)
set(OPENIMAGEIO_INCLUDE_DIRS ${OPENIMAGEIO_INCLUDE_DIR})
set(OIIO_OPTIMIZED optimized ${OPENIMAGEIO_LIBPATH}/OpenImageIO.lib optimized ${OPENIMAGEIO_LIBPATH}/OpenImageIO_Util.lib)
set(OIIO_DEBUG debug ${OPENIMAGEIO_LIBPATH}/OpenImageIO_d.lib debug ${OPENIMAGEIO_LIBPATH}/OpenImageIO_Util_d.lib)
set(OIIO_OPTIMIZED
optimized ${OPENIMAGEIO_LIBPATH}/OpenImageIO.lib
optimized ${OPENIMAGEIO_LIBPATH}/OpenImageIO_Util.lib
)
set(OIIO_DEBUG
debug ${OPENIMAGEIO_LIBPATH}/OpenImageIO_d.lib
debug ${OPENIMAGEIO_LIBPATH}/OpenImageIO_Util_d.lib
)
set(OPENIMAGEIO_LIBRARIES ${OIIO_OPTIMIZED} ${OIIO_DEBUG})
set(OPENIMAGEIO_TOOL "${OPENIMAGEIO}/bin/oiiotool.exe")
endif()
@ -761,7 +791,10 @@ if(WITH_OPENVDB)
set(OPENVDB ${LIBDIR}/openVDB)
set(OPENVDB_LIBPATH ${OPENVDB}/lib)
set(OPENVDB_INCLUDE_DIRS ${OPENVDB}/include)
set(OPENVDB_LIBRARIES optimized ${OPENVDB_LIBPATH}/openvdb.lib debug ${OPENVDB_LIBPATH}/openvdb_d.lib )
set(OPENVDB_LIBRARIES
optimized ${OPENVDB_LIBPATH}/openvdb.lib
debug ${OPENVDB_LIBPATH}/openvdb_d.lib
)
endif()
set(OPENVDB_DEFINITIONS -DNOMINMAX -D_USE_MATH_DEFINES)
endif()
@ -785,7 +818,10 @@ if(WITH_OPENIMAGEDENOISE)
get_target_property(OPENIMAGEDENOISE_LIBRARIES_RELEASE OpenImageDenoise IMPORTED_IMPLIB_RELEASE)
get_target_property(OPENIMAGEDENOISE_LIBRARIES_DEBUG OpenImageDenoise IMPORTED_IMPLIB_DEBUG)
if(EXISTS ${OPENIMAGEDENOISE_LIBRARIES_DEBUG})
set(OPENIMAGEDENOISE_LIBRARIES optimized ${OPENIMAGEDENOISE_LIBRARIES_RELEASE} debug ${OPENIMAGEDENOISE_LIBRARIES_DEBUG})
set(OPENIMAGEDENOISE_LIBRARIES
optimized ${OPENIMAGEDENOISE_LIBRARIES_RELEASE}
debug ${OPENIMAGEDENOISE_LIBRARIES_DEBUG}
)
else()
if(EXISTS ${OPENIMAGEDENOISE_LIBRARIES_RELEASE})
set(OPENIMAGEDENOISE_LIBRARIES ${OPENIMAGEDENOISE_LIBRARIES_RELEASE})
@ -820,7 +856,10 @@ if(WITH_ALEMBIC)
set(ALEMBIC_INCLUDE_DIR ${ALEMBIC}/include)
set(ALEMBIC_INCLUDE_DIRS ${ALEMBIC_INCLUDE_DIR})
set(ALEMBIC_LIBPATH ${ALEMBIC}/lib)
set(ALEMBIC_LIBRARIES optimized ${ALEMBIC}/lib/Alembic.lib debug ${ALEMBIC}/lib/Alembic_d.lib)
set(ALEMBIC_LIBRARIES
optimized ${ALEMBIC}/lib/Alembic.lib
debug ${ALEMBIC}/lib/Alembic_d.lib
)
set(ALEMBIC_FOUND 1)
endif()
@ -870,11 +909,17 @@ endif()
if(WITH_TBB)
windows_find_package(TBB)
if(NOT TBB_FOUND)
set(TBB_LIBRARIES optimized ${LIBDIR}/tbb/lib/tbb.lib debug ${LIBDIR}/tbb/lib/tbb_debug.lib)
set(TBB_LIBRARIES
optimized ${LIBDIR}/tbb/lib/tbb.lib
debug ${LIBDIR}/tbb/lib/tbb_debug.lib
)
set(TBB_INCLUDE_DIR ${LIBDIR}/tbb/include)
set(TBB_INCLUDE_DIRS ${TBB_INCLUDE_DIR})
if(WITH_TBB_MALLOC_PROXY)
set(TBB_MALLOC_LIBRARIES optimized ${LIBDIR}/tbb/lib/tbbmalloc.lib debug ${LIBDIR}/tbb/lib/tbbmalloc_debug.lib)
set(TBB_MALLOC_LIBRARIES
optimized ${LIBDIR}/tbb/lib/tbbmalloc.lib
debug ${LIBDIR}/tbb/lib/tbbmalloc_debug.lib
)
add_definitions(-DWITH_TBB_MALLOC)
endif()
endif()
@ -1126,9 +1171,15 @@ if(WITH_XR_OPENXR)
# support the transition between the old and new lib versions
# this can be removed after the next lib update.
if(EXISTS ${XR_OPENXR_SDK_LIBPATH}/openxr_loader_d.lib)
set(XR_OPENXR_SDK_LIBRARIES optimized ${XR_OPENXR_SDK_LIBPATH}/openxr_loader.lib debug ${XR_OPENXR_SDK_LIBPATH}/openxr_loader_d.lib)
set(XR_OPENXR_SDK_LIBRARIES
optimized ${XR_OPENXR_SDK_LIBPATH}/openxr_loader.lib
debug ${XR_OPENXR_SDK_LIBPATH}/openxr_loader_d.lib
)
else()
set(XR_OPENXR_SDK_LIBRARIES optimized ${XR_OPENXR_SDK_LIBPATH}/openxr_loader.lib debug ${XR_OPENXR_SDK_LIBPATH}/openxr_loaderd.lib)
set(XR_OPENXR_SDK_LIBRARIES
optimized ${XR_OPENXR_SDK_LIBPATH}/openxr_loader.lib
debug ${XR_OPENXR_SDK_LIBPATH}/openxr_loaderd.lib
)
endif()
endif()
@ -1139,7 +1190,10 @@ if(WITH_GMP)
else()
set(GMP_DLL_LIB_NAME libgmp-10.lib)
endif()
set(GMP_LIBRARIES ${LIBDIR}/gmp/lib/${GMP_DLL_LIB_NAME} optimized ${LIBDIR}/gmp/lib/libgmpxx.lib debug ${LIBDIR}/gmp/lib/libgmpxx_d.lib)
set(GMP_LIBRARIES ${LIBDIR}/gmp/lib/${GMP_DLL_LIB_NAME}
optimized ${LIBDIR}/gmp/lib/libgmpxx.lib
debug ${LIBDIR}/gmp/lib/libgmpxx_d.lib
)
set(GMP_ROOT_DIR ${LIBDIR}/gmp)
set(GMP_FOUND ON)
endif()
@ -1193,7 +1247,10 @@ if(WITH_CYCLES AND WITH_CYCLES_PATH_GUIDING)
if(openpgl_FOUND)
get_target_property(OPENPGL_LIBRARIES_RELEASE openpgl::openpgl LOCATION_RELEASE)
get_target_property(OPENPGL_LIBRARIES_DEBUG openpgl::openpgl LOCATION_DEBUG)
set(OPENPGL_LIBRARIES optimized ${OPENPGL_LIBRARIES_RELEASE} debug ${OPENPGL_LIBRARIES_DEBUG})
set(OPENPGL_LIBRARIES
optimized ${OPENPGL_LIBRARIES_RELEASE}
debug ${OPENPGL_LIBRARIES_DEBUG}
)
get_target_property(OPENPGL_INCLUDE_DIR openpgl::openpgl INTERFACE_INCLUDE_DIRECTORIES)
else()
set(WITH_CYCLES_PATH_GUIDING OFF)
@ -1232,7 +1289,10 @@ if(WITH_CYCLES AND (WITH_CYCLES_DEVICE_ONEAPI OR (WITH_CYCLES_EMBREE AND EMBREE_
list(APPEND PLATFORM_BUNDLED_LIBRARIES ${_sycl_runtime_libraries})
unset(_sycl_runtime_libraries)
set(SYCL_LIBRARIES optimized ${SYCL_LIBRARY} debug ${SYCL_LIBRARY_DEBUG})
set(SYCL_LIBRARIES
optimized ${SYCL_LIBRARY}
debug ${SYCL_LIBRARY_DEBUG}
)
endif()
@ -1240,6 +1300,7 @@ endif()
list(JOIN PLATFORM_BUNDLED_LIBRARY_DIRS ";" _library_paths)
set(PLATFORM_ENV_BUILD_DIRS "${LIBDIR}/epoxy/bin\;${LIBDIR}/tbb/bin\;${LIBDIR}/OpenImageIO/bin\;${LIBDIR}/boost/lib\;${LIBDIR}/openexr/bin\;${LIBDIR}/imath/bin\;${LIBDIR}/shaderc/bin\;${PATH}")
set(PLATFORM_ENV_BUILD "PATH=${PLATFORM_ENV_BUILD_DIRS}")
# Install needs the additional folders from PLATFORM_ENV_BUILD_DIRS as well, as tools like idiff and abcls use the release mode dlls
# Install needs the additional folders from PLATFORM_ENV_BUILD_DIRS as well, as tools like:
# `idiff` and `abcls` use the release mode dlls.
set(PLATFORM_ENV_INSTALL "PATH=${CMAKE_INSTALL_PREFIX_WITH_CONFIG}/blender.shared/\;${PLATFORM_ENV_BUILD_DIRS}\;$ENV{PATH}")
unset(_library_paths)

View File

@ -27,8 +27,8 @@ function(blender_test_set_envvars testname envvars_list)
if(NOT CMAKE_BUILD_TYPE MATCHES "Release")
if(WITH_COMPILER_ASAN)
set(_lsan_options "LSAN_OPTIONS=print_suppressions=false:suppressions=${CMAKE_SOURCE_DIR}/tools/config/analysis/lsan.supp")
# FIXME That `allocator_may_return_null=true` ASAN option is only needed for the `guardedalloc` test,
# would be nice to allow tests definition to pass extra envvars better.
# FIXME: That `allocator_may_return_null=true` ASAN option is only needed for the
# `guardedalloc` test, would be nice to allow tests definition to pass extra envvars better.
set(_asan_options "ASAN_OPTIONS=allocator_may_return_null=true")
if(DEFINED ENV{LSAN_OPTIONS})
set(_lsan_options "${_lsan_options}:$ENV{LSAN_OPTIONS}")

View File

@ -95,7 +95,8 @@ elseif(WIN32 AND MSVC AND NOT CMAKE_CXX_COMPILER_ID MATCHES "Clang")
# grained control and the speedup we get here is too big to ignore.
set(CYCLES_KERNEL_FLAGS "/fp:fast -D_CRT_SECURE_NO_WARNINGS /GS-")
# "jumptablerdata" improves performance when there is contention in large switch statements such as in svm.h
# "jumptablerdata" improves performance when there is contention in large switch statements
# such as in `svm.h`.
# This flag is supported starting with MSVC 17.7 preview 3:
# https://learn.microsoft.com/en-us/cpp/build/reference/jump-table-rdata
if(CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.37.32820)
@ -149,7 +150,7 @@ elseif(CMAKE_COMPILER_IS_GNUCC OR (CMAKE_CXX_COMPILER_ID MATCHES "Clang"))
string(APPEND CMAKE_CXX_FLAGS " ${CYCLES_KERNEL_FLAGS}")
endif()
elseif(WIN32 AND CMAKE_CXX_COMPILER_ID MATCHES "Intel")
elseif(WIN32 AND CMAKE_CXX_COMPILER_ID STREQUAL "Intel")
check_cxx_compiler_flag(/QxSSE4.2 CXX_HAS_SSE42)
check_cxx_compiler_flag(/arch:AVX CXX_HAS_AVX)
check_cxx_compiler_flag(/QxCORE-AVX2 CXX_HAS_AVX2)
@ -161,7 +162,7 @@ elseif(WIN32 AND CMAKE_CXX_COMPILER_ID MATCHES "Intel")
set(CYCLES_AVX2_KERNEL_FLAGS "/QxCORE-AVX2")
endif()
endif()
elseif(CMAKE_CXX_COMPILER_ID MATCHES "Intel")
elseif(CMAKE_CXX_COMPILER_ID STREQUAL "Intel")
check_cxx_compiler_flag(-xsse4.2 CXX_HAS_SSE42)
check_cxx_compiler_flag(-xavx CXX_HAS_AVX)
check_cxx_compiler_flag(-xcore-avx2 CXX_HAS_AVX2)

View File

@ -35,14 +35,22 @@ static const char *oidn_device_type_to_string(const OIDNDeviceType type)
return "DEFAULT";
case OIDN_DEVICE_TYPE_CPU:
return "CPU";
/* The initial GPU support was added in OIDN 2.0. */
# if OIDN_VERSION_MAJOR >= 2
case OIDN_DEVICE_TYPE_SYCL:
return "SYCL";
case OIDN_DEVICE_TYPE_CUDA:
return "CUDA";
case OIDN_DEVICE_TYPE_HIP:
return "HIP";
# endif
/* The Metal support was added in OIDN 2.2.*/
# if (OIDN_VERSION_MAJOR > 2) || ((OIDN_VERSION_MAJOR == 2) && (OIDN_VERSION_MINOR >= 2))
case OIDN_DEVICE_TYPE_METAL:
return "METAL";
# endif
}
return "UNKNOWN";
}

View File

@ -1217,7 +1217,9 @@ typedef enum KernelBVHLayout {
} KernelBVHLayout;
/* Specialized struct that can become constants in dynamic compilation. */
#define KERNEL_STRUCT_BEGIN(name, parent) ccl_align(16) struct name {
#define KERNEL_STRUCT_BEGIN(name, parent) \
struct ccl_align(16) name \
{
#define KERNEL_STRUCT_END(name) \
} \
; \
@ -1259,7 +1261,8 @@ typedef struct KernelLightLinkSet {
uint light_tree_root;
} KernelLightLinkSet;
typedef ccl_align(16) struct KernelData {
typedef struct ccl_align(16) KernelData
{
/* Features and limits. */
uint kernel_features;
uint max_closures;
@ -1294,7 +1297,8 @@ typedef ccl_align(16) struct KernelData {
# endif
#endif
int pad2, pad3;
} KernelData;
}
KernelData;
static_assert_align(KernelData, 16);
/* Kernel data structures. */

View File

@ -21,7 +21,7 @@
#include "GPU_immediate.h"
#include "GPU_shader.h"
#include "GPU_uniform_buffer.h"
#include "GPU_uniform_buffer.hh"
#include "gpu_shader_create_info.hh"

View File

@ -1434,10 +1434,7 @@ def brush_basic_gpencil_paint_settings(layout, context, brush, *, compact=False)
def brush_basic_grease_pencil_paint_settings(layout, context, brush, *, compact=False):
tool_settings = context.tool_settings
settings = tool_settings.gpencil_paint
gp_settings = brush.gpencil_settings
tool = context.workspace.tools.from_space_view3d_mode(context.mode, create=False)
if gp_settings is None:
return

View File

@ -330,7 +330,6 @@ class VIEWLAYER_PT_filter(ViewLayerButtonsPanel, Panel):
layout.use_property_decorate = False
scene = context.scene
rd = scene.render
view_layer = context.view_layer
col = layout.column(heading="Include")

View File

@ -17,8 +17,6 @@ class NLA_HT_header(Header):
def draw(self, context):
layout = self.layout
st = context.space_data
layout.template_header()
NLA_MT_editor_menus.draw_collapsible(context, layout)

View File

@ -2669,7 +2669,7 @@ class SEQUENCER_PT_modifiers(SequencerButtonsPanel, Panel):
col.prop(mod, "gamma")
else:
if mod.type == 'SOUND_EQUALIZER':
eq_row = box.row()
# eq_row = box.row()
# eq_graphs = eq_row.operator_menu_enum("sequencer.strip_modifier_equalizer_redefine", "graphs")
# eq_graphs.name = mod.name
flow = box.grid_flow(

View File

@ -2664,7 +2664,6 @@ class VIEW3D_PT_tools_grease_pencil_v3_brush_mix_palette(View3DPanel, Panel):
layout.use_property_decorate = False
tool_settings = context.tool_settings
settings = tool_settings.gpencil_paint
brush = settings.brush
col = layout.column()
col.enabled = settings.color_mode == 'VERTEXCOLOR'

View File

@ -0,0 +1,297 @@
/* SPDX-FileCopyrightText: 2024 Blender Authors
*
* SPDX-License-Identifier: GPL-2.0-or-later */
/** \file
* \ingroup animrig
*
* \brief Animation data-block functionality.
*/
#pragma once
#include "ANIM_fcurve.hh"
#include "DNA_anim_types.h"
#include "BLI_math_vector.hh"
#include "BLI_set.hh"
#include "BLI_string_ref.hh"
struct AnimationEvalContext;
struct FCurve;
struct ID;
struct Main;
struct PointerRNA;
namespace blender::animrig {
/* Forward declarations for the types defined later in this file. */
class Layer;
class Strip;
class Binding;
/* Use an alias for the Binding handle type to help disambiguate function parameters. */
using binding_handle_t = decltype(::AnimationBinding::handle);
/**
* Container of animation data for one or more animated IDs.
*
* Broadly an Animation consists of Layers, each Layer has Strips, and it's the
* Strips that eventually contain the animation data.
*
* Temporary limitation: each Animation can only contain one Layer.
*
* Which sub-set of that data drives the animation of which ID is determined by
* which Binding is associated with that ID.
*
* \see AnimData::animation
* \see AnimData::binding_handle
*/
class Animation : public ::Animation {
public:
Animation() = default;
/**
* Copy constructor is deleted, as code should use regular ID library
* management functions to duplicate this data-block.
*/
Animation(const Animation &other) = delete;
/* Animation Layers access. */
blender::Span<const Layer *> layers() const;
blender::MutableSpan<Layer *> layers();
const Layer *layer(int64_t index) const;
Layer *layer(int64_t index);
/* Animation Binding access. */
blender::Span<const Binding *> bindings() const;
blender::MutableSpan<Binding *> bindings();
const Binding *binding(int64_t index) const;
Binding *binding(int64_t index);
/** Free all data in the `Animation`. Doesn't delete the `Animation` itself. */
void free_data();
};
static_assert(sizeof(Animation) == sizeof(::Animation),
"DNA struct and its C++ wrapper must have the same size");
/**
* Strips contain the actual animation data.
*
* Although the data model allows for different strip types, currently only a
* single type is implemented: keyframe strips.
*/
class Strip : public ::AnimationStrip {
public:
Strip() = default;
/**
* Strip cannot be duplicated via the copy constructor. Either use a concrete
* strip type's copy constructor, or use Strip::duplicate().
*
* The reason why the copy constructor won't work is due to the double nature
* of the inheritance at play here:
*
* C-style inheritance: `KeyframeAnimationStrip` "inherits" `AnimationStrip"
* by embedding the latter. This means that any `KeyframeAnimationStrip *`
* can be reinterpreted as `AnimationStrip *`.
*
* C++-style inheritance: the C++ wrappers inherit the DNA structs, so
* `animrig::Strip` inherits `::AnimationStrip`, and
* `animrig::KeyframeStrip` inherits `::KeyframeAnimationStrip`.
*/
Strip(const Strip &other) = delete;
~Strip();
Strip *duplicate(StringRefNull allocation_name) const;
enum class Type : int8_t { Keyframe = 0 };
/**
* Strip type, so it's known which subclass this can be wrapped in without
* having to rely on C++ RTTI.
*/
Type type() const
{
return Type(this->strip_type);
}
template<typename T> bool is() const;
template<typename T> T &as();
template<typename T> const T &as() const;
};
static_assert(sizeof(Strip) == sizeof(::AnimationStrip),
"DNA struct and its C++ wrapper must have the same size");
/**
* Layers can be stacked on top of each other to define the animation. Each
* layer has a mix mode and an influence (0-1), which define how it is mixed
* with the layers below it.
*
* Layers contain one or more Strips, which in turn contain the animation data
* itself.
*
* Temporary limitation: at most one strip may exist on a layer, and it extends
* from negative to positive infinity.
*/
class Layer : public ::AnimationLayer {
public:
Layer() = default;
Layer(const Layer &other);
~Layer();
enum class Flags : uint8_t {
/* Set by default, cleared to mute. */
Enabled = (1 << 0),
/* When adding/removing a flag, also update the ENUM_OPERATORS() invocation below. */
};
Flags flags() const
{
return static_cast<Flags>(this->layer_flags);
}
enum class MixMode : int8_t {
/** Channels in this layer override the same channels from underlying layers. */
Replace = 0,
/** Channels in this layer are added to underlying layers as sequential operations. */
Offset = 1,
/** Channels in this layer are added to underlying layers on a per-channel basis. */
Add = 2,
/** Channels in this layer are subtracted to underlying layers on a per-channel basis. */
Subtract = 3,
/** Channels in this layer are multiplied with underlying layers on a per-channel basis. */
Multiply = 4,
};
MixMode mix_mode() const
{
return static_cast<MixMode>(this->layer_mix_mode);
}
/* Strip access. */
blender::Span<const Strip *> strips() const;
blender::MutableSpan<Strip *> strips();
const Strip *strip(int64_t index) const;
Strip *strip(int64_t index);
};
static_assert(sizeof(Layer) == sizeof(::AnimationLayer),
"DNA struct and its C++ wrapper must have the same size");
ENUM_OPERATORS(Layer::Flags, Layer::Flags::Enabled);
/**
* Identifier for a sub-set of the animation data inside an Animation data-block.
*
* An animatable ID specifies both an `Animation*` and an `AnimationBinding::handle`
* to identify which F-Curves (and in the future other animation data) it will
* be animated by.
*
* This is called an 'binding' because it acts like an binding socket of the
* Animation data-block, into which an animatable ID can be noodled.
*
* \see AnimData::binding_handle
*/
class Binding : public ::AnimationBinding {
public:
Binding() = default;
Binding(const Binding &other) = default;
~Binding() = default;
};
static_assert(sizeof(Binding) == sizeof(::AnimationBinding),
"DNA struct and its C++ wrapper must have the same size");
/**
* KeyframeStrips effectively contain a bag of F-Curves for each Binding.
*/
class KeyframeStrip : public ::KeyframeAnimationStrip {
public:
KeyframeStrip() = default;
KeyframeStrip(const KeyframeStrip &other);
~KeyframeStrip();
/* ChannelBag array access. */
blender::Span<const ChannelBag *> channelbags() const;
blender::MutableSpan<ChannelBag *> channelbags();
const ChannelBag *channelbag(int64_t index) const;
ChannelBag *channelbag(int64_t index);
};
static_assert(sizeof(KeyframeStrip) == sizeof(::KeyframeAnimationStrip),
"DNA struct and its C++ wrapper must have the same size");
template<> KeyframeStrip &Strip::as<KeyframeStrip>();
template<> const KeyframeStrip &Strip::as<KeyframeStrip>() const;
/**
* Collection of F-Curves, intended for a specific Binding handle.
*/
class ChannelBag : public ::AnimationChannelBag {
public:
ChannelBag() = default;
ChannelBag(const ChannelBag &other);
~ChannelBag();
/* FCurves access. */
blender::Span<const FCurve *> fcurves() const;
blender::MutableSpan<FCurve *> fcurves();
const FCurve *fcurve(int64_t index) const;
FCurve *fcurve(int64_t index);
};
static_assert(sizeof(ChannelBag) == sizeof(::AnimationChannelBag),
"DNA struct and its C++ wrapper must have the same size");
} // namespace blender::animrig
/* Wrap functions for the DNA structs. */
inline blender::animrig::Animation &Animation::wrap()
{
return *reinterpret_cast<blender::animrig::Animation *>(this);
}
inline const blender::animrig::Animation &Animation::wrap() const
{
return *reinterpret_cast<const blender::animrig::Animation *>(this);
}
inline blender::animrig::Layer &AnimationLayer::wrap()
{
return *reinterpret_cast<blender::animrig::Layer *>(this);
}
inline const blender::animrig::Layer &AnimationLayer::wrap() const
{
return *reinterpret_cast<const blender::animrig::Layer *>(this);
}
inline blender::animrig::Binding &AnimationBinding::wrap()
{
return *reinterpret_cast<blender::animrig::Binding *>(this);
}
inline const blender::animrig::Binding &AnimationBinding::wrap() const
{
return *reinterpret_cast<const blender::animrig::Binding *>(this);
}
inline blender::animrig::Strip &AnimationStrip::wrap()
{
return *reinterpret_cast<blender::animrig::Strip *>(this);
}
inline const blender::animrig::Strip &AnimationStrip::wrap() const
{
return *reinterpret_cast<const blender::animrig::Strip *>(this);
}
inline blender::animrig::KeyframeStrip &KeyframeAnimationStrip::wrap()
{
return *reinterpret_cast<blender::animrig::KeyframeStrip *>(this);
}
inline const blender::animrig::KeyframeStrip &KeyframeAnimationStrip::wrap() const
{
return *reinterpret_cast<const blender::animrig::KeyframeStrip *>(this);
}
inline blender::animrig::ChannelBag &AnimationChannelBag::wrap()
{
return *reinterpret_cast<blender::animrig::ChannelBag *>(this);
}
inline const blender::animrig::ChannelBag &AnimationChannelBag::wrap() const
{
return *reinterpret_cast<const blender::animrig::ChannelBag *>(this);
}

View File

@ -21,6 +21,7 @@ set(INC_SYS
set(SRC
intern/action.cc
intern/anim_rna.cc
intern/animation.cc
intern/animdata.cc
intern/bone_collections.cc
intern/bonecolor.cc
@ -31,6 +32,7 @@ set(SRC
intern/visualkey.cc
ANIM_action.hh
ANIM_animation.hh
ANIM_animdata.hh
ANIM_armature_iter.hh
ANIM_bone_collections.hh
@ -50,6 +52,7 @@ set(LIB
bf::dna
PRIVATE bf_editor_interface
PRIVATE bf::intern::guardedalloc
PRIVATE bf::intern::atomic
)

View File

@ -0,0 +1,260 @@
/* SPDX-FileCopyrightText: 2024 Blender Authors
*
* SPDX-License-Identifier: GPL-2.0-or-later */
#include "DNA_anim_defaults.h"
#include "DNA_anim_types.h"
#include "DNA_defaults.h"
#include "BLI_listbase.h"
#include "BLI_listbase_wrapper.hh"
#include "BLI_math_base.h"
#include "BLI_string.h"
#include "BLI_string_utf8.h"
#include "BLI_string_utils.hh"
#include "BKE_anim_data.hh"
#include "BKE_animation.hh"
#include "BKE_fcurve.hh"
#include "BKE_lib_id.hh"
#include "BKE_main.hh"
#include "ED_keyframing.hh"
#include "MEM_guardedalloc.h"
#include "atomic_ops.h"
#include "ANIM_animation.hh"
#include "ANIM_fcurve.hh"
#include <cstdio>
#include <cstring>
namespace blender::animrig {
/* ----- Animation implementation ----------- */
blender::Span<const Layer *> Animation::layers() const
{
return blender::Span<Layer *>{reinterpret_cast<Layer **>(this->layer_array),
this->layer_array_num};
}
blender::MutableSpan<Layer *> Animation::layers()
{
return blender::MutableSpan<Layer *>{reinterpret_cast<Layer **>(this->layer_array),
this->layer_array_num};
}
const Layer *Animation::layer(const int64_t index) const
{
return &this->layer_array[index]->wrap();
}
Layer *Animation::layer(const int64_t index)
{
return &this->layer_array[index]->wrap();
}
blender::Span<const Binding *> Animation::bindings() const
{
return blender::Span<Binding *>{reinterpret_cast<Binding **>(this->binding_array),
this->binding_array_num};
}
blender::MutableSpan<Binding *> Animation::bindings()
{
return blender::MutableSpan<Binding *>{reinterpret_cast<Binding **>(this->binding_array),
this->binding_array_num};
}
const Binding *Animation::binding(const int64_t index) const
{
return &this->binding_array[index]->wrap();
}
Binding *Animation::binding(const int64_t index)
{
return &this->binding_array[index]->wrap();
}
void Animation::free_data()
{
/* Free layers. */
for (Layer *layer : this->layers()) {
MEM_delete(layer);
}
MEM_SAFE_FREE(this->layer_array);
this->layer_array_num = 0;
/* Free bindings. */
for (Binding *binding : this->bindings()) {
MEM_delete(binding);
}
MEM_SAFE_FREE(this->binding_array);
this->binding_array_num = 0;
}
/* ----- AnimationLayer implementation ----------- */
Layer::Layer(const Layer &other)
{
memcpy(this, &other, sizeof(*this));
/* Strips. */
this->strip_array = MEM_cnew_array<AnimationStrip *>(other.strip_array_num, __func__);
for (int i : other.strips().index_range()) {
this->strip_array[i] = other.strip(i)->duplicate(__func__);
}
}
Layer::~Layer()
{
for (Strip *strip : this->strips()) {
MEM_delete(strip);
}
MEM_SAFE_FREE(this->strip_array);
this->strip_array_num = 0;
}
blender::Span<const Strip *> Layer::strips() const
{
return blender::Span<Strip *>{reinterpret_cast<Strip **>(this->strip_array),
this->strip_array_num};
}
blender::MutableSpan<Strip *> Layer::strips()
{
return blender::MutableSpan<Strip *>{reinterpret_cast<Strip **>(this->strip_array),
this->strip_array_num};
}
const Strip *Layer::strip(const int64_t index) const
{
return &this->strip_array[index]->wrap();
}
Strip *Layer::strip(const int64_t index)
{
return &this->strip_array[index]->wrap();
}
/* ----- AnimationBinding implementation ----------- */
/* ----- AnimationStrip implementation ----------- */
Strip *Strip::duplicate(const StringRefNull allocation_name) const
{
switch (this->type()) {
case Type::Keyframe: {
const KeyframeStrip &source = this->as<KeyframeStrip>();
KeyframeStrip *copy = MEM_new<KeyframeStrip>(allocation_name.c_str(), source);
return &copy->strip.wrap();
}
}
BLI_assert_unreachable();
return nullptr;
}
Strip::~Strip()
{
switch (this->type()) {
case Type::Keyframe:
this->as<KeyframeStrip>().~KeyframeStrip();
return;
}
BLI_assert_unreachable();
}
/* ----- KeyframeAnimationStrip implementation ----------- */
KeyframeStrip::KeyframeStrip(const KeyframeStrip &other)
{
memcpy(this, &other, sizeof(*this));
this->channelbags_array = MEM_cnew_array<AnimationChannelBag *>(other.channelbags_array_num,
__func__);
Span<const ChannelBag *> channelbags_src = other.channelbags();
for (int i : channelbags_src.index_range()) {
this->channelbags_array[i] = MEM_new<animrig::ChannelBag>(__func__, *other.channelbag(i));
}
}
KeyframeStrip::~KeyframeStrip()
{
for (ChannelBag *channelbag_for_binding : this->channelbags()) {
MEM_delete(channelbag_for_binding);
}
MEM_SAFE_FREE(this->channelbags_array);
this->channelbags_array_num = 0;
}
template<> bool Strip::is<KeyframeStrip>() const
{
return this->type() == Type::Keyframe;
}
template<> KeyframeStrip &Strip::as<KeyframeStrip>()
{
BLI_assert_msg(this->is<KeyframeStrip>(), "Strip is not a KeyframeStrip");
return *reinterpret_cast<KeyframeStrip *>(this);
}
template<> const KeyframeStrip &Strip::as<KeyframeStrip>() const
{
BLI_assert_msg(this->is<KeyframeStrip>(), "Strip is not a KeyframeStrip");
return *reinterpret_cast<const KeyframeStrip *>(this);
}
blender::Span<const ChannelBag *> KeyframeStrip::channelbags() const
{
return blender::Span<ChannelBag *>{reinterpret_cast<ChannelBag **>(this->channelbags_array),
this->channelbags_array_num};
}
blender::MutableSpan<ChannelBag *> KeyframeStrip::channelbags()
{
return blender::MutableSpan<ChannelBag *>{
reinterpret_cast<ChannelBag **>(this->channelbags_array), this->channelbags_array_num};
}
const ChannelBag *KeyframeStrip::channelbag(const int64_t index) const
{
return &this->channelbags_array[index]->wrap();
}
ChannelBag *KeyframeStrip::channelbag(const int64_t index)
{
return &this->channelbags_array[index]->wrap();
}
/* AnimationChannelBag implementation. */
ChannelBag::ChannelBag(const ChannelBag &other)
{
this->binding_handle = other.binding_handle;
this->fcurve_array_num = other.fcurve_array_num;
this->fcurve_array = MEM_cnew_array<FCurve *>(other.fcurve_array_num, __func__);
for (int i = 0; i < other.fcurve_array_num; i++) {
const FCurve *fcu_src = other.fcurve_array[i];
this->fcurve_array[i] = BKE_fcurve_copy(fcu_src);
}
}
ChannelBag::~ChannelBag()
{
for (FCurve *fcu : this->fcurves()) {
BKE_fcurve_free(fcu);
}
MEM_SAFE_FREE(this->fcurve_array);
this->fcurve_array_num = 0;
}
blender::Span<const FCurve *> ChannelBag::fcurves() const
{
return blender::Span<FCurve *>{this->fcurve_array, this->fcurve_array_num};
}
blender::MutableSpan<FCurve *> ChannelBag::fcurves()
{
return blender::MutableSpan<FCurve *>{this->fcurve_array, this->fcurve_array_num};
}
const FCurve *ChannelBag::fcurve(const int64_t index) const
{
return this->fcurve_array[index];
}
FCurve *ChannelBag::fcurve(const int64_t index)
{
return this->fcurve_array[index];
}
} // namespace blender::animrig

View File

@ -43,20 +43,24 @@ class RuntimeAssetLibrary;
class AssetLibraryService {
static std::unique_ptr<AssetLibraryService> instance_;
/** Identify libraries with the library type, and the absolute path of the library's root path
/**
* Identify libraries with the library type, and the absolute path of the library's root path
* (normalize with #normalize_directory_path()!). The type is relevant since the current file
* library may point to the same path as a custom library. */
* library may point to the same path as a custom library.
*/
using OnDiskLibraryIdentifier = std::pair<eAssetLibraryType, std::string>;
/* Mapping of a (type, root path) pair to the AssetLibrary instance. */
/** Mapping of a (type, root path) pair to the AssetLibrary instance. */
Map<OnDiskLibraryIdentifier, std::unique_ptr<OnDiskAssetLibrary>> on_disk_libraries_;
/** Library without a known path, i.e. the "Current File" library if the file isn't saved yet. If
/**
* Library without a known path, i.e. the "Current File" library if the file isn't saved yet. If
* the file was saved, a valid path for the library can be determined and #on_disk_libraries_
* above should be used. */
* above should be used.
*/
std::unique_ptr<RuntimeAssetLibrary> current_file_library_;
/** The "all" asset library, merging all other libraries into one. */
std::unique_ptr<AllAssetLibrary> all_library_;
/* Handlers for managing the life cycle of the AssetLibraryService instance. */
/** Handlers for managing the life cycle of the AssetLibraryService instance. */
bCallbackFuncStore on_load_callback_store_;
static bool atexit_handler_registered_;

View File

@ -45,7 +45,7 @@ bool AssetStorage::remove_asset(AssetRepresentation &asset)
void AssetStorage::remap_ids_and_remove_invalid(const blender::bke::id::IDRemapper &mappings)
{
Set<AssetRepresentation *> removed_assets{};
Set<AssetRepresentation *> removed_assets;
for (auto &asset_ptr : local_id_assets_) {
AssetRepresentation &asset = *asset_ptr;

View File

@ -49,7 +49,7 @@ static blender::Vector<uint8_t> filtered_rows_from_thumb(const Thumbnail *thumb)
/* In the image data sent to the compression step, each scan-line is preceded by a filter type
* byte containing the numeric code of the filter algorithm used for that scan-line. */
const size_t line_size = thumb->width * 4;
blender::Vector<uint8_t> filtered{};
blender::Vector<uint8_t> filtered;
size_t final_size = thumb->height * (line_size + 1);
filtered.reserve(final_size);
for (int i = 0; i < thumb->height; i++) {
@ -88,7 +88,7 @@ std::optional<blender::Vector<uint8_t>> blendthumb_create_png_data_from_thumb(
}
/* Create `IDAT` chunk data. */
blender::Vector<uint8_t> image_data{};
blender::Vector<uint8_t> image_data;
{
auto image_data_opt = zlib_compress(filtered_rows_from_thumb(thumb));
if (image_data_opt == std::nullopt) {
@ -98,7 +98,7 @@ std::optional<blender::Vector<uint8_t>> blendthumb_create_png_data_from_thumb(
}
/* Create the IHDR chunk data. */
blender::Vector<uint8_t> ihdr_data{};
blender::Vector<uint8_t> ihdr_data;
{
const size_t ihdr_data_final_size = 4 + 4 + 5;
ihdr_data.reserve(ihdr_data_final_size);
@ -115,7 +115,7 @@ std::optional<blender::Vector<uint8_t>> blendthumb_create_png_data_from_thumb(
}
/* Join it all together to create a PNG image. */
blender::Vector<uint8_t> png_buf{};
blender::Vector<uint8_t> png_buf;
{
const size_t png_buf_final_size = (
/* Header. */

View File

@ -88,11 +88,11 @@ void BKE_animdata_foreach_id(AnimData *adt, LibraryForeachIDData *data);
/**
* Make a copy of the given AnimData - to be used when copying data-blocks.
*
* \note: Regarding handling of IDs managed by the #AnimData struct, this function follows the
* behaviors of the generic #BKE_id_copy_ex, please see its documetation for more details.
* \note Regarding handling of IDs managed by the #AnimData struct, this function follows the
* behaviors of the generic #BKE_id_copy_ex, please see its documentation for more details.
*
* \param flag: Control ID pointers management, see LIB_ID_CREATE_.../LIB_ID_COPY_... flags in
* #BKE_lib_id.hh
* `BKE_lib_id.hh`.
*
* \return The copied animdata.
*/

View File

@ -0,0 +1,17 @@
/* SPDX-FileCopyrightText: 2024 Blender Authors
*
* SPDX-License-Identifier: GPL-2.0-or-later */
/** \file
* \ingroup bke
*
* This file only contains the memory management functions for the Animation
* data-block. For all other functionality, see `source/blender/animrig`.
*/
#pragma once
struct Animation;
struct Main;
Animation *BKE_animation_add(Main *bmain, const char name[]);

View File

@ -273,6 +273,7 @@ extern IDTypeInfo IDType_ID_CV;
extern IDTypeInfo IDType_ID_PT;
extern IDTypeInfo IDType_ID_VO;
extern IDTypeInfo IDType_ID_GP;
extern IDTypeInfo IDType_ID_AN;
/** Empty shell mostly, but needed for read code. */
extern IDTypeInfo IDType_ID_LINK_PLACEHOLDER;

View File

@ -128,7 +128,7 @@ void BKE_lib_libblock_session_uid_renew(ID *id);
*/
void *BKE_id_new(Main *bmain, short type, const char *name);
/**
* Same as for #BKE_id_new, but allows creating a data-block for (whithin) a given owner library.
* Same as for #BKE_id_new, but allows creating a data-block for (within) a given owner library.
*
* \param owner_library the Library to 'assign' the newly created ID to. Use `nullptr` to make ID
* not use any library (i.e. become a local ID). Use `std::nullopt` for default behavior (i.e.

View File

@ -21,6 +21,7 @@
*/
#include "BLI_compiler_attrs.h"
#include "BLI_function_ref.hh"
#include "BLI_map.hh"
#include "BLI_set.hh"
#include "BLI_span.hh"
@ -265,14 +266,14 @@ using IDTypeFilter = uint64_t;
namespace blender::bke::id {
class IDRemapper {
blender::Map<ID *, ID *> mappings_;
Map<ID *, ID *> mappings_;
IDTypeFilter source_types_ = 0;
/**
* Store all IDs using another ID with the 'NEVER_NULL' flag, which have (or
* should have been) remapped to `nullptr`.
*/
blender::Set<ID *> never_null_users_;
Set<ID *> never_null_users_;
public:
/**
@ -282,14 +283,14 @@ class IDRemapper {
bool allow_idtype_mismatch = false;
public:
void clear(void)
void clear()
{
mappings_.clear();
never_null_users_.clear();
source_types_ = 0;
}
bool is_empty(void) const
bool is_empty() const
{
return mappings_.is_empty();
}
@ -326,24 +327,24 @@ class IDRemapper {
never_null_users_.add(id);
}
const blender::Set<ID *> &never_null_users(void) const
const Set<ID *> &never_null_users() const
{
return never_null_users_;
}
/** Iterate over all remapping pairs in the remapper, and call the callback function on them. */
void iter(IDRemapperIterFunction func, void *user_data) const
void iter(FunctionRef<void(ID *old_id, ID *new_id)> func) const
{
for (auto item : mappings_.items()) {
func(item.key, item.value, user_data);
func(item.key, item.value);
}
}
/** Return a readable string for the given result. Can be used for debugging purposes. */
static const blender::StringRefNull result_to_string(const IDRemapperApplyResult result);
static const StringRefNull result_to_string(const IDRemapperApplyResult result);
/** Print out the rules inside the given id_remapper. Can be used for debugging purposes. */
void print(void) const;
void print() const;
};
} // namespace blender::bke::id

View File

@ -223,6 +223,7 @@ struct Main {
ListBase collections;
ListBase armatures;
ListBase actions;
ListBase animations;
ListBase nodetrees;
ListBase brushes;
ListBase particles;

View File

@ -55,6 +55,7 @@ set(SRC
intern/anim_path.cc
intern/anim_sys.cc
intern/anim_visualization.cc
intern/animation.cc
intern/anonymous_attribute_id.cc
intern/appdir.cc
intern/armature.cc
@ -68,8 +69,8 @@ set(SRC
intern/attribute_access.cc
intern/attribute_math.cc
intern/autoexec.cc
intern/bake_geometry_nodes_modifier.cc
intern/bake_data_block_map.cc
intern/bake_geometry_nodes_modifier.cc
intern/bake_items.cc
intern/bake_items_paths.cc
intern/bake_items_serialize.cc
@ -327,6 +328,7 @@ set(SRC
BKE_anim_data.hh
BKE_anim_path.h
BKE_anim_visualization.h
BKE_animation.hh
BKE_animsys.h
BKE_anonymous_attribute_id.hh
BKE_appdir.hh
@ -336,8 +338,8 @@ set(SRC
BKE_attribute.hh
BKE_attribute_math.hh
BKE_autoexec.hh
BKE_bake_geometry_nodes_modifier.hh
BKE_bake_data_block_map.hh
BKE_bake_geometry_nodes_modifier.hh
BKE_bake_items.hh
BKE_bake_items_paths.hh
BKE_bake_items_serialize.hh

View File

@ -292,6 +292,7 @@ void BKE_animdata_foreach_id(AnimData *adt, LibraryForeachIDData *data)
BKE_LIB_FOREACHID_PROCESS_FUNCTION_CALL(data, BKE_fcurve_foreach_id(fcu, data));
}
BKE_LIB_FOREACHID_PROCESS_IDSUPER(data, adt->animation, IDWALK_CB_USER);
BKE_LIB_FOREACHID_PROCESS_IDSUPER(data, adt->action, IDWALK_CB_USER);
BKE_LIB_FOREACHID_PROCESS_IDSUPER(data, adt->tmpact, IDWALK_CB_USER);

View File

@ -0,0 +1,255 @@
/* SPDX-FileCopyrightText: 2024 Blender Authors
*
* SPDX-License-Identifier: GPL-2.0-or-later */
/** \file Animation data-block.
* \ingroup bke
*/
#include "BLI_map.hh"
#include "BLI_string_utf8.h"
#include "BLO_read_write.hh"
#include "BKE_animation.hh"
#include "BKE_fcurve.hh"
#include "BKE_idtype.hh"
#include "BKE_lib_id.hh"
#include "BKE_lib_query.hh"
#include "BKE_main.hh"
#include "ANIM_animation.hh"
#include "DNA_anim_types.h"
#include "DNA_defaults.h"
#include "BLT_translation.hh"
struct BlendWriter;
struct BlendDataReader;
namespace blender::bke {
static void animation_copy_data(Main * /*bmain*/,
std::optional<Library *> /*owner_library*/,
ID *id_dst,
const ID *id_src,
const int /*flag*/)
{
Animation *dna_anim_dst = reinterpret_cast<Animation *>(id_dst);
animrig::Animation &anim_dst = dna_anim_dst->wrap();
const Animation *dna_anim_src = reinterpret_cast<const Animation *>(id_src);
const animrig::Animation &anim_src = dna_anim_src->wrap();
/* Copy all simple properties. */
anim_dst.layer_array_num = anim_src.layer_array_num;
anim_dst.layer_active_index = anim_src.layer_active_index;
anim_dst.binding_array_num = anim_src.binding_array_num;
anim_dst.last_binding_handle = anim_src.last_binding_handle;
/* Layers. */
anim_dst.layer_array = MEM_cnew_array<AnimationLayer *>(anim_src.layer_array_num, __func__);
for (int i : anim_src.layers().index_range()) {
anim_dst.layer_array[i] = MEM_new<animrig::Layer>(__func__, *anim_src.layer(i));
}
/* Bindings. */
anim_dst.binding_array = MEM_cnew_array<AnimationBinding *>(anim_src.binding_array_num,
__func__);
for (int i : anim_src.bindings().index_range()) {
anim_dst.binding_array[i] = MEM_new<animrig::Binding>(__func__, *anim_src.binding(i));
}
}
/** Free (or release) any data used by this animation (does not free the animation itself). */
static void animation_free_data(ID *id)
{
reinterpret_cast<Animation *>(id)->wrap().free_data();
}
static void animation_foreach_id(ID *id, LibraryForeachIDData *data)
{
animrig::Animation &anim = reinterpret_cast<Animation *>(id)->wrap();
for (animrig::Layer *layer : anim.layers()) {
for (animrig::Strip *strip : layer->strips()) {
switch (strip->type()) {
case animrig::Strip::Type::Keyframe: {
auto &key_strip = strip->as<animrig::KeyframeStrip>();
for (animrig::ChannelBag *channelbag_for_binding : key_strip.channelbags()) {
for (FCurve *fcurve : channelbag_for_binding->fcurves()) {
BKE_LIB_FOREACHID_PROCESS_FUNCTION_CALL(data, BKE_fcurve_foreach_id(fcurve, data));
}
}
}
}
}
}
}
static void write_channelbag(BlendWriter *writer, animrig::ChannelBag &channelbag)
{
BLO_write_struct(writer, AnimationChannelBag, &channelbag);
Span<FCurve *> fcurves = channelbag.fcurves();
BLO_write_pointer_array(writer, fcurves.size(), fcurves.data());
for (FCurve *fcurve : fcurves) {
BLO_write_struct(writer, FCurve, fcurve);
BKE_fcurve_blend_write_data(writer, fcurve);
}
}
static void write_keyframe_strip(BlendWriter *writer, animrig::KeyframeStrip &key_strip)
{
BLO_write_struct(writer, KeyframeAnimationStrip, &key_strip);
auto channelbags = key_strip.channelbags();
BLO_write_pointer_array(writer, channelbags.size(), channelbags.data());
for (animrig::ChannelBag *channelbag : channelbags) {
write_channelbag(writer, *channelbag);
}
}
static void write_strips(BlendWriter *writer, Span<animrig::Strip *> strips)
{
BLO_write_pointer_array(writer, strips.size(), strips.data());
for (animrig::Strip *strip : strips) {
switch (strip->type()) {
case animrig::Strip::Type::Keyframe: {
auto &key_strip = strip->as<animrig::KeyframeStrip>();
write_keyframe_strip(writer, key_strip);
}
}
}
}
static void write_layers(BlendWriter *writer, Span<animrig::Layer *> layers)
{
BLO_write_pointer_array(writer, layers.size(), layers.data());
for (animrig::Layer *layer : layers) {
BLO_write_struct(writer, AnimationLayer, layer);
write_strips(writer, layer->strips());
}
}
static void write_bindings(BlendWriter *writer, Span<animrig::Binding *> bindings)
{
BLO_write_pointer_array(writer, bindings.size(), bindings.data());
for (animrig::Binding *binding : bindings) {
BLO_write_struct(writer, AnimationBinding, binding);
}
}
static void animation_blend_write(BlendWriter *writer, ID *id, const void *id_address)
{
animrig::Animation &anim = reinterpret_cast<Animation *>(id)->wrap();
BLO_write_id_struct(writer, Animation, id_address, &anim.id);
BKE_id_blend_write(writer, &anim.id);
write_layers(writer, anim.layers());
write_bindings(writer, anim.bindings());
}
static void read_channelbag(BlendDataReader *reader, animrig::ChannelBag &channelbag)
{
BLO_read_pointer_array(reader, reinterpret_cast<void **>(&channelbag.fcurve_array));
for (int i = 0; i < channelbag.fcurve_array_num; i++) {
BLO_read_data_address(reader, &channelbag.fcurve_array[i]);
BKE_fcurve_blend_read_data(reader, channelbag.fcurve_array[i]);
}
}
static void read_keyframe_strip(BlendDataReader *reader, animrig::KeyframeStrip &strip)
{
BLO_read_pointer_array(reader, reinterpret_cast<void **>(&strip.channelbags_array));
for (int i = 0; i < strip.channelbags_array_num; i++) {
BLO_read_data_address(reader, &strip.channelbags_array[i]);
AnimationChannelBag *channelbag = strip.channelbags_array[i];
read_channelbag(reader, channelbag->wrap());
}
}
static void read_animation_layers(BlendDataReader *reader, animrig::Animation &anim)
{
BLO_read_pointer_array(reader, reinterpret_cast<void **>(&anim.layer_array));
for (int layer_idx = 0; layer_idx < anim.layer_array_num; layer_idx++) {
BLO_read_data_address(reader, &anim.layer_array[layer_idx]);
AnimationLayer *layer = anim.layer_array[layer_idx];
BLO_read_pointer_array(reader, reinterpret_cast<void **>(&layer->strip_array));
for (int strip_idx = 0; strip_idx < layer->strip_array_num; strip_idx++) {
BLO_read_data_address(reader, &layer->strip_array[strip_idx]);
AnimationStrip *dna_strip = layer->strip_array[strip_idx];
animrig::Strip &strip = dna_strip->wrap();
switch (strip.type()) {
case animrig::Strip::Type::Keyframe: {
read_keyframe_strip(reader, strip.as<animrig::KeyframeStrip>());
}
}
}
}
}
static void read_animation_bindings(BlendDataReader *reader, animrig::Animation &anim)
{
BLO_read_pointer_array(reader, reinterpret_cast<void **>(&anim.binding_array));
for (int i = 0; i < anim.binding_array_num; i++) {
BLO_read_data_address(reader, &anim.binding_array[i]);
}
}
static void animation_blend_read_data(BlendDataReader *reader, ID *id)
{
animrig::Animation &animation = reinterpret_cast<Animation *>(id)->wrap();
read_animation_layers(reader, animation);
read_animation_bindings(reader, animation);
}
} // namespace blender::bke
IDTypeInfo IDType_ID_AN = {
/*id_code*/ ID_AN,
/*id_filter*/ FILTER_ID_AN,
/*dependencies_id_types*/ 0,
/*main_listbase_index*/ INDEX_ID_AN,
/*struct_size*/ sizeof(Animation),
/*name*/ "Animation",
/*name_plural*/ N_("animations"),
/*translation_context*/ BLT_I18NCONTEXT_ID_ANIMATION,
/*flags*/ IDTYPE_FLAGS_NO_ANIMDATA,
/*asset_type_info*/ nullptr,
/*init_data*/ nullptr,
/*copy_data*/ blender::bke::animation_copy_data,
/*free_data*/ blender::bke::animation_free_data,
/*make_local*/ nullptr,
/*foreach_id*/ blender::bke::animation_foreach_id,
/*foreach_cache*/ nullptr,
/*foreach_path*/ nullptr,
/*owner_pointer_get*/ nullptr,
/*blend_write*/ blender::bke::animation_blend_write,
/*blend_read_data*/ blender::bke::animation_blend_read_data,
/*blend_read_after_liblink*/ nullptr,
/*blend_read_undo_preserve*/ nullptr,
/*lib_override_apply_post*/ nullptr,
};
Animation *BKE_animation_add(Main *bmain, const char name[])
{
Animation *anim = static_cast<Animation *>(BKE_id_new(bmain, ID_AN, name));
return anim;
}

View File

@ -474,7 +474,7 @@ static void build_mesh_positions(const CurvesInfo &curves_info,
}
const Span<float3> tangents = curves_info.main.evaluated_tangents();
const Span<float3> normals = curves_info.main.evaluated_normals();
Span<float> radii_eval = {};
Span<float> radii_eval;
if (const GVArray radii = *curves_info.main.attributes().lookup("radius", AttrDomain::Point)) {
radii_eval = evaluate_attribute(radii, curves_info.main, eval_buffer).typed<float>();
}

View File

@ -83,6 +83,7 @@ static void id_type_init()
INIT_TYPE(ID_GR);
INIT_TYPE(ID_AR);
INIT_TYPE(ID_AC);
INIT_TYPE(ID_AN);
INIT_TYPE(ID_NT);
INIT_TYPE(ID_BR);
INIT_TYPE(ID_PA);
@ -225,6 +226,7 @@ int BKE_idtype_idcode_to_index(const short idcode)
switch ((ID_Type)idcode) {
CASE_IDINDEX(AC);
CASE_IDINDEX(AN);
CASE_IDINDEX(AR);
CASE_IDINDEX(BR);
CASE_IDINDEX(CA);
@ -284,6 +286,7 @@ int BKE_idtype_idfilter_to_index(const uint64_t id_filter)
switch (id_filter) {
CASE_IDINDEX(AC);
CASE_IDINDEX(AN);
CASE_IDINDEX(AR);
CASE_IDINDEX(BR);
CASE_IDINDEX(CA);

View File

@ -65,7 +65,8 @@ IDRemapperApplyResult IDRemapper::apply(ID **r_id_ptr,
return ID_REMAP_RESULT_SOURCE_NOT_MAPPABLE;
}
if (!mappings_.contains(*r_id_ptr)) {
ID *const *new_id = mappings_.lookup_ptr(*r_id_ptr);
if (new_id == nullptr) {
return ID_REMAP_RESULT_SOURCE_UNAVAILABLE;
}
@ -73,7 +74,7 @@ IDRemapperApplyResult IDRemapper::apply(ID **r_id_ptr,
id_us_min(*r_id_ptr);
}
*r_id_ptr = mappings_.lookup(*r_id_ptr);
*r_id_ptr = *new_id;
if (options & ID_REMAP_APPLY_UNMAP_WHEN_REMAPPING_TO_SELF && *r_id_ptr == id_self) {
*r_id_ptr = nullptr;
}
@ -92,7 +93,7 @@ IDRemapperApplyResult IDRemapper::apply(ID **r_id_ptr,
return ID_REMAP_RESULT_SOURCE_REMAPPED;
}
const blender::StringRefNull IDRemapper::result_to_string(const IDRemapperApplyResult result)
const StringRefNull IDRemapper::result_to_string(const IDRemapperApplyResult result)
{
switch (result) {
case ID_REMAP_RESULT_SOURCE_NOT_MAPPABLE:
@ -108,17 +109,16 @@ const blender::StringRefNull IDRemapper::result_to_string(const IDRemapperApplyR
return "";
}
void IDRemapper::print(void) const
void IDRemapper::print() const
{
auto print_cb = [](ID *old_id, ID *new_id, void * /*user_data*/) {
this->iter([](ID *old_id, ID *new_id) {
if (old_id != nullptr && new_id != nullptr) {
printf("Remap %s(%p) to %s(%p)\n", old_id->name, old_id, new_id->name, new_id);
}
if (old_id != nullptr && new_id == nullptr) {
printf("Unassign %s(%p)\n", old_id->name, old_id);
}
};
this->iter(print_cb, nullptr);
});
}
} // namespace blender::bke::id

View File

@ -616,7 +616,7 @@ struct UnusedIDsData {
std::array<int, INDEX_ID_MAX> *num_local;
std::array<int, INDEX_ID_MAX> *num_linked;
blender::Set<ID *> unused_ids{};
blender::Set<ID *> unused_ids;
UnusedIDsData(Main *bmain, const int id_tag, LibQueryUnusedIDsData &parameters)
: bmain(bmain),

View File

@ -216,7 +216,7 @@ static int foreach_libblock_remap_callback(LibraryIDLinkCallbackData *cb_data)
const IDRemapperApplyResult expected_mapping_result = id_remapper.get_mapping_result(
*id_p, id_remapper_options, id_self);
/* Exit, when no modifications will be done; ensuring id->runtime counters won't changed. */
/* Exit when no modifications will be done, ensuring id->runtime counters won't changed. */
if (ELEM(expected_mapping_result,
ID_REMAP_RESULT_SOURCE_UNAVAILABLE,
ID_REMAP_RESULT_SOURCE_NOT_MAPPABLE))
@ -429,9 +429,8 @@ static void libblock_remap_data_postprocess_nodetree_update(Main *bmain, ID *new
ntreeUpdateAllUsers(bmain, new_id);
}
static void libblock_remap_data_update_tags(ID *old_id, ID *new_id, void *user_data)
static void libblock_remap_data_update_tags(ID *old_id, ID *new_id, IDRemap *id_remap_data)
{
IDRemap *id_remap_data = static_cast<IDRemap *>(user_data);
const int remap_flags = id_remap_data->flag;
if ((remap_flags & ID_REMAP_SKIP_USER_CLEAR) == 0) {
/* XXX We may not want to always 'transfer' fake-user from old to new id...
@ -454,9 +453,7 @@ static void libblock_remap_data_update_tags(ID *old_id, ID *new_id, void *user_d
}
}
static void libblock_remap_reset_remapping_status_callback(ID *old_id,
ID *new_id,
void * /*user_data*/)
static void libblock_remap_reset_remapping_status_fn(ID *old_id, ID *new_id)
{
BKE_libblock_runtime_reset_remapping_status(old_id);
if (new_id != nullptr) {
@ -511,7 +508,7 @@ static void libblock_remap_data(
IDWALK_DO_LIBRARY_POINTER :
IDWALK_NOP));
id_remapper.iter(libblock_remap_reset_remapping_status_callback, nullptr);
id_remapper.iter(libblock_remap_reset_remapping_status_fn);
if (id) {
#ifdef DEBUG_PRINT
@ -550,24 +547,17 @@ static void libblock_remap_data(
FOREACH_MAIN_ID_END;
}
id_remapper.iter(libblock_remap_data_update_tags, &id_remap_data);
id_remapper.iter([&](ID *old_id, ID *new_id) {
libblock_remap_data_update_tags(old_id, new_id, &id_remap_data);
});
}
struct LibBlockRemapMultipleUserData {
Main *bmain;
int remap_flags;
};
static void libblock_remap_foreach_idpair_cb(ID *old_id, ID *new_id, void *user_data)
static void libblock_remap_foreach_idpair(ID *old_id, ID *new_id, Main *bmain, int remap_flags)
{
if (old_id == new_id) {
return;
}
LibBlockRemapMultipleUserData *data = static_cast<LibBlockRemapMultipleUserData *>(user_data);
Main *bmain = data->bmain;
const int remap_flags = data->remap_flags;
BLI_assert(old_id != nullptr);
BLI_assert((new_id == nullptr) || remap_flags & ID_REMAP_ALLOW_IDTYPE_MISMATCH ||
GS(old_id->name) == GS(new_id->name));
@ -661,11 +651,9 @@ void BKE_libblock_remap_multiple_locked(Main *bmain, IDRemapper &mappings, const
libblock_remap_data(bmain, nullptr, ID_REMAP_TYPE_REMAP, mappings, remap_flags);
LibBlockRemapMultipleUserData user_data = {nullptr};
user_data.bmain = bmain;
user_data.remap_flags = remap_flags;
mappings.iter(libblock_remap_foreach_idpair_cb, &user_data);
mappings.iter([&](ID *old_id, ID *new_id) {
libblock_remap_foreach_idpair(old_id, new_id, bmain, remap_flags);
});
/* We assume editors do not hold references to their IDs... This is false in some cases
* (Image is especially tricky here),
@ -738,17 +726,11 @@ void BKE_libblock_unlink(Main *bmain, void *idv, const bool do_skip_indirect)
* ... sigh
*/
struct LibBlockRelinkMultipleUserData {
Main *bmain;
blender::Span<ID *> ids;
};
static void libblock_relink_foreach_idpair_cb(ID *old_id, ID *new_id, void *user_data)
static void libblock_relink_foreach_idpair(ID *old_id,
ID *new_id,
Main *bmain,
const blender::Span<ID *> ids)
{
LibBlockRelinkMultipleUserData *data = static_cast<LibBlockRelinkMultipleUserData *>(user_data);
Main *bmain = data->bmain;
const blender::Span<ID *> ids = data->ids;
BLI_assert(old_id != nullptr);
BLI_assert((new_id == nullptr) || GS(old_id->name) == GS(new_id->name));
BLI_assert(old_id != new_id);
@ -815,9 +797,9 @@ void BKE_libblock_relink_multiple(Main *bmain,
switch (remap_type) {
case ID_REMAP_TYPE_REMAP: {
LibBlockRelinkMultipleUserData user_data = {bmain, ids};
id_remapper.iter(libblock_relink_foreach_idpair_cb, &user_data);
id_remapper.iter([&](ID *old_id, ID *new_id) {
libblock_relink_foreach_idpair(old_id, new_id, bmain, ids);
});
break;
}
case ID_REMAP_TYPE_CLEANUP: {

View File

@ -860,6 +860,8 @@ ListBase *which_libbase(Main *bmain, short type)
return &(bmain->armatures);
case ID_AC:
return &(bmain->actions);
case ID_AN:
return &(bmain->animations);
case ID_NT:
return &(bmain->nodetrees);
case ID_BR:
@ -905,6 +907,7 @@ int set_listbasepointers(Main *bmain, ListBase *lb[/*INDEX_ID_MAX*/])
/* Moved here to avoid problems when freeing with animato (aligorith). */
lb[INDEX_ID_AC] = &(bmain->actions);
lb[INDEX_ID_AN] = &(bmain->animations);
lb[INDEX_ID_KE] = &(bmain->shapekeys);

View File

@ -1256,7 +1256,7 @@ void BKE_object_material_array_assign(
/* now we have the right number of slots */
for (int i = 0; i < totcol; i++) {
if (to_object_only && ob->matbits[i] == 0) {
if (to_object_only && ob->matbits && ob->matbits[i] == 0) {
/* If we only assign to object, and that slot uses obdata material, do nothing. */
continue;
}

View File

@ -521,8 +521,8 @@ if(WITH_GTESTS)
tests/BLI_kdopbvh_test.cc
tests/BLI_kdtree_test.cc
tests/BLI_length_parameterize_test.cc
tests/BLI_linear_allocator_test.cc
tests/BLI_linear_allocator_chunked_list_test.cc
tests/BLI_linear_allocator_test.cc
tests/BLI_linklist_lockfree_test.cc
tests/BLI_listbase_test.cc
tests/BLI_map_test.cc

View File

@ -298,7 +298,7 @@ BLI_INLINE void bilinear_fl_impl(const float *buffer,
x2 = 0;
}
}
else if (x2 < 0 || x1 >= width) {
else if (border && (x2 < 0 || x1 >= width)) {
copy_vn_fl(output, components, 0.0f);
return;
}
@ -307,7 +307,7 @@ BLI_INLINE void bilinear_fl_impl(const float *buffer,
y2 = 0;
}
}
else if (y2 < 0 || y1 >= height) {
else if (border && (y2 < 0 || y1 >= height)) {
copy_vn_fl(output, components, 0.0f);
return;
}

View File

@ -86,6 +86,7 @@ const char *BLT_translate_do_new_dataname(const char *msgctxt, const char *msgid
/* ID-types contexts. */
/* WARNING! Keep it in sync with ID-types in `blenkernel/intern/idtype.cc`. */
#define BLT_I18NCONTEXT_ID_ACTION "Action"
#define BLT_I18NCONTEXT_ID_ANIMATION "Animation"
#define BLT_I18NCONTEXT_ID_ARMATURE "Armature"
#define BLT_I18NCONTEXT_ID_BRUSH "Brush"
#define BLT_I18NCONTEXT_ID_CACHEFILE "CacheFile"

View File

@ -12,6 +12,7 @@
#include "BLI_math_base.hh"
#include "BLI_math_interp.hh"
#include "BLI_math_vector.h"
#include "BLI_math_vector_types.hh"
#include "BLI_rect.h"
#include <cstring>
@ -201,6 +202,20 @@ class MemoryBuffer {
read_elem_checked(floor_x(x), floor_y(y), out);
}
/* Equivalent to the GLSL texture() function with bilinear interpolation and extended boundary
* conditions. The coordinates are thus expected to have half-pixels offsets. For float buffers,
* the green and green channels will be zero and the alpha will be one. */
float4 texture_bilinear_extend(float2 coordinates) const
{
const int2 size = int2(get_width(), get_height());
const float2 texel_coordinates = (coordinates * float2(size)) - 0.5f;
float4 result = float4(0.0f, 0.0f, 0.0f, 1.0f);
math::interpolate_bilinear_fl(
buffer_, result, size.x, size.y, num_channels_, texel_coordinates.x, texel_coordinates.y);
return result;
}
void read_elem_bilinear(float x, float y, float *out) const
{
/* Only clear past +/-1 borders to be able to smooth edges. */

View File

@ -16,7 +16,7 @@
#include "GPU_capabilities.h"
#include "GPU_shader.h"
#include "GPU_texture.h"
#include "GPU_uniform_buffer.h"
#include "GPU_uniform_buffer.hh"
#include "gpu_shader_create_info.hh"

View File

@ -17,7 +17,7 @@
#include "GPU_material.hh"
#include "GPU_shader.h"
#include "GPU_texture.h"
#include "GPU_uniform_buffer.h"
#include "GPU_uniform_buffer.hh"
#include "gpu_shader_create_info.hh"

View File

@ -557,6 +557,10 @@ void DepsgraphNodeBuilder::build_id(ID *id, const bool force_be_visible)
case ID_AC:
build_action((bAction *)id);
break;
case ID_AN:
/* TODO: actually handle this ID type properly, will be done in a followup commit. */
build_generic_id(id);
break;
case ID_AR:
build_armature((bArmature *)id);
break;

View File

@ -525,6 +525,10 @@ void DepsgraphRelationBuilder::build_id(ID *id)
case ID_AC:
build_action((bAction *)id);
break;
case ID_AN:
/* TODO: actually handle this ID type properly, will be done in a followup commit. */
build_generic_id(id);
break;
case ID_AR:
build_armature((bArmature *)id);
break;

View File

@ -25,7 +25,7 @@
#include "GPU_capabilities.h"
#include "GPU_material.hh"
#include "GPU_texture.h"
#include "GPU_uniform_buffer.h"
#include "GPU_uniform_buffer.hh"
#include "DEG_depsgraph_query.hh"

View File

@ -24,7 +24,7 @@
#include "GPU_platform.h"
#include "GPU_texture.h"
#include "GPU_uniform_buffer.h"
#include "GPU_uniform_buffer.hh"
#include "eevee_camera.hh"
#include "eevee_instance.hh"

View File

@ -395,8 +395,10 @@ class ShadowPunctual : public NonCopyable, NonMovable {
int tilemaps_needed_;
/** Scaling factor to the light shape for shadow ray casting. */
float softness_factor_;
/** radius * softness_factor (Bypasses LightModule radius modifications to avoid unnecesary
* padding in the shadow projection). */
/**
* `radius * softness_factor` (Bypasses LightModule radius modifications
* to avoid unnecessary padding in the shadow projection).
*/
float shadow_radius_;
public:

View File

@ -69,7 +69,7 @@ ShadowSampleParams debug_shadow_sample_get(vec3 P, LightData light)
return shadow_directional_sample_params_get(shadow_tilemaps_tx, light, P);
}
else {
return shadow_punctual_sample_params_get(shadow_tilemaps_tx, light, P);
return shadow_punctual_sample_params_get(light, P);
}
}

View File

@ -152,9 +152,7 @@ vec3 shadow_punctual_reconstruct_position(ShadowSampleParams params,
return mat3(light.object_mat) * lP + light._position;
}
ShadowSampleParams shadow_punctual_sample_params_get(usampler2D tilemaps_tx,
LightData light,
vec3 P)
ShadowSampleParams shadow_punctual_sample_params_get(LightData light, vec3 P)
{
vec3 lP = (P - light._position) * mat3(light.object_mat);
@ -179,7 +177,7 @@ ShadowEvalResult shadow_punctual_sample_get(SHADOW_ATLAS_TYPE atlas_tx,
LightData light,
vec3 P)
{
ShadowSampleParams params = shadow_punctual_sample_params_get(tilemaps_tx, light, P);
ShadowSampleParams params = shadow_punctual_sample_params_get(light, P);
float depth = shadow_read_depth(atlas_tx, tilemaps_tx, params);

View File

@ -429,7 +429,7 @@ vec3 shadow_pcf_offset(LightData light, const bool is_directional, vec3 P, vec3
params = shadow_directional_sample_params_get(shadow_tilemaps_tx, light, P);
}
else {
params = shadow_punctual_sample_params_get(shadow_tilemaps_tx, light, P);
params = shadow_punctual_sample_params_get(light, P);
}
ShadowTileData tile = shadow_tile_data_get(shadow_tilemaps_tx, params);
if (!tile.is_allocated) {

View File

@ -16,7 +16,7 @@
#include "BLI_math_color.h"
#include "BLI_memblock.h"
#include "GPU_uniform_buffer.h"
#include "GPU_uniform_buffer.hh"
#include "IMB_imbuf_types.hh"

View File

@ -29,7 +29,7 @@
#include "DNA_view3d_types.h"
#include "GPU_texture.h"
#include "GPU_uniform_buffer.h"
#include "GPU_uniform_buffer.hh"
#include "gpencil_engine.h"

View File

@ -158,7 +158,7 @@ struct SceneState {
bool xray_mode = false;
DRWState cull_state = DRW_STATE_NO_DRAW;
Vector<float4> clip_planes = {};
Vector<float4> clip_planes;
float4 background_color = float4(0);
@ -293,7 +293,7 @@ class MeshPass : public PassMain {
private:
using TextureSubPassKey = std::pair<GPUTexture *, eGeometryType>;
Map<TextureSubPassKey, PassMain::Sub *> texture_subpass_map_ = {};
Map<TextureSubPassKey, PassMain::Sub *> texture_subpass_map_;
PassMain::Sub *passes_[geometry_type_len][shader_type_len] = {{nullptr}};

View File

@ -21,7 +21,7 @@ static bool get_matcap_tx(Texture &matcap_tx, StudioLight &studio_light)
if (matcap_diffuse && matcap_diffuse->float_buffer.data) {
int layers = 1;
float *buffer = matcap_diffuse->float_buffer.data;
Vector<float> combined_buffer = {};
Vector<float> combined_buffer;
if (matcap_specular && matcap_specular->float_buffer.data) {
int size = matcap_diffuse->x * matcap_diffuse->y * 4;

View File

@ -96,8 +96,8 @@ void ShadowPass::ShadowView::setup(View &view, float3 light_direction, bool forc
float4 frustum_planes[6];
DRW_culling_frustum_planes_get(nullptr, (float(*)[4])frustum_planes);
Vector<float4> faces_result = {};
Vector<float3> corners_result = {};
Vector<float4> faces_result;
Vector<float3> corners_result;
/* "Unlit" frustum faces are left "as-is" */

View File

@ -75,7 +75,7 @@
#include "GPU_framebuffer.h"
#include "GPU_storage_buffer.h"
#include "GPU_texture.h"
#include "GPU_uniform_buffer.h"
#include "GPU_uniform_buffer.hh"
namespace blender::draw {

View File

@ -35,7 +35,7 @@
#include "GPU_shader.h"
#include "GPU_storage_buffer.h"
#include "GPU_texture.h"
#include "GPU_uniform_buffer.h"
#include "GPU_uniform_buffer.hh"
#include "draw_cache.hh"
#include "draw_common.h"

View File

@ -24,7 +24,7 @@
#include "GPU_drawlist.h"
#include "GPU_framebuffer.h"
#include "GPU_shader.h"
#include "GPU_uniform_buffer.h"
#include "GPU_uniform_buffer.hh"
#include "GPU_viewport.h"
#include "draw_instance_data.h"

View File

@ -62,7 +62,7 @@
#include "GPU_platform.h"
#include "GPU_shader_shared.h"
#include "GPU_state.h"
#include "GPU_uniform_buffer.h"
#include "GPU_uniform_buffer.hh"
#include "GPU_viewport.h"
#include "RE_engine.h"

View File

@ -46,7 +46,7 @@
#include "GPU_capabilities.h"
#include "GPU_material.hh"
#include "GPU_uniform_buffer.h"
#include "GPU_uniform_buffer.hh"
#include "intern/gpu_codegen.h"

View File

@ -26,7 +26,6 @@ set(SRC
intern/asset_handle.cc
intern/asset_import.cc
intern/asset_indexer.cc
intern/asset_library_reference.cc
intern/asset_library_reference_enum.cc
intern/asset_list.cc
intern/asset_mark_clear.cc

View File

@ -1,38 +0,0 @@
/* SPDX-FileCopyrightText: 2023 Blender Authors
*
* SPDX-License-Identifier: GPL-2.0-or-later */
/** \file
* \ingroup edasset
*/
#include "BLI_hash.hh"
#include "asset_library_reference.hh"
namespace blender::ed::asset {
AssetLibraryReferenceWrapper::AssetLibraryReferenceWrapper(const AssetLibraryReference &reference)
: AssetLibraryReference(reference)
{
}
bool operator==(const AssetLibraryReferenceWrapper &a, const AssetLibraryReferenceWrapper &b)
{
return (a.type == b.type) &&
((a.type == ASSET_LIBRARY_CUSTOM) ? (a.custom_library_index == b.custom_library_index) :
true);
}
uint64_t AssetLibraryReferenceWrapper::hash() const
{
uint64_t hash1 = DefaultHash<decltype(type)>{}(type);
if (type != ASSET_LIBRARY_CUSTOM) {
return hash1;
}
uint64_t hash2 = DefaultHash<decltype(custom_library_index)>{}(custom_library_index);
return hash1 ^ (hash2 * 33); /* Copied from DefaultHash for std::pair. */
}
} // namespace blender::ed::asset

View File

@ -10,25 +10,24 @@
#pragma once
#include <cstdint>
#include "BLI_hash.hh"
#include "DNA_asset_types.h"
namespace blender::ed::asset {
inline bool operator==(const AssetLibraryReference &a, const AssetLibraryReference &b)
{
return (a.type == b.type) &&
((a.type == ASSET_LIBRARY_CUSTOM) ? (a.custom_library_index == b.custom_library_index) :
true);
}
/**
* Wrapper to add logic to the AssetLibraryReference DNA struct.
*/
class AssetLibraryReferenceWrapper : public AssetLibraryReference {
public:
/* Intentionally not `explicit`, allow implicit conversion for convenience. Might have to be
* NOLINT */
AssetLibraryReferenceWrapper(const AssetLibraryReference &reference);
~AssetLibraryReferenceWrapper() = default;
namespace blender {
friend bool operator==(const AssetLibraryReferenceWrapper &a,
const AssetLibraryReferenceWrapper &b);
uint64_t hash() const;
template<> struct DefaultHash<AssetLibraryReference> {
uint64_t operator()(const AssetLibraryReference &value) const
{
return get_default_hash(value.type, value.custom_library_index);
}
};
} // namespace blender::ed::asset
} // namespace blender

View File

@ -81,7 +81,7 @@ class PreviewTimer {
wmTimer *timer_ = nullptr;
public:
void ensureRunning(const bContext *C)
void ensure_running(const bContext *C)
{
if (!timer_) {
timer_ = WM_event_timer_add_notifier(
@ -113,20 +113,20 @@ class AssetList : NonCopyable {
void setup();
void fetch(const bContext &C);
void ensurePreviewsJob(const bContext *C);
void ensure_previews_job(const bContext *C);
void clear(const bContext *C);
AssetHandle asset_get_by_index(int index) const;
bool needsRefetch() const;
bool isLoaded() const;
bool isAssetPreviewLoading(const AssetHandle &asset) const;
bool needs_refetch() const;
bool is_loaded() const;
bool is_asset_preview_loading(const AssetHandle &asset) const;
asset_system::AssetLibrary *asset_library() const;
void iterate(AssetListHandleIterFn fn) const;
void iterate(AssetListIterFn fn) const;
int size() const;
void tagMainDataDirty() const;
void remapID(ID *id_old, ID *id_new) const;
void tag_main_data_dirty() const;
void remap_id(ID *id_old, ID *id_new) const;
};
AssetList::AssetList(eFileSelectType filesel_type, const AssetLibraryReference &asset_library_ref)
@ -183,17 +183,17 @@ void AssetList::fetch(const bContext &C)
filelist_filter(files);
}
bool AssetList::needsRefetch() const
bool AssetList::needs_refetch() const
{
return filelist_needs_force_reset(filelist_) || filelist_needs_reading(filelist_);
}
bool AssetList::isLoaded() const
bool AssetList::is_loaded() const
{
return filelist_is_ready(filelist_);
}
bool AssetList::isAssetPreviewLoading(const AssetHandle &asset) const
bool AssetList::is_asset_preview_loading(const AssetHandle &asset) const
{
return filelist_file_is_preview_pending(filelist_, asset.file_data);
}
@ -224,13 +224,13 @@ void AssetList::iterate(AssetListHandleIterFn fn) const
void AssetList::iterate(AssetListIterFn fn) const
{
iterate([&fn](AssetHandle handle) {
this->iterate([&fn](AssetHandle handle) {
auto &asset = reinterpret_cast<asset_system::AssetRepresentation &>(*handle.file_data->asset);
return fn(asset);
});
}
void AssetList::ensurePreviewsJob(const bContext *C)
void AssetList::ensure_previews_job(const bContext *C)
{
FileList *files = filelist_;
int numfiles = filelist_files_ensure(files);
@ -246,7 +246,7 @@ void AssetList::ensurePreviewsJob(const bContext *C)
const bool previews_running = filelist_cache_previews_running(files) &&
!filelist_cache_previews_done(files);
if (previews_running) {
previews_timer_.ensureRunning(C);
previews_timer_.ensure_running(C);
}
else {
/* Preview is not running, no need to keep generating update events! */
@ -306,19 +306,19 @@ int AssetList::size() const
return filelist_files_ensure(filelist_);
}
void AssetList::tagMainDataDirty() const
void AssetList::tag_main_data_dirty() const
{
if (filelist_needs_reset_on_main_changes(filelist_)) {
filelist_tag_force_reset_mainfiles(filelist_);
}
}
void AssetList::remapID(ID * /*id_old*/, ID * /*id_new*/) const
void AssetList::remap_id(ID * /*id_old*/, ID * /*id_new*/) const
{
/* Trigger full re-fetch of the file list if main data was changed, don't even attempt remap
* pointers. We could give file list types a id-remap callback, but it's probably not worth it.
* Refreshing local file lists is relatively cheap. */
tagMainDataDirty();
this->tag_main_data_dirty();
}
/** \} */
@ -331,7 +331,7 @@ void AssetList::remapID(ID * /*id_old*/, ID * /*id_new*/) const
* Class managing a global asset list map, each entry being a list for a specific asset library.
*/
class AssetListStorage {
using AssetListMap = Map<AssetLibraryReferenceWrapper, AssetList>;
using AssetListMap = Map<AssetLibraryReference, AssetList>;
public:
/* Purely static class, can't instantiate this. */
@ -340,8 +340,8 @@ class AssetListStorage {
static void fetch_library(const AssetLibraryReference &library_reference, const bContext &C);
static void destruct();
static AssetList *lookup_list(const AssetLibraryReference &library_ref);
static void tagMainDataDirty();
static void remapID(ID *id_new, ID *id_old);
static void tag_main_data_dirty();
static void remap_id(ID *id_new, ID *id_old);
private:
static std::optional<eFileSelectType> asset_library_reference_to_fileselect_type(
@ -363,7 +363,7 @@ void AssetListStorage::fetch_library(const AssetLibraryReference &library_refere
}
auto [list, is_new] = ensure_list_storage(library_reference, *filesel_type);
if (is_new || list.needsRefetch()) {
if (is_new || list.needs_refetch()) {
list.setup();
list.fetch(C);
}
@ -379,17 +379,17 @@ AssetList *AssetListStorage::lookup_list(const AssetLibraryReference &library_re
return global_storage().lookup_ptr(library_ref);
}
void AssetListStorage::tagMainDataDirty()
void AssetListStorage::tag_main_data_dirty()
{
for (AssetList &list : global_storage().values()) {
list.tagMainDataDirty();
list.tag_main_data_dirty();
}
}
void AssetListStorage::remapID(ID *id_new, ID *id_old)
void AssetListStorage::remap_id(ID *id_new, ID *id_old)
{
for (AssetList &list : global_storage().values()) {
list.remapID(id_new, id_old);
list.remap_id(id_new, id_old);
}
}
@ -461,10 +461,10 @@ bool is_loaded(const AssetLibraryReference *library_reference)
if (!list) {
return false;
}
if (list->needsRefetch()) {
if (list->needs_refetch()) {
return false;
}
return list->isLoaded();
return list->is_loaded();
}
void ensure_previews_job(const AssetLibraryReference *library_reference, const bContext *C)
@ -472,7 +472,7 @@ void ensure_previews_job(const AssetLibraryReference *library_reference, const b
AssetList *list = AssetListStorage::lookup_list(*library_reference);
if (list) {
list->ensurePreviewsJob(C);
list->ensure_previews_job(C);
}
}
@ -533,7 +533,7 @@ bool asset_image_is_loading(const AssetLibraryReference *library_reference,
const AssetHandle *asset_handle)
{
const AssetList *list = AssetListStorage::lookup_list(*library_reference);
return list->isAssetPreviewLoading(*asset_handle);
return list->is_asset_preview_loading(*asset_handle);
}
ImBuf *asset_image_get(const AssetHandle *asset_handle)
@ -562,12 +562,12 @@ int size(const AssetLibraryReference *library_reference)
void storage_tag_main_data_dirty()
{
AssetListStorage::tagMainDataDirty();
AssetListStorage::tag_main_data_dirty();
}
void storage_id_remap(ID *id_old, ID *id_new)
{
AssetListStorage::remapID(id_old, id_new);
AssetListStorage::remap_id(id_old, id_new);
}
void storage_exit()

View File

@ -35,7 +35,7 @@
#include "GPU_matrix.h"
#include "GPU_shader_shared.h"
#include "GPU_state.h"
#include "GPU_uniform_buffer.h"
#include "GPU_uniform_buffer.hh"
#include "ED_gpencil_legacy.hh"

View File

@ -188,6 +188,8 @@ enum eV3DDepthOverrideMode {
};
/**
* Redraw the viewport depth buffer.
* Call #view3d_has_depth_buffer_being_used if you want to check if the viewport already has depth
* buffer updated.
*/
void ED_view3d_depth_override(Depsgraph *depsgraph,
ARegion *region,
@ -209,6 +211,8 @@ bool ED_view3d_depth_unproject_v3(const ARegion *region,
double depth,
float r_location_world[3]);
bool ED_view3d_has_depth_buffer_being_used(const Depsgraph *depsgraph, const View3D *v3d);
/**
* Utilities to perform navigation.
* Call `ED_view3d_navigation_init` to create a context and `ED_view3d_navigation_do` to perform
@ -850,18 +854,16 @@ void ED_view3d_autodist_last_clear(wmWindow *win);
/**
* Get the world-space 3d location from a screen-space 2d point.
* TODO: Implement #alphaoverride. We don't want to zoom into billboards.
* It may be useful to call #ED_view3d_depth_override before.
*
* \param mval: Input screen-space pixel location.
* \param mouse_worldloc: Output world-space location.
* \param fallback_depth_pt: Use this points depth when no depth can be found.
*/
bool ED_view3d_autodist(Depsgraph *depsgraph,
ARegion *region,
bool ED_view3d_autodist(ARegion *region,
View3D *v3d,
const int mval[2],
float mouse_worldloc[3],
bool alphaoverride,
const float fallback_depth_pt[3]);
/**

View File

@ -179,7 +179,10 @@ static void depthdropper_depth_sample_pt(bContext *C,
view3d_operator_needs_opengl(C);
if (ED_view3d_autodist(depsgraph, region, v3d, mval, co, true, nullptr)) {
/* Ensure the depth buffer is updated for #ED_view3d_autodist. */
ED_view3d_depth_override(depsgraph, region, v3d, nullptr, V3D_DEPTH_NO_GPENCIL, nullptr);
if (ED_view3d_autodist(region, v3d, mval, co, nullptr)) {
const float mval_center_fl[2] = {float(region->winx) / 2, float(region->winy) / 2};
float co_align[3];

View File

@ -2392,6 +2392,8 @@ int UI_icon_from_idcode(const int idcode)
switch ((ID_Type)idcode) {
case ID_AC:
return ICON_ACTION;
case ID_AN:
return ICON_ACTION; /* TODO: give Animation its own icon. */
case ID_AR:
return ICON_ARMATURE_DATA;
case ID_BR:

View File

@ -1119,6 +1119,8 @@ static const char *template_id_browse_tip(const StructRNA *type)
return N_("Browse Armature data to be linked");
case ID_AC:
return N_("Browse Action to be linked");
case ID_AN:
return N_("Browse Animation to be linked");
case ID_NT:
return N_("Browse Node Tree to be linked");
case ID_BR:

View File

@ -317,8 +317,7 @@ void OBJECT_OT_hide_view_clear(wmOperatorType *ot)
/* flags */
ot->flag = OPTYPE_REGISTER | OPTYPE_UNDO;
PropertyRNA *prop = RNA_def_boolean(ot->srna, "select", true, "Select", "");
RNA_def_property_flag(prop, PropertyFlag(PROP_SKIP_SAVE | PROP_HIDDEN));
RNA_def_boolean(ot->srna, "select", true, "Select", "");
}
static int object_hide_view_set_exec(bContext *C, wmOperator *op)

View File

@ -616,6 +616,7 @@ static int gather_frames_to_render_for_id(LibraryIDLinkCallbackData *cb_data)
case ID_SCR: /* Screen */
case ID_GR: /* Group */
case ID_AC: /* bAction */
case ID_AN: /* Animation */
case ID_BR: /* Brush */
case ID_WM: /* WindowManager */
case ID_LS: /* FreestyleLineStyle */

View File

@ -382,6 +382,17 @@ struct EraseOperationExecutor {
float factor;
bool is_src_point;
bool is_cut;
/**
* Source point is the last of the curve.
*/
bool is_src_end_point() const
{
/* The src_next_point index increments for all points except the last, where it is set to the
* first point index. This can be used to detect the curve end from the source index alone.
*/
return is_src_point && src_point >= src_next_point;
}
};
/**
@ -547,18 +558,16 @@ struct EraseOperationExecutor {
threading::parallel_for(dst.curves_range(), 4096, [&](const IndexRange dst_curves) {
for (const int dst_curve : dst_curves) {
const IndexRange dst_curve_points = dst_points_by_curve[dst_curve];
if (dst_transfer_data[dst_curve_points.first()].is_cut) {
const PointTransferData &start_point_transfer =
dst_transfer_data[dst_curve_points.first()];
const PointTransferData &end_point_transfer = dst_transfer_data[dst_curve_points.last()];
if (start_point_transfer.is_cut) {
dst_start_caps.span[dst_curve] = GP_STROKE_CAP_TYPE_FLAT;
}
if (dst_curve == dst_curves.last()) {
continue;
}
const PointTransferData &next_point_transfer =
dst_transfer_data[dst_points_by_curve[dst_curve + 1].first()];
if (next_point_transfer.is_cut) {
/* The is_cut flag does not work for end points, but any end point that isn't the source
* point must also be a cut. */
if (!end_point_transfer.is_src_end_point()) {
dst_end_caps.span[dst_curve] = GP_STROKE_CAP_TYPE_FLAT;
}
}

View File

@ -537,7 +537,11 @@ static void hide_show_begin(bContext *C, gesture::GestureData * /*gesture_data*/
Depsgraph *depsgraph = CTX_data_ensure_evaluated_depsgraph(C);
PBVH *pbvh = BKE_sculpt_object_pbvh_ensure(depsgraph, ob);
#ifndef NDEBUG
BLI_assert(BKE_object_sculpt_pbvh_get(ob) == pbvh);
#else
(void)pbvh;
#endif
}
static void hide_show_apply_for_symmetry_pass(bContext *C, gesture::GestureData *gesture_data)

View File

@ -5800,7 +5800,10 @@ void paint_proj_stroke(const bContext *C,
view3d_operator_needs_opengl(C);
if (!ED_view3d_autodist(depsgraph, region, v3d, mval_i, cursor, false, nullptr)) {
/* Ensure the depth buffer is updated for #ED_view3d_autodist. */
ED_view3d_depth_override(depsgraph, region, v3d, nullptr, V3D_DEPTH_NO_GPENCIL, nullptr);
if (!ED_view3d_autodist(region, v3d, mval_i, cursor, nullptr)) {
return;
}

View File

@ -808,8 +808,8 @@ static void action_id_remap(ScrArea * /*area*/,
{
SpaceAction *sact = (SpaceAction *)slink;
mappings.apply((ID **)&sact->action, ID_REMAP_APPLY_DEFAULT);
mappings.apply((ID **)&sact->ads.filter_grp, ID_REMAP_APPLY_DEFAULT);
mappings.apply(reinterpret_cast<ID **>(&sact->action), ID_REMAP_APPLY_DEFAULT);
mappings.apply(reinterpret_cast<ID **>(&sact->ads.filter_grp), ID_REMAP_APPLY_DEFAULT);
mappings.apply(&sact->ads.source, ID_REMAP_APPLY_DEFAULT);
}

View File

@ -901,7 +901,7 @@ static void buttons_id_remap(ScrArea * /*area*/,
if (sbuts->texuser) {
ButsContextTexture *ct = static_cast<ButsContextTexture *>(sbuts->texuser);
mappings.apply((ID **)&ct->texture, ID_REMAP_APPLY_DEFAULT);
mappings.apply(reinterpret_cast<ID **>(&ct->texture), ID_REMAP_APPLY_DEFAULT);
BLI_freelistN(&ct->users);
ct->user = nullptr;
}

View File

@ -1161,8 +1161,8 @@ static void clip_id_remap(ScrArea * /*area*/,
return;
}
mappings.apply((ID **)&sclip->clip, ID_REMAP_APPLY_ENSURE_REAL);
mappings.apply((ID **)&sclip->mask_info.mask, ID_REMAP_APPLY_ENSURE_REAL);
mappings.apply(reinterpret_cast<ID **>(&sclip->clip), ID_REMAP_APPLY_ENSURE_REAL);
mappings.apply(reinterpret_cast<ID **>(&sclip->mask_info.mask), ID_REMAP_APPLY_ENSURE_REAL);
}
static void clip_foreach_id(SpaceLink *space_link, LibraryForeachIDData *data)

View File

@ -821,8 +821,8 @@ static void graph_id_remap(ScrArea * /*area*/,
return;
}
mappings.apply((ID **)&sgraph->ads->filter_grp, ID_REMAP_APPLY_DEFAULT);
mappings.apply((ID **)&sgraph->ads->source, ID_REMAP_APPLY_DEFAULT);
mappings.apply(reinterpret_cast<ID **>(&sgraph->ads->filter_grp), ID_REMAP_APPLY_DEFAULT);
mappings.apply(reinterpret_cast<ID **>(&sgraph->ads->source), ID_REMAP_APPLY_DEFAULT);
}
static void graph_foreach_id(SpaceLink *space_link, LibraryForeachIDData *data)

View File

@ -1017,9 +1017,9 @@ static void image_id_remap(ScrArea * /*area*/,
return;
}
mappings.apply((ID **)&simg->image, ID_REMAP_APPLY_ENSURE_REAL);
mappings.apply((ID **)&simg->gpd, ID_REMAP_APPLY_UPDATE_REFCOUNT);
mappings.apply((ID **)&simg->mask_info.mask, ID_REMAP_APPLY_ENSURE_REAL);
mappings.apply(reinterpret_cast<ID **>(&simg->image), ID_REMAP_APPLY_ENSURE_REAL);
mappings.apply(reinterpret_cast<ID **>(&simg->gpd), ID_REMAP_APPLY_UPDATE_REFCOUNT);
mappings.apply(reinterpret_cast<ID **>(&simg->mask_info.mask), ID_REMAP_APPLY_ENSURE_REAL);
}
static void image_foreach_id(SpaceLink *space_link, LibraryForeachIDData *data)

View File

@ -42,7 +42,7 @@
#include "GPU_platform.h"
#include "GPU_shader_shared.h"
#include "GPU_state.h"
#include "GPU_uniform_buffer.h"
#include "GPU_uniform_buffer.hh"
#include "DRW_engine.hh"

View File

@ -1150,10 +1150,8 @@ static void node_widgets()
WM_gizmogrouptype_append_and_link(gzmap_type, NODE_GGT_backdrop_corner_pin);
}
static void node_id_remap_cb(ID *old_id, ID *new_id, void *user_data)
static void node_id_remap(ID *old_id, ID *new_id, SpaceNode *snode)
{
SpaceNode *snode = static_cast<SpaceNode *>(user_data);
if (snode->id == old_id) {
/* nasty DNA logic for SpaceNode:
* ideally should be handled by editor code, but would be bad level call
@ -1240,7 +1238,9 @@ static void node_id_remap(ScrArea * /*area*/,
* We could also move a remap address at a time to use the IDRemapper as that should get closer
* to cleaner code. See {D13615} for more information about this topic.
*/
mappings.iter(node_id_remap_cb, slink);
mappings.iter([&](ID *old_id, ID *new_id) {
node_id_remap(old_id, new_id, reinterpret_cast<SpaceNode *>(slink));
});
}
static void node_foreach_id(SpaceLink *space_link, LibraryForeachIDData *data)

View File

@ -2433,6 +2433,8 @@ static BIFIconID tree_element_get_icon_from_id(const ID *id)
return ICON_WORLD_DATA;
case ID_AC:
return ICON_ACTION;
case ID_AN:
return ICON_ACTION; /* TODO: give Animation its own icon. */
case ID_NLA:
return ICON_NLA;
case ID_TXT: {

View File

@ -139,6 +139,7 @@ struct TreeElementIcon {
ID_GR, \
ID_AR, \
ID_AC, \
ID_AN, \
ID_BR, \
ID_PA, \
ID_GD_LEGACY, \

View File

@ -147,6 +147,7 @@ static void get_element_operation_type(
case ID_KE:
case ID_WO:
case ID_AC:
case ID_AN:
case ID_TXT:
case ID_GR:
case ID_LS:

View File

@ -100,10 +100,10 @@ class OverrideIDHierarchyBuilder {
const ID &override_root_id_;
/* The ancestor IDs leading to the current ID, to avoid IDs recursing into themselves. Changes
* with every level of recursion. */
Set<const ID *> parent_ids{};
Set<const ID *> parent_ids;
/* The IDs that were already added to #parent_te, to avoid duplicates. Entirely new set with
* every level of recursion. */
Set<const ID *> sibling_ids{};
Set<const ID *> sibling_ids;
};
public:

View File

@ -88,6 +88,7 @@ std::unique_ptr<TreeElementID> TreeElementID::create_from_id(TreeElement &legacy
case ID_TXT:
case ID_SO:
case ID_AC:
case ID_AN:
case ID_PAL:
case ID_PC:
case ID_CF:

View File

@ -915,7 +915,7 @@ static void sequencer_id_remap(ScrArea * /*area*/,
const blender::bke::id::IDRemapper &mappings)
{
SpaceSeq *sseq = (SpaceSeq *)slink;
mappings.apply((ID **)&sseq->gpd, ID_REMAP_APPLY_DEFAULT);
mappings.apply(reinterpret_cast<ID **>(&sseq->gpd), ID_REMAP_APPLY_DEFAULT);
}
static void sequencer_foreach_id(SpaceLink *space_link, LibraryForeachIDData *data)

View File

@ -394,7 +394,7 @@ static void text_id_remap(ScrArea * /*area*/,
const blender::bke::id::IDRemapper &mappings)
{
SpaceText *stext = (SpaceText *)slink;
mappings.apply((ID **)&stext->text, ID_REMAP_APPLY_ENSURE_REAL);
mappings.apply(reinterpret_cast<ID **>(&stext->text), ID_REMAP_APPLY_ENSURE_REAL);
}
static void text_foreach_id(SpaceLink *space_link, LibraryForeachIDData *data)

Some files were not shown because too many files have changed in this diff Show More