15#include "util/color.h"
27 const float motion_scale)
29 const int num_points = pointcloud->get_points().size();
32 pointcloud->set_motion_steps(3);
35 float3 *
P = pointcloud->get_points().data();
36 float *radius = pointcloud->get_radius().data();
44 float motion_times[2] = {-1.0f, 1.0f};
45 for (
int step = 0; step < 2; step++) {
46 const float relative_time = motion_times[step] * 0.5f * motion_scale;
47 float4 *mP = attr_mP->
data_float4() + step * num_points;
49 for (
int i = 0; i < num_points; i++) {
50 float3 Pi =
P[i] +
make_float3(b_attribute[i][0], b_attribute[i][1], b_attribute[i][2]) *
58 const ::PointCloud &b_pointcloud,
59 const bool need_motion,
60 const float motion_scale)
68 static const ustring u_velocity(
"velocity");
70 const ustring name{std::string_view(iter.
name)};
72 if (need_motion && name == u_velocity) {
77 if (attributes.find(name)) {
83 using BlenderT = decltype(dummy);
84 using Converter = typename ccl::AttributeConverter<BlenderT>;
85 using CyclesT = typename Converter::CyclesT;
86 if constexpr (!std::is_void_v<CyclesT>) {
87 Attribute *attr = attributes.add(name, Converter::type_desc, ATTR_ELEMENT_VERTEX);
88 CyclesT *data = reinterpret_cast<CyclesT *>(attr->data());
90 const blender::VArraySpan src = b_attr.varray.typed<BlenderT>();
91 for (const int i : src.index_range()) {
92 data[i] = Converter::convert(src[i]);
101 const ::PointCloud &b_pointcloud,
102 const bool need_motion,
103 const float motion_scale)
111 float3 *points = pointcloud->get_points().data();
114 points[i] =
make_float3(b_positions[i][0], b_positions[i][1], b_positions[i][2]);
117 float *radius = pointcloud->get_radius().data();
119 std::copy(b_radius.
data(), b_radius.
data() + b_positions.
size(), radius);
122 std::fill(radius, radius + b_positions.
size(), 0.01f);
125 int *shader = pointcloud->get_shader().data();
126 std::fill(shader, shader + b_positions.
size(), 0);
140 const ::PointCloud &b_pointcloud,
145 bool new_attribute =
false;
149 new_attribute =
true;
152 const int num_points = pointcloud->
num_points();
156 float4 *mP = attr_mP->
data_float4() + motion_step * num_points;
157 bool have_motion =
false;
158 const array<float3> &pointcloud_points = pointcloud->get_points();
164 for (
int i = 0; i < std::min<int>(num_points, b_positions.
size()); i++) {
165 const float3 P =
make_float3(b_positions[i][0], b_positions[i][1], b_positions[i][2]);
166 const float radius = b_radius.
is_empty() ? 0.01f : b_radius[i];
168 have_motion = have_motion || (
P != pointcloud_points[i]);
173 if (b_positions.
size() != num_points || !have_motion) {
176 else if (motion_step > 0) {
179 for (
int step = 0; step < motion_step; step++) {
191 size_t old_numpoints = pointcloud->
num_points();
196 new_pointcloud.set_used_shaders(used_shaders);
199 BL::PointCloud b_pointcloud(b_ob_info.
object_data);
202 const float motion_scale = (need_motion) ?
203 scene->motion_shutter_time() /
204 (b_scene.render().fps() / b_scene.render().fps_base()) :
208 *
static_cast<const ::
PointCloud *
>(b_pointcloud.ptr.data),
213 for (
const SocketType &socket : new_pointcloud.type->inputs) {
215 if (socket.name ==
"use_motion_blur" || socket.name ==
"motion_steps" ||
216 socket.name ==
"used_shaders")
220 pointcloud->
set_value(socket, new_pointcloud, socket);
229 const bool rebuild = (pointcloud && old_numpoints != pointcloud->
num_points());
233void BlenderSync::sync_pointcloud_motion(
PointCloud *pointcloud,
243 if (ccl::BKE_object_is_deform_modified(b_ob_info, b_scene, preview)) {
245 BL::PointCloud b_pointcloud(b_ob_info.
object_data);
247 pointcloud, *
static_cast<const ::
PointCloud *
>(b_pointcloud.ptr.data), motion_step);
General operations for point clouds.
static void export_pointcloud(Scene *scene, PointCloud *pointcloud, const ::PointCloud &b_pointcloud, const bool need_motion, const float motion_scale)
static void export_pointcloud_motion(PointCloud *pointcloud, const ::PointCloud &b_pointcloud, int motion_step)
static void copy_attributes(PointCloud *pointcloud, const ::PointCloud &b_pointcloud, const bool need_motion, const float motion_scale)
static CCL_NAMESPACE_BEGIN void attr_create_motion_from_velocity(PointCloud *pointcloud, const blender::Span< blender::float3 > b_attribute, const float motion_scale)
Attribute * add(ustring name, TypeDesc type, AttributeElement element)
list< Attribute > attributes
Attribute * find(ustring name) const
void remove(ustring name)
void clear(bool preserve_voxel_data=false)
void tag_update(Scene *scene, bool rebuild)
bool need_attribute(Scene *scene, AttributeStandard std)
const CPPType & type() const
constexpr const T * data() const
constexpr int64_t size() const
constexpr IndexRange index_range() const
constexpr bool is_empty() const
void foreach_attribute(const FunctionRef< void(const AttributeIter &)> fn) const
int domain_size(const AttrDomain domain) const
GAttributeReader get() const
static bool object_need_motion_attribute(BObjectInfo &b_ob_info, Scene *scene)
#define CCL_NAMESPACE_END
ccl_device_inline float hash_uint2_to_float(uint kx, uint ky)
@ ATTR_STD_MOTION_VERTEX_POSITION
void convert_to_static_type(const CPPType &cpp_type, const Func &func)
void set_value(const SocketType &input, const Node &other, const SocketType &other_input)
size_t num_points() const
void resize(int numpoints)
void copy_center_to_motion_step(const int motion_step)