Blender  V2.93
sculpt_detail.c
Go to the documentation of this file.
1 /*
2  * This program is free software; you can redistribute it and/or
3  * modify it under the terms of the GNU General Public License
4  * as published by the Free Software Foundation; either version 2
5  * of the License, or (at your option) any later version.
6  *
7  * This program is distributed in the hope that it will be useful,
8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
10  * GNU General Public License for more details.
11  *
12  * You should have received a copy of the GNU General Public License
13  * along with this program; if not, write to the Free Software Foundation,
14  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
15  *
16  * The Original Code is Copyright (C) 2020 Blender Foundation.
17  * All rights reserved.
18  */
19 
24 #include "MEM_guardedalloc.h"
25 
26 #include "BLI_blenlib.h"
27 #include "BLI_math.h"
28 
29 #include "BLT_translation.h"
30 
31 #include "DNA_mesh_types.h"
32 
33 #include "BKE_context.h"
34 #include "BKE_paint.h"
35 #include "BKE_pbvh.h"
36 #include "BKE_screen.h"
37 
38 #include "DEG_depsgraph.h"
39 
40 #include "GPU_immediate.h"
41 #include "GPU_immediate_util.h"
42 #include "GPU_matrix.h"
43 #include "GPU_state.h"
44 
45 #include "WM_api.h"
46 #include "WM_types.h"
47 
48 #include "ED_screen.h"
49 #include "ED_sculpt.h"
50 #include "ED_space_api.h"
51 #include "ED_view3d.h"
52 #include "sculpt_intern.h"
53 
54 #include "RNA_access.h"
55 #include "RNA_define.h"
56 
57 #include <math.h>
58 #include <stdlib.h>
59 
60 typedef struct {
61  const float *ray_start;
62  bool hit;
63  float depth;
64  float edge_length;
65 
66  struct IsectRayPrecalc isect_precalc;
68 
70 {
73 
74  return SCULPT_mode_poll(C) && ob->sculpt->bm &&
76 }
77 
79 {
81 
82  return SCULPT_mode_poll(C) && ob->sculpt->bm;
83 }
84 
86 {
89  SculptSession *ss = ob->sculpt;
90  float size;
91  float bb_min[3], bb_max[3], center[3], dim[3];
92  int totnodes;
93  PBVHNode **nodes;
94 
95  BKE_pbvh_search_gather(ss->pbvh, NULL, NULL, &nodes, &totnodes);
96 
97  if (!totnodes) {
98  return OPERATOR_CANCELLED;
99  }
100 
101  for (int i = 0; i < totnodes; i++) {
103  }
104  /* Get the bounding box, its center and size. */
105  BKE_pbvh_bounding_box(ob->sculpt->pbvh, bb_min, bb_max);
106  add_v3_v3v3(center, bb_min, bb_max);
107  mul_v3_fl(center, 0.5f);
108  sub_v3_v3v3(dim, bb_max, bb_min);
109  size = max_fff(dim[0], dim[1], dim[2]);
110 
111  /* Update topology size. */
112  float object_space_constant_detail = 1.0f / (sd->constant_detail * mat4_to_scale(ob->obmat));
113  BKE_pbvh_bmesh_detail_size_set(ss->pbvh, object_space_constant_detail);
114 
115  SCULPT_undo_push_begin(ob, "Dynamic topology flood fill");
117 
119  ss->pbvh, PBVH_Collapse | PBVH_Subdivide, center, NULL, size, false, false)) {
120  for (int i = 0; i < totnodes; i++) {
122  }
123  }
124 
125  MEM_SAFE_FREE(nodes);
127 
128  /* Force rebuild of PBVH for better BB placement. */
129  SCULPT_pbvh_clear(ob);
130  /* Redraw. */
132 
133  return OPERATOR_FINISHED;
134 }
135 
137 {
138  /* Identifiers. */
139  ot->name = "Detail Flood Fill";
140  ot->idname = "SCULPT_OT_detail_flood_fill";
141  ot->description = "Flood fill the mesh with the selected detail setting";
142 
143  /* API callbacks. */
146 
148 }
149 
154 
156  {SAMPLE_DETAIL_DYNTOPO, "DYNTOPO", 0, "Dyntopo", "Sample dyntopo detail"},
157  {SAMPLE_DETAIL_VOXEL, "VOXEL", 0, "Voxel", "Sample mesh voxel size"},
158  {0, NULL, 0, NULL, NULL},
159 };
160 
161 static void sample_detail_voxel(bContext *C, ViewContext *vc, int mx, int my)
162 {
164  Object *ob = vc->obact;
165  Mesh *mesh = ob->data;
166 
167  SculptSession *ss = ob->sculpt;
170 
171  /* Update the active vertex. */
172  const float mouse[2] = {mx, my};
173  SCULPT_cursor_geometry_info_update(C, &sgi, mouse, false);
174  BKE_sculpt_update_object_for_edit(depsgraph, ob, true, false, false);
175 
176  /* Average the edge length of the connected edges to the active vertex. */
177  int active_vertex = SCULPT_active_vertex_get(ss);
178  const float *active_vertex_co = SCULPT_active_vertex_co_get(ss);
179  float edge_length = 0.0f;
180  int tot = 0;
182  SCULPT_VERTEX_NEIGHBORS_ITER_BEGIN (ss, active_vertex, ni) {
183  edge_length += len_v3v3(active_vertex_co, SCULPT_vertex_co_get(ss, ni.index));
184  tot += 1;
185  }
187  if (tot > 0) {
188  mesh->remesh_voxel_size = edge_length / (float)tot;
189  }
190 }
191 
192 static void sculpt_raycast_detail_cb(PBVHNode *node, void *data_v, float *tmin)
193 {
194  if (BKE_pbvh_node_get_tmin(node) < *tmin) {
195  SculptDetailRaycastData *srd = data_v;
197  node, srd->ray_start, &srd->isect_precalc, &srd->depth, &srd->edge_length)) {
198  srd->hit = true;
199  *tmin = srd->depth;
200  }
201  }
202 }
203 
204 static void sample_detail_dyntopo(bContext *C, ViewContext *vc, ARegion *region, int mx, int my)
205 {
207  Object *ob = vc->obact;
208  Brush *brush = BKE_paint_brush(&sd->paint);
209 
210  SCULPT_stroke_modifiers_check(C, ob, brush);
211 
212  const float mouse[2] = {mx - region->winrct.xmin, my - region->winrct.ymin};
213  float ray_start[3], ray_end[3], ray_normal[3];
214  float depth = SCULPT_raycast_init(vc, mouse, ray_start, ray_end, ray_normal, false);
215 
217  srd.hit = 0;
218  srd.ray_start = ray_start;
219  srd.depth = depth;
220  srd.edge_length = 0.0f;
222 
223  BKE_pbvh_raycast(ob->sculpt->pbvh, sculpt_raycast_detail_cb, &srd, ray_start, ray_normal, false);
224 
225  if (srd.hit && srd.edge_length > 0.0f) {
226  /* Convert edge length to world space detail resolution. */
227  sd->constant_detail = 1 / (srd.edge_length * mat4_to_scale(ob->obmat));
228  }
229 }
230 
231 static int sample_detail(bContext *C, int mx, int my, int mode)
232 {
233  /* Find 3D view to pick from. */
234  bScreen *screen = CTX_wm_screen(C);
235  ScrArea *area = BKE_screen_find_area_xy(screen, SPACE_VIEW3D, mx, my);
236  ARegion *region = (area) ? BKE_area_find_region_xy(area, RGN_TYPE_WINDOW, mx, my) : NULL;
237  if (region == NULL) {
238  return OPERATOR_CANCELLED;
239  }
240 
241  /* Set context to 3D view. */
242  ScrArea *prev_area = CTX_wm_area(C);
243  ARegion *prev_region = CTX_wm_region(C);
245  CTX_wm_region_set(C, region);
246 
248  ViewContext vc;
250 
251  Object *ob = vc.obact;
252  if (ob == NULL) {
253  return OPERATOR_CANCELLED;
254  }
255 
256  SculptSession *ss = ob->sculpt;
257  if (!ss->pbvh) {
258  return OPERATOR_CANCELLED;
259  }
260 
261  /* Pick sample detail. */
262  switch (mode) {
264  if (BKE_pbvh_type(ss->pbvh) != PBVH_BMESH) {
265  CTX_wm_area_set(C, prev_area);
266  CTX_wm_region_set(C, prev_region);
267  return OPERATOR_CANCELLED;
268  }
269  sample_detail_dyntopo(C, &vc, region, mx, my);
270  break;
271  case SAMPLE_DETAIL_VOXEL:
272  if (BKE_pbvh_type(ss->pbvh) != PBVH_FACES) {
273  CTX_wm_area_set(C, prev_area);
274  CTX_wm_region_set(C, prev_region);
275  return OPERATOR_CANCELLED;
276  }
277  sample_detail_voxel(C, &vc, mx, my);
278  break;
279  }
280 
281  /* Restore context. */
282  CTX_wm_area_set(C, prev_area);
283  CTX_wm_region_set(C, prev_region);
284 
285  return OPERATOR_FINISHED;
286 }
287 
289 {
290  int ss_co[2];
291  RNA_int_get_array(op->ptr, "location", ss_co);
292  int mode = RNA_enum_get(op->ptr, "mode");
293  return sample_detail(C, ss_co[0], ss_co[1], mode);
294 }
295 
297 {
298  ED_workspace_status_text(C, TIP_("Click on the mesh to set the detail"));
301  return OPERATOR_RUNNING_MODAL;
302 }
303 
305 {
306  switch (event->type) {
307  case LEFTMOUSE:
308  if (event->val == KM_PRESS) {
309  const int ss_co[2] = {event->x, event->y};
310 
311  int mode = RNA_enum_get(op->ptr, "mode");
312  sample_detail(C, ss_co[0], ss_co[1], mode);
313 
314  RNA_int_set_array(op->ptr, "location", ss_co);
318 
319  return OPERATOR_FINISHED;
320  }
321  break;
322  case EVT_ESCKEY:
323  case RIGHTMOUSE: {
326 
327  return OPERATOR_CANCELLED;
328  }
329  }
330 
331  return OPERATOR_RUNNING_MODAL;
332 }
333 
335 {
336  /* Identifiers. */
337  ot->name = "Sample Detail Size";
338  ot->idname = "SCULPT_OT_sample_detail_size";
339  ot->description = "Sample the mesh detail on clicked point";
340 
341  /* API callbacks. */
346 
348 
350  "location",
351  2,
352  NULL,
353  0,
354  SHRT_MAX,
355  "Location",
356  "Screen coordinates of sampling",
357  0,
358  SHRT_MAX);
360  "mode",
363  "Detail Mode",
364  "Target sculpting workflow that is going to use the sampled size");
365 }
366 
367 /* Dynamic-topology detail size.
368  *
369  * Currently, there are two operators editing the detail size:
370  * - SCULPT_OT_set_detail_size uses radial control for all methods
371  * - SCULPT_OT_dyntopo_detail_size_edit shows a triangle grid representation of the detail
372  * resolution (for constant detail method, falls back to radial control for the remaining methods).
373  */
374 
375 static void set_brush_rc_props(PointerRNA *ptr, const char *prop)
376 {
377  char *path = BLI_sprintfN("tool_settings.sculpt.brush.%s", prop);
378  RNA_string_set(ptr, "data_path_primary", path);
379  MEM_freeN(path);
380 }
381 
383 {
385 
386  PointerRNA props_ptr;
387  wmOperatorType *ot = WM_operatortype_find("WM_OT_radial_control", true);
388 
390 
392  set_brush_rc_props(&props_ptr, "constant_detail_resolution");
394  &props_ptr, "data_path_primary", "tool_settings.sculpt.constant_detail_resolution");
395  }
396  else if (sd->flags & SCULPT_DYNTOPO_DETAIL_BRUSH) {
397  set_brush_rc_props(&props_ptr, "constant_detail_resolution");
398  RNA_string_set(&props_ptr, "data_path_primary", "tool_settings.sculpt.detail_percent");
399  }
400  else {
401  set_brush_rc_props(&props_ptr, "detail_size");
402  RNA_string_set(&props_ptr, "data_path_primary", "tool_settings.sculpt.detail_size");
403  }
404 
406 
407  WM_operator_properties_free(&props_ptr);
408 }
409 
411 {
413 
414  return OPERATOR_FINISHED;
415 }
416 
418 {
419  /* Identifiers. */
420  ot->name = "Set Detail Size";
421  ot->idname = "SCULPT_OT_set_detail_size";
422  ot->description =
423  "Set the mesh detail (either relative or constant one, depending on current dyntopo mode)";
424 
425  /* API callbacks. */
428 
430 }
431 
432 /* -------------------------------------------------------------------- */
436 /* Defines how much the mouse movement will modify the detail size value. */
437 #define DETAIL_SIZE_DELTA_SPEED 0.08f
438 #define DETAIL_SIZE_DELTA_ACCURATE_SPEED 0.004f
439 
441  void *draw_handle;
443 
444  float init_mval[2];
445  float accurate_mval[2];
446 
447  float outline_col[4];
448 
451 
454  float detail_size;
455  float radius;
456 
457  float preview_tri[3][3];
458  float gizmo_mat[4][4];
460 
463  const float start_co[3],
464  const float end_co[3],
465  bool flip,
466  const float angle)
467 {
468  float object_space_constant_detail = 1.0f /
470 
471  /* The constant detail represents the maximum edge length allowed before subdividing it. If the
472  * triangle grid preview is created with this value it will represent an ideal mesh density where
473  * all edges have the exact maximum length, which never happens in practice. As the minimum edge
474  * length for dyntopo is 0.4 * max_edge_length, this adjust the detail size to the average
475  * between max and min edge length so the preview is more accurate. */
476  object_space_constant_detail *= 0.7f;
477 
478  const float total_len = len_v3v3(cd->preview_tri[0], cd->preview_tri[1]);
479  const int tot_lines = (int)(total_len / object_space_constant_detail) + 1;
480  const float tot_lines_fl = total_len / object_space_constant_detail;
481  float spacing_disp[3];
482  sub_v3_v3v3(spacing_disp, end_co, start_co);
483  normalize_v3(spacing_disp);
484 
485  float line_disp[3];
486  rotate_v2_v2fl(line_disp, spacing_disp, DEG2RAD(angle));
487  mul_v3_fl(spacing_disp, total_len / tot_lines_fl);
488 
489  immBegin(GPU_PRIM_LINES, (uint)tot_lines * 2);
490  for (int i = 0; i < tot_lines; i++) {
491  float line_length;
492  if (flip) {
493  line_length = total_len * ((float)i / (float)tot_lines_fl);
494  }
495  else {
496  line_length = total_len * (1.0f - ((float)i / (float)tot_lines_fl));
497  }
498  float line_start[3];
499  copy_v3_v3(line_start, start_co);
500  madd_v3_v3v3fl(line_start, line_start, spacing_disp, i);
501  float line_end[3];
502  madd_v3_v3v3fl(line_end, line_start, line_disp, line_length);
503  immVertex3fv(pos3d, line_start);
504  immVertex3fv(pos3d, line_end);
505  }
506  immEnd();
507 }
508 
510  ARegion *UNUSED(ar),
511  void *arg)
512 {
515  GPU_line_smooth(true);
516 
519  GPU_matrix_push();
521 
522  /* Draw Cursor */
524  GPU_line_width(3.0f);
525 
526  imm_draw_circle_wire_3d(pos3d, 0, 0, cd->radius, 80);
527 
528  /* Draw Triangle. */
529  immUniformColor4f(0.9f, 0.9f, 0.9f, 0.8f);
531  immVertex3fv(pos3d, cd->preview_tri[0]);
532  immVertex3fv(pos3d, cd->preview_tri[1]);
533 
534  immVertex3fv(pos3d, cd->preview_tri[1]);
535  immVertex3fv(pos3d, cd->preview_tri[2]);
536 
537  immVertex3fv(pos3d, cd->preview_tri[2]);
538  immVertex3fv(pos3d, cd->preview_tri[0]);
539  immEnd();
540 
541  /* Draw Grid */
542  GPU_line_width(1.0f);
544  pos3d, cd, cd->preview_tri[0], cd->preview_tri[1], false, 60.0f);
546  pos3d, cd, cd->preview_tri[0], cd->preview_tri[1], true, 120.0f);
548  pos3d, cd, cd->preview_tri[0], cd->preview_tri[2], false, -60.0f);
549 
551  GPU_matrix_pop();
553  GPU_line_smooth(false);
554 }
555 
557 {
558  Object *active_object = CTX_data_active_object(C);
559  SculptSession *ss = active_object->sculpt;
560  ARegion *region = CTX_wm_region(C);
563  ss->draw_faded_cursor = false;
564  MEM_freeN(op->customdata);
566 }
567 
570 {
571  SculptSession *ss = ob->sculpt;
572  const int active_vertex = SCULPT_active_vertex_get(ss);
573 
574  float len_accum = 0;
575  int num_neighbors = 0;
577  SCULPT_VERTEX_NEIGHBORS_ITER_BEGIN (ss, active_vertex, ni) {
578  len_accum += len_v3v3(SCULPT_vertex_co_get(ss, active_vertex),
579  SCULPT_vertex_co_get(ss, ni.index));
580  num_neighbors++;
581  }
583 
584  if (num_neighbors > 0) {
585  const float avg_edge_len = len_accum / num_neighbors;
586  /* Use 0.7 as the average of min and max dyntopo edge length. */
587  const float detail_size = 0.7f / (avg_edge_len * mat4_to_scale(cd->active_object->obmat));
588  cd->detail_size = clamp_f(detail_size, 1.0f, 500.0f);
589  }
590 }
591 
593  const wmEvent *event)
594 {
595  const float mval[2] = {event->mval[0], event->mval[1]};
596 
597  float detail_size_delta;
598  if (cd->accurate_mode) {
599  detail_size_delta = mval[0] - cd->accurate_mval[0];
601  detail_size_delta * DETAIL_SIZE_DELTA_ACCURATE_SPEED;
602  }
603  else {
604  detail_size_delta = mval[0] - cd->init_mval[0];
605  cd->detail_size = cd->init_detail_size + detail_size_delta * DETAIL_SIZE_DELTA_SPEED;
606  }
607 
608  if (event->type == EVT_LEFTSHIFTKEY && event->val == KM_PRESS) {
609  cd->accurate_mode = true;
610  copy_v2_v2(cd->accurate_mval, mval);
612  }
613  if (event->type == EVT_LEFTSHIFTKEY && event->val == KM_RELEASE) {
614  cd->accurate_mode = false;
615  cd->accurate_detail_size = 0.0f;
616  }
617 
618  cd->detail_size = clamp_f(cd->detail_size, 1.0f, 500.0f);
619 }
620 
622 {
623  Object *active_object = CTX_data_active_object(C);
624  SculptSession *ss = active_object->sculpt;
625  ARegion *region = CTX_wm_region(C);
628 
629  /* Cancel modal operator */
630  if ((event->type == EVT_ESCKEY && event->val == KM_PRESS) ||
631  (event->type == RIGHTMOUSE && event->val == KM_PRESS)) {
633  ED_region_tag_redraw(region);
634  return OPERATOR_FINISHED;
635  }
636 
637  /* Finish modal operator */
638  if ((event->type == LEFTMOUSE && event->val == KM_RELEASE) ||
639  (event->type == EVT_RETKEY && event->val == KM_PRESS) ||
640  (event->type == EVT_PADENTER && event->val == KM_PRESS)) {
642  sd->constant_detail = cd->detail_size;
643  ss->draw_faded_cursor = false;
644  MEM_freeN(op->customdata);
645  ED_region_tag_redraw(region);
647  return OPERATOR_FINISHED;
648  }
649 
650  ED_region_tag_redraw(region);
651 
652  if (event->type == EVT_LEFTCTRLKEY && event->val == KM_PRESS) {
653  cd->sample_mode = true;
654  }
655  if (event->type == EVT_LEFTCTRLKEY && event->val == KM_RELEASE) {
656  cd->sample_mode = false;
657  }
658 
659  /* Sample mode sets the detail size sampling the average edge length under the surface. */
660  if (cd->sample_mode) {
661  dyntopo_detail_size_sample_from_surface(active_object, cd);
662  return OPERATOR_RUNNING_MODAL;
663  }
664  /* Regular mode, changes the detail size by moving the cursor. */
666 
667  return OPERATOR_RUNNING_MODAL;
668 }
669 
671 {
673 
674  /* Fallback to radial control for modes other than SCULPT_DYNTOPO_DETAIL_CONSTANT [same as in
675  * SCULPT_OT_set_detail_size]. */
678 
679  return OPERATOR_FINISHED;
680  }
681 
682  /* Special method for SCULPT_DYNTOPO_DETAIL_CONSTANT. */
683  ARegion *region = CTX_wm_region(C);
684  Object *active_object = CTX_data_active_object(C);
685  Brush *brush = BKE_paint_brush(&sd->paint);
686 
688  "Dyntopo Detail Size Edit OP Custom Data");
689 
690  /* Initial operator Custom Data setup. */
693  cd->active_object = active_object;
694  cd->init_mval[0] = event->mval[0];
695  cd->init_mval[1] = event->mval[1];
696  cd->detail_size = sd->constant_detail;
698  copy_v4_v4(cd->outline_col, brush->add_col);
699  op->customdata = cd;
700 
701  SculptSession *ss = active_object->sculpt;
702  cd->radius = ss->cursor_radius;
703 
704  /* Generates the matrix to position the gizmo in the surface of the mesh using the same location
705  * and orientation as the brush cursor. */
706  float cursor_trans[4][4], cursor_rot[4][4];
707  const float z_axis[4] = {0.0f, 0.0f, 1.0f, 0.0f};
708  float quat[4];
709  copy_m4_m4(cursor_trans, active_object->obmat);
710  translate_m4(
711  cursor_trans, ss->cursor_location[0], ss->cursor_location[1], ss->cursor_location[2]);
712 
713  float cursor_normal[3];
714  if (!is_zero_v3(ss->cursor_sampled_normal)) {
715  copy_v3_v3(cursor_normal, ss->cursor_sampled_normal);
716  }
717  else {
718  copy_v3_v3(cursor_normal, ss->cursor_normal);
719  }
720 
721  rotation_between_vecs_to_quat(quat, z_axis, cursor_normal);
722  quat_to_mat4(cursor_rot, quat);
723  copy_m4_m4(cd->gizmo_mat, cursor_trans);
724  mul_m4_m4_post(cd->gizmo_mat, cursor_rot);
725 
726  /* Initialize the position of the triangle vertices. */
727  const float y_axis[3] = {0.0f, cd->radius, 0.0f};
728  for (int i = 0; i < 3; i++) {
729  zero_v3(cd->preview_tri[i]);
730  rotate_v2_v2fl(cd->preview_tri[i], y_axis, DEG2RAD(120.0f * i));
731  }
732 
734 
736  ED_region_tag_redraw(region);
737 
738  ss->draw_faded_cursor = true;
739 
740  const char *status_str = TIP_(
741  "Move the mouse to change the dyntopo detail size. LMB: confirm size, ESC/RMB: cancel");
742  ED_workspace_status_text(C, status_str);
743 
744  return OPERATOR_RUNNING_MODAL;
745 }
746 
748 {
749  /* identifiers */
750  ot->name = "Edit Dyntopo Detail Size";
751  ot->description = "Modify the detail size of dyntopo interactively";
752  ot->idname = "SCULPT_OT_dyntopo_detail_size_edit";
753 
754  /* api callbacks */
759 
761 }
typedef float(TangentPoint)[2]
struct ScrArea * CTX_wm_area(const bContext *C)
Definition: context.c:714
void CTX_wm_region_set(bContext *C, struct ARegion *region)
Definition: context.c:985
struct Depsgraph * CTX_data_ensure_evaluated_depsgraph(const bContext *C)
Definition: context.c:1424
struct Object * CTX_data_active_object(const bContext *C)
Definition: context.c:1279
struct bScreen * CTX_wm_screen(const bContext *C)
Definition: context.c:709
struct ARegion * CTX_wm_region(const bContext *C)
Definition: context.c:725
struct Depsgraph * CTX_data_depsgraph_pointer(const bContext *C)
Definition: context.c:1401
void CTX_wm_area_set(bContext *C, struct ScrArea *area)
Definition: context.c:973
struct ToolSettings * CTX_data_tool_settings(const bContext *C)
Definition: context.c:1208
struct wmWindow * CTX_wm_window(const bContext *C)
Definition: context.c:699
void BKE_sculpt_update_object_for_edit(struct Depsgraph *depsgraph, struct Object *ob_orig, bool need_pmap, bool need_mask, bool need_colors)
Definition: paint.c:1817
struct Brush * BKE_paint_brush(struct Paint *paint)
Definition: paint.c:604
A BVH for high poly meshes.
PBVHType BKE_pbvh_type(const PBVH *pbvh)
Definition: pbvh.c:1661
float BKE_pbvh_node_get_tmin(PBVHNode *node)
Definition: pbvh.c:954
bool BKE_pbvh_bmesh_update_topology(PBVH *pbvh, PBVHTopologyUpdateMode mode, const float center[3], const float view_normal[3], float radius, const bool use_frontface, const bool use_projected)
Definition: pbvh_bmesh.c:1957
void BKE_pbvh_raycast(PBVH *pbvh, BKE_pbvh_HitOccludedCallback cb, void *data, const float ray_start[3], const float ray_normal[3], bool original)
Definition: pbvh.c:2006
bool BKE_pbvh_bmesh_node_raycast_detail(PBVHNode *node, const float ray_start[3], struct IsectRayPrecalc *isect_precalc, float *depth, float *r_edge_length)
Definition: pbvh_bmesh.c:1572
@ PBVH_Collapse
Definition: BKE_pbvh.h:245
@ PBVH_Subdivide
Definition: BKE_pbvh.h:244
@ PBVH_BMESH
Definition: BKE_pbvh.h:212
@ PBVH_FACES
Definition: BKE_pbvh.h:210
void BKE_pbvh_bounding_box(const PBVH *pbvh, float min[3], float max[3])
Definition: pbvh.c:1675
void BKE_pbvh_bmesh_detail_size_set(PBVH *pbvh, float detail_size)
Definition: pbvh_bmesh.c:2110
void BKE_pbvh_node_mark_topology_update(PBVHNode *node)
Definition: pbvh_bmesh.c:2116
void BKE_pbvh_search_gather(PBVH *pbvh, BKE_pbvh_SearchCallback scb, void *search_data, PBVHNode ***array, int *tot)
Definition: pbvh.c:843
struct ScrArea * BKE_screen_find_area_xy(struct bScreen *screen, const int spacetype, int x, int y)
Definition: screen.c:1018
struct ARegion * BKE_area_find_region_xy(struct ScrArea *area, const int regiontype, int x, int y)
Definition: screen.c:933
MINLINE float max_fff(float a, float b, float c)
MINLINE float clamp_f(float value, float min, float max)
void isect_ray_tri_watertight_v3_precalc(struct IsectRayPrecalc *isect_precalc, const float ray_direction[3])
Definition: math_geom.c:1879
void translate_m4(float mat[4][4], float tx, float ty, float tz)
Definition: math_matrix.c:2325
void copy_m4_m4(float m1[4][4], const float m2[4][4])
Definition: math_matrix.c:95
float mat4_to_scale(const float M[4][4])
Definition: math_matrix.c:2196
void mul_m4_m4_post(float R[4][4], const float B[4][4])
Definition: math_matrix.c:383
void rotation_between_vecs_to_quat(float q[4], const float v1[3], const float v2[3])
#define DEG2RAD(_deg)
void quat_to_mat4(float mat[4][4], const float q[4])
MINLINE void copy_v4_v4(float r[4], const float a[4])
MINLINE float len_v3v3(const float a[3], const float b[3]) ATTR_WARN_UNUSED_RESULT
void rotate_v2_v2fl(float r[2], const float p[2], const float angle)
Definition: math_vector.c:914
MINLINE float normalize_v3(float r[3])
MINLINE void sub_v3_v3v3(float r[3], const float a[3], const float b[3])
MINLINE void copy_v2_v2(float r[2], const float a[2])
MINLINE void mul_v3_fl(float r[3], float f)
MINLINE void copy_v3_v3(float r[3], const float a[3])
MINLINE bool is_zero_v3(const float a[3]) ATTR_WARN_UNUSED_RESULT
MINLINE void add_v3_v3v3(float r[3], const float a[3], const float b[3])
MINLINE void madd_v3_v3v3fl(float r[3], const float a[3], const float b[3], float f)
MINLINE void zero_v3(float r[3])
size_t size_t char * BLI_sprintfN(const char *__restrict format,...) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL(1) ATTR_MALLOC ATTR_PRINTF_FORMAT(1
unsigned int uint
Definition: BLI_sys_types.h:83
#define UNUSED(x)
#define TIP_(msgid)
struct Depsgraph Depsgraph
Definition: DEG_depsgraph.h:51
@ SCULPT_DYNTOPO_DETAIL_MANUAL
@ SCULPT_DYNTOPO_DETAIL_CONSTANT
@ SCULPT_DYNTOPO_DETAIL_BRUSH
@ RGN_TYPE_WINDOW
@ SPACE_VIEW3D
@ OPERATOR_CANCELLED
@ OPERATOR_FINISHED
@ OPERATOR_RUNNING_MODAL
void ED_region_tag_redraw(struct ARegion *region)
Definition: area.c:667
void ED_workspace_status_text(struct bContext *C, const char *str)
Definition: area.c:840
#define REGION_DRAW_POST_VIEW
Definition: ED_space_api.h:66
void * ED_region_draw_cb_activate(struct ARegionType *art, void(*draw)(const struct bContext *, struct ARegion *, void *), void *customdata, int type)
Definition: spacetypes.c:238
void ED_region_draw_cb_exit(struct ARegionType *, void *)
Definition: spacetypes.c:253
void ED_view3d_viewcontext_init(struct bContext *C, struct ViewContext *vc, struct Depsgraph *depsgraph)
NSNotificationCenter * center
void immUniformColor4f(float r, float g, float b, float a)
void immUnbindProgram(void)
void immBindBuiltinProgram(eGPUBuiltinShader shader_id)
void immUniformColor4fv(const float rgba[4])
GPUVertFormat * immVertexFormat(void)
void immVertex3fv(uint attr_id, const float data[3])
void immBegin(GPUPrimType, uint vertex_len)
void immEnd(void)
void imm_draw_circle_wire_3d(uint pos, float x, float y, float radius, int nsegments)
void GPU_matrix_pop(void)
Definition: gpu_matrix.cc:142
#define GPU_matrix_mul(x)
Definition: GPU_matrix.h:223
void GPU_matrix_push(void)
Definition: gpu_matrix.cc:135
@ GPU_PRIM_LINES
Definition: GPU_primitive.h:36
@ GPU_SHADER_3D_UNIFORM_COLOR
Definition: GPU_shader.h:200
@ GPU_BLEND_NONE
Definition: GPU_state.h:55
@ GPU_BLEND_ALPHA
Definition: GPU_state.h:57
void GPU_blend(eGPUBlend blend)
Definition: gpu_state.cc:55
void GPU_line_width(float width)
Definition: gpu_state.cc:173
void GPU_line_smooth(bool enable)
Definition: gpu_state.cc:85
@ GPU_FETCH_FLOAT
uint GPU_vertformat_attr_add(GPUVertFormat *, const char *name, GPUVertCompType, uint comp_len, GPUVertFetchMode)
@ GPU_COMP_F32
Read Guarded memory(de)allocation.
#define MEM_SAFE_FREE(v)
#define C
Definition: RandGen.cpp:39
#define ND_DRAW
Definition: WM_types.h:362
@ OPTYPE_UNDO
Definition: WM_types.h:155
@ OPTYPE_REGISTER
Definition: WM_types.h:153
@ WM_OP_INVOKE_DEFAULT
Definition: WM_types.h:197
#define NC_SCENE
Definition: WM_types.h:279
#define ND_TOOLSETTINGS
Definition: WM_types.h:349
#define KM_PRESS
Definition: WM_types.h:242
#define NC_OBJECT
Definition: WM_types.h:280
#define KM_RELEASE
Definition: WM_types.h:243
ATTR_WARN_UNUSED_RESULT const BMVert const BMEdge * e
static DBVT_INLINE btScalar size(const btDbvtVolume &a)
Definition: btDbvt.cpp:52
SIMD_FORCE_INLINE btScalar angle(const btVector3 &v) const
Return the angle between this and another vector.
Definition: btVector3.h:356
OperationNode * node
const Depsgraph * depsgraph
void(* MEM_freeN)(void *vmemh)
Definition: mallocn.c:41
void *(* MEM_callocN)(size_t len, const char *str)
Definition: mallocn.c:45
static void area(int d1, int d2, int e1, int e2, float weights[2])
void RNA_int_set_array(PointerRNA *ptr, const char *name, const int *values)
Definition: rna_access.c:6343
void RNA_int_get_array(PointerRNA *ptr, const char *name, int *values)
Definition: rna_access.c:6331
void RNA_string_set(PointerRNA *ptr, const char *name, const char *value)
Definition: rna_access.c:6550
int RNA_enum_get(PointerRNA *ptr, const char *name)
Definition: rna_access.c:6402
PropertyRNA * RNA_def_int_array(StructOrFunctionRNA *cont_, const char *identifier, int len, const int *default_value, int hardmin, int hardmax, const char *ui_name, const char *ui_description, int softmin, int softmax)
Definition: rna_define.c:3643
PropertyRNA * RNA_def_enum(StructOrFunctionRNA *cont_, const char *identifier, const EnumPropertyItem *items, int default_value, const char *ui_name, const char *ui_description)
Definition: rna_define.c:3771
const float * SCULPT_vertex_co_get(SculptSession *ss, int index)
Definition: sculpt.c:134
int SCULPT_active_vertex_get(SculptSession *ss)
Definition: sculpt.c:277
bool SCULPT_cursor_geometry_info_update(bContext *C, SculptCursorGeometryInfo *out, const float mouse[2], bool use_sampled_normal)
Definition: sculpt.c:7452
const float * SCULPT_active_vertex_co_get(SculptSession *ss)
Definition: sculpt.c:285
void SCULPT_vertex_random_access_ensure(SculptSession *ss)
Definition: sculpt.c:112
void SCULPT_stroke_modifiers_check(const bContext *C, Object *ob, const Brush *brush)
Definition: sculpt.c:7327
bool SCULPT_mode_poll(bContext *C)
Definition: sculpt.c:6601
float SCULPT_raycast_init(ViewContext *vc, const float mouse[2], float ray_start[3], float ray_end[3], float ray_normal[3], bool original)
Definition: sculpt.c:7412
static void sample_detail_voxel(bContext *C, ViewContext *vc, int mx, int my)
static int sculpt_sample_detail_size_invoke(bContext *C, wmOperator *op, const wmEvent *UNUSED(e))
void SCULPT_OT_sample_detail_size(wmOperatorType *ot)
static void sculpt_raycast_detail_cb(PBVHNode *node, void *data_v, float *tmin)
static bool sculpt_and_constant_or_manual_detail_poll(bContext *C)
Definition: sculpt_detail.c:69
static void dyntopo_detail_size_edit_draw(const bContext *UNUSED(C), ARegion *UNUSED(ar), void *arg)
static int dyntopo_detail_size_edit_modal(bContext *C, wmOperator *op, const wmEvent *event)
void SCULPT_OT_detail_flood_fill(wmOperatorType *ot)
static int sculpt_sample_detail_size_exec(bContext *C, wmOperator *op)
static void dyntopo_detail_size_parallel_lines_draw(uint pos3d, DyntopoDetailSizeEditCustomData *cd, const float start_co[3], const float end_co[3], bool flip, const float angle)
void SCULPT_OT_set_detail_size(wmOperatorType *ot)
static void sample_detail_dyntopo(bContext *C, ViewContext *vc, ARegion *region, int mx, int my)
static void dyntopo_detail_size_sample_from_surface(Object *ob, DyntopoDetailSizeEditCustomData *cd)
static int sculpt_sample_detail_size_modal(bContext *C, wmOperator *op, const wmEvent *event)
static void dyntopo_detail_size_update_from_mouse_delta(DyntopoDetailSizeEditCustomData *cd, const wmEvent *event)
static bool sculpt_and_dynamic_topology_poll(bContext *C)
Definition: sculpt_detail.c:78
static int sculpt_detail_flood_fill_exec(bContext *C, wmOperator *UNUSED(op))
Definition: sculpt_detail.c:85
static int sample_detail(bContext *C, int mx, int my, int mode)
#define DETAIL_SIZE_DELTA_ACCURATE_SPEED
static void dyntopo_detail_size_edit_cancel(bContext *C, wmOperator *op)
static void sculpt_detail_size_set_radial_control(bContext *C)
struct DyntopoDetailSizeEditCustomData DyntopoDetailSizeEditCustomData
static EnumPropertyItem prop_sculpt_sample_detail_mode_types[]
void SCULPT_OT_dyntopo_detail_size_edit(wmOperatorType *ot)
eSculptSampleDetailModeTypes
@ SAMPLE_DETAIL_DYNTOPO
@ SAMPLE_DETAIL_VOXEL
#define DETAIL_SIZE_DELTA_SPEED
static int sculpt_set_detail_size_exec(bContext *C, wmOperator *UNUSED(op))
static void set_brush_rc_props(PointerRNA *ptr, const char *prop)
static int dyntopo_detail_size_edit_invoke(bContext *C, wmOperator *op, const wmEvent *event)
void SCULPT_pbvh_clear(Object *ob)
void SCULPT_undo_push_begin(struct Object *ob, const char *name)
Definition: sculpt_undo.c:1383
#define SCULPT_VERTEX_NEIGHBORS_ITER_BEGIN(ss, v_index, neighbor_iterator)
#define SCULPT_VERTEX_NEIGHBORS_ITER_END(neighbor_iterator)
void SCULPT_undo_push_end(void)
Definition: sculpt_undo.c:1400
SculptUndoNode * SCULPT_undo_push_node(Object *ob, PBVHNode *node, SculptUndoType type)
Definition: sculpt_undo.c:1292
@ SCULPT_UNDO_COORDS
struct ARegionType * type
float add_col[4]
float remesh_voxel_size
float obmat[4][4]
struct SculptSession * sculpt
void * data
struct IsectRayPrecalc isect_precalc
Definition: sculpt_detail.c:66
const float * ray_start
Definition: sculpt_detail.c:61
float cursor_normal[3]
Definition: BKE_paint.h:533
float cursor_location[3]
Definition: BKE_paint.h:532
bool draw_faded_cursor
Definition: BKE_paint.h:530
float cursor_radius
Definition: BKE_paint.h:531
struct BMesh * bm
Definition: BKE_paint.h:493
float cursor_sampled_normal[3]
Definition: BKE_paint.h:534
struct PBVH * pbvh
Definition: BKE_paint.h:504
Paint paint
float constant_detail
struct Object * obact
Definition: ED_view3d.h:78
int ymin
Definition: DNA_vec_types.h:80
int xmin
Definition: DNA_vec_types.h:79
short val
Definition: WM_types.h:579
short type
Definition: WM_types.h:577
int(* invoke)(struct bContext *, struct wmOperator *, const struct wmEvent *) ATTR_WARN_UNUSED_RESULT
Definition: WM_types.h:752
const char * name
Definition: WM_types.h:721
int(* modal)(struct bContext *, struct wmOperator *, const struct wmEvent *) ATTR_WARN_UNUSED_RESULT
Definition: WM_types.h:768
const char * idname
Definition: WM_types.h:723
bool(* poll)(struct bContext *) ATTR_WARN_UNUSED_RESULT
Definition: WM_types.h:776
void(* cancel)(struct bContext *, struct wmOperator *)
Definition: WM_types.h:760
struct StructRNA * srna
Definition: WM_types.h:802
const char * description
Definition: WM_types.h:726
int(* exec)(struct bContext *, struct wmOperator *) ATTR_WARN_UNUSED_RESULT
Definition: WM_types.h:736
struct PointerRNA * ptr
void WM_cursor_modal_set(wmWindow *win, int val)
Definition: wm_cursors.c:207
void WM_cursor_modal_restore(wmWindow *win)
Definition: wm_cursors.c:216
@ WM_CURSOR_EYEDROPPER
Definition: wm_cursors.h:51
wmEventHandler_Op * WM_event_add_modal_handler(bContext *C, wmOperator *op)
void WM_main_add_notifier(unsigned int type, void *reference)
void WM_event_add_notifier(const bContext *C, uint type, void *reference)
int WM_operator_name_call_ptr(bContext *C, wmOperatorType *ot, short context, PointerRNA *properties)
@ RIGHTMOUSE
@ EVT_LEFTCTRLKEY
@ EVT_PADENTER
@ LEFTMOUSE
@ EVT_ESCKEY
@ EVT_LEFTSHIFTKEY
@ EVT_RETKEY
PointerRNA * ptr
Definition: wm_files.c:3157
wmOperatorType * ot
Definition: wm_files.c:3156
wmOperatorType * WM_operatortype_find(const char *idname, bool quiet)
void WM_operator_properties_create_ptr(PointerRNA *ptr, wmOperatorType *ot)
Definition: wm_operators.c:584
void WM_operator_properties_free(PointerRNA *ptr)
Definition: wm_operators.c:711