32 #include "RNA_prototypes.h"
85 return *(
reinterpret_cast<uint *
>(&
c));
90 return c.r == 0.0f &&
c.g == 0.0f &&
c.b == 0.0f &&
c.a == 0.0f;
95 return c.r == 0 &&
c.g == 0 &&
c.b == 0 &&
c.a == 0;
100 if constexpr (std::is_same_v<Color, ColorPaint4b>) {
110 if constexpr (std::is_same_v<Color, ColorPaint4b>) {
164 a->do_mask_normal = do_mask_normal;
165 if (do_mask_normal) {
167 a->angle = (
a->angle_inner + 90.0f) * 0.5f;
170 a->angle_inner =
a->angle =
angle;
175 a->angle_range =
a->angle -
a->angle_inner;
177 if (
a->angle_range <= 0.0f) {
178 a->do_mask_normal =
false;
181 a->angle__cos =
cosf(
a->angle);
182 a->angle_inner__cos =
cosf(
a->angle_inner);
189 if (angle_cos <= a->angle__cos) {
193 if (angle_cos < a->angle_inner__cos) {
194 *mask_p *= (
a->angle -
acosf(angle_cos)) /
a->angle_range;
224 if (dv_prev->
flag == 1) {
248 static_cast<const ID *
>(ob->
data));
250 return layer !=
nullptr;
314 template<
typename Color,
typename Traits, eAttrDomain domain>
330 ColorPaint4b col = vpaint_get_current_col<ColorPaint4b, ByteTraits, ATTR_DOMAIN_CORNER>(
331 scene, vp, secondary);
337 template<
typename Color,
typename Traits>
342 const typename Traits::ValueType alpha,
343 const typename Traits::BlendType brush_alpha_value)
345 using Value =
typename Traits::ValueType;
350 const Color color_blend = BLI_mix_colors<Color, Traits>(
blend, color_curr, color_paint, alpha);
358 color_test = BLI_mix_colors<Color, Traits>(
blend, color_orig, color_paint, brush_alpha_value);
360 cp = (
Value *)&color_blend;
361 ct = (
Value *)&color_test;
362 co = (
Value *)&color_orig;
364 for (
a = 0;
a < 4;
a++) {
369 else if (cp[
a] > co[
a]) {
377 else if (cp[
a] > ct[
a]) {
387 cp = (
Value *)&color_blend;
388 cc = (
Value *)&color_curr;
400 const float UNUSED(brush_alpha_value),
409 paintval = 1.0f - paintval;
430 CLAMP(weight, 0.0f, 1.0f);
452 const float co_ss_3d[3] = {co_ss[0], co_ss[1], 0.0f};
463 if (newval < oldval) {
464 return MIN2(newval, curval);
466 if (newval > oldval) {
467 return MAX2(newval, curval);
473 float weight,
float old_weight,
float locked_weight,
float free_weight,
bool auto_normalize)
477 if (auto_normalize || free_weight <= 0.0f) {
479 weight *= (1.0f - locked_weight);
487 if (old_weight >= free_weight) {
491 else if (weight < 1.0f) {
492 weight = weight * (free_weight - old_weight) / (1 - weight);
505 const int defbase_tot,
506 const bool *vgroup_validmap)
508 float sum = 0.0f, fac;
512 for (i = dvert->
totweight, dw = dvert->
dw; i != 0; i--, dw++) {
513 if (dw->
def_nr < defbase_tot && vgroup_validmap[dw->
def_nr]) {
519 if ((tot == 0) || (
sum == 1.0f)) {
526 for (i = dvert->
totweight, dw = dvert->
dw; i != 0; i--, dw++) {
527 if (dw->
def_nr < defbase_tot && vgroup_validmap[dw->
def_nr]) {
536 for (i = dvert->
totweight, dw = dvert->
dw; i != 0; i--, dw++) {
537 if (dw->
def_nr < defbase_tot && vgroup_validmap[dw->
def_nr]) {
549 const int defbase_tot,
550 const bool *vgroup_validmap,
551 const bool *lock_flags)
553 float sum = 0.0f, fac;
554 float sum_unlock = 0.0f;
555 float lock_weight = 0.0f;
559 if (lock_flags ==
nullptr) {
564 for (i = dvert->
totweight, dw = dvert->
dw; i != 0; i--, dw++) {
565 if (dw->
def_nr < defbase_tot && vgroup_validmap[dw->
def_nr]) {
568 if (lock_flags[dw->
def_nr]) {
569 lock_weight += dw->
weight;
589 for (i = dvert->
totweight, dw = dvert->
dw; i != 0; i--, dw++) {
590 if (dw->
def_nr < defbase_tot && vgroup_validmap[dw->
def_nr]) {
591 if (lock_flags[dw->
def_nr] ==
false) {
597 return (lock_weight == 1.0f);
599 if (sum_unlock != 0.0f) {
600 fac = (1.0f - lock_weight) / sum_unlock;
602 for (i = dvert->
totweight, dw = dvert->
dw; i != 0; i--, dw++) {
603 if (dw->
def_nr < defbase_tot && vgroup_validmap[dw->
def_nr]) {
604 if (lock_flags[dw->
def_nr] ==
false) {
614 fac = (1.0f - lock_weight) / tot;
616 CLAMP(fac, 0.0f, 1.0f);
618 for (i = dvert->
totweight, dw = dvert->
dw; i != 0; i--, dw++) {
619 if (dw->
def_nr < defbase_tot && vgroup_validmap[dw->
def_nr]) {
620 if (lock_flags[dw->
def_nr] ==
false) {
635 const int defbase_tot,
636 const bool *vgroup_validmap,
637 const bool *lock_flags,
638 const bool *lock_with_active)
643 dvert, defbase_tot, vgroup_validmap, lock_with_active);
660 static bool has_unselected_unlocked_bone_group(
int defbase_tot,
663 const bool *lock_flags,
664 const bool *vgroup_validmap)
667 if (defbase_tot == selected) {
670 for (i = 0; i < defbase_tot; i++) {
671 if (vgroup_validmap[i] && !defbase_sel[i] && !lock_flags[i]) {
680 const int defbase_tot,
681 const bool *defbase_sel,
687 float change = *change_p;
690 for (i = dvert->
totweight, dw = dvert->
dw; i != 0; i--, dw++) {
691 if (dw->
def_nr < defbase_tot && defbase_sel[dw->
def_nr]) {
693 val = dw->
weight * change;
695 change = 1.0f / dw->
weight;
705 const int defbase_tot,
707 const bool *defbase_sel)
716 for (i = dvert->
totweight, dw = dvert->
dw; i != 0; i--, dw++) {
717 if (dw->
def_nr < defbase_tot && defbase_sel[dw->
def_nr]) {
719 val = dw->
weight * change;
733 const int defbase_tot,
735 const bool *defbase_sel)
741 for (i = dvert->
totweight, dw = dvert->
dw; i != 0; i--, dw++) {
742 if (dw->
def_nr < defbase_tot && defbase_sel[dw->
def_nr]) {
822 float weight_prev, weight_cur;
823 float dw_rel_locked = 0.0f, dw_rel_free = 1.0f;
839 if (index_mirr == index && vgroup_mirr == wpi->
active.
index) {
840 index_mirr = vgroup_mirr = -1;
844 index_mirr = vgroup_mirr = -1;
854 CLAMP(dw_rel_locked, 0.0f, 1.0f);
860 restrict_to_existing =
true;
865 if (restrict_to_existing) {
877 if (index_mirr != -1) {
878 dv_mirr = &me->
dvert[index_mirr];
882 if (dw_mirr ==
nullptr) {
883 index_mirr = vgroup_mirr = -1;
888 if (index != index_mirr) {
894 int dw_offset = (int)(dw - dv_mirr->
dw);
898 if (totweight_prev != dv_mirr->
totweight) {
899 dw = &dv_mirr->
dw[dw_offset];
919 if (index_mirr != -1) {
931 weight_prev = weight_cur;
945 if (index_mirr == index) {
959 CLAMP(weight, 0.0f, 1.0f);
968 if (index_mirr != -1) {
990 if (index_mirr != -1) {
993 if (index != index_mirr) {
1035 int index_mirr = -1;
1039 float curw, curw_real, oldw, neww, change, curw_mirr, change_mirr;
1040 float dw_rel_free, dw_rel_locked;
1046 if (!
ELEM(index_mirr, -1, index)) {
1047 dv_mirr = &me->
dvert[index_mirr];
1067 CLAMP(dw_rel_locked, 0.0f, 1.0f);
1075 if (index_mirr != -1) {
1099 change = neww / curw_real;
1104 if (dv_mirr !=
nullptr) {
1108 if (curw_mirr == 0.0f) {
1114 float orig = change_mirr = curw_real * change / curw_mirr;
1122 change *= change_mirr / orig;
1133 if (dv_mirr !=
nullptr) {
1142 if (dv_mirr !=
nullptr) {
1271 for (
int i = 0; i < me->
totvert; i++, dv++) {
1297 ob->
mode |= mode_flag;
1378 ob->
mode &= ~mode_flag;
1457 const bool is_mode_set = (ob->
mode & mode_flag) != 0;
1516 ot->
name =
"Weight Paint Mode";
1517 ot->
idname =
"PAINT_OT_weight_paint_toggle";
1604 float view_dir[3] = {0.0f, 0.0f, 1.0f};
1644 cache->
brush = brush;
1718 int defbase_tot, defbase_tot_sel;
1737 if (vgroup_index.
mirror != -1) {
1750 if (ts->multipaint && defbase_tot_sel > 1) {
1756 ob, defbase_tot, defbase_sel, defbase_sel, &defbase_tot_sel);
1759 for (i = 0; i < defbase_tot; i++) {
1760 if (defbase_sel[i]) {
1787 wpd->
do_multipaint = (ts->multipaint && defbase_tot_sel > 1);
1792 if (ts->auto_normalize || ts->multipaint || wpd->
lock_flags !=
nullptr ||
1793 ts->wpaint_lock_relative) {
1798 if (ts->wpaint_lock_relative &&
1802 defbase_tot, wpd->
lock_flags, defbase_sel, defbase_tot_sel))) {
1821 tmpflags = (
bool *)
MEM_mallocN(
sizeof(
bool) * defbase_tot, __func__);
1830 else if (ts->auto_normalize) {
1834 (
bool *)
MEM_callocN(
sizeof(
bool) * defbase_tot, __func__);
1839 (
bool *)
MEM_callocN(
sizeof(
bool) * defbase_tot, __func__);
1853 if (ob->sculpt->mode.wpaint.dvert_prev !=
nullptr) {
1854 MDeformVert *dv = ob->sculpt->mode.wpaint.dvert_prev;
1855 for (
int i = 0; i < me->
totvert; i++, dv++) {
1867 float *r_brush_size_pressure,
1868 float *r_brush_alpha_value,
1869 float *r_brush_alpha_pressure)
1894 CLAMP(weight, 0.0f, 1.0f);
1937 const bool has_grids = (pbvh_type ==
PBVH_GRIDS);
1944 float brush_size_pressure, brush_alpha_value, brush_alpha_pressure;
1946 scene, ss, brush, &brush_size_pressure, &brush_alpha_value, &brush_alpha_pressure);
1953 ss, &test,
data->brush->falloff_shape);
1955 ss,
data->brush->falloff_shape);
1961 if (sculpt_brush_test_sq_fn(&test, vd.
co)) {
1966 const float grid_alpha = has_grids ? 1.0f / vd.
gridsize : 1.0f;
1967 const char v_flag =
data->me->mvert[v_index].flag;
1969 if (!(use_face_sel || use_vert_sel) || v_flag &
SELECT) {
1971 int total_hit_loops = 0;
1972 float weight_final = 0.0f;
1975 const MPoly *mp = &
data->me->mpoly[p_index];
1977 total_hit_loops += mp->
totloop;
1978 for (
int k = 0; k < mp->
totloop; k++) {
1980 const MLoop *ml = &
data->me->mloop[l_index];
1981 weight_final +=
data->wpd->precomputed_weight[ml->
v];
1986 if (total_hit_loops != 0) {
1988 const float angle_cos = (use_normal && vd.
no) ?
1997 const float final_alpha = brush_fade *
brush_strength * grid_alpha *
1998 brush_alpha_pressure;
2001 if (ss->
mode.
wpaint.alpha_weight[v_index] < final_alpha) {
2002 ss->
mode.
wpaint.alpha_weight[v_index] = final_alpha;
2009 weight_final /= total_hit_loops;
2012 data->vp,
data->ob,
data->wpi, v_index, final_alpha, weight_final);
2028 const bool has_grids = (pbvh_type ==
PBVH_GRIDS);
2034 float brush_size_pressure, brush_alpha_value, brush_alpha_pressure;
2036 scene, ss, brush, &brush_size_pressure, &brush_alpha_value, &brush_alpha_pressure);
2049 ss, &test,
data->brush->falloff_shape);
2051 ss,
data->brush->falloff_shape);
2057 if (sculpt_brush_test_sq_fn(&test, vd.
co)) {
2062 const float grid_alpha = has_grids ? 1.0f / vd.
gridsize : 1.0f;
2063 const MVert *mv_curr = &
data->me->mvert[v_index];
2066 if (!(use_face_sel || use_vert_sel) || mv_curr->
flag &
SELECT) {
2068 const float angle_cos = (use_normal && vd.
no) ?
2075 bool do_color =
false;
2078 float stroke_dot_max = 0.0f;
2082 float weight_final = 0.0;
2085 const MPoly *mp = &
data->me->mpoly[p_index];
2087 for (
int k = 0; k < mp->
totloop; k++, ml_other++) {
2088 const uint v_other_index = ml_other->
v;
2089 if (v_other_index != v_index) {
2090 const MVert *mv_other = &
data->me->mvert[v_other_index];
2099 const float stroke_dot =
dot_v3v3(other_dir, brush_dir);
2101 if (stroke_dot > stroke_dot_max) {
2102 stroke_dot_max = stroke_dot;
2103 weight_final =
data->wpd->precomputed_weight[v_other_index];
2113 const float final_alpha = brush_fade *
brush_strength * grid_alpha *
2114 brush_alpha_pressure;
2116 if (final_alpha <= 0.0f) {
2121 data->vp,
data->ob,
data->wpi, v_index, final_alpha, (
float)weight_final);
2138 const bool has_grids = (pbvh_type ==
PBVH_GRIDS);
2145 const float paintweight =
data->strength;
2146 float brush_size_pressure, brush_alpha_value, brush_alpha_pressure;
2148 scene, ss, brush, &brush_size_pressure, &brush_alpha_value, &brush_alpha_pressure);
2155 ss, &test,
data->brush->falloff_shape);
2157 ss,
data->brush->falloff_shape);
2163 if (sculpt_brush_test_sq_fn(&test, vd.
co)) {
2169 const float grid_alpha = has_grids ? 1.0f / vd.
gridsize : 1.0f;
2171 const char v_flag =
data->me->mvert[v_index].flag;
2173 if (!(use_face_sel || use_vert_sel) || v_flag &
SELECT) {
2175 const float angle_cos = (use_normal && vd.
no) ?
dot_v3v3(sculpt_normal_frontface, vd.
no) :
2183 const float final_alpha = brush_fade *
brush_strength * grid_alpha *
2184 brush_alpha_pressure;
2187 if (ss->
mode.
wpaint.alpha_weight[v_index] < final_alpha) {
2188 ss->
mode.
wpaint.alpha_weight[v_index] = final_alpha;
2210 const bool has_grids = (pbvh_type ==
PBVH_GRIDS);
2222 ss, &test,
data->brush->falloff_shape);
2224 ss,
data->brush->falloff_shape);
2230 if (sculpt_brush_test_sq_fn(&test, vd.
co)) {
2231 const float angle_cos = (use_normal && vd.
no) ?
dot_v3v3(sculpt_normal_frontface, vd.
no) :
2233 if (angle_cos > 0.0 &&
2237 const char v_flag =
data->me->mvert[v_index].flag;
2240 if (!(use_face_sel || use_vert_sel) || v_flag &
SELECT) {
2257 data->custom_data = accum;
2264 double accum_weight = 0.0;
2265 for (
int i = 0; i < totnode; i++) {
2266 accum_len += accum[i].
len;
2267 accum_weight += accum[i].
value;
2269 if (accum_len != 0) {
2270 accum_weight /= accum_len;
2340 data.original =
true;
2359 data.original =
true;
2360 data.dist_ray_to_aabb_precalc = &dist_ray_to_aabb_precalc;
2411 for (
int i = 1; i < wp->
radial_symm[axis -
'X']; i++) {
2413 wpaint_do_paint(
C, ob, wp, sd, wpd, wpi, me, brush, symm, axis, i,
angle);
2430 cache->mirror_symmetry_pass = 0;
2431 wpaint_do_paint(
C, ob, wp, sd, wpd, wpi, me, brush, 0,
'X', 0, 0);
2436 cache->symmetry = symm;
2440 copy_v3_v3(cache->true_last_location, cache->true_location);
2441 cache->is_last_valid =
true;
2447 for (i = 1; i <= symm; i++) {
2448 if ((symm & i && (symm != 5 || i != 3) && (symm != 6 || (!
ELEM(i, 3, 5))))) {
2449 cache->mirror_symmetry_pass = i;
2450 cache->radial_symmetry_pass = 0;
2454 wpaint_do_paint(
C, ob, wp, sd, wpd, wpi, me, brush, i,
'X', 0, 0);
2458 wpaint_do_paint(
C, ob, wp, sd, wpd, wpi, me, brush, i,
'Y', 0, 0);
2462 wpaint_do_paint(
C, ob, wp, sd, wpd, wpi, me, brush, i,
'Z', 0, 0);
2467 copy_v3_v3(cache->true_last_location, cache->true_location);
2468 cache->is_last_valid =
true;
2497 if (wpd ==
nullptr) {
2686 ot->
name =
"Weight Paint";
2687 ot->
idname =
"PAINT_OT_weight_paint";
2688 ot->
description =
"Paint a stroke in the current vertex group's weights";
2718 const bool is_mode_set = (ob->
mode & mode_flag) != 0;
2759 ot->
name =
"Vertex Paint Mode";
2760 ot->
idname =
"PAINT_OT_vertex_paint_toggle";
2761 ot->
description =
"Toggle the vertex paint mode in 3D view";
2801 template<
typename Color,
typename Traits, eAttrDomain domain>
2819 template<
typename Color,
typename Traits, eAttrDomain domain>
2834 vpd = MEM_new<VPaintData<Color, Traits, domain>>(
"VPaintData");
2836 if constexpr (std::is_same_v<Color, ColorPaint4f>) {
2850 vpd->
paintcol = vpaint_get_current_col<Color, Traits, domain>(
2871 return static_cast<void *
>(vpd);
2888 if (me ==
nullptr || me->
totpoly == 0) {
2900 void *vpd =
nullptr;
2904 vpd = vpaint_init_vpaint<ColorPaint4f, FloatTraits, ATTR_DOMAIN_POINT>(
2908 vpd = vpaint_init_vpaint<ColorPaint4b, ByteTraits, ATTR_DOMAIN_POINT>(
2914 vpd = vpaint_init_vpaint<ColorPaint4f, FloatTraits, ATTR_DOMAIN_CORNER>(
2918 vpd = vpaint_init_vpaint<ColorPaint4b, ByteTraits, ATTR_DOMAIN_CORNER>(
2935 template<
class Color = ColorPa
int4b,
typename Traits = ByteTraits>
2946 using Blend =
typename Traits::BlendType;
2956 for (
int n : range) {
2958 const bool has_grids = (pbvh_type ==
PBVH_GRIDS);
2962 float brush_size_pressure, brush_alpha_value, brush_alpha_pressure;
2964 scene, ss, brush, &brush_size_pressure, &brush_alpha_value, &brush_alpha_pressure);
2966 const bool use_vert_sel = (me->
editflag &
2980 if (sculpt_brush_test_sq_fn(&test, vd.
co)) {
2985 const float grid_alpha = has_grids ? 1.0f / vd.
gridsize : 1.0f;
2989 if (!use_vert_sel ||
mv->flag &
SELECT) {
2991 const float angle_cos = (use_normal && vd.
no) ?
3002 Color color_final(0, 0, 0, 0);
3004 int total_hit_loops = 0;
3005 Blend
blend[4] = {0};
3011 total_hit_loops += mp->
totloop;
3012 for (
int k = 0; k < mp->
totloop; k++) {
3025 if (total_hit_loops != 0) {
3029 color_final.r = Traits::round(
3030 sqrtf(Traits::divide_round(
blend[0], total_hit_loops)));
3031 color_final.g = Traits::round(
3032 sqrtf(Traits::divide_round(
blend[1], total_hit_loops)));
3033 color_final.b = Traits::round(
3034 sqrtf(Traits::divide_round(
blend[2], total_hit_loops)));
3035 color_final.a = Traits::round(
3036 sqrtf(Traits::divide_round(
blend[3], total_hit_loops)));
3046 Color color_orig(0, 0, 0, 0);
3048 if (previous_color !=
nullptr) {
3050 if (
isZero(previous_color[l_index])) {
3051 previous_color[l_index] = lcol[l_index];
3053 color_orig = previous_color[l_index];
3055 const float final_alpha = Traits::range * brush_fade *
brush_strength *
3056 brush_alpha_pressure * grid_alpha;
3059 lcol[l_index] = vpaint_blend<Color, Traits>(vp,
3077 template<
class Color = ColorPa
int4b,
typename Traits = ByteTraits>
3088 using Blend =
typename Traits::BlendType;
3098 for (
int n : range) {
3100 const bool has_grids = (pbvh_type ==
PBVH_GRIDS);
3104 float brush_size_pressure, brush_alpha_value, brush_alpha_pressure;
3106 scene, ss, brush, &brush_size_pressure, &brush_alpha_value, &brush_alpha_pressure);
3108 const bool use_vert_sel = (me->
editflag &
3122 if (sculpt_brush_test_sq_fn(&test, vd.
co)) {
3127 const float grid_alpha = has_grids ? 1.0f / vd.
gridsize : 1.0f;
3131 if (!use_vert_sel ||
mv->flag &
SELECT) {
3133 const float angle_cos = (use_normal && vd.
no) ?
3144 Color color_final(0, 0, 0, 0);
3146 int total_hit_loops = 0;
3147 Blend
blend[4] = {0};
3153 total_hit_loops += mp->
totloop;
3154 for (
int k = 0; k < mp->
totloop; k++) {
3169 if (total_hit_loops != 0) {
3173 color_final.r = Traits::round(
3174 sqrtf(Traits::divide_round(
blend[0], total_hit_loops)));
3175 color_final.g = Traits::round(
3176 sqrtf(Traits::divide_round(
blend[1], total_hit_loops)));
3177 color_final.b = Traits::round(
3178 sqrtf(Traits::divide_round(
blend[2], total_hit_loops)));
3179 color_final.a = Traits::round(
3180 sqrtf(Traits::divide_round(
blend[3], total_hit_loops)));
3191 Color color_orig(0, 0, 0, 0);
3193 if (previous_color !=
nullptr) {
3195 if (
isZero(previous_color[v_index])) {
3196 previous_color[v_index] = lcol[v_index];
3198 color_orig = previous_color[v_index];
3200 const float final_alpha = Traits::range * brush_fade *
brush_strength *
3201 brush_alpha_pressure * grid_alpha;
3204 lcol[v_index] = vpaint_blend<Color, Traits>(vp,
3222 template<
typename Color = ColorPa
int4b,
typename Traits, eAttrDomain domain>
3238 const bool has_grids = (pbvh_type ==
PBVH_GRIDS);
3247 for (
int n : range) {
3248 float brush_size_pressure, brush_alpha_value, brush_alpha_pressure;
3251 scene, ss, brush, &brush_size_pressure, &brush_alpha_value, &brush_alpha_pressure);
3254 const bool use_vert_sel = (me->
editflag &
3273 if (sculpt_brush_test_sq_fn(&test, vd.
co)) {
3278 const float grid_alpha = has_grids ? 1.0f / vd.
gridsize : 1.0f;
3282 if (!use_vert_sel || mv_curr->
flag &
SELECT) {
3286 const float angle_cos = (use_normal && vd.
no) ?
3296 bool do_color =
false;
3299 float stroke_dot_max = 0.0f;
3303 Color color_final(0, 0, 0, 0);
3313 for (
int k = 0; k < mp->
totloop; k++, ml_other++) {
3314 const uint v_other_index = ml_other->
v;
3315 if (v_other_index != v_index) {
3316 const MVert *mv_other = &me->
mvert[v_other_index];
3326 const float stroke_dot =
dot_v3v3(other_dir, brush_dir);
3330 elem_index = ml_other->
v;
3336 if (stroke_dot > stroke_dot_max) {
3337 stroke_dot_max = stroke_dot;
3338 color_final = color_prev_smear[elem_index];
3347 const float final_alpha = Traits::range * brush_fade *
brush_strength *
3348 brush_alpha_pressure * grid_alpha;
3357 elem_index = v_index;
3361 elem_index = l_index;
3368 Color color_orig(0, 0, 0, 0);
3370 if (color_prev !=
nullptr) {
3372 if (
isZero(color_prev[elem_index])) {
3373 color_prev[elem_index] = lcol[elem_index];
3375 color_orig = color_prev[elem_index];
3379 lcol[elem_index] = vpaint_blend<Color, Traits>(vp,
3387 color_curr[elem_index] = lcol[elem_index];
3401 template<
typename Color,
typename Traits, eAttrDomain domain>
3410 using Blend =
typename Traits::BlendType;
3413 sizeof(*accum) * totnode, __func__);
3415 for (
int n : range) {
3418 const bool has_grids = (pbvh_type ==
PBVH_GRIDS);
3422 const bool use_vert_sel = (me->
editflag &
3427 memset(accum2->
value, 0,
sizeof(accum2->
value));
3437 if (sculpt_brush_test_sq_fn(&test, vd.
co)) {
3443 if (!use_vert_sel ||
mv->flag &
SELECT) {
3453 elem_index = v_index;
3471 Blend accum_len = 0;
3472 Blend accum_value[3] = {0};
3475 for (
int i = 0; i < totnode; i++) {
3476 accum_len += accum[i].
len;
3477 accum_value[0] += accum[i].
value[0];
3478 accum_value[1] += accum[i].
value[1];
3479 accum_value[2] += accum[i].
value[2];
3481 if (accum_len != 0) {
3482 blend.r = Traits::round(
sqrtf(Traits::divide_round(accum_value[0], accum_len)));
3483 blend.g = Traits::round(
sqrtf(Traits::divide_round(accum_value[1], accum_len)));
3484 blend.b = Traits::round(
sqrtf(Traits::divide_round(accum_value[2], accum_len)));
3485 blend.a = Traits::range;
3491 template<
typename Color,
typename Traits, eAttrDomain domain>
3494 const float v_co[3],
3505 *r_color = fromFloat<Color>(rgba_br);
3509 template<
typename Color,
typename Traits, eAttrDomain domain>
3529 for (
int n : range) {
3530 const bool has_grids = (pbvh_type ==
PBVH_GRIDS);
3534 float brush_size_pressure, brush_alpha_value, brush_alpha_pressure;
3536 scene, ss, brush, &brush_size_pressure, &brush_alpha_value, &brush_alpha_pressure);
3538 const bool use_vert_sel = (me->
editflag &
3554 if (sculpt_brush_test_sq_fn(&test, vd.
co)) {
3560 const float grid_alpha = has_grids ? 1.0f / vd.
gridsize : 1.0f;
3564 if (!use_vert_sel ||
mv->flag &
SELECT) {
3568 const float angle_cos = (use_normal && vd.
no) ?
3578 Color color_final = paintcol;
3581 float tex_alpha = 1.0;
3584 tex_alpha = paint_and_tex_color_alpha<Color, Traits, domain>(
3588 Color color_orig(0, 0, 0, 0);
3591 int v_index = vd.
index;
3593 if (previous_color !=
nullptr) {
3595 if (
isZero(previous_color[v_index])) {
3596 previous_color[v_index] = lcol[v_index];
3598 color_orig = previous_color[v_index];
3600 const float final_alpha = Traits::frange * brush_fade *
brush_strength *
3601 tex_alpha * brush_alpha_pressure * grid_alpha;
3603 lcol[v_index] = vpaint_blend<Color, Traits>(vp,
3620 if (previous_color !=
nullptr) {
3622 if (
isZero(previous_color[l_index])) {
3623 previous_color[l_index] = lcol[l_index];
3625 color_orig = previous_color[l_index];
3627 const float final_alpha = Traits::frange * brush_fade *
brush_strength *
3628 tex_alpha * brush_alpha_pressure * grid_alpha;
3631 lcol[l_index] = vpaint_blend<Color, Traits>(vp,
3649 template<
typename Color,
typename Traits, eAttrDomain domain>
3661 do_vpaint_brush_blur_verts<Color, Traits>(
C, sd, vp, vpd, ob, me, nodes, totnode, lcol);
3664 do_vpaint_brush_blur_loops<Color, Traits>(
C, sd, vp, vpd, ob, me, nodes, totnode, lcol);
3668 template<
typename Color,
typename Traits, eAttrDomain domain>
3688 calculate_average_color<Color, Traits, domain>(vpd, ob, me, brush, lcol, nodes, totnode);
3689 vpaint_do_draw<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, nodes, totnode, lcol);
3692 vpaint_do_draw<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, nodes, totnode, lcol);
3695 vpaint_do_blur<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, nodes, totnode, lcol);
3698 do_vpaint_brush_smear<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, nodes, totnode, lcol);
3705 template<
typename Color,
typename Traits, eAttrDomain domain>
3729 vpaint_paint_leaves<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, color_data, nodes, totnode);
3736 template<
typename Color,
typename Traits, eAttrDomain domain>
3747 for (
int i = 1; i < vp->
radial_symm[axis -
'X']; i++) {
3749 vpaint_do_paint<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, brush, symm, axis, i,
angle);
3755 template<
typename Color,
typename Traits, eAttrDomain domain>
3767 cache->mirror_symmetry_pass = 0;
3768 vpaint_do_paint<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, brush, i,
'X', 0, 0);
3769 vpaint_do_radial_symmetry<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, brush, i,
'X');
3770 vpaint_do_radial_symmetry<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, brush, i,
'Y');
3771 vpaint_do_radial_symmetry<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, brush, i,
'Z');
3773 cache->symmetry = symm;
3777 for (i = 1; i <= symm; i++) {
3778 if (symm & i && (symm != 5 || i != 3) && (symm != 6 || (!
ELEM(i, 3, 5)))) {
3779 cache->mirror_symmetry_pass = i;
3780 cache->radial_symmetry_pass = 0;
3784 vpaint_do_paint<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, brush, i,
'X', 0, 0);
3785 vpaint_do_radial_symmetry<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, brush, i,
'X');
3788 vpaint_do_paint<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, brush, i,
'Y', 0, 0);
3789 vpaint_do_radial_symmetry<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, brush, i,
'Y');
3792 vpaint_do_paint<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, brush, i,
'Z', 0, 0);
3793 vpaint_do_radial_symmetry<Color, Traits, domain>(
C, sd, vp, vpd, ob, me, brush, i,
'Z');
3798 copy_v3_v3(cache->true_last_location, cache->true_location);
3799 cache->is_last_valid =
true;
3802 template<
typename Color,
typename Traits, eAttrDomain domain>
3826 vpaint_do_symmetrical_brush_actions<Color, Traits, domain>(
C, sd, vp, vpd, ob);
3862 vpaint_stroke_update_step_intern<ColorPaint4f, FloatTraits, ATTR_DOMAIN_POINT>(
3863 C, stroke, itemptr);
3866 vpaint_stroke_update_step_intern<ColorPaint4b, ByteTraits, ATTR_DOMAIN_POINT>(
3867 C, stroke, itemptr);
3872 vpaint_stroke_update_step_intern<ColorPaint4f, FloatTraits, ATTR_DOMAIN_CORNER>(
3873 C, stroke, itemptr);
3876 vpaint_stroke_update_step_intern<ColorPaint4b, ByteTraits, ATTR_DOMAIN_CORNER>(
3877 C, stroke, itemptr);
3882 template<
typename Color,
typename Traits, eAttrDomain domain>
3898 MEM_delete<VPaintData<Color, Traits, domain>>(vpd);
3911 vpaint_free_vpaintdata<ColorPaint4f, FloatTraits, ATTR_DOMAIN_POINT>(ob, vpd);
3914 vpaint_free_vpaintdata<ColorPaint4b, ByteTraits, ATTR_DOMAIN_POINT>(ob, vpd);
3919 vpaint_free_vpaintdata<ColorPaint4f, FloatTraits, ATTR_DOMAIN_CORNER>(ob, vpd);
3922 vpaint_free_vpaintdata<ColorPaint4b, ByteTraits, ATTR_DOMAIN_CORNER>(ob, vpd);
4013 ot->
name =
"Vertex Paint";
4014 ot->
idname =
"PAINT_OT_vertex_paint";
4015 ot->
description =
"Paint a stroke in the active color attribute layer";
4036 template<
typename Color,
typename Traits, eAttrDomain domain>
4045 Color paintcol = fromFloat<Color>(paintcol_in);
4060 for (
int i = 0; i < cdata->
totlayer; i++) {
4062 cd_offset = layer->
offset;
4090 for (
int i = 0; i < me->
totpoly; i++, mp++) {
4101 color_layer[mp->
loopstart + j] = paintcol;
4104 color_layer[vidx] = paintcol;
4108 }
while (j < mp->totloop);
4128 bool only_selected =
true)
4140 if (!only_selected) {
4148 ok = vertex_color_set<ColorPaint4f, FloatTraits, ATTR_DOMAIN_POINT>(ob, fill_color, layer);
4151 ok = vertex_color_set<ColorPaint4b, ByteTraits, ATTR_DOMAIN_POINT>(ob, fill_color, layer);
4156 ok = vertex_color_set<ColorPaint4f, FloatTraits, ATTR_DOMAIN_CORNER>(ob, fill_color, layer);
4159 ok = vertex_color_set<ColorPaint4b, ByteTraits, ATTR_DOMAIN_CORNER>(ob, fill_color, layer);
4168 const float fill_color[4],
4180 ColorPaint4f paintcol = vpaint_get_current_col<ColorPaint4f, FloatTraits, ATTR_DOMAIN_POINT>(
4193 ot->
name =
"Set Vertex Colors";
4194 ot->
idname =
"PAINT_OT_vertex_color_set";
4195 ot->
description =
"Fill the active vertex color layer with the current paint color";
typedef float(TangentPoint)[2]
Generic geometry attributes built on CustomData.
struct CustomDataLayer * BKE_id_attributes_active_color_get(const struct ID *id)
eAttrDomain BKE_id_attribute_domain(const struct ID *id, const struct CustomDataLayer *layer)
void BKE_brush_size_set(struct Scene *scene, struct Brush *brush, int size)
float BKE_brush_curve_strength(const struct Brush *br, float p, float len)
float BKE_brush_sample_tex_3d(const struct Scene *scene, const struct Brush *br, const float point[3], float rgba[4], int thread, struct ImagePool *pool)
bool BKE_brush_use_size_pressure(const struct Brush *brush)
float BKE_brush_weight_get(const struct Scene *scene, const struct Brush *brush)
const float * BKE_brush_secondary_color_get(const struct Scene *scene, const struct Brush *brush)
float BKE_brush_alpha_get(const struct Scene *scene, const struct Brush *brush)
const float * BKE_brush_color_get(const struct Scene *scene, const struct Brush *brush)
int BKE_brush_size_get(const struct Scene *scene, const struct Brush *brush)
void BKE_brush_unprojected_radius_set(struct Scene *scene, struct Brush *brush, float unprojected_radius)
bool BKE_brush_use_alpha_pressure(const struct Brush *brush)
struct ScrArea * CTX_wm_area(const bContext *C)
struct Scene * CTX_data_scene(const bContext *C)
struct Depsgraph * CTX_data_ensure_evaluated_depsgraph(const bContext *C)
struct Depsgraph * CTX_data_depsgraph_on_load(const bContext *C)
struct Object * CTX_data_active_object(const bContext *C)
struct wmMsgBus * CTX_wm_message_bus(const bContext *C)
struct ARegion * CTX_wm_region(const bContext *C)
struct Main * CTX_data_main(const bContext *C)
struct ToolSettings * CTX_data_tool_settings(const bContext *C)
struct RegionView3D * CTX_wm_region_view3d(const bContext *C)
struct ID * BKE_libblock_find_name(struct Main *bmain, short type, const char *name) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL()
void BKE_mesh_flush_select_from_verts(struct Mesh *me)
void BKE_mesh_tessface_clear(struct Mesh *mesh)
struct Mesh * BKE_mesh_from_object(struct Object *ob)
void BKE_mesh_batch_cache_dirty_tag(struct Mesh *me, eMeshBatchDirtyMode mode)
void BKE_mesh_flush_select_from_polys(struct Mesh *me)
void BKE_mesh_vert_loop_map_create(MeshElemMap **r_map, int **r_mem, const struct MPoly *mpoly, const struct MLoop *mloop, int totvert, int totpoly, int totloop)
void BKE_mesh_vert_poly_map_create(MeshElemMap **r_map, int **r_mem, const struct MPoly *mpoly, const struct MLoop *mloop, int totvert, int totpoly, int totloop)
@ BKE_MESH_BATCH_DIRTY_ALL
General operations, lookup, etc. for blender objects.
void BKE_object_free_derived_caches(struct Object *ob)
struct Mesh * BKE_object_get_original_mesh(const struct Object *object)
void BKE_paint_brush_set(struct Paint *paint, struct Brush *br)
struct Paint * BKE_paint_get_active_from_paintmode(struct Scene *sce, ePaintMode mode)
void BKE_sculpt_toolsettings_data_ensure(struct Scene *scene)
const char PAINT_CURSOR_VERTEX_PAINT[3]
void BKE_sculpt_update_object_for_edit(struct Depsgraph *depsgraph, struct Object *ob_orig, bool need_pmap, bool need_mask, bool is_paint_tool)
struct Brush * BKE_paint_toolslots_brush_get(struct Paint *paint, int slot_index)
struct Brush * BKE_paint_brush(struct Paint *paint)
void BKE_paint_init(struct Main *bmain, struct Scene *sce, ePaintMode mode, const char col[3])
bool BKE_paint_ensure(struct ToolSettings *ts, struct Paint **r_paint)
void BKE_sculptsession_free(struct Object *ob)
const char PAINT_CURSOR_WEIGHT_PAINT[3]
void BKE_paint_toolslots_brush_validate(struct Main *bmain, struct Paint *paint)
const struct Brush * BKE_paint_brush_for_read(const struct Paint *p)
#define BKE_pbvh_vertex_iter_begin(pbvh, node, vi, mode)
PBVHType BKE_pbvh_type(const PBVH *pbvh)
#define BKE_pbvh_vertex_iter_end
void BKE_pbvh_ensure_node_loops(PBVH *pbvh)
void BKE_pbvh_parallel_range_settings(struct TaskParallelSettings *settings, bool use_threading, int totnode)
void BKE_pbvh_update_bounds(PBVH *pbvh, int flags)
void BKE_pbvh_search_gather(PBVH *pbvh, BKE_pbvh_SearchCallback scb, void *search_data, PBVHNode ***array, int *tot)
void BKE_report(ReportList *reports, eReportType type, const char *message)
Generic array manipulation API.
#define BLI_array_binary_or(arr, arr_a, arr_b, arr_len)
void * BLI_findlink(const struct ListBase *listbase, int number) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL(1)
int BLI_listbase_count(const struct ListBase *listbase) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL(1)
void rgb_uchar_to_float(float r_col[3], const unsigned char col_ub[3])
void dist_squared_ray_to_aabb_v3_precalc(struct DistRayAABB_Precalc *neasrest_precalc, const float ray_origin[3], const float ray_direction[3])
void mul_m3_v3(const float M[3][3], float r[3])
void mul_m4_m4m4(float R[4][4], const float A[4][4], const float B[4][4])
void copy_m3_m4(float m1[3][3], const float m2[4][4])
bool invert_m4_m4(float R[4][4], const float A[4][4])
void swap_m4m4(float m1[4][4], float m2[4][4])
void mul_v3_m4v3(float r[3], const float M[4][4], const float v[3])
MINLINE float normalize_v3(float r[3])
MINLINE void mul_v3_v3(float r[3], const float a[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 copy_v3_v3(float r[3], const float a[3])
void project_plane_v3_v3v3(float out[3], const float p[3], const float v_plane[3])
MINLINE float dot_v3v3(const float a[3], const float b[3]) ATTR_WARN_UNUSED_RESULT
MINLINE void zero_v4(float r[4])
MINLINE float normalize_v3_v3(float r[3], const float a[3])
MINLINE void zero_v2(float r[2])
MINLINE void zero_v3(float r[3])
MINLINE void add_v3_v3(float r[3], const float a[3])
void BLI_rcti_union(struct rcti *rct_a, const struct rcti *rct_b)
bool BLI_rcti_is_empty(const struct rcti *rect)
char * BLI_strncpy(char *__restrict dst, const char *__restrict src, size_t maxncpy) ATTR_NONNULL()
void BLI_task_parallel_range(int start, int stop, void *userdata, TaskParallelRangeFunc func, const TaskParallelSettings *settings)
BLI_INLINE void BLI_parallel_range_settings_defaults(TaskParallelSettings *settings)
#define UNUSED_VARS_NDEBUG(...)
struct Depsgraph Depsgraph
void DEG_id_tag_update(struct ID *id, int flag)
@ ID_RECALC_COPY_ON_WRITE
#define ID_IS_LINKED(_id)
@ BRUSH_FRONTFACE_FALLOFF
@ PAINT_FALLOFF_SHAPE_SPHERE
@ ME_EDIT_MIRROR_VERTEX_GROUPS
#define ME_USING_MIRROR_X_VERTEX_GROUPS(_me)
Object is a sort of wrapper for general info.
@ VP_FLAG_VGROUP_RESTRICT
#define OPERATOR_RETVAL_CHECK(ret)
void ED_paint_cursor_start(struct Paint *p, bool(*poll)(struct bContext *C))
void ED_mesh_mirror_topo_table_end(struct Object *ob)
bool ED_vgroup_sync_from_pose(struct Object *ob)
bool ED_mesh_color_ensure(struct Mesh *me, const char *name)
void ED_mesh_mirror_spatial_table_end(struct Object *ob)
int mesh_get_x_mirror_vert(struct Object *ob, struct Mesh *me_eval, int index, bool use_topology)
void ED_object_posemode_set_for_weight_paint(struct bContext *C, struct Main *bmain, struct Object *ob, bool is_mode_set)
bool ED_object_mode_compat_set(struct bContext *C, struct Object *ob, eObjectMode mode, struct ReportList *reports)
void ED_region_tag_redraw_partial(struct ARegion *region, const struct rcti *rct, bool rebuild)
void ED_region_tag_redraw(struct ARegion *region)
@ V3D_PROJ_TEST_CLIP_NEAR
void ED_view3d_viewcontext_init(struct bContext *C, struct ViewContext *vc, struct Depsgraph *depsgraph)
void ED_view3d_ob_project_mat_get(const struct RegionView3D *v3d, const struct Object *ob, float r_pmat[4][4])
eV3DProjStatus ED_view3d_project_float_object(const struct ARegion *region, const float co[3], float r_co[2], eV3DProjTest flag)
void view3d_operator_needs_opengl(const struct bContext *C)
void ED_view3d_init_mats_rv3d(const struct Object *ob, struct RegionView3D *rv3d)
_GL_VOID GLfloat value _GL_VOID_RET _GL_VOID const GLuint GLboolean *residences _GL_BOOL_RET _GL_VOID GLsizei GLfloat GLfloat GLfloat GLfloat const GLubyte *bitmap _GL_VOID_RET _GL_VOID GLenum const void *lists _GL_VOID_RET _GL_VOID const GLdouble *equation _GL_VOID_RET _GL_VOID GLdouble GLdouble blue _GL_VOID_RET _GL_VOID GLfloat GLfloat blue _GL_VOID_RET _GL_VOID GLint GLint blue _GL_VOID_RET _GL_VOID GLshort GLshort blue _GL_VOID_RET _GL_VOID GLubyte GLubyte blue _GL_VOID_RET _GL_VOID GLuint GLuint blue _GL_VOID_RET _GL_VOID GLushort GLushort blue _GL_VOID_RET _GL_VOID GLbyte GLbyte GLbyte alpha _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble alpha _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat alpha _GL_VOID_RET _GL_VOID GLint GLint GLint alpha _GL_VOID_RET _GL_VOID GLshort GLshort GLshort alpha _GL_VOID_RET _GL_VOID GLubyte GLubyte GLubyte alpha _GL_VOID_RET _GL_VOID GLuint GLuint GLuint alpha _GL_VOID_RET _GL_VOID GLushort GLushort GLushort alpha _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLint GLsizei GLsizei GLenum type _GL_VOID_RET _GL_VOID GLsizei GLenum GLenum const void *pixels _GL_VOID_RET _GL_VOID const void *pointer _GL_VOID_RET _GL_VOID GLdouble v _GL_VOID_RET _GL_VOID GLfloat v _GL_VOID_RET _GL_VOID GLint GLint i2 _GL_VOID_RET _GL_VOID GLint j _GL_VOID_RET _GL_VOID GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble GLdouble GLdouble zFar _GL_VOID_RET _GL_UINT GLdouble *equation _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLenum GLfloat *v _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLfloat *values _GL_VOID_RET _GL_VOID GLushort *values _GL_VOID_RET _GL_VOID GLenum GLfloat *params _GL_VOID_RET _GL_VOID GLenum GLdouble *params _GL_VOID_RET _GL_VOID GLenum GLint *params _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_BOOL GLfloat param _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID GLenum GLfloat param _GL_VOID_RET _GL_VOID GLenum GLint param _GL_VOID_RET _GL_VOID GLushort pattern _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLint const GLdouble *points _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLint GLdouble GLdouble GLint GLint const GLdouble *points _GL_VOID_RET _GL_VOID GLdouble GLdouble u2 _GL_VOID_RET _GL_VOID GLdouble GLdouble GLint GLdouble GLdouble v2 _GL_VOID_RET _GL_VOID GLenum GLfloat param _GL_VOID_RET _GL_VOID GLenum GLint param _GL_VOID_RET _GL_VOID GLenum mode _GL_VOID_RET _GL_VOID GLdouble GLdouble nz _GL_VOID_RET _GL_VOID GLfloat GLfloat nz _GL_VOID_RET _GL_VOID GLint GLint nz _GL_VOID_RET _GL_VOID GLshort GLshort nz _GL_VOID_RET _GL_VOID GLsizei const void *pointer _GL_VOID_RET _GL_VOID GLsizei const GLfloat *values _GL_VOID_RET _GL_VOID GLsizei const GLushort *values _GL_VOID_RET _GL_VOID GLint param _GL_VOID_RET _GL_VOID const GLuint const GLclampf *priorities _GL_VOID_RET _GL_VOID GLdouble y _GL_VOID_RET _GL_VOID GLfloat y _GL_VOID_RET _GL_VOID GLint y _GL_VOID_RET _GL_VOID GLshort y _GL_VOID_RET _GL_VOID GLdouble GLdouble z _GL_VOID_RET _GL_VOID GLfloat GLfloat z _GL_VOID_RET _GL_VOID GLint GLint z _GL_VOID_RET _GL_VOID GLshort GLshort z _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble w _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat w _GL_VOID_RET _GL_VOID GLint GLint GLint w _GL_VOID_RET _GL_VOID GLshort GLshort GLshort w _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble y2 _GL_VOID_RET _GL_VOID GLfloat GLfloat GLfloat y2 _GL_VOID_RET _GL_VOID GLint GLint GLint y2 _GL_VOID_RET _GL_VOID GLshort GLshort GLshort y2 _GL_VOID_RET _GL_VOID GLdouble GLdouble GLdouble z _GL_VOID_RET _GL_VOID GLdouble GLdouble z _GL_VOID_RET _GL_VOID GLuint *buffer _GL_VOID_RET _GL_VOID GLdouble t _GL_VOID_RET _GL_VOID GLfloat t _GL_VOID_RET _GL_VOID GLint t _GL_VOID_RET _GL_VOID GLshort t _GL_VOID_RET _GL_VOID GLdouble GLdouble r _GL_VOID_RET _GL_VOID GLfloat GLfloat r _GL_VOID_RET _GL_VOID GLint GLint r _GL_VOID_RET _GL_VOID GLshort GLshort r _GL_VOID_RET _GL_VOID GLdouble GLdouble r
BLI_INLINE void IMB_colormanagement_srgb_to_scene_linear_v3(float scene_linear[3], const float srgb[3])
Read Guarded memory(de)allocation.
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 Sky Generate a procedural sky texture Noise Generate fractal Perlin noise Wave Generate procedural bands or rings with noise 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 or normal between and object coordinate space Combine Create a color from its and value channels Color Retrieve a color or the default fallback if none is specified Separate Split a vector into its and Z components Generates normals with round corners and may slow down renders Vector Displace the surface along an arbitrary direction White Return a random value or color based on an input seed Float Map an input float to a curve and outputs a float value Separate Color
Group Output data from inside of a node group A color picker Mix two input colors RGB to Convert a color s luminance to a grayscale value Generate a normal vector and a dot product Bright Control the brightness and contrast of the input color Vector Map an input vectors to used to fine tune the interpolation of the input Camera Retrieve information about the camera and how it relates to the current shading point s position Clamp a value between a minimum and a maximum Vector Perform vector math operation Invert a producing a negative Combine Generate a color from its and blue Hue Saturation Value
Group Output data from inside of a node group A color picker Mix two input colors RGB to Convert a color s luminance to a grayscale value Generate a normal vector and a dot product Bright Control the brightness and contrast of the input color Vector Map an input vectors to used to fine tune the interpolation of the input Camera Retrieve information about the camera and how it relates to the current shading point s position CLAMP
Group Output data from inside of a node group A color picker Mix two input colors RGB to Convert a color s luminance to a grayscale value Generate a normal vector and a dot product Bright Control the brightness and contrast of the input color Vector Map an input vectors to used to fine tune the interpolation of the input Camera Retrieve information about the camera and how it relates to the current shading point s position Clamp a value between a minimum and a maximum Vector Perform vector math operation Invert a color
#define BM_ELEM_CD_GET_VOID_P(ele, offset)
#define BM_elem_flag_test(ele, hflag)
#define BM_ITER_MESH(ele, iter, bm, itype)
ATTR_WARN_UNUSED_RESULT BMesh * bm
ATTR_WARN_UNUSED_RESULT const BMLoop * l
static T sum(const btAlignedObjectArray< T > &items)
SIMD_FORCE_INLINE btScalar angle(const btVector3 &v) const
Return the angle between this and another vector.
const Depsgraph * depsgraph
void *(* MEM_malloc_arrayN)(size_t len, size_t size, const char *str)
void(* MEM_freeN)(void *vmemh)
void *(* MEM_dupallocN)(const void *vmemh)
void *(* MEM_callocN)(size_t len, const char *str)
void *(* MEM_mallocN)(size_t len, const char *str)
static void area(int d1, int d2, int e1, int e2, float weights[2])
void parallel_for(IndexRange range, int64_t grain_size, const Function &function)
ColorSceneLinear4f< eAlpha::Straight > ColorPaint4f
static const pxr::TfToken rgba("rgba", pxr::TfToken::Immortal)
void paint_cursor_delete_textures(void)
void paint_stroke_cancel(struct bContext *C, struct wmOperator *op, struct PaintStroke *stroke)
float ED_wpaint_blend_tool(int tool, float weight, float paintval, float alpha)
int paint_stroke_modal(struct bContext *C, struct wmOperator *op, const struct wmEvent *event, struct PaintStroke **stroke_p)
int paint_stroke_exec(struct bContext *C, struct wmOperator *op, struct PaintStroke *stroke)
bool ED_wpaint_ensure_data(struct bContext *C, struct ReportList *reports, enum eWPaintFlag flag, struct WPaintVGroupIndex *vgroup_index)
struct PaintStroke * paint_stroke_new(struct bContext *C, struct wmOperator *op, StrokeGetLocation get_location, StrokeTestStart test_start, StrokeUpdateStep update_step, StrokeRedraw redraw, StrokeDone done, int event_type)
void paint_stroke_set_mode_data(struct PaintStroke *stroke, void *mode_data)
float paint_calc_object_space_radius(struct ViewContext *vc, const float center[3], float pixel_radius)
void paint_stroke_free(struct bContext *C, struct wmOperator *op, struct PaintStroke *stroke)
void ED_vpaint_proj_handle_free(struct VertProjHandle *vp_handle)
struct VertProjHandle * ED_vpaint_proj_handle_create(struct Depsgraph *depsgraph, struct Scene *scene, struct Object *ob, struct CoNo **r_vcosnos)
bool paint_supports_dynamic_size(struct Brush *br, enum ePaintMode mode)
void * paint_stroke_mode_data(struct PaintStroke *stroke)
struct ViewContext * paint_stroke_view_context(struct PaintStroke *stroke)
void paint_stroke_operator_properties(struct wmOperatorType *ot)
static void do_wpaint_brush_smear_task_cb_ex(void *__restrict userdata, const int n, const TaskParallelTLS *__restrict UNUSED(tls))
static int wpaint_exec(bContext *C, wmOperator *op)
void PAINT_OT_vertex_color_set(wmOperatorType *ot)
void ED_object_wpaintmode_exit_ex(Object *ob)
void ED_object_vpaintmode_exit_ex(Object *ob)
static bool wpaint_stroke_test_start(bContext *C, wmOperator *op, const float mouse[2])
static void vpaint_do_draw(bContext *C, Sculpt *UNUSED(sd), VPaint *vp, VPaintData< Color, Traits, domain > *vpd, Object *ob, Mesh *me, PBVHNode **nodes, int totnode, Color *lcol)
static void vpaint_stroke_update_step_intern(bContext *C, PaintStroke *stroke, PointerRNA *itemptr)
static bool vpaint_stroke_test_start(bContext *C, wmOperator *op, const float mouse[2])
static void do_weight_paint_normalize_all(MDeformVert *dvert, const int defbase_tot, const bool *vgroup_validmap)
void ED_object_wpaintmode_enter_ex(Main *bmain, Depsgraph *depsgraph, Scene *scene, Object *ob)
void ED_object_vpaintmode_enter(bContext *C, Depsgraph *depsgraph)
bool BKE_object_attributes_active_color_fill(Object *ob, const float fill_color[4], bool only_selected)
void PAINT_OT_weight_paint(wmOperatorType *ot)
static void vertex_paint_init_session_data(const ToolSettings *ts, Object *ob)
static float paint_and_tex_color_alpha(VPaint *vp, VPaintData< Color, Traits, domain > *vpd, const float v_co[3], Color *r_color)
static Color vpaint_get_current_col(Scene *scene, VPaint *vp, bool secondary)
static void wpaint_do_radial_symmetry(bContext *C, Object *ob, VPaint *wp, Sculpt *sd, WPaintData *wpd, WeightPaintInfo *wpi, Mesh *me, Brush *brush, const char symm, const int axis)
static PBVHNode ** vwpaint_pbvh_gather_generic(Object *ob, VPaint *wp, Sculpt *sd, Brush *brush, int *r_totnode)
void PAINT_OT_vertex_paint(wmOperatorType *ot)
static int vpaint_mode_toggle_exec(bContext *C, wmOperator *op)
static float wpaint_get_active_weight(const MDeformVert *dv, const WeightPaintInfo *wpi)
static void get_brush_alpha_data(const Scene *scene, const SculptSession *ss, const Brush *brush, float *r_brush_size_pressure, float *r_brush_alpha_value, float *r_brush_alpha_pressure)
uint vpaint_get_current_color(Scene *scene, VPaint *vp, bool secondary)
static bool weight_paint_poll_ex(bContext *C, bool check_tool)
static int wpaint_mode_toggle_exec(bContext *C, wmOperator *op)
bool weight_paint_mode_poll(bContext *C)
static void vpaint_paint_leaves(bContext *C, Sculpt *sd, VPaint *vp, VPaintData< Color, Traits, domain > *vpd, Object *ob, Mesh *me, Color *lcol, PBVHNode **nodes, int totnode)
static int vpaint_invoke(bContext *C, wmOperator *op, const wmEvent *event)
static bool vertex_paint_poll_ex(bContext *C, bool check_tool)
bool weight_paint_poll(bContext *C)
static void paint_and_tex_color_alpha_intern(VPaint *vp, const ViewContext *vc, const float co[3], float r_rgba[4])
static float wpaint_blend(const VPaint *wp, float weight, const float alpha, float paintval, const float UNUSED(brush_alpha_value), const bool do_flip)
static void vwpaint_update_cache_invariants(bContext *C, VPaint *vp, SculptSession *ss, wmOperator *op, const float mval[2])
static Color vpaint_blend(const VPaint *vp, Color color_curr, Color color_orig, Color color_paint, const typename Traits::ValueType alpha, const typename Traits::BlendType brush_alpha_value)
void ED_object_wpaintmode_exit(bContext *C)
static void vpaint_stroke_done(const bContext *C, PaintStroke *stroke)
static bool brush_use_accumulate_ex(const Brush *brush, const int ob_mode)
static bool multipaint_verify_change(MDeformVert *dvert, const int defbase_tot, float change, const bool *defbase_sel)
static void vpaint_do_blur(bContext *C, Sculpt *sd, VPaint *vp, VPaintData< Color, Traits, domain > *vpd, Object *ob, Mesh *me, PBVHNode **nodes, int totnode, Color *lcol)
static void vpaint_do_symmetrical_brush_actions(bContext *C, Sculpt *sd, VPaint *vp, VPaintData< Color, Traits, domain > *vpd, Object *ob)
static bool isZero(ColorPaint4f c)
static int vpaint_exec(bContext *C, wmOperator *op)
bool vertex_paint_poll_ignore_tool(bContext *C)
static int wpaint_invoke(bContext *C, wmOperator *op, const wmEvent *event)
static void precompute_weight_values(bContext *C, Object *ob, Brush *brush, WPaintData *wpd, WeightPaintInfo *wpi, Mesh *me)
void ED_object_vpaintmode_enter_ex(Main *bmain, Depsgraph *depsgraph, Scene *scene, Object *ob)
static bool paint_object_attributes_active_color_fill_ex(Object *ob, ColorPaint4f fill_color, bool only_selected=true)
static void wpaint_do_symmetrical_brush_actions(bContext *C, Object *ob, VPaint *wp, Sculpt *sd, WPaintData *wpd, WeightPaintInfo *wpi)
static void vpaint_free_vpaintdata(Object *UNUSED(ob), void *_vpd)
static bool paint_mode_toggle_poll_test(bContext *C)
static void do_wpaint_brush_draw_task_cb_ex(void *__restrict userdata, const int n, const TaskParallelTLS *__restrict UNUSED(tls))
static void smooth_brush_toggle_off(const bContext *C, Paint *paint, StrokeCache *cache)
static void do_weight_paint_vertex(const VPaint *wp, Object *ob, const WeightPaintInfo *wpi, const uint index, float alpha, float paintweight)
static float wpaint_clamp_monotonic(float oldval, float curval, float newval)
static ColorPaint4f toFloat(const Color &c)
static void do_wpaint_precompute_weight_cb_ex(void *__restrict userdata, const int n, const TaskParallelTLS *__restrict UNUSED(tls))
static void wpaint_paint_leaves(bContext *C, Object *ob, Sculpt *sd, VPaint *vp, WPaintData *wpd, WeightPaintInfo *wpi, Mesh *me, PBVHNode **nodes, int totnode)
static void vpaint_do_radial_symmetry(bContext *C, Sculpt *sd, VPaint *vp, VPaintData< Color, Traits, domain > *vpd, Object *ob, Mesh *me, Brush *brush, const char symm, const int axis)
static bool vwpaint_use_normal(const VPaint *vp)
static void paint_last_stroke_update(Scene *scene, const float location[3])
void ED_object_vpaintmode_exit(bContext *C)
static float wpaint_undo_lock_relative(float weight, float old_weight, float locked_weight, float free_weight, bool auto_normalize)
static void do_wpaint_brush_blur_task_cb_ex(void *__restrict userdata, const int n, const TaskParallelTLS *__restrict UNUSED(tls))
bool vertex_paint_mode_poll(bContext *C)
static void vpaint_do_paint(bContext *C, Sculpt *sd, VPaint *vp, VPaintData< Color, Traits, domain > *vpd, Object *ob, Mesh *me, Brush *brush, const char symm, const int axis, const int i, const float angle)
bool weight_paint_poll_ignore_tool(bContext *C)
static void wpaint_stroke_done(const bContext *C, PaintStroke *stroke)
static void wpaint_cancel(bContext *C, wmOperator *op)
static void smooth_brush_toggle_on(const bContext *C, Paint *paint, StrokeCache *cache)
static int get_vcol_elements(Mesh *me, size_t *r_elem_size)
static bool vertex_color_set(Object *ob, ColorPaint4f paintcol_in, CustomDataLayer *layer)
static int wpaint_modal(bContext *C, wmOperator *op, const wmEvent *event)
static void vpaint_stroke_update_step(bContext *C, wmOperator *UNUSED(op), PaintStroke *stroke, PointerRNA *itemptr)
static void vertex_paint_init_stroke(Scene *scene, Depsgraph *depsgraph, Object *ob)
static void vertex_paint_init_session(Depsgraph *depsgraph, Scene *scene, Object *ob, eObjectMode object_mode)
static bool brush_use_accumulate(const VPaint *vp)
void PAINT_OT_weight_paint_toggle(wmOperatorType *ot)
static void do_weight_paint_vertex_multi(const VPaint *wp, Object *ob, const WeightPaintInfo *wpi, const uint index, float alpha, float paintweight)
static void do_vpaint_brush_blur_loops(bContext *C, Sculpt *UNUSED(sd), VPaint *vp, VPaintData< Color, Traits, ATTR_DOMAIN_CORNER > *vpd, Object *ob, Mesh *me, PBVHNode **nodes, int totnode, Color *lcol)
static void do_vpaint_brush_smear(bContext *C, Sculpt *UNUSED(sd), VPaint *vp, VPaintData< Color, Traits, domain > *vpd, Object *ob, Mesh *me, PBVHNode **nodes, int totnode, Color *lcol)
static void multipaint_apply_change(MDeformVert *dvert, const int defbase_tot, float change, const bool *defbase_sel)
static void wpaint_do_paint(bContext *C, Object *ob, VPaint *wp, Sculpt *sd, WPaintData *wpd, WeightPaintInfo *wpi, Mesh *me, Brush *brush, const char symm, const int axis, const int i, const float angle)
static Color fromFloat(const ColorPaint4f &c)
static void view_angle_limits_init(NormalAnglePrecalc *a, float angle, bool do_mask_normal)
static void do_weight_paint_vertex_single(const VPaint *wp, Object *ob, const WeightPaintInfo *wpi, const uint index, float alpha, float paintweight)
static void calculate_average_weight(SculptThreadedTaskData *data, PBVHNode **UNUSED(nodes), int totnode)
static void multipaint_clamp_change(MDeformVert *dvert, const int defbase_tot, const bool *defbase_sel, float *change_p)
static float view_angle_limits_apply_falloff(const NormalAnglePrecalc *a, float angle_cos, float *mask_p)
void PAINT_OT_vertex_paint_toggle(wmOperatorType *ot)
static void wpaint_stroke_update_step(bContext *C, wmOperator *UNUSED(op), PaintStroke *stroke, PointerRNA *itemptr)
static int vpaint_modal(bContext *C, wmOperator *op, const wmEvent *event)
static void do_weight_paint_normalize_all_locked_try_active(MDeformVert *dvert, const int defbase_tot, const bool *vgroup_validmap, const bool *lock_flags, const bool *lock_with_active)
static MDeformVert * defweight_prev_init(MDeformVert *dvert_prev, MDeformVert *dvert_curr, int index)
static int vertex_color_set_exec(bContext *C, wmOperator *UNUSED(op))
static void ed_vwpaintmode_enter_generic(Main *bmain, Depsgraph *depsgraph, Scene *scene, Object *ob, const eObjectMode mode_flag)
static void do_wpaint_brush_calc_average_weight_cb_ex(void *__restrict userdata, const int n, const TaskParallelTLS *__restrict UNUSED(tls))
static void vpaint_cancel(bContext *C, wmOperator *op)
static void calculate_average_color(VPaintData< Color, Traits, domain > *vpd, Object *ob, Mesh *me, const Brush *brush, Color *lcol, PBVHNode **nodes, int totnode)
void ED_object_wpaintmode_enter(bContext *C, Depsgraph *depsgraph)
static void vwpaint_init_stroke(Depsgraph *depsgraph, Object *ob)
static uint color2uint(ColorPaint4b c)
bool vertex_paint_poll(bContext *C)
static void do_vpaint_brush_blur_verts(bContext *C, Sculpt *UNUSED(sd), VPaint *vp, VPaintData< Color, Traits, ATTR_DOMAIN_POINT > *vpd, Object *ob, Mesh *me, PBVHNode **nodes, int totnode, Color *lcol)
static void ed_vwpaintmode_exit_generic(Object *ob, const eObjectMode mode_flag)
static void * vpaint_init_vpaint(bContext *C, wmOperator *op, Scene *scene, Depsgraph *depsgraph, VPaint *vp, Object *ob, Mesh *me, const Brush *brush)
static void vwpaint_update_cache_variants(bContext *C, VPaint *vp, Object *ob, PointerRNA *ptr)
static bool do_weight_paint_normalize_all_locked(MDeformVert *dvert, const int defbase_tot, const bool *vgroup_validmap, const bool *lock_flags)
void RNA_float_get_array(PointerRNA *ptr, const char *name, float *values)
float RNA_float_get(PointerRNA *ptr, const char *name)
bool RNA_boolean_get(PointerRNA *ptr, const char *name)
int RNA_enum_get(PointerRNA *ptr, const char *name)
bool SCULPT_pbvh_calc_area_normal(const Brush *brush, Object *ob, PBVHNode **nodes, int totnode, bool use_threading, float r_area_no[3])
bool SCULPT_stroke_get_location(bContext *C, float out[3], const float mval[2], bool force_original)
void SCULPT_cache_calc_brushdata_symm(StrokeCache *cache, const char symm, const char axis, const float angle)
const float * SCULPT_brush_frontface_normal_from_falloff_shape(SculptSession *ss, char falloff_shape)
SculptBrushTestFn SCULPT_brush_test_init_with_falloff_shape(SculptSession *ss, SculptBrushTest *test, char falloff_shape)
bool SCULPT_search_sphere_cb(PBVHNode *node, void *data_v)
bool SCULPT_has_loop_colors(const Object *ob)
char SCULPT_mesh_symmetry_xyz_get(Object *object)
bool SCULPT_search_circle_cb(PBVHNode *node, void *data_v)
void SCULPT_cache_free(StrokeCache *cache)
bool SCULPT_get_redraw_rect(ARegion *region, RegionView3D *rv3d, Object *ob, rcti *rect)
static float brush_strength(const Sculpt *sd, const StrokeCache *cache, const float feather, const UnifiedPaintSettings *ups, const PaintModeSettings *UNUSED(paint_mode_settings))
void SCULPT_undo_push_begin(struct Object *ob, const char *name)
void SCULPT_undo_push_end(struct Object *ob)
bool(* SculptBrushTestFn)(SculptBrushTest *test, const float co[3])
SculptUndoNode * SCULPT_undo_push_node(Object *ob, PBVHNode *node, SculptUndoType type)
struct CurveMapping * curve
struct BMEditMesh * edit_mesh
struct MDeformVert * dvert
ListBase vertex_group_names
struct SculptSession * sculpt
struct Paint_Runtime runtime
struct ParticleSystem * next
struct ToolSettings * toolsettings
struct SculptSession::@53::@54 vpaint
struct SculptSession::@53::@55 wpaint
union SculptSession::@53 mode
struct StrokeCache * cache
struct MeshElemMap * vert_to_loop
struct MeshElemMap * vert_to_poly
const struct Brush * brush
float true_view_normal[3]
float projection_mat[4][4]
void * prev_colors_vpaint
char saved_active_brush_name[MAX_ID_NAME]
float sculpt_normal_symm[3]
float average_stroke_accum[3]
int average_stroke_counter
struct VertProjHandle * vp_handle
NormalAnglePrecalc normal_angle_precalc
struct VPaintData::@510 smear
struct RegionView3D * rv3d
const bool * vgroup_unlocked
NormalAnglePrecalc normal_angle_precalc
WeightPaintGroupData active
const bool * vgroup_validmap
const bool * vgroup_locked
bool precomputed_weight_ready
float * precomputed_weight
WeightPaintGroupData mirror
const bool * vgroup_locked
WeightPaintGroupData mirror
const bool * vgroup_unlocked
const bool * vgroup_validmap
WeightPaintGroupData active
int(* invoke)(struct bContext *, struct wmOperator *, const struct wmEvent *) ATTR_WARN_UNUSED_RESULT
int(* modal)(struct bContext *, struct wmOperator *, const struct wmEvent *) ATTR_WARN_UNUSED_RESULT
bool(* poll)(struct bContext *) ATTR_WARN_UNUSED_RESULT
void(* cancel)(struct bContext *, struct wmOperator *)
int(* exec)(struct bContext *, struct wmOperator *) ATTR_WARN_UNUSED_RESULT
struct ReportList * reports
struct wmOperatorType * type
static int blend(const Tex *tex, const float texvec[3], TexResult *texres)
wmEventHandler_Op * WM_event_add_modal_handler(bContext *C, wmOperator *op)
void WM_event_add_notifier(const bContext *C, uint type, void *reference)
#define WM_msg_publish_rna_prop(mbus, id_, data_, type_, prop_)