Blender V5.0
draw_vector_displacement.cc
Go to the documentation of this file.
1/* SPDX-FileCopyrightText: 2024 Blender Authors
2 *
3 * SPDX-License-Identifier: GPL-2.0-or-later */
4
6
7#include "DNA_brush_types.h"
8#include "DNA_mesh_types.h"
9#include "DNA_object_types.h"
10#include "DNA_scene_types.h"
11
12#include "BKE_mesh.hh"
13#include "BKE_paint.hh"
14#include "BKE_paint_bvh.hh"
15#include "BKE_subdiv_ccg.hh"
16
18#include "BLI_task.h"
19#include "BLI_task.hh"
20
24
25#include "bmesh.hh"
26
28
30
37
39 const Brush &brush,
40 const Span<float3> vert_positions,
41 const Span<int> verts,
42 const MutableSpan<float3> r_colors)
43{
44 BLI_assert(verts.size() == r_colors.size());
45
46 const int thread_id = BLI_task_parallel_thread_id(nullptr);
47
48 for (const int i : verts.index_range()) {
49 float texture_value;
50 float4 texture_rgba;
51 /* NOTE: This is not a thread-safe call. */
53 ss, brush, vert_positions[verts[i]], thread_id, &texture_value, texture_rgba);
54
55 r_colors[i] = float3(texture_rgba);
56 }
57}
58
60 const Brush &brush,
61 const Span<float3> positions,
62 const MutableSpan<float3> r_colors)
63{
64 BLI_assert(positions.size() == r_colors.size());
65
66 const int thread_id = BLI_task_parallel_thread_id(nullptr);
67
68 for (const int i : positions.index_range()) {
69 float texture_value;
70 float4 texture_rgba;
71 /* NOTE: This is not a thread-safe call. */
72 sculpt_apply_texture(ss, brush, positions[i], thread_id, &texture_value, texture_rgba);
73 r_colors[i] = float3(texture_rgba);
74 }
75}
76
77static void calc_faces(const Depsgraph &depsgraph,
78 const Sculpt &sd,
79 const Brush &brush,
80 const Span<float3> vert_normals,
81 const MeshAttributeData &attribute_data,
82 const bke::pbvh::MeshNode &node,
83 Object &object,
84 LocalData &tls,
85 const PositionDeformData &position_data)
86{
87 SculptSession &ss = *object.sculpt;
88 const StrokeCache &cache = *ss.cache;
89
90 const Span<int> verts = node.verts();
91
92 tls.factors.resize(verts.size());
93 const MutableSpan<float> factors = tls.factors;
94 fill_factor_from_hide_and_mask(attribute_data.hide_vert, attribute_data.mask, verts, factors);
95 filter_region_clip_factors(ss, position_data.eval, verts, factors);
96 if (brush.flag & BRUSH_FRONTFACE) {
97 calc_front_face(cache.view_normal_symm, vert_normals, verts, factors);
98 }
99
100 tls.distances.resize(verts.size());
101 const MutableSpan<float> distances = tls.distances;
103 ss, position_data.eval, verts, eBrushFalloffShape(brush.falloff_shape), distances);
104 filter_distances_with_radius(cache.radius, distances, factors);
105 apply_hardness_to_distances(cache, distances);
106 calc_brush_strength_factors(cache, brush, distances, factors);
107
108 auto_mask::calc_vert_factors(depsgraph, object, cache.automasking.get(), node, verts, factors);
109
110 tls.translations.resize(verts.size());
111 const MutableSpan<float3> translations = tls.translations;
112 calc_brush_texture_colors(ss, brush, position_data.eval, verts, translations);
113 scale_translations(translations, factors);
114 for (const int i : verts.index_range()) {
115 SCULPT_calc_vertex_displacement(ss, brush, translations[i]);
116 }
117
118 clip_and_lock_translations(sd, ss, position_data.eval, verts, translations);
119 position_data.deform(translations, verts);
120}
121
122static void calc_grids(const Depsgraph &depsgraph,
123 const Sculpt &sd,
124 Object &object,
125 const Brush &brush,
127 LocalData &tls)
128{
129 SculptSession &ss = *object.sculpt;
130 const StrokeCache &cache = *ss.cache;
131 SubdivCCG &subdiv_ccg = *ss.subdiv_ccg;
132
133 const Span<int> grids = node.grids();
134 const MutableSpan positions = gather_grids_positions(subdiv_ccg, grids, tls.positions);
135
136 tls.factors.resize(positions.size());
137 const MutableSpan<float> factors = tls.factors;
138 fill_factor_from_hide_and_mask(subdiv_ccg, grids, factors);
139 filter_region_clip_factors(ss, positions, factors);
140 if (brush.flag & BRUSH_FRONTFACE) {
141 calc_front_face(cache.view_normal_symm, subdiv_ccg, grids, factors);
142 }
143
144 tls.distances.resize(positions.size());
145 const MutableSpan<float> distances = tls.distances;
146 calc_brush_distances(ss, positions, eBrushFalloffShape(brush.falloff_shape), distances);
147 filter_distances_with_radius(cache.radius, distances, factors);
148 apply_hardness_to_distances(cache, distances);
149 calc_brush_strength_factors(cache, brush, distances, factors);
150
151 auto_mask::calc_grids_factors(depsgraph, object, cache.automasking.get(), node, grids, factors);
152
153 tls.translations.resize(positions.size());
154 const MutableSpan<float3> translations = tls.translations;
155 calc_brush_texture_colors(ss, brush, positions, translations);
156 scale_translations(translations, factors);
157 for (const int i : positions.index_range()) {
158 SCULPT_calc_vertex_displacement(ss, brush, translations[i]);
159 }
160
161 clip_and_lock_translations(sd, ss, positions, translations);
162 apply_translations(translations, grids, subdiv_ccg);
163}
164
165static void calc_bmesh(const Depsgraph &depsgraph,
166 const Sculpt &sd,
167 Object &object,
168 const Brush &brush,
170 LocalData &tls)
171{
172 SculptSession &ss = *object.sculpt;
173 const StrokeCache &cache = *ss.cache;
174
176 const MutableSpan positions = gather_bmesh_positions(verts, tls.positions);
177
178 tls.factors.resize(verts.size());
179 const MutableSpan<float> factors = tls.factors;
181 filter_region_clip_factors(ss, positions, factors);
182 if (brush.flag & BRUSH_FRONTFACE) {
183 calc_front_face(cache.view_normal_symm, verts, factors);
184 }
185
186 tls.distances.resize(verts.size());
187 const MutableSpan<float> distances = tls.distances;
188 calc_brush_distances(ss, positions, eBrushFalloffShape(brush.falloff_shape), distances);
189 filter_distances_with_radius(cache.radius, distances, factors);
190 apply_hardness_to_distances(cache, distances);
191 calc_brush_strength_factors(cache, brush, distances, factors);
192
193 auto_mask::calc_vert_factors(depsgraph, object, cache.automasking.get(), node, verts, factors);
194
195 tls.translations.resize(positions.size());
196 const MutableSpan<float3> translations = tls.translations;
197 calc_brush_texture_colors(ss, brush, positions, translations);
198 scale_translations(translations, factors);
199 for (const int i : positions.index_range()) {
200 SCULPT_calc_vertex_displacement(ss, brush, translations[i]);
201 }
202
203 clip_and_lock_translations(sd, ss, positions, translations);
204 apply_translations(translations, verts);
205}
206
207} // namespace draw_vector_displacement_cc
208
210 const Sculpt &sd,
211 Object &object,
212 const IndexMask &node_mask)
213{
214 bke::pbvh::Tree &pbvh = *bke::object::pbvh_get(object);
215 const Brush &brush = *BKE_paint_brush_for_read(&sd.paint);
216
218 switch (pbvh.type()) {
220 Mesh &mesh = *static_cast<Mesh *>(object.data);
221 const PositionDeformData position_data(depsgraph, object);
222 const Span<float3> vert_normals = bke::pbvh::vert_normals_eval(depsgraph, object);
224 const MeshAttributeData attribute_data(mesh);
225 node_mask.foreach_index(GrainSize(1), [&](const int i) {
226 LocalData &tls = all_tls.local();
228 sd,
229 brush,
230 vert_normals,
231 attribute_data,
232 nodes[i],
233 object,
234 tls,
235 position_data);
236 bke::pbvh::update_node_bounds_mesh(position_data.eval, nodes[i]);
237 });
238 break;
239 }
241 SubdivCCG &subdiv_ccg = *object.sculpt->subdiv_ccg;
242 MutableSpan<float3> positions = subdiv_ccg.positions;
244 node_mask.foreach_index(GrainSize(1), [&](const int i) {
245 LocalData &tls = all_tls.local();
246 calc_grids(depsgraph, sd, object, brush, nodes[i], tls);
247 bke::pbvh::update_node_bounds_grids(subdiv_ccg.grid_area, positions, nodes[i]);
248 });
249 break;
250 }
253 node_mask.foreach_index(GrainSize(1), [&](const int i) {
254 LocalData &tls = all_tls.local();
255 calc_bmesh(depsgraph, sd, object, brush, nodes[i], tls);
257 });
258 break;
259 }
260 }
261 pbvh.tag_positions_changed(node_mask);
263}
264
265} // namespace blender::ed::sculpt_paint::brushes
const Brush * BKE_paint_brush_for_read(const Paint *paint)
Definition paint.cc:650
A BVH for high poly meshes.
const blender::Set< BMVert *, 0 > & BKE_pbvh_bmesh_node_unique_verts(blender::bke::pbvh::BMeshNode *node)
#define BLI_assert(a)
Definition BLI_assert.h:46
int BLI_task_parallel_thread_id(const TaskParallelTLS *tls)
@ BRUSH_FRONTFACE
eBrushFalloffShape
Object is a sort of wrapper for general info.
BPy_StructRNA * depsgraph
void resize(const int64_t new_size)
constexpr int64_t size() const
Definition BLI_span.hh:493
constexpr IndexRange index_range() const
Definition BLI_span.hh:670
constexpr int64_t size() const
Definition BLI_span.hh:252
constexpr IndexRange index_range() const
Definition BLI_span.hh:401
void tag_positions_changed(const IndexMask &node_mask)
Definition pbvh.cc:635
Span< NodeT > nodes() const
void flush_bounds_to_parents()
Definition pbvh.cc:1306
void foreach_index(Fn &&fn) const
static float verts[][3]
pbvh::Tree * pbvh_get(Object &object)
Definition paint.cc:3052
void update_node_bounds_bmesh(BMeshNode &node)
Definition pbvh.cc:1294
void update_node_bounds_mesh(Span< float3 > positions, MeshNode &node)
Definition pbvh.cc:1274
Span< float3 > vert_normals_eval(const Depsgraph &depsgraph, const Object &object_orig)
Definition pbvh.cc:1059
void update_node_bounds_grids(int grid_area, Span< float3 > positions, GridsNode &node)
Definition pbvh.cc:1283
void calc_vert_factors(const Depsgraph &depsgraph, const Object &object, const Cache &automasking, const bke::pbvh::MeshNode &node, Span< int > verts, MutableSpan< float > factors)
void calc_grids_factors(const Depsgraph &depsgraph, const Object &object, const Cache &automasking, const bke::pbvh::GridsNode &node, Span< int > grids, MutableSpan< float > factors)
static void calc_bmesh(const Depsgraph &depsgraph, const Sculpt &sd, Object &object, const Brush &brush, const float3 &direction, const float strength, bke::pbvh::BMeshNode &node, LocalData &tls)
static void calc_faces(const Depsgraph &depsgraph, const Sculpt &sd, const Brush &brush, const float4 &test_plane, const float strength, const MeshAttributeData &attribute_data, const Span< float3 > vert_normals, const bke::pbvh::MeshNode &node, Object &object, LocalData &tls, const PositionDeformData &position_data)
Definition clay.cc:56
static void calc_grids(const Depsgraph &depsgraph, const Sculpt &sd, Object &object, const Brush &brush, const float4 &test_plane, const float strength, bke::pbvh::GridsNode &node, LocalData &tls)
Definition clay.cc:93
static BLI_NOINLINE void fill_factor_from_hide_and_mask(const Mesh &mesh, const Span< int > face_indices, const MutableSpan< float > r_factors)
static void calc_grids(const Depsgraph &depsgraph, const Sculpt &sd, Object &object, const Brush &brush, bke::pbvh::GridsNode &node, LocalData &tls)
static void calc_faces(const Depsgraph &depsgraph, const Sculpt &sd, const Brush &brush, const Span< float3 > vert_normals, const MeshAttributeData &attribute_data, const bke::pbvh::MeshNode &node, Object &object, LocalData &tls, const PositionDeformData &position_data)
static void calc_brush_texture_colors(SculptSession &ss, const Brush &brush, const Span< float3 > vert_positions, const Span< int > verts, const MutableSpan< float3 > r_colors)
static void calc_bmesh(const Depsgraph &depsgraph, const Sculpt &sd, Object &object, const Brush &brush, bke::pbvh::BMeshNode &node, LocalData &tls)
void do_draw_vector_displacement_brush(const Depsgraph &depsgraph, const Sculpt &sd, Object &object, const IndexMask &node_mask)
MutableSpan< float3 > gather_grids_positions(const SubdivCCG &subdiv_ccg, const Span< int > grids, Vector< float3 > &positions)
void gather_bmesh_positions(const Set< BMVert *, 0 > &verts, MutableSpan< float3 > positions)
Definition sculpt.cc:6367
void calc_brush_strength_factors(const StrokeCache &cache, const Brush &brush, Span< float > distances, MutableSpan< float > factors)
Definition sculpt.cc:7183
void apply_hardness_to_distances(float radius, float hardness, MutableSpan< float > distances)
Definition sculpt.cc:7156
void filter_distances_with_radius(float radius, Span< float > distances, MutableSpan< float > factors)
Definition sculpt.cc:7105
void filter_region_clip_factors(const SculptSession &ss, Span< float3 > vert_positions, Span< int > verts, MutableSpan< float > factors)
Definition sculpt.cc:6972
void scale_translations(MutableSpan< float3 > translations, Span< float > factors)
Definition sculpt.cc:7495
void clip_and_lock_translations(const Sculpt &sd, const SculptSession &ss, Span< float3 > positions, Span< int > verts, MutableSpan< float3 > translations)
Definition sculpt.cc:7335
void calc_brush_distances(const SculptSession &ss, Span< float3 > vert_positions, Span< int > vert, eBrushFalloffShape falloff_shape, MutableSpan< float > r_distances)
Definition sculpt.cc:7055
void apply_translations(Span< float3 > translations, Span< int > verts, MutableSpan< float3 > positions)
Definition sculpt.cc:7268
void calc_front_face(const float3 &view_normal, Span< float3 > normals, MutableSpan< float > factors)
Definition sculpt.cc:6914
VecBase< float, 4 > float4
VecBase< float, 3 > float3
void sculpt_apply_texture(const SculptSession &ss, const Brush &brush, const float brush_point[3], const int thread_id, float *r_value, float r_rgba[4])
Definition sculpt.cc:2322
void SCULPT_calc_vertex_displacement(const SculptSession &ss, const Brush &brush, float translation[3])
Definition sculpt.cc:2388
char falloff_shape
blender::ed::sculpt_paint::StrokeCache * cache
Definition BKE_paint.hh:417
SubdivCCG * subdiv_ccg
Definition BKE_paint.hh:395
blender::Array< blender::float3 > positions
std::unique_ptr< auto_mask::Cache > automasking
i
Definition text_draw.cc:230