Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAntonioya <blendergit@gmail.com>2018-08-30 12:06:44 +0300
committerAntonioya <blendergit@gmail.com>2018-08-30 12:11:47 +0300
commit0845b1c8c8da818607fcff0a1bdb2114a0cb9729 (patch)
tree42bcb0ce5d58457985edb14723ce874c9d226f18 /source/blender/blenkernel/intern/gpencil_modifier.c
parent3071d67c3aeba4e5bec73f88b24eed972424dae0 (diff)
GP: Improve Subdivide and Simplify
Now the weights are managed in the operators. The subdivide operator and modifier code have been replaced with a shared function. Some cleanup also.
Diffstat (limited to 'source/blender/blenkernel/intern/gpencil_modifier.c')
-rw-r--r--source/blender/blenkernel/intern/gpencil_modifier.c138
1 files changed, 125 insertions, 13 deletions
diff --git a/source/blender/blenkernel/intern/gpencil_modifier.c b/source/blender/blenkernel/intern/gpencil_modifier.c
index fd1170c1a9c..9c119e9776a 100644
--- a/source/blender/blenkernel/intern/gpencil_modifier.c
+++ b/source/blender/blenkernel/intern/gpencil_modifier.c
@@ -23,9 +23,9 @@
* ***** END GPL LICENSE BLOCK *****
*/
-/** \file blender/blenkernel/intern/gpencil_modifier.c
- * \ingroup bke
- */
+ /** \file blender/blenkernel/intern/gpencil_modifier.c
+ * \ingroup bke
+ */
#include <stdio.h>
@@ -241,6 +241,9 @@ static void gpencil_rdp_stroke(bGPDstroke *gps, vec2f *points2d, float epsilon)
dvert_src = &old_dvert[i];
MDeformVert *dvert = &gps->dvert[j];
memcpy(dvert, dvert_src, sizeof(MDeformVert));
+ if (dvert_src->dw) {
+ memcpy(dvert->dw, dvert_src->dw, sizeof(MDeformWeight));
+ }
}
j++;
}
@@ -314,6 +317,9 @@ void BKE_gpencil_simplify_fixed(bGPDstroke *gps)
dvert_src = &old_dvert[i];
MDeformVert *dvert = &gps->dvert[j];
memcpy(dvert, dvert_src, sizeof(MDeformVert));
+ if (dvert_src->dw) {
+ memcpy(dvert->dw, dvert_src->dw, sizeof(MDeformWeight));
+ }
}
j++;
}
@@ -341,7 +347,7 @@ void BKE_gpencil_simplify_fixed(bGPDstroke *gps)
* each loop over all the geometry being evaluated.
*/
-/* init lattice deform data */
+ /* init lattice deform data */
void BKE_gpencil_lattice_init(Object *ob)
{
GpencilModifierData *md;
@@ -417,10 +423,11 @@ void BKE_gpencil_stroke_modifiers(Depsgraph *depsgraph, Object *ob, bGPDlayer *g
/* some modifiers could require a recalc of fill triangulation data */
if (gpd->flag & GP_DATA_STROKE_FORCE_RECALC) {
if (ELEM(md->type,
- eGpencilModifierType_Hook,
- eGpencilModifierType_Lattice,
- eGpencilModifierType_Offset))
- {
+ eGpencilModifierType_Hook,
+ eGpencilModifierType_Lattice,
+ eGpencilModifierType_Noise,
+ eGpencilModifierType_Offset)) {
+
gps->flag |= GP_STROKE_RECALC_CACHES;
}
}
@@ -454,7 +461,7 @@ void BKE_gpencil_geometry_modifiers(Depsgraph *depsgraph, Object *ob, bGPDlayer
/* *************************************************** */
void BKE_gpencil_eval_geometry(Depsgraph *depsgraph,
- bGPdata *gpd)
+ bGPdata *gpd)
{
DEG_debug_print_eval(depsgraph, __func__, gpd->id.name, gpd);
int ctime = (int)DEG_get_ctime(depsgraph);
@@ -468,10 +475,10 @@ void BKE_gpencil_eval_geometry(Depsgraph *depsgraph,
* This would be better than inventing our own logic for this stuff...
*/
- /* TODO: Move the following code to "BKE_gpencil_eval_done()" (marked as an exit node)
- * later when there's more happening here. For now, let's just keep this in here to avoid
- * needing to have one more node slowing down evaluation...
- */
+ /* TODO: Move the following code to "BKE_gpencil_eval_done()" (marked as an exit node)
+ * later when there's more happening here. For now, let's just keep this in here to avoid
+ * needing to have one more node slowing down evaluation...
+ */
if (DEG_is_active(depsgraph)) {
bGPdata *gpd_orig = (bGPdata *)DEG_get_original_id(&gpd->id);
@@ -706,3 +713,108 @@ void BKE_gpencil_instance_modifier_instance_tfm(InstanceGpencilModifierData *mmd
/* calculate matrix */
loc_eul_size_to_mat4(r_mat, offset, rot, scale);
}
+
+void BKE_gpencil_subdivide(bGPDstroke *gps, int level, int flag)
+{
+ bGPDspoint *temp_points;
+ MDeformVert *temp_dverts = NULL;
+ MDeformVert *dvert = NULL;
+ MDeformVert *dvert_final = NULL;
+ MDeformVert *dvert_next = NULL;
+ int totnewpoints, oldtotpoints;
+ int i2;
+
+ for (int s = 0; s < level; s++) {
+ totnewpoints = gps->totpoints - 1;
+ /* duplicate points in a temp area */
+ temp_points = MEM_dupallocN(gps->points);
+ oldtotpoints = gps->totpoints;
+
+ /* resize the points arrys */
+ gps->totpoints += totnewpoints;
+ gps->points = MEM_recallocN(gps->points, sizeof(*gps->points) * gps->totpoints);
+ if (gps->dvert != NULL) {
+ temp_dverts = MEM_dupallocN(gps->dvert);
+ gps->dvert = MEM_recallocN(gps->dvert, sizeof(*gps->dvert) * gps->totpoints);
+ }
+ gps->flag |= GP_STROKE_RECALC_CACHES;
+
+ /* move points from last to first to new place */
+ i2 = gps->totpoints - 1;
+ for (int i = oldtotpoints - 1; i > 0; i--) {
+ bGPDspoint *pt = &temp_points[i];
+ bGPDspoint *pt_final = &gps->points[i2];
+
+ copy_v3_v3(&pt_final->x, &pt->x);
+ pt_final->pressure = pt->pressure;
+ pt_final->strength = pt->strength;
+ pt_final->time = pt->time;
+ pt_final->flag = pt->flag;
+
+ if (gps->dvert != NULL) {
+ dvert = &temp_dverts[i];
+ dvert_final = &gps->dvert[i2];
+ dvert_final->totweight = dvert->totweight;
+ dvert_final->dw = dvert->dw;
+ }
+ i2 -= 2;
+ }
+ /* interpolate mid points */
+ i2 = 1;
+ for (int i = 0; i < oldtotpoints - 1; i++) {
+ bGPDspoint *pt = &temp_points[i];
+ bGPDspoint *next = &temp_points[i + 1];
+ bGPDspoint *pt_final = &gps->points[i2];
+
+ /* add a half way point */
+ interp_v3_v3v3(&pt_final->x, &pt->x, &next->x, 0.5f);
+ pt_final->pressure = interpf(pt->pressure, next->pressure, 0.5f);
+ pt_final->strength = interpf(pt->strength, next->strength, 0.5f);
+ CLAMP(pt_final->strength, GPENCIL_STRENGTH_MIN, 1.0f);
+ pt_final->time = interpf(pt->time, next->time, 0.5f);
+
+ if (gps->dvert != NULL) {
+ dvert = &temp_dverts[i];
+ dvert_next = &temp_dverts[i + 1];
+ dvert_final = &gps->dvert[i2];
+
+ dvert_final->totweight = dvert->totweight;
+ dvert_final->dw = MEM_dupallocN(dvert->dw);
+
+ /* interpolate weight values */
+ for (int d = 0; d < dvert->totweight; d++) {
+ MDeformWeight *dw_a = &dvert->dw[d];
+ if (dvert_next->totweight > d) {
+ MDeformWeight *dw_b = &dvert_next->dw[d];
+ MDeformWeight *dw_final = &dvert_final->dw[d];
+ dw_final->weight = interpf(dw_a->weight, dw_b->weight, 0.5f);
+ }
+ }
+ }
+
+ i2 += 2;
+ }
+
+ MEM_SAFE_FREE(temp_points);
+ MEM_SAFE_FREE(temp_dverts);
+
+ /* move points to smooth stroke (not simple flag )*/
+ if ((flag & GP_SUBDIV_SIMPLE) == 0) {
+ /* duplicate points in a temp area with the new subdivide data */
+ temp_points = MEM_dupallocN(gps->points);
+
+ /* extreme points are not changed */
+ for (int i = 0; i < gps->totpoints - 2; i++) {
+ bGPDspoint *pt = &temp_points[i];
+ bGPDspoint *next = &temp_points[i + 1];
+ bGPDspoint *pt_final = &gps->points[i + 1];
+
+ /* move point */
+ interp_v3_v3v3(&pt_final->x, &pt->x, &next->x, 0.5f);
+ }
+ /* free temp memory */
+ MEM_SAFE_FREE(temp_points);
+ }
+
+ }
+}