[Bf-blender-cvs] [502c420170b] lineart-shadow: LineArt: Fix light/shade cutting for intersections

YimingWu noreply at git.blender.org
Tue May 3 05:00:53 CEST 2022


Commit: 502c420170b7f130e01cb9f1e618ab0f10d2a273
Author: YimingWu
Date:   Tue May 3 11:00:18 2022 +0800
Branches: lineart-shadow
https://developer.blender.org/rB502c420170b7f130e01cb9f1e618ab0f10d2a273

LineArt: Fix light/shade cutting for intersections

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

M	source/blender/gpencil_modifiers/intern/lineart/MOD_lineart.h
M	source/blender/gpencil_modifiers/intern/lineart/lineart_cpu.c

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

diff --git a/source/blender/gpencil_modifiers/intern/lineart/MOD_lineart.h b/source/blender/gpencil_modifiers/intern/lineart/MOD_lineart.h
index a2c619eadcd..c1eec27d914 100644
--- a/source/blender/gpencil_modifiers/intern/lineart/MOD_lineart.h
+++ b/source/blender/gpencil_modifiers/intern/lineart/MOD_lineart.h
@@ -80,6 +80,7 @@ typedef enum eLineArtElementNodeFlag {
   LRT_ELEMENT_IS_ADDITIONAL = (1 << 0),
   LRT_ELEMENT_BORDER_ONLY = (1 << 1),
   LRT_ELEMENT_NO_INTERSECTION = (1 << 2),
+  LRT_ELEMENT_INTERSECTION_DATA = (1 << 3),
 } eLineArtElementNodeFlag;
 
 typedef struct LineartElementLinkNode {
diff --git a/source/blender/gpencil_modifiers/intern/lineart/lineart_cpu.c b/source/blender/gpencil_modifiers/intern/lineart/lineart_cpu.c
index 33dbcefd5ed..0cfd3892489 100644
--- a/source/blender/gpencil_modifiers/intern/lineart/lineart_cpu.c
+++ b/source/blender/gpencil_modifiers/intern/lineart/lineart_cpu.c
@@ -2006,6 +2006,38 @@ static void lineart_register_shadow_cuts(LineartRenderBuffer *rb,
   }
 }
 
+static void lineart_register_intersection_shadow_cuts(LineartRenderBuffer *rb,
+                                                      ListBase *shadow_elns)
+{
+  LineartElementLinkNode *eln_isect_shadow = NULL, *eln_isect_original = NULL;
+  if (!shadow_elns) {
+    return;
+  }
+  LISTBASE_FOREACH (LineartElementLinkNode *, eln, shadow_elns) {
+    if (eln->flags & LRT_ELEMENT_INTERSECTION_DATA) {
+      eln_isect_shadow = eln;
+      break;
+    }
+  }
+  LISTBASE_FOREACH (LineartElementLinkNode *, eln, &rb->line_buffer_pointers) {
+    if (eln->flags & LRT_ELEMENT_INTERSECTION_DATA) {
+      eln_isect_original = eln;
+      break;
+    }
+  }
+  if (!eln_isect_shadow || !eln_isect_original) {
+    return;
+  }
+  LineartEdge *e = (LineartEdge *)eln_isect_original->pointer;
+  for (int i = 0; i < eln_isect_original->element_count; i++) {
+    LineartEdge *shadow_e = lineart_find_matching_edge(eln_isect_shadow, (uint64_t)e->from_shadow);
+    if (shadow_e) {
+      lineart_register_shadow_cuts(rb, e, shadow_e);
+    }
+    e++;
+  }
+}
+
 static void lineart_geometry_object_load_no_bmesh(LineartObjectInfo *ob_info,
                                                   LineartRenderBuffer *re_buf,
                                                   ListBase *shadow_elns)
@@ -4444,6 +4476,7 @@ static void lineart_create_edges_from_isec_data(LineartIsecData *d)
   double ZMax = rb->far_clip;
   double ZMin = rb->near_clip;
 
+  int total_lines = 0;
   for (int i = 0; i < d->thread_count; i++) {
     LineartIsecThread *th = &d->threads[i];
     if (G.debug_value == 4000) {
@@ -4452,13 +4485,32 @@ static void lineart_create_edges_from_isec_data(LineartIsecData *d)
     if (!th->current) {
       continue;
     }
-    /* We don't care about removing duplicated vert in this method, chaning can handle that,
-     * and it saves us from using locks and look up tables. */
-    LineartVert *v = lineart_mem_acquire(&rb->render_data_pool,
-                                         sizeof(LineartVert) * th->current * 2);
-    LineartEdge *e = lineart_mem_acquire(&rb->render_data_pool, sizeof(LineartEdge) * th->current);
-    LineartEdgeSegment *es = lineart_mem_acquire(&rb->render_data_pool,
-                                                 sizeof(LineartEdgeSegment) * th->current);
+    total_lines += th->current;
+  }
+
+  if (!total_lines) {
+    return;
+  }
+
+  /* We don't care about removing duplicated vert in this method, chaning can handle that,
+   * and it saves us from using locks and look up tables. */
+  LineartVert *v = lineart_mem_acquire(rb->edge_data_pool, sizeof(LineartVert) * total_lines * 2);
+  LineartEdge *e = lineart_mem_acquire(rb->edge_data_pool, sizeof(LineartEdge) * total_lines);
+  LineartEdgeSegment *es = lineart_mem_acquire(rb->edge_data_pool,
+                                               sizeof(LineartEdgeSegment) * total_lines);
+
+  LineartElementLinkNode *eln = lineart_mem_acquire(rb->edge_data_pool,
+                                                    sizeof(LineartElementLinkNode));
+  eln->element_count = total_lines;
+  eln->pointer = e;
+  eln->flags |= LRT_ELEMENT_INTERSECTION_DATA;
+  BLI_addhead(&rb->line_buffer_pointers, eln);
+
+  for (int i = 0; i < d->thread_count; i++) {
+    LineartIsecThread *th = &d->threads[i];
+    if (!th->current) {
+      continue;
+    }
     for (int j = 0; j < th->current; j++) {
       LineartVert *v1 = v;
       LineartVert *v2 = v + 1;
@@ -5959,6 +6011,9 @@ bool MOD_lineart_compute_feature_lines(Depsgraph *depsgraph,
    * can do its job. */
   lineart_main_add_triangles(rb);
 
+  /* Add shadow cuts to intersection lines as well. */
+  lineart_register_intersection_shadow_cuts(rb, shadow_elns);
+
   /* Re-link bounding areas because they have been subdivided by worker threads and we need
    * andjacent info. */
   lineart_main_bounding_areas_connect_post(rb);



More information about the Bf-blender-cvs mailing list