add feat to add multiple children and focus on specific at once
This commit is contained in:
@@ -28,8 +28,7 @@ class LazyCanvasController with ChangeNotifier {
|
|||||||
late final SpatialHashing<CanvasChildId> _spatialHash;
|
late final SpatialHashing<CanvasChildId> _spatialHash;
|
||||||
TickerProvider? _ticker;
|
TickerProvider? _ticker;
|
||||||
late BuildContext _context;
|
late BuildContext _context;
|
||||||
bool _firstBuild = true;
|
CanvasChildId? _focusChildOnBuild; // if set, will focus on this child on the next render
|
||||||
CanvasChildId? _focusChildOnInit; // if set, will focus on this child on first build
|
|
||||||
CanvasBackground background;
|
CanvasBackground background;
|
||||||
// these are used to cache result of widgetsWithScreenPositions
|
// these are used to cache result of widgetsWithScreenPositions
|
||||||
List<ChildInfo> _lastRenderedWidgets = [];
|
List<ChildInfo> _lastRenderedWidgets = [];
|
||||||
@@ -115,29 +114,30 @@ class LazyCanvasController with ChangeNotifier {
|
|||||||
|
|
||||||
/// Add a child at a given position with a widget. Returns the child ID.
|
/// Add a child at a given position with a widget. Returns the child ID.
|
||||||
/// You need the child size for optimising the focus on child
|
/// You need the child size for optimising the focus on child
|
||||||
CanvasChildId addChild(
|
CanvasChildId addChild(Offset position, Widget widget, {Size? childSize, CanvasChildId? id}) {
|
||||||
Offset position,
|
final childId = _addChildInternal(position, widget, childSize: childSize, id: id);
|
||||||
Widget widget, {
|
markDirty();
|
||||||
bool focusOnInit = false,
|
return childId;
|
||||||
Size? childSize,
|
}
|
||||||
CanvasChildId? id,
|
|
||||||
}) {
|
CanvasChildId _addChildInternal(Offset position, Widget widget, {Size? childSize, CanvasChildId? id}) {
|
||||||
assert(!useIdsFromArgs || useIdsFromArgs && id != null);
|
assert(!useIdsFromArgs || useIdsFromArgs && id != null);
|
||||||
id ??= _uuid.v4();
|
id ??= _uuid.v4();
|
||||||
if (focusOnInit) {
|
|
||||||
assert(
|
|
||||||
childSize != null,
|
|
||||||
'Child size must be provided when focusing on init (to know positions before any build). Else, you must call focusOnChild in a post frame callback.',
|
|
||||||
);
|
|
||||||
assert(_focusChildOnInit == null, 'Focus child on init is already set. Cannot set it again.');
|
|
||||||
_focusChildOnInit = id;
|
|
||||||
}
|
|
||||||
_children[id] = _ChildInfo(gsPosition: position, widget: widget, lastRenderedSize: childSize);
|
_children[id] = _ChildInfo(gsPosition: position, widget: widget, lastRenderedSize: childSize);
|
||||||
_spatialHash.add(position.toPoint(), id); // add to spatial hash
|
_spatialHash.add(position.toPoint(), id); // add to spatial hash
|
||||||
markDirty();
|
|
||||||
return id;
|
return id;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
List<CanvasChildId> addChildren(List<CanvasChildArgs> children, {CanvasChildId? focusOnBuild}) {
|
||||||
|
final ids = <CanvasChildId>[];
|
||||||
|
for (final child in children) {
|
||||||
|
ids.add(_addChildInternal(child.position, child.widget, childSize: child.childSize, id: child.id));
|
||||||
|
}
|
||||||
|
_focusChildOnBuild = focusOnBuild;
|
||||||
|
markDirty();
|
||||||
|
return ids;
|
||||||
|
}
|
||||||
|
|
||||||
/// Remove a child by its ID.
|
/// Remove a child by its ID.
|
||||||
void removeChild(CanvasChildId id) {
|
void removeChild(CanvasChildId id) {
|
||||||
if (!_children.containsKey(id)) {
|
if (!_children.containsKey(id)) {
|
||||||
@@ -223,10 +223,10 @@ class LazyCanvasController with ChangeNotifier {
|
|||||||
List<ChildInfo> widgetsWithScreenPositions({bool forceRebuild = false}) {
|
List<ChildInfo> widgetsWithScreenPositions({bool forceRebuild = false}) {
|
||||||
if (!_init) return [];
|
if (!_init) return [];
|
||||||
|
|
||||||
if (_firstBuild && _focusChildOnInit != null) {
|
if (_focusChildOnBuild != null) {
|
||||||
// if this is the first build, focus on the child if set
|
// if this is the first build, focus on the child if set
|
||||||
focusOnChild(_focusChildOnInit!, animate: false);
|
focusOnChild(_focusChildOnBuild!, animate: false);
|
||||||
_firstBuild = false;
|
_focusChildOnBuild = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!_renderCacheDirty && !forceRebuild) {
|
if (!_renderCacheDirty && !forceRebuild) {
|
||||||
|
|||||||
@@ -29,3 +29,12 @@ typedef CanvasChildId = String;
|
|||||||
// listener callbacks
|
// listener callbacks
|
||||||
typedef OnWidgetEnteredRender = void Function(CanvasChildId id);
|
typedef OnWidgetEnteredRender = void Function(CanvasChildId id);
|
||||||
typedef OnWidgetExitedRender = void Function(CanvasChildId id);
|
typedef OnWidgetExitedRender = void Function(CanvasChildId id);
|
||||||
|
|
||||||
|
class CanvasChildArgs {
|
||||||
|
final Offset position;
|
||||||
|
final Widget widget;
|
||||||
|
final Size? childSize;
|
||||||
|
CanvasChildId? id;
|
||||||
|
|
||||||
|
CanvasChildArgs({required this.position, required this.widget, this.childSize, this.id});
|
||||||
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user