Blender V4.3
grease_pencil_paint_common.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
5#include "BKE_brush.hh"
6#include "BKE_colortools.hh"
7#include "BKE_context.hh"
8#include "BKE_crazyspace.hh"
9#include "BKE_curves.hh"
10#include "BKE_grease_pencil.hh"
11#include "BKE_paint.hh"
12
13#include "BLI_index_mask.hh"
14#include "BLI_math_vector.hh"
15#include "BLI_task.hh"
16
18
19#include "DNA_brush_types.h"
21#include "DNA_screen_types.h"
22#include "DNA_view3d_types.h"
23
24#include "ED_grease_pencil.hh"
25#include "ED_view3d.hh"
26
28
29#include <iostream>
30
32
34{
35 using namespace blender::bke::greasepencil;
36
37 const Scene &scene = *CTX_data_scene(&C);
38 Object &ob_orig = *CTX_data_active_object(&C);
39 GreasePencil &grease_pencil = *static_cast<GreasePencil *>(ob_orig.data);
41 const Brush &brush = *BKE_paint_brush(&paint);
42 const bool active_layer_only = ((brush.gpencil_settings->flag & GP_BRUSH_ACTIVE_LAYER_ONLY) !=
43 0);
44
45 if (active_layer_only) {
46 /* Apply only to the drawing at the current frame of the active layer. */
47 if (!grease_pencil.has_active_layer()) {
48 return {};
49 }
50 const Layer &active_layer = *grease_pencil.get_active_layer();
52 scene, grease_pencil, active_layer);
53 }
54
55 /* Apply to all editable drawings. */
57}
58
76
77float brush_radius(const Scene &scene, const Brush &brush, const float pressure = 1.0f)
78{
79 float radius = BKE_brush_size_get(&scene, &brush);
80 if (BKE_brush_use_size_pressure(&brush)) {
82 }
83 return radius;
84}
85
86float brush_point_influence(const Scene &scene,
87 const Brush &brush,
88 const float2 &co,
89 const InputSample &sample,
90 const float multi_frame_falloff)
91{
92 const float radius = brush_radius(scene, brush, sample.pressure);
93 /* Basic strength factor from brush settings. */
94 const float brush_pressure = BKE_brush_use_alpha_pressure(&brush) ? sample.pressure : 1.0f;
95 const float influence_base = BKE_brush_alpha_get(&scene, &brush) * brush_pressure *
96 multi_frame_falloff;
97
98 /* Distance falloff. */
99 const int2 mval_i = int2(math::round(sample.mouse_position));
100 const float distance = math::distance(mval_i, int2(co));
101 /* Apply Brush curve. */
102 const float brush_falloff = BKE_brush_curve_strength(&brush, distance, radius);
103
104 return influence_base * brush_falloff;
105}
106
108{
109 int j = verts.size() - 1;
110 bool isect = false;
111 float distance = FLT_MAX;
112 for (int i = 0; i < verts.size(); i++) {
113 /* Based on implementation of #isect_point_poly_v2. */
114 if (((verts[i].y > pt.y) != (verts[j].y > pt.y)) &&
115 (pt.x <
116 (verts[j].x - verts[i].x) * (pt.y - verts[i].y) / (verts[j].y - verts[i].y) + verts[i].x))
117 {
118 isect = !isect;
119 }
121 j = i;
122 }
123 return isect ? 0.0f : distance;
124}
125
126float brush_fill_influence(const Scene &scene,
127 const Brush &brush,
128 const Span<float2> fill_positions,
129 const InputSample &sample,
130 const float multi_frame_falloff)
131{
132 const float radius = brush_radius(scene, brush, sample.pressure);
133 /* Basic strength factor from brush settings. */
134 const float brush_pressure = BKE_brush_use_alpha_pressure(&brush) ? sample.pressure : 1.0f;
135 const float influence_base = BKE_brush_alpha_get(&scene, &brush) * brush_pressure *
136 multi_frame_falloff;
137
138 /* Distance falloff. */
139 const float distance = closest_distance_to_surface_2d(sample.mouse_position, fill_positions);
140 /* Apply Brush curve. */
141 const float brush_falloff = BKE_brush_curve_strength(&brush, distance, radius);
142
143 return influence_base * brush_falloff;
144}
145
147 const Brush &brush,
148 const float2 &mouse_position,
149 const float pressure,
150 const float multi_frame_falloff,
151 const IndexMask &selection,
152 const Span<float2> view_positions,
153 Vector<float> &influences,
154 IndexMaskMemory &memory)
155{
156 if (selection.is_empty()) {
157 return {};
158 }
159
160 const float radius = brush_radius(scene, brush, pressure);
161 const float radius_squared = radius * radius;
162 const float brush_pressure = BKE_brush_use_alpha_pressure(&brush) ? pressure : 1.0f;
163 const float influence_base = BKE_brush_alpha_get(&scene, &brush) * brush_pressure *
164 multi_frame_falloff;
165 const int2 mval_i = int2(math::round(mouse_position));
166
167 Array<float> all_influences(selection.min_array_size());
168 const IndexMask influence_mask = IndexMask::from_predicate(
169 selection, GrainSize(4096), memory, [&](const int point) {
170 /* Distance falloff. */
171 const float distance_squared = math::distance_squared(int2(view_positions[point]), mval_i);
172 if (distance_squared > radius_squared) {
173 all_influences[point] = 0.0f;
174 return false;
175 }
176 /* Apply Brush curve. */
177 const float brush_falloff = BKE_brush_curve_strength(
178 &brush, math::sqrt(distance_squared), radius);
179 all_influences[point] = influence_base * brush_falloff;
180 return all_influences[point] > 0.0f;
181 });
182 influences.resize(influence_mask.size());
183 array_utils::gather(all_influences.as_span(), influence_mask, influences.as_mutable_span());
184
185 return influence_mask;
186}
187
188bool brush_using_vertex_color(const GpPaint *gp_paint, const Brush *brush)
189{
190 const int brush_draw_mode = brush->gpencil_settings->brush_draw_mode;
191 const bool brush_use_pinned_mode = (brush_draw_mode != GP_BRUSH_MODE_ACTIVE);
192 if (brush_use_pinned_mode) {
193 return (brush_draw_mode == GP_BRUSH_MODE_VERTEXCOLOR);
194 }
195 return (gp_paint->mode == GPPAINT_FLAG_USE_VERTEXCOLOR);
196}
197
198bool is_brush_inverted(const Brush &brush, const BrushStrokeMode stroke_mode)
199{
200 /* The basic setting is the brush's setting. During runtime, the user can hold down the Ctrl key
201 * to invert the basic behavior. */
202 return bool(brush.flag & BRUSH_DIR_IN) ^ (stroke_mode == BrushStrokeMode::BRUSH_STROKE_INVERT);
203}
204
206 const Object &object,
207 const bke::greasepencil::Layer &layer)
208{
209 const float4x4 view_to_world = float4x4(params.rv3d.viewinv);
210 const float4x4 layer_to_world = layer.to_world_space(object);
211 const float4x4 world_to_layer = math::invert(layer_to_world);
212
213 auto screen_to_world = [=](const float3 &world_pos, const float2 &screen_delta) {
214 const float zfac = ED_view3d_calc_zfac(&params.rv3d, world_pos);
215 float3 world_delta;
216 ED_view3d_win_to_delta(&params.region, screen_delta, zfac, world_delta);
217 return world_delta;
218 };
219
220 switch (params.toolsettings.gp_sculpt.lock_axis) {
221 case GP_LOCKAXIS_VIEW: {
222 const float3 world_normal = view_to_world.z_axis();
223 return [=](const float3 &position, const float2 &screen_delta) {
224 const float3 world_pos = math::transform_point(layer_to_world, position);
225 const float3 world_delta = screen_to_world(world_pos, screen_delta);
226 const float3 layer_delta = math::transform_direction(
227 world_to_layer, world_delta - world_normal * math::dot(world_delta, world_normal));
228 return position + layer_delta;
229 };
230 }
231 case GP_LOCKAXIS_X: {
232 return [=](const float3 &position, const float2 &screen_delta) {
233 const float3 world_pos = math::transform_point(layer_to_world, position);
234 const float3 world_delta = screen_to_world(world_pos, screen_delta);
235 const float3 layer_delta = math::transform_direction(
236 world_to_layer, float3(0.0f, world_delta.y, world_delta.z));
237 return position + layer_delta;
238 };
239 }
240 case GP_LOCKAXIS_Y: {
241 return [=](const float3 &position, const float2 &screen_delta) {
242 const float3 world_pos = math::transform_point(layer_to_world, position);
243 const float3 world_delta = screen_to_world(world_pos, screen_delta);
244 const float3 layer_delta = math::transform_direction(
245 world_to_layer, float3(world_delta.x, 0.0f, world_delta.z));
246 return position + layer_delta;
247 };
248 }
249 case GP_LOCKAXIS_Z: {
250 return [=](const float3 &position, const float2 &screen_delta) {
251 const float3 world_pos = math::transform_point(layer_to_world, position);
252 const float3 world_delta = screen_to_world(world_pos, screen_delta);
253 const float3 layer_delta = math::transform_direction(
254 world_to_layer, float3(world_delta.x, world_delta.y, 0.0f));
255 return position + layer_delta;
256 };
257 }
258 case GP_LOCKAXIS_CURSOR: {
259 const float3 world_normal = params.scene.cursor.matrix<float3x3>().z_axis();
260 return [=](const float3 &position, const float2 &screen_delta) {
261 const float3 world_pos = math::transform_point(layer_to_world, position);
262 const float3 world_delta = screen_to_world(world_pos, screen_delta);
263 const float3 layer_delta = math::transform_direction(
264 world_to_layer, world_delta - world_normal * math::dot(world_delta, world_normal));
265 return position + layer_delta;
266 };
267 }
268 }
269
271 return [](const float3 &, const float2 &) { return float3(); };
272}
273
275 const Scene &scene,
276 Depsgraph &depsgraph,
279 Object &object,
280 const int layer_index,
281 const int frame_number,
282 const float multi_frame_falloff,
284{
286 GreasePencil &grease_pencil = *static_cast<GreasePencil *>(object.data);
287
288 const bke::greasepencil::Layer &layer = grease_pencil.layer(layer_index);
289 return {*scene.toolsettings,
290 region,
291 rv3d,
292 scene,
293 object,
294 ob_eval,
295 layer,
299 drawing};
300}
301
303 const bool use_masking,
304 IndexMaskMemory &memory)
305{
306
308 params.ob_orig, params.drawing, params.layer_index, memory) :
310 params.ob_orig, params.drawing, params.layer_index, memory));
311}
312
314 const bool use_masking,
315 IndexMaskMemory &memory)
316{
317
319 params.ob_orig, params.drawing, params.layer_index, memory) :
321 params.ob_orig, params.drawing, params.layer_index, memory));
322}
323
325 const bool use_masking,
326 IndexMaskMemory &memory)
327{
329 params.ob_orig, params.drawing, params.layer_index, memory) :
330 params.drawing.strokes().curves_range());
331}
332
339
341 const IndexMask &selection)
342{
344
345 Array<float2> view_positions(deformation.positions.size());
346
347 /* Compute screen space positions. */
348 const float4x4 transform = params.layer.to_world_space(params.ob_eval);
349 selection.foreach_index(GrainSize(4096), [&](const int64_t point_i) {
351 &params.region,
352 math::transform_point(transform, deformation.positions[point_i]),
353 view_positions[point_i],
355 if (result != V3D_PROJ_RET_OK) {
356 view_positions[point_i] = float2(0);
357 }
358 });
359
360 return view_positions;
361}
362
364 const IndexMask &selection)
365{
366 const RegionView3D *rv3d = static_cast<RegionView3D *>(params.region.regiondata);
368
369 const VArray<float> radii = params.drawing.radii();
370 Array<float> view_radii(radii.size());
371 /* Compute screen space radii. */
372 const float4x4 transform = params.layer.to_world_space(params.ob_eval);
373 selection.foreach_index(GrainSize(4096), [&](const int64_t point_i) {
374 const float pixel_size = ED_view3d_pixel_size(
375 rv3d, math::transform_point(transform, deformation.positions[point_i]));
376 view_radii[point_i] = radii[point_i] / pixel_size;
377 });
378
379 return view_radii;
380}
381
383{
384 return brush.gpencil_settings != nullptr &&
386}
387
388bool do_vertex_color_fill(const Brush &brush)
389{
390 return brush.gpencil_settings != nullptr &&
392}
393
395{
396 return is_brush_inverted(brush, this->stroke_mode);
397}
398
400{
401 return input_sample.mouse_position - this->prev_mouse_position;
402}
403
405 const bContext &C, FunctionRef<bool(const GreasePencilStrokeParams &params)> fn) const
406{
407 using namespace blender::bke::greasepencil;
408
409 const Scene &scene = *CTX_data_scene(&C);
410 Depsgraph &depsgraph = *CTX_data_depsgraph_pointer(&C);
411 ARegion &region = *CTX_wm_region(&C);
413 Object &object = *CTX_data_active_object(&C);
414 GreasePencil &grease_pencil = *static_cast<GreasePencil *>(object.data);
415
416 std::atomic<bool> changed = false;
418 for (const int64_t i : drawings.index_range()) {
419 const MutableDrawingInfo &info = drawings[i];
421 scene,
422 depsgraph,
423 region,
424 rv3d,
425 object,
426 info.layer_index,
427 info.frame_number,
429 info.drawing);
430 if (fn(params)) {
431 changed = true;
432 }
433 }
434
435 if (changed) {
436 DEG_id_tag_update(&grease_pencil.id, ID_RECALC_GEOMETRY);
437 WM_event_add_notifier(&C, NC_GEOM | ND_DATA, &grease_pencil);
438 }
439}
440
442 const bContext &C,
443 const GrainSize grain_size,
444 FunctionRef<bool(const GreasePencilStrokeParams &params)> fn) const
445{
446 using namespace blender::bke::greasepencil;
447
448 const Scene &scene = *CTX_data_scene(&C);
449 Depsgraph &depsgraph = *CTX_data_depsgraph_pointer(&C);
450 ARegion &region = *CTX_wm_region(&C);
452 Object &object = *CTX_data_active_object(&C);
453 GreasePencil &grease_pencil = *static_cast<GreasePencil *>(object.data);
454
455 std::atomic<bool> changed = false;
457 threading::parallel_for(drawings.index_range(), grain_size.value, [&](const IndexRange range) {
458 for (const int64_t i : range) {
459 const MutableDrawingInfo &info = drawings[i];
460 GreasePencilStrokeParams params = GreasePencilStrokeParams::from_context(
461 scene,
462 depsgraph,
463 region,
464 rv3d,
465 object,
466 info.layer_index,
467 info.frame_number,
468 info.multi_frame_falloff,
469 info.drawing);
470 if (fn(params)) {
471 changed = true;
472 }
473 }
474 });
475
476 if (changed) {
477 DEG_id_tag_update(&grease_pencil.id, ID_RECALC_GEOMETRY);
478 WM_event_add_notifier(&C, NC_GEOM | ND_DATA, &grease_pencil);
479 }
480}
481
483 const bContext &C,
485 const DeltaProjectionFunc &projection_fn)> fn) const
486{
487 using namespace blender::bke::greasepencil;
488
489 const Scene &scene = *CTX_data_scene(&C);
490 Depsgraph &depsgraph = *CTX_data_depsgraph_pointer(&C);
491 ARegion &region = *CTX_wm_region(&C);
493 Object &object = *CTX_data_active_object(&C);
494 Object &object_eval = *DEG_get_evaluated_object(&depsgraph, &object);
495 GreasePencil &grease_pencil = *static_cast<GreasePencil *>(object.data);
496
497 std::atomic<bool> changed = false;
499 threading::parallel_for_each(drawings, [&](const MutableDrawingInfo &info) {
500 const Layer &layer = grease_pencil.layer(info.layer_index);
501
503 scene,
504 depsgraph,
505 region,
506 rv3d,
507 object,
508 info.layer_index,
509 info.frame_number,
511 info.drawing);
512 const DeltaProjectionFunc projection_fn = get_screen_projection_fn(params, object_eval, layer);
513 if (fn(params, projection_fn)) {
514 changed = true;
515 }
516 });
517
518 if (changed) {
519 DEG_id_tag_update(&grease_pencil.id, ID_RECALC_GEOMETRY);
520 WM_event_add_notifier(&C, NC_GEOM | ND_DATA, &grease_pencil);
521 }
522}
523
525 const InputSample &start_sample)
526{
528 Brush &brush = *BKE_paint_brush(&paint);
529
530 init_brush(brush);
531
532 this->start_mouse_position = start_sample.mouse_position;
533 this->prev_mouse_position = start_sample.mouse_position;
534}
535
537{
538 this->prev_mouse_position = extension_sample.mouse_position;
539}
540
541} // namespace blender::ed::sculpt_paint::greasepencil
bool BKE_brush_use_alpha_pressure(const Brush *brush)
Definition brush.cc:1096
int BKE_brush_size_get(const Scene *scene, const Brush *brush)
Definition brush.cc:1075
float BKE_brush_curve_strength(eBrushCurvePreset preset, const CurveMapping *cumap, float distance, float brush_radius)
Definition brush.cc:1388
bool BKE_brush_use_size_pressure(const Brush *brush)
Definition brush.cc:1091
void BKE_brush_init_gpencil_settings(Brush *brush)
Definition brush.cc:563
float BKE_brush_alpha_get(const Scene *scene, const Brush *brush)
Definition brush.cc:1153
float BKE_curvemapping_evaluateF(const CurveMapping *cumap, int cur, float value)
void BKE_curvemapping_init(CurveMapping *cumap)
Depsgraph * CTX_data_depsgraph_pointer(const bContext *C)
Object * CTX_data_active_object(const bContext *C)
Scene * CTX_data_scene(const bContext *C)
RegionView3D * CTX_wm_region_view3d(const bContext *C)
ARegion * CTX_wm_region(const bContext *C)
Low-level operations for curves.
Low-level operations for grease pencil.
Paint * BKE_paint_get_active_from_context(const bContext *C)
Definition paint.cc:477
Brush * BKE_paint_brush(Paint *paint)
Definition paint.cc:649
#define BLI_assert_unreachable()
Definition BLI_assert.h:97
#define BLI_assert(a)
Definition BLI_assert.h:50
#define ELEM(...)
void DEG_id_tag_update(ID *id, unsigned int flags)
Object * DEG_get_evaluated_object(const Depsgraph *depsgraph, Object *object)
@ ID_RECALC_GEOMETRY
Definition DNA_ID.h:1041
@ GP_BRUSH_MODE_VERTEXCOLOR
@ GP_BRUSH_MODE_ACTIVE
@ GP_BRUSH_ACTIVE_LAYER_ONLY
@ BRUSH_DIR_IN
@ GPPAINT_MODE_STROKE
@ GPPAINT_MODE_FILL
@ GPPAINT_MODE_BOTH
@ GPPAINT_FLAG_USE_VERTEXCOLOR
@ GP_LOCKAXIS_X
@ GP_LOCKAXIS_VIEW
@ GP_LOCKAXIS_Y
@ GP_LOCKAXIS_Z
@ GP_LOCKAXIS_CURSOR
@ V3D_PROJ_TEST_NOP
Definition ED_view3d.hh:275
float ED_view3d_pixel_size(const RegionView3D *rv3d, const float co[3])
eV3DProjStatus
Definition ED_view3d.hh:251
@ V3D_PROJ_RET_OK
Definition ED_view3d.hh:252
void ED_view3d_win_to_delta(const ARegion *region, const float xy_delta[2], float zfac, float r_out[3])
float ED_view3d_calc_zfac(const RegionView3D *rv3d, const float co[3])
eV3DProjStatus ED_view3d_project_float_global(const ARegion *region, const float co[3], float r_co[2], eV3DProjTest flag)
in reality light always falls off quadratically Particle Retrieve the data of the particle that spawned the object for example to give variation to multiple instances of an object Point Retrieve information about points in a point cloud Retrieve the edges of an object as it appears to Cycles topology will always appear triangulated Convert a blackbody temperature to an RGB value Normal Generate a perturbed normal from an RGB normal map image Typically used for faking highly detailed surfaces Generate an OSL shader from a file or text data block Image Sample an image file as a texture Gabor Generate Gabor noise Gradient Generate interpolated color and intensity values based on the input vector Magic Generate a psychedelic color texture Voronoi Generate Worley noise based on the distance to random points Typically used to generate textures such as or biological cells Brick Generate a procedural texture producing bricks Texture Retrieve multiple types of texture coordinates nTypically used as inputs for texture nodes Vector Convert a point
#define C
Definition RandGen.cpp:29
#define NC_GEOM
Definition WM_types.hh:360
#define ND_DATA
Definition WM_types.hh:475
BPy_StructRNA * depsgraph
Span< T > as_span() const
Definition BLI_array.hh:232
static IndexMask from_predicate(const IndexMask &universe, GrainSize grain_size, IndexMaskMemory &memory, Fn &&predicate)
IndexRange index_range() const
void resize(const int64_t new_size)
MutableSpan< T > as_mutable_span()
float4x4 to_world_space(const Object &object) const
void foreach_editable_drawing(const bContext &C, FunctionRef< bool(const GreasePencilStrokeParams &params)> fn) const
static float verts[][3]
uiWidgetBaseParameters params[MAX_WIDGET_BASE_BATCH]
void gather(const GVArray &src, const IndexMask &indices, GMutableSpan dst, int64_t grain_size=4096)
GeometryDeformation get_evaluated_grease_pencil_drawing_deformation(const Object *ob_eval, const Object &ob_orig, int layer_index, int frame)
IndexMask retrieve_editable_and_selected_strokes(Object &object, const bke::greasepencil::Drawing &drawing, int layer_index, IndexMaskMemory &memory)
IndexMask retrieve_editable_points(Object &object, const bke::greasepencil::Drawing &drawing, int layer_index, IndexMaskMemory &memory)
IndexMask retrieve_editable_and_selected_fill_strokes(Object &object, const bke::greasepencil::Drawing &drawing, int layer_index, IndexMaskMemory &memory)
IndexMask retrieve_editable_and_selected_points(Object &object, const bke::greasepencil::Drawing &drawing, int layer_index, IndexMaskMemory &memory)
Vector< MutableDrawingInfo > retrieve_editable_drawings_from_layer_with_falloff(const Scene &scene, GreasePencil &grease_pencil, const blender::bke::greasepencil::Layer &layer)
Vector< MutableDrawingInfo > retrieve_editable_drawings_with_falloff(const Scene &scene, GreasePencil &grease_pencil)
IndexMask retrieve_editable_strokes(Object &object, const bke::greasepencil::Drawing &drawing, int layer_index, IndexMaskMemory &memory)
bool is_brush_inverted(const Brush &brush, BrushStrokeMode stroke_mode)
float closest_distance_to_surface_2d(const float2 pt, const Span< float2 > verts)
Array< float > calculate_view_radii(const GreasePencilStrokeParams &params, const IndexMask &selection)
Vector< ed::greasepencil::MutableDrawingInfo > get_drawings_for_painting(const bContext &C)
IndexMask point_selection_mask(const GreasePencilStrokeParams &params, const bool use_masking, IndexMaskMemory &memory)
Array< float2 > calculate_view_positions(const GreasePencilStrokeParams &params, const IndexMask &selection)
IndexMask fill_selection_mask(const GreasePencilStrokeParams &params, const bool use_masking, IndexMaskMemory &memory)
bool brush_using_vertex_color(const GpPaint *gp_paint, const Brush *brush)
IndexMask brush_point_influence_mask(const Scene &scene, const Brush &brush, const float2 &mouse_position, float pressure, float multi_frame_falloff, const IndexMask &selection, Span< float2 > view_positions, Vector< float > &influences, IndexMaskMemory &memory)
float brush_point_influence(const Scene &scene, const Brush &brush, const float2 &co, const InputSample &sample, float multi_frame_falloff)
IndexMask stroke_selection_mask(const GreasePencilStrokeParams &params, const bool use_masking, IndexMaskMemory &memory)
float brush_fill_influence(const Scene &scene, const Brush &brush, Span< float2 > fill_positions, const InputSample &sample, float multi_frame_falloff)
bke::crazyspace::GeometryDeformation get_drawing_deformation(const GreasePencilStrokeParams &params)
DeltaProjectionFunc get_screen_projection_fn(const GreasePencilStrokeParams &params, const Object &object, const bke::greasepencil::Layer &layer)
float brush_radius(const Scene &scene, const Brush &brush, float pressure)
std::function< float3(const float3 position, const float2 &screen_delta)> DeltaProjectionFunc
T sqrt(const T &a)
T distance(const T &a, const T &b)
T dot(const QuaternionBase< T > &a, const QuaternionBase< T > &b)
T min(const T &a, const T &b)
CartesianBasis invert(const CartesianBasis &basis)
T distance_squared(const VecBase< T, Size > &a, const VecBase< T, Size > &b)
VecBase< T, 3 > transform_direction(const MatBase< T, 3, 3 > &mat, const VecBase< T, 3 > &direction)
T round(const T &a)
VecBase< T, 3 > transform_point(const CartesianBasis &basis, const VecBase< T, 3 > &v)
void parallel_for_each(Range &&range, const Function &function)
Definition BLI_task.hh:58
void parallel_for(const IndexRange range, const int64_t grain_size, const Function &function, const TaskSizeHints &size_hints=detail::TaskSizeHints_Static(1))
Definition BLI_task.hh:95
MatBase< float, 4, 4 > float4x4
VecBase< int32_t, 2 > int2
VecBase< float, 2 > float2
MatBase< float, 3, 3 > float3x3
VecBase< float, 3 > float3
float distance(float a, float b)
GPU_SHADER_INTERFACE_INFO(overlay_edit_curve_handle_iface, "vert").flat(Type pos vertex_in(1, Type::UINT, "data") .vertex_out(overlay_edit_curve_handle_iface) .geometry_layout(PrimitiveIn Frequency::GEOMETRY storage_buf(1, Qualifier::READ, "uint", "data[]", Frequency::GEOMETRY) .push_constant(Type Frequency::GEOMETRY selection[]
BrushStrokeMode
@ BRUSH_STROKE_INVERT
#define FLT_MAX
Definition stdcycles.h:14
__int64 int64_t
Definition stdint.h:89
struct CurveMapping * curve_sensitivity
struct CurveMapping * curve_strength
struct CurveMapping * curve_jitter
struct CurveMapping * curve_rand_pressure
struct CurveMapping * curve_rand_strength
struct CurveMapping * curve_rand_saturation
struct CurveMapping * curve_rand_hue
struct CurveMapping * curve_rand_uv
struct CurveMapping * curve_rand_value
struct CurveMapping * curve
struct BrushGpencilSettings * gpencil_settings
static GreasePencilStrokeParams from_context(const Scene &scene, Depsgraph &depsgraph, ARegion &region, RegionView3D &rv3d, Object &object, int layer_index, int frame_number, float multi_frame_falloff, bke::greasepencil::Drawing &drawing)
void WM_event_add_notifier(const bContext *C, uint type, void *reference)