restore method
Write state back. Groups are REVIVED by name and keys by id, the way
the scene revives nodes: a bound motion holds group objects and a
player holds its writers, and an undo must not detach them.
Write state back, re-pointing each group at scene by the name the
snapshot recorded.
scene is what makes an undo across a rename work. The scene's own
restore revives nodes by name, so a node renamed since the snapshot
comes back as a NEW object and a group left holding the old one would
animate something nobody is drawing.
Implementation
void restore(MotionSnapshot state, {SceneDocument? scene}) {
params
..clear()
..addAll(state._params);
var live = {for (var g in groups) g.name: g};
var revived = <AnimateGroup>[];
for (var snap in state._groups) {
var into = live[snap.name];
if (into == null || !identical(into.node, snap.node)) {
revived.add(snap.copy());
continue;
}
_restoreTracks(into.tracks, snap.tracks);
revived.add(into);
}
if (scene != null) {
for (var (index, g) in revived.indexed) {
if (index >= state._targets.length) continue;
var node = scene.nodeNamed(state._targets[index]);
if (node != null) g.node = node;
}
}
groups
..clear()
..addAll(revived);
// Same mapping in the other direction: the snapshot's arrangement names
// the snapshot's groups, and what plays has to be the live ones.
var back = <AnimateGroup, AnimateGroup>{};
for (var (index, snap) in state._groups.indexed) {
if (index < revived.length) back[snap] = revived[index];
}
timeline = _copyExpr(state._timeline, back);
}