@@ -41,6 +41,8 @@ class GCDrawer extends GCDrawerBase {
4141 // Used in copyArea to capture the widget's actual rendered pixels via toImageSync().
4242 GlobalKey ? widgetBoundaryKey;
4343
44+ List <Shape > _staging = [];
45+
4446 /// Standalone mode: registers comm listeners for state + all draw ops + imageInit/gcDispose.
4547 /// Used for headless image rendering (new GC(image)).
4648 GCDrawer .standalone (VGC state) : onShapesUpdated = null , onGCDispose = null , super (state) {
@@ -63,9 +65,20 @@ class GCDrawer extends GCDrawerBase {
6365 /// Embedded mode: registers comm listeners for state + all draw ops + gcDispose.
6466 /// onShapesUpdated triggers GCImpl.setState().
6567 GCDrawer .embedded (VGC state, {this .onShapesUpdated, this .onGCDispose}) : super (state) {
66- EquoCommService .onRaw ("${state .swt }/${state .id }/gcDispose" , (_) {
67- if (shapes.isNotEmpty) onGCDispose? .call (List .from (shapes));
68+ EquoCommService .onRaw ("${state .swt }/${state .id }/gcDispose" , (_) async {
69+ final cycleStaging = _staging;
70+ _staging = [];
71+
72+ final pending = List <Future <ImageShape >>.from (_pendingImages);
73+ _pendingImages.clear ();
74+ if (pending.isNotEmpty) await Future .wait (pending);
75+
76+ cycleStaging.removeWhere ((s) => s is _PlaceholderShape );
77+
6878 shapes.clear ();
79+ shapes.addAll (cycleStaging);
80+
81+ if (shapes.isNotEmpty) onGCDispose? .call (List .from (shapes));
6982 onShapesUpdated? .call (shapes);
7083 });
7184 }
@@ -102,11 +115,13 @@ class GCDrawer extends GCDrawerBase {
102115
103116 // ── Shape helpers ───────────────────────────────────────────────────────
104117
105- void clearShapes () => shapes.clear ();
118+ void clearShapes () {
119+ shapes.clear ();
120+ _staging = [];
121+ }
106122
107123 void _addShape (Shape shape) {
108- shapes.add (shape);
109- onShapesUpdated? .call (shapes);
124+ _staging.add (shape);
110125 }
111126
112127 Rect _getRectFromArgs (int ? x, int ? y, int ? w, int ? h) => Rect .fromLTWH (
@@ -431,26 +446,29 @@ class GCDrawer extends GCDrawerBase {
431446 VGCDrawImageImageintintintintintintintint o) {
432447 if (o.image == null ) return ;
433448 final capturedClipping = clipping;
434- final idx = shapes.length;
435- shapes.add (_PlaceholderShape ());
449+ final targetStaging = _staging;
450+ final idx = targetStaging.length;
451+ targetStaging.add (_PlaceholderShape ());
436452 final f = ImageShape .fromVImageDetailed (o.image! , o, capturedClipping);
437453 _pendingImages.add (f);
438454 f.then ((s) {
439- if (idx < shapes.length) {
440- shapes[idx] = s;
441- onShapesUpdated? .call (shapes);
442- }
455+ if (idx < targetStaging.length) targetStaging[idx] = s;
443456 });
444457 }
445458
446459 void _processImageAsync (
447460 VImage vImage,
448461 VGCDrawImageImageintintintintintintintint opArgs,
449462 Rect ? capturedClipping,
450- ) async {
451- final imageShape =
452- await ImageShape .fromVImageDetailed (vImage, opArgs, capturedClipping);
453- _addShape (imageShape);
463+ ) {
464+ final targetStaging = _staging;
465+ final idx = targetStaging.length;
466+ targetStaging.add (_PlaceholderShape ());
467+ final f = ImageShape .fromVImageDetailed (vImage, opArgs, capturedClipping);
468+ _pendingImages.add (f);
469+ f.then ((imageShape) {
470+ if (idx < targetStaging.length) targetStaging[idx] = imageShape;
471+ });
454472 }
455473
456474 @override
@@ -569,12 +587,12 @@ class GCDrawer extends GCDrawerBase {
569587 (o.destX ?? 0 ) - (o.srcX ?? 0 ).toDouble (),
570588 (o.destY ?? 0 ) - (o.srcY ?? 0 ).toDouble (),
571589 );
572- final copiedShapes = shapes
590+ final copiedShapes = _staging
573591 .where ((shape) => _shapeIntersects (shape, srcRect))
574592 .map ((shape) => _translateShapeWithClip (shape, destOffset, srcRect))
575593 .toList ();
576594 for (final s in copiedShapes) {
577- _addShape (s);
595+ _staging. add (s);
578596 }
579597 }
580598
@@ -617,7 +635,7 @@ class GCDrawer extends GCDrawerBase {
617635 ui.Paint ()..color = const Color (0xFFFFFFFF ),
618636 );
619637 }
620- for (final shape in shapes) {
638+ for (final shape in [... shapes, ..._staging] ) {
621639 shape.draw (canvas);
622640 }
623641 final fullImage =
@@ -653,12 +671,12 @@ class GCDrawer extends GCDrawerBase {
653671 (o.destX).toDouble () - (o.srcX).toDouble (),
654672 (o.destY).toDouble () - (o.srcY).toDouble (),
655673 );
656- final copiedShapes = shapes
674+ final copiedShapes = _staging
657675 .where ((shape) => _shapeIntersects (shape, srcRect))
658676 .map ((shape) => _translateShapeWithClip (shape, destOffset, srcRect))
659677 .toList ();
660678 for (final s in copiedShapes) {
661- _addShape (s);
679+ _staging. add (s);
662680 }
663681 }
664682
0 commit comments