[Bf-blender-cvs] SVN commit: /data/svn/bf-blender [59101] branches/ soc-2013-meshdata_transfer/source/blender/bmesh/tools/bmesh_data_transfer.c : Appending the shapekeys to the BM_mesh_data_copy()
Walid Shouman
eng.walidshouman at gmail.com
Tue Aug 13 08:08:55 CEST 2013
Revision: 59101
http://projects.blender.org/scm/viewvc.php?view=rev&root=bf-blender&revision=59101
Author: walid
Date: 2013-08-13 06:08:54 +0000 (Tue, 13 Aug 2013)
Log Message:
-----------
Appending the shapekeys to the BM_mesh_data_copy()
Modified Paths:
--------------
branches/soc-2013-meshdata_transfer/source/blender/bmesh/tools/bmesh_data_transfer.c
Modified: branches/soc-2013-meshdata_transfer/source/blender/bmesh/tools/bmesh_data_transfer.c
===================================================================
--- branches/soc-2013-meshdata_transfer/source/blender/bmesh/tools/bmesh_data_transfer.c 2013-08-13 05:36:36 UTC (rev 59100)
+++ branches/soc-2013-meshdata_transfer/source/blender/bmesh/tools/bmesh_data_transfer.c 2013-08-13 06:08:54 UTC (rev 59101)
@@ -2252,7 +2252,82 @@
case CD_SHAPEKEY:
{
- return false;
+ float v_src_offset[3];
+ float v_dst_offset[3];
+
+ int CD_offset_src, CD_offset_dst;
+ int CD_basis_src, CD_basis_dst;
+
+ coord_pool *offsets_grp;
+
+ CD_basis_src = CustomData_get_n_offset(&bm_src->vdata, CD_SHAPEKEY, 0); //get the offset of the basis
+ CD_basis_dst = CustomData_get_n_offset(&bm_dst->vdata, CD_SHAPEKEY, 0);
+
+ //Alloc loop
+ offsets_grp = MEM_mallocN(sizeof(*offsets_grp) * bm_dst->totvert, "offsets_grp bmesh_data_transfer.c");
+ BM_ITER_MESH (v, &iter, bm_dst, BM_VERTS_OF_MESH) {
+
+ BM_ITER_ELEM_INDEX (f_dst, &fiter, v, BM_FACES_OF_VERT, a) {}
+ offsets_grp[v->head.index].coord = MEM_mallocN(sizeof(*(offsets_grp[v->head.index].coord)) * a,
+ "offsets_grp[v->head.index].coord bmesh_data_transfer.c");
+
+ offsets_grp[v->head.index].count = 0; //if that wasn't fast enf we may use calloc for the offsets_grp
+ }
+
+ //Multi layers loop
+ for (src_lay_iter = src_lay_start, dst_lay_iter = dst_lay_start; src_lay_iter <= src_lay_end;
+ src_lay_iter++, dst_lay_iter++) {
+
+ //fix the layer index of the source & dest
+ CD_offset_src = CustomData_get_n_offset(&bm_src->vdata, CD_SHAPEKEY,src_lay_iter); //get the offset of the
+ CD_offset_dst = CustomData_get_n_offset(&bm_dst->vdata, CD_SHAPEKEY,dst_lay_iter); //lay_iter(th)CD_SHAPEKEY layer
+
+ b = 0;
+ //Copy loop
+ BM_ITER_MESH (f_dst, &fiter, bm_dst, BM_FACES_OF_MESH) {
+ BM_ITER_ELEM (v, &iter, f_dst, BM_VERTS_OF_FACE) {
+
+ // Interpolating according to the spatially found weights
+ // Get weights from face.
+ zero_v3(v_dst_offset);
+ for (a = 0; a < l_weights[b].count; a++) {
+ float weight = l_weights[b].l_w[a].weight;
+
+ sub_v3_v3v3(v_src_offset, BM_ELEM_CD_GET_VOID_P(l_weights[b].l_w[a].l->v, CD_offset_src),
+ BM_ELEM_CD_GET_VOID_P(l_weights[b].l_w[a].l->v, CD_basis_src));
+ madd_v3_v3fl(v_dst_offset, v_src_offset, weight);
+ }
+
+ copy_v3_v3(offsets_grp[v->head.index].coord[offsets_grp[v->head.index].count], v_dst_offset);
+ (offsets_grp[v->head.index].count)++;
+
+ b++;
+ }
+ }
+
+ //Normalising loop
+ //Normalising coords for each vertex
+ BM_ITER_MESH (v, &iter, bm_dst, BM_VERTS_OF_MESH) {
+ zero_v3(v_dst_offset);
+ mid_poly_v3(v_dst_offset, offsets_grp[v->head.index].coord, offsets_grp[v->head.index].count);
+
+ add_v3_v3v3(BM_ELEM_CD_GET_VOID_P(v, CD_offset_dst), BM_ELEM_CD_GET_VOID_P(v, CD_basis_dst),
+ v_dst_offset);
+ //reset for the upcoming layer
+ offsets_grp[v->head.index].count = 0;
+ }
+
+ }
+
+ //Free loop
+ //Freeing allocated memory blocks
+ BM_ITER_MESH (v, &iter, bm_dst, BM_VERTS_OF_MESH) {
+ MEM_freeN(offsets_grp[v->head.index].coord);
+ }
+
+ MEM_freeN(offsets_grp);
+
+ return true;
}
case CD_MLOOPUV:
@@ -2648,6 +2723,16 @@
//===end of extra appended variables for the vgroup copy
+ //---extra variables for the shapekey
+ int CD_offset_src, CD_offset_dst;
+ int CD_basis_src, CD_basis_dst;
+
+ coord_pool *offsets_grp;
+ float v_src_offset[3];
+ float v_dst_offset[3];
+
+ //===end of extra variables for the shapekey
+
//Is that good to support edit mesh mode at the cost of receiving me_src too ?
//if (me_src->edit_btmesh != NULL) em_src = me_src->edit_btmesh; //edit mesh mode
//else
@@ -2824,7 +2909,7 @@
}
case CD_SHAPEKEY:
{
-// BM_mesh_multi_layer_copy(bm_src, bm_dst, replace_info, CD_SHAPEKEY, l_weights);
+ BM_mesh_multi_layer_copy(bm_src, bm_dst, replace_info, CD_SHAPEKEY, l_weights);
break;
}
case CD_MLOOPUV:
@@ -3103,6 +3188,111 @@
case CD_SHAPEKEY:
{
+ //Alloc loop
+ offsets_grp = MEM_mallocN(sizeof(*offsets_grp) * bm_dst->totvert, "offsets_grp bmesh_data_transfer.c");
+ BM_ITER_MESH (v, &iter, bm_dst, BM_VERTS_OF_MESH) {
+
+ BM_ITER_ELEM_INDEX (f_dst, &fiter, v, BM_FACES_OF_VERT, a) {}
+ offsets_grp[v->head.index].coord = MEM_mallocN(sizeof(*(offsets_grp[v->head.index].coord)) * a,
+ "offsets_grp[v->head.index].coord bmesh_data_transfer.c");
+
+ offsets_grp[v->head.index].count = 0; //if that wasn't fast enf we may use calloc for the offsets_grp
+ }
+
+ CD_basis_src = CustomData_get_n_offset(&bm_src->vdata, CD_SHAPEKEY, 0); //get the offset of the basis
+ CD_basis_dst = CustomData_get_n_offset(&bm_dst->vdata, CD_SHAPEKEY, 0);
+
+ //fix the layer index of the source & dest
+ CD_offset_src = CustomData_get_n_offset(&bm_src->vdata, CD_SHAPEKEY, src_lay_start);
+ CD_offset_dst = CustomData_get_n_offset(&bm_dst->vdata, CD_SHAPEKEY, dst_lay_start);
+
+ //the way we do it is by looping over each face!!
+ BM_ITER_MESH (f_dst, &fiter, bm_dst, BM_FACES_OF_MESH) {
+
+ //get the dst face center
+ BM_face_calc_center_mean(f_dst, f_mid_dst);
+
+ //supporting either to copy relative to the target or not
+ if (relative_to_target == true) {
+ // Transform into target space.
+ mul_v3_m4v3(f_mid_dst_proj, tmp_mat, f_mid_dst); //to start searching for a match
+
+ // Node tree accelerated search for closest face.
+ f_src = BKE_bmbvh_find_face_closest(bmtree_src, f_mid_dst_proj, FLT_MAX); //would return null if the source didn't
+ //have faces within the radius range!!
+ }
+
+ else {
+ // Node tree accelerated search for closest face.
+ f_src = BKE_bmbvh_find_face_closest(bmtree_src, f_mid_dst, FLT_MAX); //would return null if the source didn't
+ //have faces within the radius range!!
+ }
+
+ //we should be so cautious about reallocating extra memory in loops!!
+ if (f_src->len > exp_vert_per_face) {
+ if (f_src->len > v_src_max_count) {
+ v_co_list_src = MEM_reallocN(v_co_list_src, sizeof(*v_co_list_src) * f_src->len);
+ tmp_weight = MEM_reallocN(tmp_weight, sizeof(*tmp_weight) * f_src->len);
+ v_src_max_count = f_src->len;
+ }
+ }
+
+ BM_ITER_ELEM_INDEX (v, &iter, f_src, BM_VERTS_OF_FACE, b) {
+ copy_v3_v3(v_co_list_src[b], v->co);
+ }
+
+ //get the face center
+ BM_face_calc_center_mean(f_src, f_mid_src);
+
+ BM_ITER_ELEM (v, &iter, f_dst, BM_VERTS_OF_FACE) {
+ if (relative_to_target == true) {
+ zero_v3(v_dst_co);
+
+ // Transform into target space.
+ mul_v3_m4v3(v_dst_co, tmp_mat, v->co);
+ }
+
+ else {
+ copy_v3_v3(v_dst_co, v->co);
+ }
+
+ // Project each vertex onto face.
+ project_v3_plane(v_dst_co, f_src->no, f_mid_src);
+
+ // Interpolate weights over face.
+
+ //spatially finding the weights from the face's vertices
+ interp_weights_poly_v3(tmp_weight, v_co_list_src, f_src->len, v_dst_co);
+
+ // Interpolating according to the spatially found weights
+ // Get weights from face.
+ zero_v3(v_dst_offset);
+ BM_ITER_ELEM_INDEX (v2, &iter2, f_src, BM_VERTS_OF_FACE, a) {
+ sub_v3_v3v3(v_src_offset, BM_ELEM_CD_GET_VOID_P(v2, CD_offset_src),
+ BM_ELEM_CD_GET_VOID_P(v2, CD_basis_src));
+ madd_v3_v3fl(v_dst_offset, v_src_offset, tmp_weight[a]);
+ }
+
+ copy_v3_v3(offsets_grp[v->head.index].coord[offsets_grp[v->head.index].count], v_dst_offset);
+ (offsets_grp[v->head.index].count)++;
+ }
+ }
+
+ BM_ITER_MESH (v, &iter, bm_dst, BM_VERTS_OF_MESH) {
+ zero_v3(v_dst_offset);
+ mid_poly_v3(v_dst_offset, offsets_grp[v->head.index].coord, offsets_grp[v->head.index].count);
+
+ add_v3_v3v3(BM_ELEM_CD_GET_VOID_P(v, CD_offset_dst), BM_ELEM_CD_GET_VOID_P(v, CD_basis_dst),
+ v_dst_offset);
+ offsets_grp[v->head.index].count = 0; //reset for the upcoming layer
+ }
+
+ BM_ITER_MESH (v, &iter, bm_dst, BM_VERTS_OF_MESH) {
+ MEM_freeN(offsets_grp[v->head.index].coord);
+ }
+
+ MEM_freeN(offsets_grp);
+
break;
}
More information about the Bf-blender-cvs
mailing list