/* Static function for alloc (duplicate in modifiers_bmesh.c) */ static BMFace *bm_face_create_from_mpoly(MPoly *mp, MLoop *ml, BMesh *bm, BMVert **vtable, BMEdge **etable) { BMVert **verts = BLI_array_alloca(verts, mp->totloop); BMEdge **edges = BLI_array_alloca(edges, mp->totloop); int j; for (j = 0; j < mp->totloop; j++, ml++) { verts[j] = vtable[ml->v]; edges[j] = etable[ml->e]; } return BM_face_create(bm, verts, edges, mp->totloop, BM_CREATE_SKIP_CD); }
/** * \brief Make NGon * * Makes an ngon from an unordered list of edges. * Verts \a v1 and \a v2 define the winding of the new face. * * \a edges are not required to be ordered, simply to to form * a single closed loop as a whole. * * \note While this function will work fine when the edges * are already sorted, if the edges are always going to be sorted, * #BM_face_create should be considered over this function as it * avoids some unnecessary work. */ BMFace *BM_face_create_ngon( BMesh *bm, BMVert *v1, BMVert *v2, BMEdge **edges, const int len, const BMFace *f_example, const eBMCreateFlag create_flag) { BMEdge **edges_sort = BLI_array_alloca(edges_sort, len); BMVert **verts_sort = BLI_array_alloca(verts_sort, len); BLI_assert(len && v1 && v2 && edges && bm); if (bm_edges_sort_winding(v1, v2, edges, len, edges_sort, verts_sort)) { return BM_face_create(bm, verts_sort, edges_sort, len, f_example, create_flag); } return NULL; }
/* helper function for 'BM_mesh_copy' */ static BMFace *bm_mesh_copy_new_face( BMesh *bm_new, BMesh *bm_old, BMVert **vtable, BMEdge **etable, BMFace *f) { BMLoop **loops = BLI_array_alloca(loops, f->len); BMVert **verts = BLI_array_alloca(verts, f->len); BMEdge **edges = BLI_array_alloca(edges, f->len); BMFace *f_new; BMLoop *l_iter, *l_first; int j; j = 0; l_iter = l_first = BM_FACE_FIRST_LOOP(f); do { loops[j] = l_iter; verts[j] = vtable[BM_elem_index_get(l_iter->v)]; edges[j] = etable[BM_elem_index_get(l_iter->e)]; j++; } while ((l_iter = l_iter->next) != l_first); f_new = BM_face_create(bm_new, verts, edges, f->len, NULL, BM_CREATE_SKIP_CD); if (UNLIKELY(f_new == NULL)) { return NULL; } /* use totface in case adding some faces fails */ BM_elem_index_set(f_new, (bm_new->totface - 1)); /* set_inline */ BM_elem_attrs_copy_ex(bm_old, bm_new, f, f_new, 0xff, 0x0); f_new->head.hflag = f->head.hflag; /* low level! don't do this for normal api use */ j = 0; l_iter = l_first = BM_FACE_FIRST_LOOP(f_new); do { BM_elem_attrs_copy(bm_old, bm_new, loops[j], l_iter); j++; } while ((l_iter = l_iter->next) != l_first); return f_new; }