75 SOCKET_NODE(geometry,
"Geometry", Geometry::get_node_base_type());
83 SOCKET_BOOLEAN(hide_on_missing_motion,
"Hide on Missing Motion",
false);
87 SOCKET_FLOAT(shadow_terminator_shading_offset,
"Shadow Terminator Shading Offset", 0.0f);
88 SOCKET_FLOAT(shadow_terminator_geometry_offset,
"Shadow Terminator Geometry Offset", 0.1f);
94 SOCKET_BOOLEAN(is_caustics_receiver,
"Receive Shadow Caustics",
false);
98 SOCKET_NODE(particle_system,
"Particle System", ParticleSystem::get_node_type());
104 SOCKET_UINT(receiver_light_set,
"Light Set Index", 0);
106 SOCKET_UINT(blocker_shadow_set,
"Shadow Set Index", 0);
114 particle_system =
nullptr;
129 bool have_motion =
false;
131 for (
size_t i = 0;
i < motion.size();
i++) {
133 if (hide_on_missing_motion) {
147 have_motion = have_motion || motion[
i] != tfm;
158 const BoundBox mbounds = geometry->bounds;
169 for (
float t = 0.0f; t < 1.0f; t += (1.0f / 128.0f)) {
178 if (geometry->transform_applied) {
193 geometry->apply_transform(tfm, apply_to_motion);
198 geometry->transform_negative_scaled =
true;
202 geometry->compute_bounds();
217 if (use_holdout_is_modified()) {
221 if (is_shadow_catcher_is_modified()) {
228 if (tfm_is_modified() || motion_is_modified()) {
232 if (visibility_is_modified()) {
236 for (
Node *node : geometry->get_used_shaders()) {
244 scene->
camera->need_flags_update =
true;
250 return (motion.size() > 1);
255 return (
use_motion()) ? 2.0f *
step / (motion.size() - 1) - 1.0f : 0.0f;
274 if (geometry->is_light()) {
296 Mesh *mesh =
static_cast<Mesh *
>(geometry);
305 for (
Node *node : mesh->get_used_shaders()) {
311 step_rate =
fminf(shader->get_volume_step_rate(), step_rate);
323 if (geometry->is_volume()) {
335 float voxel_step_size = volume->get_step_size();
337 if (voxel_step_size == 0.0f) {
358 else if (volume->get_object_space()) {
364 if (voxel_step_size > 0.0f) {
365 step_size =
fminf(voxel_step_size, step_size);
377 step_size *= step_rate;
398 if (!(get_visibility() &
408 for (
Node *node : geom->get_used_shaders()) {
419 if (get_receiver_light_set()) {
432 if (get_blocker_shadow_set()) {
457 if (
static_cast<Volume *
>(geom)->get_object_space()) {
469 geom->
is_hair() ?
static_cast<Hair *
>(geom)->get_curve_keys().size() :
490 const float pass_id = ob->pass_id;
491 const float random_number = (float)ob->random_id * (1.0f / (
float)0xFFFFFFFF);
493 ob->particle_index +
state->particle_offset[ob->particle_system] :
499 kobject.
color[0] = color.
x;
500 kobject.
color[1] = color.
y;
501 kobject.
color[2] = color.
z;
502 kobject.
alpha = ob->alpha;
510 ob->receiver_light_set;
514 ob->blocker_shadow_set;
517 if (geom->get_use_motion_blur()) {
518 state->have_motion =
true;
532 Mesh *mesh =
static_cast<Mesh *
>(geom);
557 tfm_pre = ob->motion[0];
558 tfm_post = ob->motion[ob->motion.size() - 1];
569 tfm_pre = tfm_pre * itfm;
570 tfm_post = tfm_post * itfm;
574 object_motion_pass[motion_pass_offset + 0] = tfm_pre;
575 object_motion_pass[motion_pass_offset + 1] = tfm_post;
582 if (ob->tfm_is_modified() || ob->motion_is_modified() || update_all) {
588 state->have_motion =
true;
596 kobject.
dupli_uv[0] = ob->dupli_uv[0];
597 kobject.
dupli_uv[1] = ob->dupli_uv[1];
603 if (ob->asset_name_is_modified() || update_all) {
606 ob->asset_name.c_str(), ob->asset_name.length(), 0);
619 if (ob->is_caustics_caster) {
622 if (ob->is_caustics_receiver) {
627 if (ob->use_holdout) {
635 state->have_curves =
true;
638 state->have_points =
true;
641 state->have_volumes =
true;
656 if (!scene->
integrator->get_use_light_tree()) {
670 uint32_t prim_offset = 0;
671 if (
Geometry *
const geom = ob->geometry) {
672 if (geom->is_hair()) {
673 prim_offset = ((
Hair *
const)geom)->curve_segment_offset;
676 prim_offset = geom->prim_offset;
680 object_prim_offset[obj_index] = prim_offset;
691 state.have_motion =
false;
692 state.have_curves =
false;
693 state.have_points =
false;
694 state.have_volumes =
false;
696 state.queue_start_object = 0;
701 state.object_motion =
nullptr;
702 state.object_motion_pass =
nullptr;
711 uint motion_offset = 0;
714 *motion_offsets = motion_offset;
719 motion_offset += ob->motion.size();
728 int numparticles = 1;
730 state.particle_offset[psys] = numparticles;
739 static const int OBJECTS_PER_TASK = 32;
740 parallel_for(blocked_range<size_t>(0, scene->
objects.
size(), OBJECTS_PER_TASK),
741 [&](
const blocked_range<size_t> &r) {
742 for (size_t i = r.begin(); i != r.end(); i++) {
743 Object *ob = state.scene->objects[i];
744 device_update_object_transform(&state, ob, update_all, scene);
752 dscene->objects.copy_to_device_if_modified();
754 dscene->object_motion_pass.copy_to_device();
757 dscene->object_motion.copy_to_device();
760 dscene->data.bvh.have_motion =
state.have_motion;
761 dscene->data.bvh.have_curves =
state.have_curves;
762 dscene->data.bvh.have_points =
state.have_points;
763 dscene->data.bvh.have_volumes =
state.have_volumes;
765 dscene->objects.clear_modified();
766 dscene->object_motion_pass.clear_modified();
767 dscene->object_motion.clear_modified();
807 scene->
update_stats->object.times.add_entry({
"device_update (assign index)", time});
813 object->index = index++;
832 {
"device_update (copy objects to device)", time});
836 progress.set_status(
"Updating Objects",
"Copying Transformations to device");
841 object->clear_modified();
857 scene->
update_stats->object.times.add_entry({
"device_update_flags", time});
881 bool has_volume_objects =
false;
883 if (object->geometry->has_volume) {
888 volume_objects.push_back(
object);
889 object_volume_step[
object->index] =
object->compute_volume_step_size();
892 object_volume_step[
object->index] =
FLT_MAX;
894 has_volume_objects =
true;
897 object_volume_step[
object->index] =
FLT_MAX;
902 if (object->geometry->has_volume) {
916 if (object->is_shadow_catcher) {
924 object->intersects_volume =
false;
925 for (
Object *volume_object : volume_objects) {
926 if (
object == volume_object) {
931 object->intersects_volume =
true;
936 else if (has_volume_objects) {
970 if (attr_map_offset == 0) {
1009 map<Geometry *, int> geometry_users;
1016 const map<Geometry *, int>::iterator it = geometry_users.find(object->geometry);
1018 if (it == geometry_users.end()) {
1019 geometry_users[
object->geometry] = 1;
1044 Mesh *mesh =
static_cast<Mesh *
>(geom);
1055 if (!(motion_blur && object->
use_motion())) {
1057 object->apply_transform(apply_to_motion);
1075 update_flags |=
flag;
1113 string manifest =
"{";
1115 unordered_set<ustring> objects;
1117 if (objects.count(object->
name)) {
1120 objects.insert(object->
name);
1124 manifest[manifest.size() - 1] =
'}';
1130 string manifest =
"{";
1131 unordered_set<ustring> assets;
1133 if (assets.count(ob->asset_name)) {
1136 assets.insert(ob->asset_name);
1138 ob->asset_name.c_str(), ob->asset_name.length(), 0);
1139 manifest +=
string_printf(
"\"%s\":\"%08x\",", ob->asset_name.c_str(), hash_asset);
1141 manifest[manifest.size() - 1] =
'}';
static DBVT_INLINE btScalar size(const btDbvtVolume &a)
list< Attribute > attributes
Attribute * find(ustring name) const
device_vector< DecomposedTransform > object_motion
device_vector< Transform > object_motion_pass
device_vector< float > object_volume_step
device_vector< uint > object_prim_offset
device_vector< uint > object_flag
device_vector< KernelObject > objects
virtual BVHLayoutMask get_bvh_layout_mask(const uint kernel_features) const =0
bool has_true_displacement() const
bool is_pointcloud() const
virtual PrimitiveType primitive_type() const =0
void tag_update(Scene *scene, const uint32_t flag)
void tag_update(Scene *scene, const uint32_t flag)
string get_cryptomatte_objects(Scene *scene)
void device_update(Device *device, DeviceScene *dscene, Scene *scene, Progress &progress)
void device_update_object_transform(UpdateObjectTransformState *state, Object *ob, bool update_all, const Scene *scene)
void device_free(Device *device, DeviceScene *dscene, bool force_free)
string get_cryptomatte_assets(Scene *scene)
void device_update_geom_offsets(Device *device, DeviceScene *dscene, Scene *scene)
void device_update_prim_offsets(Device *device, DeviceScene *dscene, Scene *scene)
void device_update_transforms(DeviceScene *dscene, Scene *scene, Progress &progress)
void apply_static_transforms(DeviceScene *dscene, Scene *scene, Progress &progress)
void device_update_flags(Device *device, DeviceScene *dscene, Scene *scene, Progress &progress, bool bounds_valid=true)
bool has_volume_attribute_dependency
EmissionSampling emission_sampling
bool has_volume_spatial_varying
void free_if_need_realloc(bool force_free)
T * alloc(const size_t width, const size_t height=0, const size_t depth=0)
#define LIGHT_LINK_SET_MAX
#define OBJECT_MOTION_PASS_SIZE
#define LIGHT_LINK_MASK_ALL
#define SHADOW_CATCHER_OBJECT_VISIBILITY(is_shadow_catcher, visibility)
#define CCL_NAMESPACE_END
VecBase< float, D > normalize(VecOp< float, D >) RET
#define assert(assertion)
VecBase< float, D > step(VecOp< float, D >, VecOp< float, D >) RET
ccl_device_inline float object_volume_density(KernelGlobals kg, const int object)
ccl_device_inline uint particle_index(KernelGlobals kg, const int particle)
@ ATTR_STD_VOLUME_VELOCITY
@ ATTR_STD_MOTION_VERTEX_POSITION
@ PATH_RAY_VOLUME_SCATTER
@ PATH_RAY_ALL_VISIBILITY
@ SD_OBJECT_HAS_VOLUME_ATTRIBUTES
@ SD_OBJECT_INTERSECTS_VOLUME
@ SD_OBJECT_NEGATIVE_SCALE
@ SD_OBJECT_HAS_VOLUME_MOTION
@ SD_OBJECT_CAUSTICS_RECEIVER
@ SD_OBJECT_SHADOW_CATCHER
@ SD_OBJECT_TRANSFORM_APPLIED
@ SD_OBJECT_HAS_VERTEX_MOTION
@ SD_OBJECT_CAUSTICS_CASTER
@ BVH_LAYOUT_MULTI_HIPRT_EMBREE
@ BVH_LAYOUT_MULTI_METAL_EMBREE
CCL_NAMESPACE_BEGIN ccl_device_inline float2 zero_float2()
ccl_device_inline float average(const float2 a)
ccl_device_inline float reduce_min(const float2 a)
ccl_device_inline float2 fabs(const float2 a)
ccl_device_inline float3 one_float3()
CCL_NAMESPACE_BEGIN ccl_device_inline float3 zero_float3()
uint32_t util_murmur_hash3(const void *key, const int len, const uint32_t seed)
float util_hash_to_float(const uint32_t hash)
static void update(bNodeTree *ntree)
#define SOCKET_POINT(name, ui_name, default_value,...)
#define SOCKET_FLOAT(name, ui_name, default_value,...)
#define SOCKET_INT(name, ui_name, default_value,...)
#define SOCKET_NODE(name, ui_name, node_type,...)
#define SOCKET_TRANSFORM(name, ui_name, default_value,...)
#define SOCKET_UINT(name, ui_name, default_value,...)
#define NODE_DEFINE(structname)
#define SOCKET_COLOR(name, ui_name, default_value,...)
#define SOCKET_TRANSFORM_ARRAY(name, ui_name, default_value,...)
#define SOCKET_BOOLEAN(name, ui_name, default_value,...)
#define SOCKET_POINT2(name, ui_name, default_value,...)
#define SOCKET_STRING(name, ui_name, default_value,...)
#define SOCKET_UINT64(name, ui_name, default_value,...)
static float object_volume_density(const Transform &tfm, Geometry *geom)
static int object_num_motion_verts(Geometry *geom)
CCL_NAMESPACE_BEGIN string string_printf(const char *format,...)
ImageHandle & data_voxel()
BoundBox transformed(const Transform *tfm) const
__forceinline bool intersects(const BoundBox &other)
uint64_t shadow_set_membership
float shadow_terminator_geometry_offset
uint attribute_map_offset
uint64_t light_set_membership
float shadow_terminator_shading_offset
AttributeSet subd_attributes
static NodeType * add(const char *name, CreateFunc create, Type type=NONE, const NodeType *base=nullptr)
Node(const NodeType *type, ustring name=ustring())
void compute_bounds(bool motion_blur)
NODE_DECLARE BoundBox bounds
bool usable_as_light() const
float shadow_terminator_shading_offset
vector< ParamValue > attributes
int get_device_index() const
int motion_step(const float time) const
void apply_transform(bool apply_to_motion)
float compute_volume_step_size() const
bool has_light_linking() const
float shadow_terminator_geometry_offset
bool is_traceable() const
uint visibility_for_tracing() const
void tag_update(Scene *scene)
float motion_time(const int step) const
bool has_shadow_linking() const
struct LightgroupMembership * lightgroup
unique_ptr< ObjectManager > object_manager
MotionType need_motion() const
unique_ptr< LightManager > light_manager
unique_ptr< SceneUpdateStats > update_stats
void tag_shadow_catcher_modified()
unique_ptr_vector< ParticleSystem > particle_systems
unique_ptr< GeometryManager > geometry_manager
unique_ptr_vector< Object > objects
map< ustring, int > lightgroups
@ IMAGE_DATA_TYPE_NANOVDB_FP16
@ IMAGE_DATA_TYPE_NANOVDB_FLOAT
@ IMAGE_DATA_TYPE_NANOVDB_FLOAT3
@ IMAGE_DATA_TYPE_NANOVDB_FPN