[Bf-blender-cvs] [38cf0d7d13a] master: GPencil: Improve Thickness handling for Outline operator

Antonio Vazquez noreply at git.blender.org
Tue Aug 30 17:12:09 CEST 2022


Commit: 38cf0d7d13a306b0c0c96f6f95ed8c2dcef4df12
Author: Antonio Vazquez
Date:   Tue Aug 30 17:03:13 2022 +0200
Branches: master
https://developer.blender.org/rB38cf0d7d13a306b0c0c96f6f95ed8c2dcef4df12

GPencil: Improve Thickness handling for Outline operator

Actually, when you increase the thickness of the stroke in the outline conversion, the shape of the stroke changes and becomes thicker.

This commit includes a new algorithm to correct this problem. A new `Keep Shape`  parameter allows you to disable it because, for artist reasons, it may be good to keep the old algorithm and change the shape.

===================================================================

M	source/blender/blenkernel/BKE_gpencil_geom.h
M	source/blender/blenkernel/intern/gpencil_geom.cc
M	source/blender/editors/gpencil/gpencil_edit.c
M	source/blender/editors/gpencil/gpencil_paint.c
M	source/blender/io/gpencil/intern/gpencil_io_base.cc
M	source/blender/io/gpencil/intern/gpencil_io_export_pdf.cc
M	source/blender/io/gpencil/intern/gpencil_io_export_svg.cc

===================================================================

diff --git a/source/blender/blenkernel/BKE_gpencil_geom.h b/source/blender/blenkernel/BKE_gpencil_geom.h
index ad3b1971ca9..39ef738c631 100644
--- a/source/blender/blenkernel/BKE_gpencil_geom.h
+++ b/source/blender/blenkernel/BKE_gpencil_geom.h
@@ -488,7 +488,8 @@ struct bGPDstroke *BKE_gpencil_stroke_perimeter_from_view(struct RegionView3D *r
                                                           const struct bGPDlayer *gpl,
                                                           struct bGPDstroke *gps,
                                                           int subdivisions,
-                                                          const float diff_mat[4][4]);
+                                                          const float diff_mat[4][4],
+                                                          const float thickness_chg);
 /**
  * Get average pressure.
  */
