[Bf-blender-cvs] SVN commit: /data/svn/bf-blender [43182] branches/soc-2011-onion-uv-tools/ source/blender/editors/uvedit/uvedit_smart_stitch.c: smart stitch
Antony Riakiotakis
kalast at gmail.com
Thu Jan 5 22:39:55 CET 2012
Revision: 43182
http://projects.blender.org/scm/viewvc.php?view=rev&root=bf-blender&revision=43182
Author: psy-fi
Date: 2012-01-05 21:39:45 +0000 (Thu, 05 Jan 2012)
Log Message:
-----------
smart stitch
==============
-avoid inf calculation when computing rotation.
-fix crash when part of the mesh is hidden.
Modified Paths:
--------------
branches/soc-2011-onion-uv-tools/source/blender/editors/uvedit/uvedit_smart_stitch.c
Modified: branches/soc-2011-onion-uv-tools/source/blender/editors/uvedit/uvedit_smart_stitch.c
===================================================================
--- branches/soc-2011-onion-uv-tools/source/blender/editors/uvedit/uvedit_smart_stitch.c 2012-01-05 19:09:37 UTC (rev 43181)
+++ branches/soc-2011-onion-uv-tools/source/blender/editors/uvedit/uvedit_smart_stitch.c 2012-01-05 21:39:45 UTC (rev 43182)
@@ -120,6 +120,8 @@
UvEdge *uvedges;
/* container of first of a group of coincident uvs, these will be operated upon */
UvElement **uvs;
+ /* maps uvelements to their first coincident uv */
+ int *map;
/* 2D normals per uv to calculate rotation for snapping */
float *normals;
/* edge storage */
@@ -129,7 +131,7 @@
int total_boundary_edges;
int total_separate_uvs;
/* hold selection related information */
- void **selection_stack;
+ UvElement **selection_stack;
int selection_size;
/* island that stays in place */
int static_island;
@@ -350,32 +352,50 @@
edgecos = uv1[0]*uv2[0] + uv1[1]*uv2[1];
edgesin = uv1[0]*uv2[1] - uv2[0]*uv1[1];
-
island_stitch_data[element->island].numOfEdges++;
- island_stitch_data[element->island].rotation += (edgesin > 0)? acos(edgecos): -acos(edgecos);
+ island_stitch_data[element->island].rotation += (edgesin > 0)? acos(MAX2(-1.0, MIN2(1.0, edgecos))): -acos(MAX2(-1.0, MIN2(1.0, edgecos)));
}
-/*
+
static void stitch_island_calculate_vert_rotation(UvElement *element, StitchState *state, IslandStitchData *island_stitch_data)
{
+ EditFace *efa;
+ MTFace *mt;
float normal1[2], normal2[2];
float edgecos, edgesin;
int index;
+ UvElement *element_iter;
+ if((element->island == state->static_island) && !state->midpoints)
+ return;
+
+ efa = element->face;
+ mt = CustomData_em_get(&state->em->fdata, efa->data, CD_MTFACE);
+
index = (*(&element->face->v1 + element->tfindex))->tmp.l;
- normalize_v2(normal1);
- normalize_v2(normal2);
+ element_iter = state->element_map->vert[index];
- edgecos = uv1[0]*uv2[0] + uv1[1]*uv2[1];
- edgesin = uv1[0]*uv2[1] - uv2[0]*uv1[1];
+ for(; element_iter; element_iter = element_iter->next){
+ if(element_iter->separate && (element_iter != element) &&
+ (element_iter->flag & STITCH_STITCHABLE)){
+ int index_tmp;
+ /* easily possible*/
+ if(element_iter->island == element->island){
+ continue;
+ }
+ index_tmp = element_iter - state->element_map->buf;
+ index_tmp = state->map[index_tmp];
+ }
+ }
+ edgecos = 0;
+ edgesin = 0;
- island_stitch_data[element->island].numOfEdges++;
island_stitch_data[element->island].rotation += (edgesin > 0)? acos(edgecos): -acos(edgecos);
- island_stitch_data[element->island].medianPoint[0] += (mt->uv[(element->tfindex + 1)%nverts][0] + mt->uv[element->tfindex][0]) / 2.0;
- island_stitch_data[element->island].medianPoint[1] += (mt->uv[(element->tfindex + 1)%nverts][1] + mt->uv[element->tfindex][1]) / 2.0;
+ island_stitch_data[element->island].medianPoint[0] += mt->uv[element->tfindex][0];
+ island_stitch_data[element->island].medianPoint[1] += mt->uv[element->tfindex][1];;
}
-*/
+
static void stitch_state_delete(StitchState *stitch_state)
{
if(stitch_state){
@@ -394,6 +414,9 @@
if(stitch_state->tris_per_island){
MEM_freeN(stitch_state->tris_per_island);
}
+ if(stitch_state->map){
+ MEM_freeN(stitch_state->map);
+ }
if(stitch_state->normals){
MEM_freeN(stitch_state->normals);
}
@@ -465,8 +488,8 @@
StitchPreviewer *preview = uv_get_stitch_previewer();
/* static island does not change so returning immediately */
- if(!state->midpoints && state->static_island == element->island)
- return;
+ //if(state->snap_islands && !state->midpoints && state->static_island == element->island)
+ // return;
if(state->snap_islands){
island_stitch_data[element->island].addedForPreview = 1;
@@ -479,15 +502,11 @@
}
-/* registers uvs so that they can be shown in preview */
-static void stitch_setup_preview_for_stitchable_uv(UvElement *element, StitchState *state, IslandStitchData *island_stitch_data){
+/* checks if uvs are indeed stitchable and registers so that they can be shown in preview */
+static void stitch_validate_stichability(UvElement *element, StitchState *state, IslandStitchData *island_stitch_data){
UvElement *element_iter;
StitchPreviewer *preview;
- if(element->flag & STITCH_STITCHABLE){
- return;
- }
-
preview = uv_get_stitch_previewer();
element_iter = state->element_map->vert[(*(&element->face->v1 + element->tfindex))->tmp.l];
@@ -536,6 +555,8 @@
EditVert *ev;
UVVertAverage *final_position;
char stitch_midpoints = state->midpoints;
+ /* use vertex normals for snapping rotation */
+ char use_vert_normals = 1;
/* used to map uv indices to uvaverage indices for selection */
unsigned int *uvfinal_map;
@@ -564,7 +585,7 @@
*****************************************/
for(i = 0; i < state->selection_size; i++){
- UvElement *element = (UvElement *)state->selection_stack[i];
+ UvElement *element = state->selection_stack[i];
determine_uv_stitchability(element, state, island_stitch_data);
}
@@ -579,10 +600,10 @@
}
for(i = 0; i < state->selection_size; i++){
- UvElement *element = (UvElement *)state->selection_stack[i];
+ UvElement *element = state->selection_stack[i];
if(element->flag & STITCH_STITCHABLE_CANDIDATE){
element->flag &= ~STITCH_STITCHABLE_CANDIDATE;
- stitch_setup_preview_for_stitchable_uv(element, state, island_stitch_data);
+ stitch_validate_stichability(element, state, island_stitch_data);
}else{
/* add to preview for unstitchable */
preview->num_unstitchable++;
@@ -634,21 +655,23 @@
MTFace *mt = CustomData_em_get(&state->em->fdata, efa->data, CD_MTFACE);
UvElement *element = ED_get_uv_element(state->element_map, efa, 0);
- if(efa->tmp.l != STITCH_NO_PREVIEW){
- if(efa->v4) {
- memcpy(preview->preview_quads+efa->tmp.l, &mt->uv[0][0], 8*sizeof(float));
- } else {
- memcpy(preview->preview_tris+efa->tmp.l, &mt->uv[0][0], 6*sizeof(float));
+ if(element){
+ if(efa->tmp.l != STITCH_NO_PREVIEW){
+ if(efa->v4) {
+ memcpy(preview->preview_quads+efa->tmp.l, &mt->uv[0][0], 8*sizeof(float));
+ } else {
+ memcpy(preview->preview_tris+efa->tmp.l, &mt->uv[0][0], 6*sizeof(float));
+ }
}
- }
- if(element->island == state->static_island){
- if(efa->v4) {
- memcpy(preview->static_quads + quadcount*8, &mt->uv[0][0], 8*sizeof(float));
- quadcount++;
- } else {
- memcpy(preview->static_tris + tricount*6, &mt->uv[0][0], 6*sizeof(float));
- tricount++;
+ if(element->island == state->static_island){
+ if(efa->v4) {
+ memcpy(preview->static_quads + quadcount*8, &mt->uv[0][0], 8*sizeof(float));
+ quadcount++;
+ } else {
+ memcpy(preview->static_tris + tricount*6, &mt->uv[0][0], 6*sizeof(float));
+ tricount++;
+ }
}
}
}
@@ -686,7 +709,7 @@
/* first pass, calculate final position for stitchable uvs */
for(i = 0; i < state->selection_size; i++){
- UvElement *element = (UvElement *)state->selection_stack[i];
+ UvElement *element = state->selection_stack[i];
if(element->flag & STITCH_STITCHABLE){
UvElement *element_iter = state->element_map->vert[(*(&element->face->v1 + element->tfindex))->tmp.l];
uvfinal_map[(*(&element->face->v1 + element->tfindex))->tmp.l] = i;
@@ -715,7 +738,7 @@
/* second pass, calculate island rotation and translation before modifying any uvs */
if(state->snap_islands){
for(i = 0; i < state->selection_size; i++){
- UvElement *element = (UvElement *)state->selection_stack[i];
+ UvElement *element = state->selection_stack[i];
if(element->flag & STITCH_STITCHABLE){
MTFace *mt;
efa = element->face;
@@ -730,19 +753,28 @@
island_stitch_data[element->island].numOfElements++;
}
}
- }
- /* only calculate rotation when an edge has been fully selected */
- for(i = 0; i < state->total_boundary_edges; i++){
- UvEdge *edge = state->edges+i;
- if((state->uvs[edge->uv1]->flag & STITCH_STITCHABLE) &&
- (state->uvs[edge->uv2]->flag & STITCH_STITCHABLE)){
- stitch_island_calculate_edge_rotation(edge, state, final_position, uvfinal_map, island_stitch_data);
+
+ /* only calculate rotation when an edge has been fully selected */
+ for(i = 0; i < state->total_boundary_edges; i++){
+ UvEdge *edge = state->edges+i;
+ if((state->uvs[edge->uv1]->flag & STITCH_STITCHABLE) && (state->uvs[edge->uv2]->flag & STITCH_STITCHABLE)){
+ stitch_island_calculate_edge_rotation(edge, state, final_position, uvfinal_map, island_stitch_data);
+ use_vert_normals = 0;
+ }
}
+ if(0){
+ for(i = 0; i < state->selection_size; i++){
+ UvElement *element = state->selection_stack[i];
+ if(element->flag & STITCH_STITCHABLE){
+ stitch_island_calculate_vert_rotation(element, state, island_stitch_data);
+ }
+ }
+ }
}
/* third pass, propagate changes to stitchable uvs */
for(i = 0; i < state->selection_size; i++){
- UvElement *element = (UvElement *)state->selection_stack[i];
+ UvElement *element = state->selection_stack[i];
if(element->flag & STITCH_STITCHABLE){
UvElement *element_iter = state->element_map->vert[(*(&element->face->v1 + element->tfindex))->tmp.l];
for(;element_iter;){
@@ -821,10 +853,11 @@
/* Select all common uvs */
-static void stitch_select_uv(UvElement *element, StitchState *stitch_state, void **selection_stack, int *total_selected, int always_select)
+static void stitch_select_uv(UvElement *element, StitchState *stitch_state, int always_select)
{
/* This works due to setting of tmp in find nearest uv vert */
UvElement *element_iter;
+ UvElement **selection_stack = stitch_state->selection_stack;
element_iter = stitch_state->element_map->vert[(*(&element->face->v1 + element->tfindex))->tmp.l];
/* first deselect all common uvs */
@@ -837,16 +870,16 @@
continue;
element_iter->flag &= ~STITCH_SELECTED;
- for(i = 0; i < *total_selected; i++){
- if(((UvElement *)selection_stack[i]) == element_iter){
- (*total_selected)--;
- selection_stack[i] = selection_stack[*total_selected];
+ for(i = 0; i < stitch_state->selection_size; i++){
+ if(selection_stack[i] == element_iter){
+ (stitch_state->selection_size)--;
+ selection_stack[i] = selection_stack[stitch_state->selection_size];
break;
}
}
}else{
element_iter->flag |= STITCH_SELECTED;
@@ Diff output truncated at 10240 characters. @@
More information about the Bf-blender-cvs
mailing list