diff options
Diffstat (limited to 'source')
-rw-r--r-- | source/blender/blenloader/intern/readfile.c | 3 | ||||
-rw-r--r-- | source/blender/makesdna/DNA_scene_types.h | 12 | ||||
-rw-r--r-- | source/blender/src/buttons_editing.c | 18 | ||||
-rw-r--r-- | source/blender/src/editarmature.c | 126 |
4 files changed, 70 insertions, 89 deletions
diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c index 10dbe142016..e3ed6301fe0 100644 --- a/source/blender/blenloader/intern/readfile.c +++ b/source/blender/blenloader/intern/readfile.c @@ -6780,9 +6780,10 @@ static void do_versions(FileData *fd, Library *lib, Main *main) sce->toolsettings->skgen_length_ratio = 1.3f; sce->toolsettings->skgen_length_limit = 1.5f; sce->toolsettings->skgen_correlation_limit = 0.98f; + sce->toolsettings->skgen_symmetry_limit = 0.1f; sce->toolsettings->skgen_postpro = SKGEN_SMOOTH; sce->toolsettings->skgen_postpro_passes = 1; - sce->toolsettings->skgen_options = SKGEN_FILTER_INTERNAL|SKGEN_FILTER_EXTERNAL|SKGEN_REPOSITION|SKGEN_CUT_LENGTH|SKGEN_SUB_CORRELATION; + sce->toolsettings->skgen_options = SKGEN_FILTER_INTERNAL|SKGEN_FILTER_EXTERNAL|SKGEN_CUT_LENGTH|SKGEN_SUB_CORRELATION; sce->toolsettings->skgen_subdivisions[0] = SKGEN_SUB_LENGTH; sce->toolsettings->skgen_subdivisions[1] = SKGEN_SUB_CORRELATION; sce->toolsettings->skgen_subdivisions[2] = SKGEN_SUB_ANGLE; diff --git a/source/blender/makesdna/DNA_scene_types.h b/source/blender/makesdna/DNA_scene_types.h index 46b23b12c26..485f202c25a 100644 --- a/source/blender/makesdna/DNA_scene_types.h +++ b/source/blender/makesdna/DNA_scene_types.h @@ -371,12 +371,13 @@ typedef struct ToolSettings { float skgen_length_limit; float skgen_angle_limit; float skgen_correlation_limit; + float skgen_symmetry_limit; short skgen_options; char skgen_postpro; char skgen_postpro_passes; char skgen_subdivisions[3]; - char pad3[1]; + char pad3[5]; } ToolSettings; /* Used by all brushes to store their properties, which can be directly set @@ -681,11 +682,10 @@ typedef struct Scene { /* toolsettings->skgen_options */ #define SKGEN_FILTER_INTERNAL 1 #define SKGEN_FILTER_EXTERNAL 2 -#define SKGEN_REPOSITION 4 -#define SKGEN_SYMMETRY 8 -#define SKGEN_CUT_LENGTH 16 -#define SKGEN_CUT_ANGLE 32 -#define SKGEN_CUT_CORRELATION 64 +#define SKGEN_SYMMETRY 4 +#define SKGEN_CUT_LENGTH 8 +#define SKGEN_CUT_ANGLE 16 +#define SKGEN_CUT_CORRELATION 32 #define SKGEN_SUB_LENGTH 0 #define SKGEN_SUB_ANGLE 1 diff --git a/source/blender/src/buttons_editing.c b/source/blender/src/buttons_editing.c index 873dd17b905..d92df3ab760 100644 --- a/source/blender/src/buttons_editing.c +++ b/source/blender/src/buttons_editing.c @@ -4456,9 +4456,9 @@ static void editing_panel_mesh_skgen(Object *ob, Mesh *me) uiBlockBeginAlign(block); uiDefButS(block, NUM, B_DIFF, "Resolution:", 1025,150,250,19, &G.scene->toolsettings->skgen_resolution,10.0,1000.0, 0, 0, "Specifies the resolution of the graph's embedding"); uiDefButBitS(block, TOG, SKGEN_FILTER_INTERNAL, B_DIFF, "Filter In", 1025,130, 83,19, &G.scene->toolsettings->skgen_options, 0, 0, 0, 0, "Filter internal small arcs from graph"); - uiDefButF(block, NUM, B_DIFF, "Thresh:", 1111,130,164,19, &G.scene->toolsettings->skgen_threshold_internal,0.0, 1.0, 10, 0, "Specify the threshold ratio for filtering internal arcs"); + uiDefButF(block, NUM, B_DIFF, "T:", 1111,130,164,19, &G.scene->toolsettings->skgen_threshold_internal,0.0, 1.0, 10, 0, "Specify the threshold ratio for filtering internal arcs"); uiDefButBitS(block, TOG, SKGEN_FILTER_EXTERNAL, B_DIFF, "Filter Ex", 1025,110, 83,19, &G.scene->toolsettings->skgen_options, 0, 0, 0, 0, "Filter external small arcs from graph"); - uiDefButF(block, NUM, B_DIFF, "Thresh:", 1111,110,164,19, &G.scene->toolsettings->skgen_threshold_external,0.0, 1.0, 10, 0, "Specify the threshold ratio for filtering external arcs"); + uiDefButF(block, NUM, B_DIFF, "T:", 1111,110,164,19, &G.scene->toolsettings->skgen_threshold_external,0.0, 1.0, 10, 0, "Specify the threshold ratio for filtering external arcs"); for(i = 0; i < SKGEN_SUB_TOTAL; i++) { @@ -4470,23 +4470,23 @@ static void editing_panel_mesh_skgen(Object *ob, Mesh *me) switch(G.scene->toolsettings->skgen_subdivisions[i]) { case SKGEN_SUB_LENGTH: - uiDefButBitS(block, TOG, SKGEN_CUT_LENGTH, B_DIFF, "Length", 1041, y, 67,19, &G.scene->toolsettings->skgen_options, 0, 0, 0, 0, "Subdivide arcs based on embedding length"); - uiDefButF(block, NUM, B_DIFF, "Thresh:", 1111, y, 82,19, &G.scene->toolsettings->skgen_length_ratio,1.0, 4.0, 10, 0, "Specify the ratio limit between straight arc and embeddings to trigger equal subdivisions"); - uiDefButF(block, NUM, B_DIFF, "Len:", 1193, y, 82,19, &G.scene->toolsettings->skgen_length_limit,0.1,50.0, 10, 0, "Maximum length of the bones when subdividing"); + uiDefButBitS(block, TOG, SKGEN_CUT_LENGTH, B_DIFF, "Length", 1041, y, 67,19, &G.scene->toolsettings->skgen_options, 0, 0, 0, 0, "Subdivide arcs in bones of equal length"); + uiDefButF(block, NUM, B_DIFF, "T:", 1111, y, 82,19, &G.scene->toolsettings->skgen_length_ratio,1.0, 4.0, 10, 0, "Specify the ratio limit between straight arc and embeddings to trigger equal subdivisions"); + uiDefButF(block, NUM, B_DIFF, "L:", 1193, y, 82,19, &G.scene->toolsettings->skgen_length_limit,0.1,50.0, 10, 0, "Maximum length of the bones when subdividing"); break; case SKGEN_SUB_ANGLE: uiDefButBitS(block, TOG, SKGEN_CUT_ANGLE, B_DIFF, "Angle", 1041, y, 67,19, &G.scene->toolsettings->skgen_options, 0, 0, 0, 0, "Subdivide arcs based on angle"); - uiDefButF(block, NUM, B_DIFF, "Thresh:", 1111, y,164,19, &G.scene->toolsettings->skgen_angle_limit,0.0, 90.0, 10, 0, "Specify the threshold angle in degrees for subdivision"); + uiDefButF(block, NUM, B_DIFF, "T:", 1111, y,164,19, &G.scene->toolsettings->skgen_angle_limit,0.0, 90.0, 10, 0, "Specify the threshold angle in degrees for subdivision"); break; case SKGEN_SUB_CORRELATION: uiDefButBitS(block, TOG, SKGEN_CUT_CORRELATION, B_DIFF, "Correlation", 1041, y, 67,19, &G.scene->toolsettings->skgen_options, 0, 0, 0, 0, "Subdivide arcs based on correlation"); - uiDefButF(block, NUM, B_DIFF, "Thresh:", 1111, y,164,19, &G.scene->toolsettings->skgen_correlation_limit,0.0, 1.0, 0.01, 0, "Specify the threshold correlation for subdivision"); + uiDefButF(block, NUM, B_DIFF, "T:", 1111, y,164,19, &G.scene->toolsettings->skgen_correlation_limit,0.0, 1.0, 0.01, 0, "Specify the threshold correlation for subdivision"); break; } } - uiDefButBitS(block, TOG, SKGEN_REPOSITION, B_DIFF, "Reposition", 1025, 30,125,19, &G.scene->toolsettings->skgen_options, 0, 0, 0, 0, "Reposition nodes based on embedding instead of original vertice positions"); - uiDefButBitS(block, TOG, SKGEN_SYMMETRY, B_DIFF, "Symmetry", 1150, 30,125,19, &G.scene->toolsettings->skgen_options, 0, 0, 0, 0, "Restore symmetries based on topology"); + uiDefButBitS(block, TOG, SKGEN_SYMMETRY, B_DIFF, "Symmetry", 1025, 30,125,19, &G.scene->toolsettings->skgen_options, 0, 0, 0, 0, "Restore symmetries based on topology"); + uiDefButF(block, NUM, B_DIFF, "T:", 1150, 30,125,19, &G.scene->toolsettings->skgen_symmetry_limit,0.0, 1.0, 10, 0, "Specify the threshold distance for considering potential symmetric arcs"); uiDefButC(block, NUM, B_DIFF, "P:", 1025, 10, 62,19, &G.scene->toolsettings->skgen_postpro_passes, 0, 10, 10, 0, "Specify the number of processing passes on the embeddings"); uiDefButC(block, ROW, B_DIFF, "Smooth", 1087, 10, 63,19, &G.scene->toolsettings->skgen_postpro, 5.0, (float)SKGEN_SMOOTH, 0, 0, "Smooth embeddings"); uiDefButC(block, ROW, B_DIFF, "Average", 1150, 10, 62,19, &G.scene->toolsettings->skgen_postpro, 5.0, (float)SKGEN_AVERAGE, 0, 0, "Average embeddings"); diff --git a/source/blender/src/editarmature.c b/source/blender/src/editarmature.c index 489f84baf30..b4558362beb 100644 --- a/source/blender/src/editarmature.c +++ b/source/blender/src/editarmature.c @@ -3176,6 +3176,7 @@ void reestablishAxialSymmetry(ReebNode *node, int depth, float axis[3]) ReebArc *arc1 = NULL; ReebArc *arc2 = NULL; ReebNode *node1, *node2; + float limit = G.scene->toolsettings->skgen_symmetry_limit; float nor[3], vec[3], p[3]; int i; @@ -3205,64 +3206,67 @@ void reestablishAxialSymmetry(ReebNode *node, int depth, float axis[3]) Crossf(nor, vec, axis); /* mirror node2 along axis */ - mirrorAlongAxis(node2->p, node->p, nor); + VECCOPY(p, node2->p); + mirrorAlongAxis(p, node->p, nor); - /* average with node1 */ - VecAddf(node1->p, node1->p, node2->p); - VecMulf(node1->p, 0.5f); - - /* mirror back on node2 */ - VECCOPY(node2->p, node1->p); - mirrorAlongAxis(node2->p, node->p, nor); - - /* Merge buckets - * there shouldn't be any null arcs here, but just to be safe - * */ - if (arc1->bcount > 0 && arc2->bcount > 0) + /* check if it's within limit before continuing */ + if (VecLenf(node1->p, p) <= limit) { + + /* average with node1 */ + VecAddf(node1->p, node1->p, p); + VecMulf(node1->p, 0.5f); - initArcIterator(&iter1, arc1, node); - initArcIterator(&iter2, arc2, node); + /* mirror back on node2 */ + VECCOPY(node2->p, node1->p); + mirrorAlongAxis(node2->p, node->p, nor); - bucket1 = nextBucket(&iter1); - bucket2 = nextBucket(&iter2); - - /* Make sure they both start at the same value */ - while(bucket1 && bucket1->val < bucket2->val) + /* Merge buckets + * there shouldn't be any null arcs here, but just to be safe + * */ + if (arc1->bcount > 0 && arc2->bcount > 0) { + + initArcIterator(&iter1, arc1, node); + initArcIterator(&iter2, arc2, node); + bucket1 = nextBucket(&iter1); - } - - while(bucket2 && bucket2->val < bucket1->val) - { bucket2 = nextBucket(&iter2); - } - - - for( ;bucket1 && bucket2; bucket1 = nextBucket(&iter1), bucket2 = nextBucket(&iter2)) - { - bucket1->nv += bucket2->nv; /* add counts */ + + /* Make sure they both start at the same value */ + while(bucket1 && bucket1->val < bucket2->val) + { + bucket1 = nextBucket(&iter1); + } - /* mirror on axis */ - mirrorAlongAxis(bucket2->p, node->p, nor); - /* add bucket2 in bucket1 */ - VecLerpf(bucket1->p, bucket1->p, bucket2->p, (float)bucket2->nv / (float)(bucket1->nv)); - - /* copy and mirror back to bucket2 */ - bucket2->nv = bucket1->nv; - VECCOPY(bucket2->p, bucket1->p); - mirrorAlongAxis(bucket2->p, node->p, nor); + while(bucket2 && bucket2->val < bucket1->val) + { + bucket2 = nextBucket(&iter2); + } + + + for( ;bucket1 && bucket2; bucket1 = nextBucket(&iter1), bucket2 = nextBucket(&iter2)) + { + bucket1->nv += bucket2->nv; /* add counts */ + + /* mirror on axis */ + mirrorAlongAxis(bucket2->p, node->p, nor); + /* add bucket2 in bucket1 */ + VecLerpf(bucket1->p, bucket1->p, bucket2->p, (float)bucket2->nv / (float)(bucket1->nv)); + + /* copy and mirror back to bucket2 */ + bucket2->nv = bucket1->nv; + VECCOPY(bucket2->p, bucket1->p); + mirrorAlongAxis(bucket2->p, node->p, nor); + } } } } void markdownSecondarySymmetry(ReebNode *node, int depth, int level) { - float SYMMETRY_THRESHOLD = 0.005f * G.scene->toolsettings->skgen_resolution; float axis[3] = {0, 0, 0}; - float avg_weight = 0; int count = 0; - int symmetric = 1; int i; /* Only reestablish spatial symmetry if needed */ @@ -3279,8 +3283,6 @@ void markdownSecondarySymmetry(ReebNode *node, int depth, int level) if (connectedArc->flags == -depth) { count++; - - avg_weight += OTHER_NODE(connectedArc, node)->weight; } /* If arc is on the axis */ else if (connectedArc->flags == level) @@ -3291,34 +3293,15 @@ void markdownSecondarySymmetry(ReebNode *node, int depth, int level) } Normalize(axis); - avg_weight /= count; - - /* Check if all branches are within range of the average weight */ - for(i = 0; node->arcs[i] != NULL; i++) + + /* Split between axial and radial symmetry */ + if (count == 2) { - ReebArc *connectedArc = node->arcs[i]; - - if (connectedArc->flags == -depth) - { - if (fabs(OTHER_NODE(connectedArc, node)->weight - avg_weight) > SYMMETRY_THRESHOLD) - { - symmetric = 0; - break; - } - } + reestablishAxialSymmetry(node, depth, axis); } - - if (symmetric) + else { - /* Split between axial and radial symmetry */ - if (count == 2) - { - reestablishAxialSymmetry(node, depth, axis); - } - else - { - reestablishRadialSymmetry(node, depth, axis); - } + reestablishRadialSymmetry(node, depth, axis); } } @@ -3997,10 +3980,7 @@ void generateSkeleton(void) verifyBuckets(rg); - if (G.scene->toolsettings->skgen_options & SKGEN_REPOSITION) - { - repositionNodes(rg); - } + repositionNodes(rg); verifyBuckets(rg); |