diff --git a/source/blender/blenkernel/intern/gpencil_geom.cc b/source/blender/blenkernel/intern/gpencil_geom.cc
index d0075a7d161..f7d84b8dc84 100644
--- a/source/blender/blenkernel/intern/gpencil_geom.cc
+++ b/source/blender/blenkernel/intern/gpencil_geom.cc
@@ -3960,6 +3960,7 @@ static ListBase *gpencil_stroke_perimeter_ex(const bGPdata *gpd,
                                              const bGPDlayer *gpl,
                                              const bGPDstroke *gps,
                                              int subdivisions,
+                                             const float thickness_chg,
                                              int *r_num_perimeter_points)
 {
   /* sanity check */
@@ -3968,7 +3969,9 @@ static ListBase *gpencil_stroke_perimeter_ex(const bGPdata *gpd,
   }
 
   float defaultpixsize = 1000.0f / gpd->pixfactor;
+  float ovr_radius = thickness_chg / defaultpixsize / 2.0f;
   float stroke_radius = ((gps->thickness + gpl->line_change) / defaultpixsize) / 2.0f;
+  stroke_radius = max_ff(stroke_radius - ovr_radius, 0.0f);
 
   ListBase *perimeter_right_side = MEM_cnew<ListBase>(__func__);
   ListBase *perimeter_left_side = MEM_cnew<ListBase>(__func__);
@@ -4202,7 +4205,8 @@ bGPDstroke *BKE_gpencil_stroke_perimeter_from_view(struct RegionView3D *rv3d,
                                                    const bGPDlayer *gpl,
                                                    bGPDstroke *gps,
                                                    const int subdivisions,
-                                                   const float diff_mat[4][4])
+                                                   const float diff_mat[4][4],
+                                                   const float thickness_chg)
 {
   if (gps->totpoints == 0) {
     return nullptr;
@@ -4234,7 +4238,7 @@ bGPDstroke *BKE_gpencil_stroke_perimeter_from_view(struct RegionView3D *rv3d,
   BKE_gpencil_stroke_to_view_space(rv3d, gps_temp, diff_mat);
   int num_perimeter_points = 0;
   ListBase *perimeter_points = gpencil_stroke_perimeter_ex(
-      gpd, gpl, gps_temp, subdivisions, &num_perimeter_points);
+      gpd, gpl, gps_temp, subdivisions, thickness_chg, &num_perimeter_points);
 
   if (num_perimeter_points == 0) {
     return nullptr;
diff --git a/source/blender/editors/gpencil/gpencil_edit.c b/source/blender/editors/gpencil/gpencil_edit.c
index c4aa5218360..9843bd22bb6 100644
--- a/source/blender/editors/gpencil/gpencil_edit.c
+++ b/source/blender/editors/gpencil/gpencil_edit.c
@@ -3987,6 +3987,7 @@ static int gpencil_stroke_outline_exec(bContext *C, wmOperator *op)
   bGPdata *gpd = (bGPdata *)ob->data;
   const int subdivisions = RNA_int_get(op->ptr, "subdivisions");
   const float length = RNA_float_get(op->ptr, "length");
+  const bool keep = RNA_boolean_get(op->ptr, "keep");
   const int thickness = RNA_int_get(op->ptr, "thickness");
 
   const int view_mode = RNA_enum_get(op->ptr, "view_mode");
@@ -4104,8 +4105,9 @@ static int gpencil_stroke_outline_exec(bContext *C, wmOperator *op)
           CLAMP_MIN(gps_duplicate->thickness, 1.0f);
 
           /* Stroke. */
+          const float ovr_thickness = keep ? thickness : 0.0f;
           bGPDstroke *gps_perimeter = BKE_gpencil_stroke_perimeter_from_view(
-              rv3d, gpd, gpl, gps_duplicate, subdivisions, diff_mat);
+              rv3d, gpd, gpl, gps_duplicate, subdivisions, diff_mat, ovr_thickness);
           gps_perimeter->flag &= ~GP_STROKE_SELECT;
           /* Assign material. */
           switch (material_mode) {
@@ -4216,8 +4218,12 @@ void GPENCIL_OT_stroke_outline(wmOperatorType *ot)
 
   /* properties */
   ot->prop = RNA_def_enum(ot->srna, "view_mode", view_mode, GP_PERIMETER_VIEW, "View", "");
-  RNA_def_enum(
-      ot->srna, "material_mode", material_mode, GP_STROKE_USE_ACTIVE_MATERIAL, "Material Mode", "");
+  RNA_def_enum(ot->srna,
+               "material_mode",
+               material_mode,
+               GP_STROKE_USE_ACTIVE_MATERIAL,
+               "Material Mode",
+               "");
 
   RNA_def_int(ot->srna,
               "thickness",
@@ -4228,6 +4234,12 @@ void GPENCIL_OT_stroke_outline(wmOperatorType *ot)
               "Thickness of the stroke perimeter",
               1,
               1000);
+  RNA_def_boolean(ot->srna,
+                  "keep",
+                  true,
+                  "Keep Shape",
+                  "Try to keep global shape when the stroke thickness change");
+
   RNA_def_int(ot->srna, "subdivisions", 3, 0, 10, "Subdivisions", "", 0, 10);
 
   RNA_def_float(ot->srna, "length", 0.0f, 0.0f, 100.0f, "Sample Length", "", 0.0f, 100.0f);
diff --git a/source/blender/editors/gpencil/gpencil_paint.c b/source/blender/editors/gpencil/gpencil_paint.c
index 7f11ff7ebd5..b196fcae51c 100644
--- a/source/blender/editors/gpencil/gpencil_paint.c
+++ b/source/blender/editors/gpencil/gpencil_paint.c
@@ -944,7 +944,7 @@ static bGPDstroke *gpencil_stroke_to_outline(tGPsdata *p, bGPDstroke *gps)
   float diff_mat[4][4];
   unit_m4(diff_mat);
   bGPDstroke *gps_perimeter = BKE_gpencil_stroke_perimeter_from_view(
-      rv3d, p->gpd, gpl, gps_duplicate, 3, diff_mat);
+      rv3d, p->gpd, gpl, gps_duplicate, 3, diff_mat, 0.0f);
   /* Assign material. */
   if (gpencil_settings->material_alt == NULL) {
     gps_perimeter->mat_nr = gps->mat_nr;
diff --git a/source/blender/io/gpencil/intern/gpencil_io_base.cc b/source/blender/io/gpencil/intern/gpencil_io_base.cc
index 6db3eccedbe..e7d8faaacfa 100644
--- a/source/blender/io/gpencil/intern/gpencil_io_base.cc
+++ b/source/blender/io/gpencil/intern/gpencil_io_base.cc
@@ -257,7 +257,7 @@ float GpencilIO::stroke_point_radius_get(bGPDlayer *gpl, bGPDstroke *gps)
 
   /* Radius. */
   bGPDstroke *gps_perimeter = BKE_gpencil_stroke_perimeter_from_view(
-      rv3d_, gpd_, gpl, gps, 3, diff_mat_.values);
+      rv3d_, gpd_, gpl, gps, 3, diff_mat_.values, 0.0f);
 
   pt = &gps_perimeter->points[0];
   const float2 screen_ex = gpencil_3D_point_to_2D(&pt->x);
diff --git a/source/blender/io/gpencil/intern/gpencil_io_export_pdf.cc b/source/blender/io/gpencil/intern/gpencil_io_export_pdf.cc
index 700d91791a8..95e83769979 100644
--- a/source/blender/io/gpencil/intern/gpencil_io_export_pdf.cc
+++ b/source/blender/io/gpencil/intern/gpencil_io_export_pdf.cc
@@ -192,7 +192,7 @@ void GpencilExporterPDF::export_gpencil_layers()
           }
           else {
             bGPDstroke *gps_perimeter = BKE_gpencil_stroke_perimeter_from_view(
-                rv3d_, gpd_, gpl, gps_duplicate, 3, diff_mat_.values);
+                rv3d_, gpd_, gpl, gps_duplicate, 3, diff_mat_.values, 0.0f);
 
             /* Sample stroke. */
             if (params_.stroke_sample > 0.0f) {
diff --git a/source/blender/io/gpencil/intern/gpencil_io_export_svg.cc b/source/blender/io/gpencil/intern/gpencil_io_export_svg.cc
index 2601ad05ea7..e0eded35ce9 100644
--- a/source/blender/io/gpencil/intern/gpencil_io_export_svg.cc
+++ b/source/blender/io/gpencil/intern/gpencil_io_export_svg.cc
@@ -217,7 +217,7 @@ void GpencilExporterSVG::export_gpencil_layers()
           }
           else {
             bGPDstroke *gps_perimeter = BKE_gpencil_stroke_perimeter_from_view(
-                rv3d_, gpd_, gpl, gps_duplicate, 3, diff_mat_.values);
+                rv3d_, gpd_, gpl, gps_duplicate, 3, diff_mat_.values, 0.0f);
 
             /* Sample stroke. */
             if (params_.stroke_sample > 0.0f) {



More information about the Bf-blender-cvs mailing list