61 params->shape_info.tmpkey = skey;
102#define FACE_CUSTOMFILL 4
109#define FLT_FACE_SPLIT_EPSILON 0.00005f
150 return l_new ? l_new->
e :
nullptr;
164 const float no_dir[3],
176 float no_mid[3], no_ortho[3];
191 bool center_ok =
false;
194 float plane_a[4], plane_b[4], plane_c[4];
195 float v_a_no_ortho[3], v_b_no_ortho[3];
212 if (center_ok ==
false) {
219 float ofs_a[3], ofs_b[3], ofs_slerp[3];
220 float dist_a, dist_b;
245 float *co =
static_cast<float *
>(
254 else if (
params->use_smooth) {
257#define USE_SPHERE_DUAL_BLEND
259 const float eps_unit_vec = 1e-5f;
263#ifdef USE_SPHERE_DUAL_BLEND
264 float no_reflect[3], co_a[3], co_b[3];
270#ifndef USE_SPHERE_DUAL_BLEND
305 smooth =
fabsf(1.0f - 2.0f *
fabsf(0.5f - perc));
309 if (
params->use_smooth_even) {
314 if (smooth != 1.0f) {
320#undef USE_SPHERE_DUAL_BLEND
323 if (
params->use_fractal) {
324 float normal[3], co2[3], base1[3], base2[3], tvec[3];
355 if (
params->shape_info.totlayer > 1) {
361 i =
params->shape_info.totlayer - 1;
377 const float factor_edge_split,
378 const float factor_subd,
395 if (edge->
v1->f2 & edge->
v2->f2 & 1) {
398 if (edge->
v1->f2 & edge->
v2->f2 & 2) {
401 if (edge->
v1->f2 & edge->
v2->f2 & 4) {
424 float factor_edge_split, factor_subd;
427 factor_edge_split = BMO_slot_map_float_get(
params->slot_edge_percents, edge);
431 factor_edge_split = 1.0f /
float(totpoint + 1 - curpoint);
432 factor_subd =
float(curpoint + 1) /
float(totpoint + 1);
436 bm, edge, e_orig,
params, factor_edge_split, factor_subd, v_a, v_b, r_edge);
443 BMEdge *eed = edge, *e_new, e_tmp = *edge;
444 BMVert *
v, v1_tmp = *edge->
v1, v2_tmp = *edge->
v2, *v1 = edge->
v1, *
v2 = edge->
v2;
445 int i, numcuts =
params->numcuts;
450 for (
i = 0;
i < numcuts;
i++) {
461 if (
v->e &&
v->e->l) {
493 if ((numcuts % 2) == 0) {
495 for (
i = 0;
i < numcuts;
i++) {
496 if (
i == numcuts / 2) {
504 for (
i = 0;
i < numcuts;
i++) {
506 if (
i == numcuts / 2) {
536 int i, numcuts =
params->numcuts;
538 for (
i = 0;
i < numcuts;
i++) {
568 int i, numcuts =
params->numcuts;
570 v_last =
verts[numcuts];
572 for (
i = numcuts - 1;
i >= 0;
i--) {
578 if (
i != numcuts - 1) {
613 int i, numcuts =
params->numcuts;
615 for (
i = 0;
i < numcuts;
i++) {
647 for (
i = 0;
i < numcuts;
i++) {
648 if (
i == numcuts / 2) {
649 if (numcuts % 2 != 0) {
652 add = numcuts * 2 + 2;
657 for (
i = 0;
i < numcuts / 2 + 1;
i++) {
689 int numcuts =
params->numcuts;
690 int i, j, a,
b, s = numcuts + 2 ;
698 for (
i = 0;
i < numcuts + 2;
i++) {
699 lines[
i] =
verts[numcuts * 3 + 2 + (numcuts -
i + 1)];
703 for (
i = 0;
i < numcuts + 2;
i++) {
704 lines[(s - 1) * s +
i] =
verts[numcuts +
i];
708 for (
i = 0;
i < numcuts;
i++) {
710 b = numcuts + 1 + numcuts + 1 + (numcuts -
i - 1);
720 v1 = lines[(
i + 1) * s] =
verts[a];
721 v2 = lines[(
i + 1) * s + s - 1] =
verts[
b];
724 for (a = 0; a < numcuts; a++) {
730 lines[(
i + 1) * s + a + 1] =
v;
734 for (
i = 1;
i < numcuts + 2;
i++) {
735 for (j = 1; j <= numcuts; j++) {
766 int i, numcuts =
params->numcuts;
768 for (
i = 0;
i < numcuts;
i++) {
798 BMVert ***lines, *
v, v1_tmp, v2_tmp;
800 int i, j, a,
b, numcuts =
params->numcuts;
803 lines =
static_cast<BMVert ***
>(
804 MEM_callocN(
sizeof(
void *) * (numcuts + 2),
"triangle vert table"));
806 lines[0] = (
BMVert **)stackarr;
807 lines[0][0] =
verts[numcuts * 2 + 1];
810 for (
i = 0;
i < numcuts;
i++) {
811 lines[numcuts + 1][
i + 1] =
verts[
i];
813 lines[numcuts + 1][0] =
verts[numcuts * 3 + 2];
814 lines[numcuts + 1][numcuts + 1] =
verts[numcuts];
816 for (
i = 0;
i < numcuts;
i++) {
818 a = numcuts * 2 + 2 +
i;
819 b = numcuts + numcuts -
i;
828 lines[
i + 1][0] =
verts[a];
836 for (j = 0; j <
i; j++) {
838 lines[
i + 1][j + 1] =
v;
856 for (
i = 1;
i <= numcuts;
i++) {
857 for (j = 0; j <
i; j++) {
871 for (
i = 1;
i < numcuts + 2;
i++) {
901#define PATTERNS_TOT ARRAY_SIZE(patterns)
916 BMIter viter, fiter, liter;
921 float smooth, fractal, along_normal;
922 bool use_sphere, use_single_edge, use_grid_fill, use_only_quads;
923 int cornertype,
seed,
i, j, a,
b, numcuts, totesel, smooth_falloff;
942 switch (cornertype) {
954 if (use_single_edge) {
978 float *co =
static_cast<float *
>(
991 params.smooth_falloff = smooth_falloff;
994 params.along_normal = along_normal;
995 params.use_smooth = (smooth != 0.0f);
997 params.use_fractal = (fractal != 0.0f);
998 params.use_sphere = use_sphere;
1000 if (
params.use_fractal) {
1020 BMEdge *e1 =
nullptr, *e2 =
nullptr;
1021 float vec1[3], vec2[3];
1022 bool matched =
false;
1025 if (use_only_quads && face->
len != 4) {
1035 edges[
i] = l_new->
e;
1064 *BMO_slot_map_data_get(
params.slot_custom_patterns, face));
1065 for (
i = 0;
i < pat->
len;
i++) {
1067 for (j = 0; j < pat->
len; j++) {
1068 a = (j +
i) % pat->
len;
1097 if (pat->
len == face->
len) {
1098 for (a = 0; a < pat->
len; a++) {
1100 for (
b = 0;
b < pat->
len;
b++) {
1101 j = (
b + a) % pat->
len;
1126 if (!matched && totesel) {
1133 fd->
start =
nullptr;
1143 for (
i = 0;
i < einput->
len;
i++) {
1150 const float *co =
static_cast<const float *
>(
1155 using LoopPair = std::array<BMLoop *, 2>;
1178 for (a = 0; a < vlen; a++) {
1189 b = (a + numcuts + 1) % vlen;
1193 for (j = 0; j < vlen; j++) {
1194 b = (j + a + numcuts + 1) % vlen;
1206 for (j = 0; j < numcuts; j++) {
1224 if (other_loop->
f != face) {
1238 loops_split[j][0] = loops[a];
1239 loops_split[j][1] = loops[
b];
1242 loops_split[j][0] =
nullptr;
1243 loops_split[j][1] =
nullptr;
1257 for (
const LoopPair &loop_split : loops_split) {
1258 if (loop_split[0]) {
1261 f_new =
BM_face_split(
bm, face, loop_split[0], loop_split[1], &l_new,
nullptr,
false);
1276 if (l_new->
v == fd->
start) {
1284 b = (j - a + face->
len) % face->
len;
1294 const float *co =
static_cast<const float *
>(
1313 const char edge_hflag,
1315 const short smooth_falloff,
1316 const bool use_smooth_even,
1317 const float fractal,
1318 const float along_normal,
1321 const int cornertype,
1322 const short use_single_edge,
1323 const short use_grid_fill,
1324 const short use_only_quads,
1333 "subdivide_edges edges=%he "
1334 "smooth=%f smooth_falloff=%i use_smooth_even=%b "
1335 "fractal=%f along_normal=%f "
1337 "quad_corner_type=%i "
1338 "use_single_edge=%b use_grid_fill=%b "
1339 "use_only_quads=%b "
1398 if (
bm->uv_select_sync_valid) {
CustomData interface, see also DNA_customdata_types.h.
int CustomData_get_offset(const CustomData *data, eCustomDataType type)
int CustomData_get_n_offset(const CustomData *data, eCustomDataType type, int n)
int CustomData_number_of_layers(const CustomData *data, eCustomDataType type)
MINLINE float interpf(float target, float origin, float t)
void plane_from_point_normal_v3(float r_plane[4], const float plane_co[3], const float plane_no[3])
MINLINE float shell_v3v3_mid_normalized_to_dist(const float a[3], const float b[3])
bool isect_plane_plane_plane_v3(const float plane_a[4], const float plane_b[4], const float plane_c[4], float r_isect_co[3]) ATTR_WARN_UNUSED_RESULT
MINLINE float len_v3v3(const float a[3], const float b[3]) ATTR_WARN_UNUSED_RESULT
MINLINE void madd_v3_v3fl(float r[3], const float a[3], float f)
bool interp_v3_v3v3_slerp(float target[3], const float a[3], const float b[3], float t) ATTR_WARN_UNUSED_RESULT
MINLINE void sub_v3_v3(float r[3], const float a[3])
void reflect_v3_v3v3(float out[3], const float v[3], const float normal[3])
MINLINE float len_squared_v3v3(const float a[3], const float b[3]) ATTR_WARN_UNUSED_RESULT
MINLINE void sub_v3_v3v3(float r[3], const float a[3], const float b[3])
void project_v3_plane(float out[3], const float plane_no[3], const float plane_co[3])
MINLINE void mul_v3_fl(float r[3], float f)
MINLINE void copy_v3_v3(float r[3], const float a[3])
MINLINE float dot_v3v3(const float a[3], const float b[3]) ATTR_WARN_UNUSED_RESULT
void interp_v3_v3v3(float r[3], const float a[3], const float b[3], float t)
MINLINE void add_v3_v3v3(float r[3], const float a[3], const float b[3])
MINLINE void cross_v3_v3v3(float r[3], const float a[3], const float b[3])
void mid_v3_v3v3(float r[3], const float a[3], const float b[3])
void ortho_basis_v3v3_v3(float r_n1[3], float r_n2[3], const float n[3])
MINLINE void madd_v3_v3v3fl(float r[3], const float a[3], const float b[3], float f)
MINLINE float normalize_v3_length(float n[3], float unit_length)
MINLINE float normalize_v3(float n[3])
float BLI_noise_generic_turbulence(float noisesize, float x, float y, float z, int oct, bool hard, int noisebasis)
void BLI_rng_free(struct RNG *rng) ATTR_NONNULL(1)
struct RNG * BLI_rng_new_srandom(unsigned int seed)
float BLI_rng_get_float(struct RNG *rng) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL(1)
bool BLI_stack_is_empty(const BLI_Stack *stack) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL()
void BLI_stack_free(BLI_Stack *stack) ATTR_NONNULL()
void * BLI_stack_peek(BLI_Stack *stack) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL()
void * BLI_stack_push_r(BLI_Stack *stack) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL()
void BLI_stack_discard(BLI_Stack *stack) ATTR_NONNULL()
#define BLI_stack_new(esize, descr)
Read Guarded memory(de)allocation.
#define BM_ELEM_CD_GET_VOID_P(ele, offset)
void BM_data_layer_free_n(BMesh *bm, CustomData *data, int type, int n)
void BM_data_layer_add(BMesh *bm, CustomData *data, int type)
#define BM_ITER_ELEM(ele, iter, data, itype)
#define BM_ITER_MESH(ele, iter, bm, itype)
#define BM_ITER_ELEM_INDEX(ele, iter, data, itype, indexvar)
void BM_mesh_elem_hflag_disable_all(BMesh *bm, const char htype, const char hflag, const bool respecthide)
void BM_mesh_select_flush_from_verts(BMesh *bm, const bool select)
BMVert * BM_edge_split(BMesh *bm, BMEdge *e, BMVert *v, BMEdge **r_e, float fac)
Edge Split.
BMFace * BM_face_split(BMesh *bm, BMFace *f, BMLoop *l_a, BMLoop *l_b, BMLoop **r_l, BMEdge *example, const bool no_double)
Face Split.
void BMO_slot_buffer_flag_enable(BMesh *bm, BMOpSlot slot_args[BMO_OP_MAX_SLOTS], const char *slot_name, char htype, short oflag)
BMO_FLAG_BUFFER.
void BMO_slot_buffer_hflag_enable(BMesh *bm, BMOpSlot slot_args[BMO_OP_MAX_SLOTS], const char *slot_name, char htype, char hflag, bool do_flush)
BMO_FLAG_BUFFER.
#define BMO_edge_flag_test(bm, e, oflag)
void BMO_slot_map_to_flag(BMesh *bm, BMOpSlot slot_args[BMO_OP_MAX_SLOTS], const char *slot_name, char htype, short oflag)
#define BMO_edge_flag_enable(bm, e, oflag)
float BMO_slot_float_get(BMOpSlot slot_args[BMO_OP_MAX_SLOTS], const char *slot_name)
#define BMO_vert_flag_enable(bm, e, oflag)
BMOpSlot * BMO_slot_get(BMOpSlot slot_args[BMO_OP_MAX_SLOTS], const char *identifier)
BMESH OPSTACK GET SLOT.
void BMO_op_exec(BMesh *bm, BMOperator *op)
BMESH OPSTACK EXEC OP.
void BMO_slot_buffer_from_enabled_flag(BMesh *bm, BMOperator *op, BMOpSlot slot_args[BMO_OP_MAX_SLOTS], const char *slot_name, char htype, short oflag)
#define BMO_face_flag_enable(bm, e, oflag)
#define BMO_ITER(ele, iter, slot_args, slot_name, restrict_flag)
#define BMO_vert_flag_test(bm, e, oflag)
bool BMO_op_initf(BMesh *bm, BMOperator *op, int flag, const char *fmt,...)
int BMO_slot_int_get(BMOpSlot slot_args[BMO_OP_MAX_SLOTS], const char *slot_name)
void BMO_op_finish(BMesh *bm, BMOperator *op)
BMESH OPSTACK FINISH OP.
#define BMO_FLAG_DEFAULTS
#define BMO_face_flag_test(bm, e, oflag)
bool BMO_slot_bool_get(BMOpSlot slot_args[BMO_OP_MAX_SLOTS], const char *slot_name)
#define BM_CHECK_ELEMENT(el)
float bmesh_subd_falloff_calc(const int falloff, float val)
bool BM_edge_share_vert_check(BMEdge *e1, BMEdge *e2)
BMEdge * BM_edge_exists(BMVert *v_a, BMVert *v_b)
bool BM_vert_in_face(BMVert *v, BMFace *f)
BMFace * BM_vert_pair_share_face_by_len(BMVert *v_a, BMVert *v_b, BMLoop **r_l_a, BMLoop **r_l_b, const bool allow_adjacent)
BLI_INLINE bool BM_loop_is_adjacent(const BMLoop *l_a, const BMLoop *l_b) ATTR_WARN_UNUSED_RESULT ATTR_NONNULL()
ATTR_WARN_UNUSED_RESULT const BMVert * v2
ATTR_WARN_UNUSED_RESULT const BMLoop * l
ATTR_WARN_UNUSED_RESULT const BMVert const BMEdge * e
ATTR_WARN_UNUSED_RESULT const BMLoop * l_b
ATTR_WARN_UNUSED_RESULT const BMVert * v
void BM_mesh_uvselect_flush_post_subdivide(BMesh *bm, const int cd_loop_uv_offset)
void BM_mesh_esubdivide(BMesh *bm, const char edge_hflag, const float smooth, const short smooth_falloff, const bool use_smooth_even, const float fractal, const float along_normal, const int numcuts, const int seltype, const int cornertype, const short use_single_edge, const short use_grid_fill, const short use_only_quads, const int seed)
static void quad_2edge_split_path(BMesh *bm, BMFace *, BMVert **verts, const SubDParams *params)
static void interp_slerp_co_no_v3(const float co_a[3], const float no_a[3], const float co_b[3], const float no_b[3], const float no_dir[3], float fac, float r_co[3])
static const SubDPattern quad_1edge
static void quad_2edge_split_fan(BMesh *bm, BMFace *, BMVert **verts, const SubDParams *params)
static void quad_3edge_split(BMesh *bm, BMFace *, BMVert **verts, const SubDParams *params)
static void tri_1edge_split(BMesh *bm, BMFace *, BMVert **verts, const SubDParams *params)
static const SubDPattern * patterns[]
#define FLT_FACE_SPLIT_EPSILON
static const SubDPattern quad_2edge_fan
static const SubDPattern quad_4edge
static BMVert * bm_subdivide_edge_addvert(BMesh *bm, BMEdge *edge, BMEdge *e_orig, const SubDParams *params, const float factor_edge_split, const float factor_subd, BMVert *v_a, BMVert *v_b, BMEdge **r_edge)
void(*)(BMesh *bm, BMFace *face, BMVert **verts, const SubDParams *params) subd_pattern_fill_fp
static void alter_co(BMVert *v, BMEdge *, const SubDParams *params, const float perc, const BMVert *v_a, const BMVert *v_b)
static const SubDPattern quad_3edge
static const SubDPattern quad_2edge_path
void bmo_subdivide_edges_exec(BMesh *bm, BMOperator *op)
void bmo_bisect_edges_exec(BMesh *bm, BMOperator *op)
static void quad_2edge_split_innervert(BMesh *bm, BMFace *, BMVert **verts, const SubDParams *params)
static BMVert * subdivide_edge_num(BMesh *bm, BMEdge *edge, BMEdge *e_orig, int curpoint, int totpoint, const SubDParams *params, BMVert *v_a, BMVert *v_b, BMEdge **r_edge)
static void tri_3edge_subdivide(BMesh *bm, BMFace *, BMVert **verts, const SubDParams *params)
static const SubDPattern tri_1edge
static void quad_1edge_split(BMesh *bm, BMFace *, BMVert **verts, const SubDParams *params)
static void bmo_subd_init_shape_info(BMesh *bm, SubDParams *params)
static void quad_4edge_subdivide(BMesh *bm, BMFace *, BMVert **verts, const SubDParams *params)
static const SubDPattern tri_3edge
static BMEdge * connect_smallest_face(BMesh *bm, BMVert *v_a, BMVert *v_b, BMFace **r_f_new)
static const SubDPattern quad_2edge_innervert
static void bm_subdivide_multicut(BMesh *bm, BMEdge *edge, const SubDParams *params, BMVert *v_a, BMVert *v_b)
static unsigned long seed
void reinitialize(const int64_t new_size)
void * MEM_calloc_arrayN(size_t len, size_t size, const char *str)
void * MEM_callocN(size_t len, const char *str)
void MEM_freeN(void *vmemh)
static void add(blender::Map< std::string, std::string > &messages, Message &msg)
union BMOpSlot::@313121210037300127305053354046356312170117023254 data
struct BMOpSlot slots_out[BMO_OP_MAX_SLOTS]
struct BMOpSlot slots_in[BMO_OP_MAX_SLOTS]
BMOpSlot * slot_custom_patterns
struct SubDParams::@217262064261340334267141171163117170271177340220 shape_info
int cd_vert_shape_offset_tmp
BMOpSlot * slot_edge_percents
subd_pattern_fill_fp connectexec