scene_authoring library
The scene/motion authoring core — the vocabulary a generated .scene.dart
is built from, plus the pure document models and the motion runtime that
evaluates them.
This library is pure Dart, so a plain dart process (the fw CLI, the MCP
server, a codemod) can import it and parse, edit, emit and evaluate without
a Flutter engine. A test guards the import graph. The Flutter half (players,
widget bridges) lives in package:flutterware/scene.dart.
Experimental. This surface still moves with the editor and is not yet a supported API.
Classes
- AnimateGroup
-
One
late final <name> = scene.<node>.animate(…)field. -
Arg<
T> - One parameter a widget declaration names, with the value it falls back to when a scene sets nothing.
- AtExpr
- BoundGroup
- One group, bound to its node: the leaf writer. The group object itself is the writer identity in the fx stack, so first write fixes its position and re-writes stay put (probe M8).
- BoundMotion
- A motion document bound to one scene: the timeline built as a playable tree, and the pair guarded. Unplaced groups bind too — group hands them out for independent play — but only the timeline plays through apply.
- ClipBlocks
-
Several blocks on one track —
animationTime: ClipBlocks([ClipBlock(clip: 'Walk', at: 0.ms, length: 1000.ms), ClipBlock(clip: 'Run', at: 700.ms, length: 1700.ms)])— crossfading where they overlap. - ClipTrack
-
What a motion file spells for a block:
animationTime: ClipTrack(at: 0.ms, length: 2400.ms). A MotionTrack with the block and no keys, so the typedanimate()signatures take it where they take any track. - Effect
- One app-side fx writer: cosmetic, composed, never saved. Setting a property to null removes that contribution; clear removes them all.
- ExternalNode
- A widget from the app, placed in a scene.
- ExternalWidget
- What the app says about a widget a scene may place: its label, the arguments it takes, and how to make one.
- FillLayer
- FrameNode
- ItemRef
- The property reads one field of the item a repeat is drawing. Recorded against the LIST parameter rather than the closure's own name, because the closure's name is local and the binding has to outlive it.
- KindNode
-
A node of a registered kind (SceneKind): its rows live in values,
read and written by the table, and its children exist when the kind
says so. A thin subclass per kind gives the file its constructor and
the motion its typed
animate(); everything else — the wire, the JSON, the file's arguments, copy, undo, the inspector — reads the descriptor. - LinearPaint
- A gradient down the box by default, which is what a metal or a sunset face wants.
- ModelNode
- MotionClip
-
A run through a placement's clip, as one block on the timeline: from
at for length, the clip's own time advancing at speed from
offset — backwards when reverse. It stands on a number track (a
placement's
animationTime) and lowers to a straight ramp: the value at a moment is where the clip's time has got to. Past the block's end the value holds, like a track past its last key; how a time past the clip's own end reads is the placement'slooprow, which wraps it. - MotionDocument
- MotionKey
-
One keyframe.
valueis a double or a Color per the owning track's kind;curveis one of Curves (null = linear);paramRefis provenance — which motion parameter fed the value. The reference is the stronger of the two: an edit to the key moves the parameter's default (reconcileMotionBindings), and a save always spells the reference. - MotionSnapshot
- One motion's state at a moment: opaque, made by MotionDocument.snapshot, consumed by MotionDocument.restore.
- MotionTrack
- A mutable track with the door the probes demanded: key values retune freely; key time moves, inserts and removes go through methods that keep the list sorted — the everyday editor drag past a neighbour would otherwise silently break the hold rule.
- ParamRef
- The property reads one of the scene's own parameters, by name.
- ParExpr
- Playable
- Anything that can play: a duration and a total apply — a child before its window applies at 0, after it at its end (the hold rule, one level up). Groups, whole motions and combinators are all this one thing, which is what makes independent play the same call as playing the motion.
- RadialPaint
-
A gradient out from a point, STRETCHED TO THE BOX: at radius 1 it
reaches the edges on both axes, so on a wide headline it is an ellipse.
Flutter's
RadialGradientmeasures its radius against the shortest side instead, and on a 600×80 title that is a dot in the middle. - RepeatExpr
- SceneAlignment
-
A point in a box, in the -1..1 space Flutter's
Alignmentuses — where a gradient starts and ends. - SceneArgs
- An external node's arguments, read by name and by kind.
- SceneBinding
- Where a property's value comes from, when it is not a literal in the file. One entry per bound property in SceneNode.bindings.
- SceneBindSources
-
What can drive
keyonnode: the sources a bind menu offers, and whether a parameter can be made of it. - SceneChoices
-
The members a ScenePropKind.choice property can take and how the file
spells them:
NodeLayout.row,SceneFontWeight.w700. - SceneColor
-
An ARGB color. Files spell it
Color(0xAARRGGBB)— the only accepted color spelling; the mirror carries exactly that. - SceneCorners
- A node's corner radii, one per corner, clockwise from the top left.
- SceneCurve
- SceneCurves
-
The curve allowlist, as the file spells it.
SceneCurves.easeOutBackin a scene file is exactly this constant — so a mistyped curve is a compile error rather than a silent fall back to linear. - SceneDefinition
-
What a
.scene.dartclass extends — the seam between a scene as Dart and a scene as a document. - SceneDocument
- SceneEdges
- Space inside a frame, per side.
- SceneExtArgs
- SceneExtTracks
-
The generated track object a motion carries — a slot per animatable
argument, so
args: {'progress': …}for a parameter the widget does not have is not refused but unwritable. - SceneFontWeight
-
The nine weights, file-spelled
FontWeight.w<value>. - SceneGradient
- The three gradients, and what they share: colours, where each one sits, and the even spread a missing position means.
- SceneKey
- What a key names.
- SceneKind
- One node kind, as the file, the wire and the editor know it.
- SceneListenable
-
SceneMotion<
T extends SceneDefinition> -
What a
.scene.dartmotion class extends. - SceneNode
- SceneNodeArgs
- The generated argument object a node carries — one class per declared widget or nested scene, with a field per argument.
- ScenePaint
- What a pass paints with: one colour, a gradient across the box, or one of the project's own fragment shaders.
- SceneParamDecl
- ScenePartKey
- One named part of a property's value.
- SceneProp
- One authorable property.
- ScenePropertyKey
-
A property, whole:
fill,fontSize,style. - ScenePropSpec
- What an editor needs to know about an animatable property without a switch on its name: what it is, where it rests, how it reads, and where a slider would mean something.
- SceneQuad
- Four numbers that are one when they agree: edges, corners. What the property table needs to spell either as one number or four named parts.
- SceneRect
- A laid-out rectangle in artboard coordinates — what the renderer measured, never something a file spells.
- SceneRefArgs
- SceneRefNode
- An instance of another scene, by class name, with that scene's parameters overridden by args.
- SceneRepeat
- A frame drawn once per item of a list.
- SceneSnapshot
- The authored half of a document at one moment. Opaque: made by SceneDocument.snapshot, consumed by SceneDocument.restore, reusable — restoring copies out of it, never hands its own nodes over.
- SceneStyleField
- One property a SceneTextStyle may set: the property table's name for it, and how to read it off a style.
- SceneTextStyle
-
A text style: the text subset of the property table, as one value — what
a token names and a
TextNodetakes asstyle:, so a whole typographic treatment is shared in one move. - SceneTokenDecl
-
SceneValue<
T> - SeqExpr
- ShaderPaint
- A pass painted by one of the project's own fragment shaders.
- ShapeNode
- SolidPaint
- SpeedExpr
- StrokeLayer
- A stroke around the glyph outline. It widens the mark without touching the metrics, which is the whole reason several passes stay registered.
- StyleRef
- The node takes a shared text style whole — keyed under styleBindingKey rather than any one property, because a style is several at once. Each of them stays the node's to override; see SceneTextStyle.
- SurfaceNode
- A placed asset whose named mesh shows the node's first child.
- SweepPaint
-
A gradient around a point, the way a clock hand sweeps: 0° is twelve
o'clock and angles run clockwise, in degrees — the unit
rotateuses. Flutter'sSweepGradientstarts at three o'clock in radians; the renderer turns it, so the file never has to. - TextLayer
- One pass over a laid-out paragraph.
- TextNode
- TextRun
- One stretch of a paragraph, and what it differs by.
- TimelineExpr
- The arrangement — a pure time-transform tree over group references. A group appears at most once in the whole tree; groups it never names are library assets (independently playable, no autoplay).
-
Token<
T> -
One token as the app declares it, in a
final sceneTokens = [ … ]list beside the externals:Token<SceneColor>('brand', SceneColor(0xFF…)). The type argument is what the generatedSceneTokensclass types the field as, and the value is its default — so the declaration file compiles before anything has been generated from it, and the generated class is derived from it, never the other way round. - TokenRef
-
The property reads one of the package's shared tokens, by name — the
file spells
tokens.brandthrough the scene's tokens formal. - View3DNode
- What a scene file calls. The named parameters are the rows, and the common ones are every node's; the body is one map.
Enums
- NodeLayout
- How a frame arranges its children.
- SceneBlendMode
-
How a pass lands on what is already there — the modes a design tool
offers on a layer, by Flutter's names.
normalis the engine'ssrcOver; the rest are spelled the same on both sides, which the bridge test pins name by name. - SceneCrossAxisAlignment
-
File-spelled
CrossAxisAlignment.<name>; declaration order matches Flutter's, because the wire carries the index. - SceneLayerBox
- What a pass's paint is laid across. A solid colour is the same either way; a gradient is not — a two-line title in gold wants the gold to run down EACH line, not once down the paragraph with the second line in its darker half.
- SceneMainAxisAlignment
- Same contract as SceneCrossAxisAlignment, for the main axis.
- SceneParamKind
- The typed hole: a constructor parameter whose default is the mockup. Declared in the file as a primary-constructor formal with a default; referenced by node properties by bare identifier. Parameters share the class namespace with node fields.
- ScenePick
-
Where the editor finds the choices for a string row — see
SceneProp.pick. Each names something in the project, and the two that
depend on a model read the same node's
assetrow for which one. - ScenePropKind
- The kinds a property's value can take. Each has one wire spelling here and one file spelling in the tool; a property's kind is what a parameter binding is checked against.
- ScenePropOwner
- Which node kinds carry a property.
- SceneStrokeJoin
- How a stroke turns a corner. Declaration order matches Flutter's, because the bridge indexes it.
- SceneTextAlign
- How a text sits in the box it was given. Flutter's own names, because that is what the file spells and what it becomes.
- SceneTextCase
- How a text's case is forced, whatever the string says. Not a Flutter property — the renderer applies it to the string — but a design tool's, and the reason a kicker can be typed in the language it reads in and still be drawn in caps.
- SceneTextDecoration
-
The line a text carries. Flutter's
TextDecorationis a set rather than an enum, so the bridge switches rather than indexing; one line is what a design tool offers and what an import brings. - SceneTextDecorationStyle
- How that line is drawn; declaration order matches Flutter's, because the bridge indexes it.
- SceneTokenOwner
- One shared value the package declares, as the editor reads it — the name, the kind, and the value the declaration gives.
- TrackKind
- What a track's values are. Mirrors the scene's parameter kinds minus string — words are not tweened.
Extensions
- ExternalNodeAnimate on ExternalNode
- FrameNodeAnimate on FrameNode
- ModelNodeAnimate on ModelNode
- MotionDocumentJson on MotionDocument
- MotionTimelineLayout on MotionDocument
- The timeline expression, laid out: where each placed group starts and how long the whole runs. What a timeline panel draws from, and what the runtime computes for itself when it binds — the same arithmetic, kept here so the picture and the playback cannot disagree.
- MotionTrackBlend on MotionTrack
- MotionTrackEvaluate on MotionTrack
- SceneDocumentJson on SceneDocument
- SceneMillis on int
-
Milliseconds, so a file can write
240.ms— the only spelling the motion grammar accepts for a time. -
SceneMotionPlay
on SceneMotion<
SceneDefinition> - A compiled motion's timeline as a playable tree, built once per motion.
- SceneNodeAnimate on SceneNode
- The imposed properties, animatable on every node whatever its kind.
- SceneReadPlane on SceneDocument
- The read plane: what a document with no constructor does instead of one.
- SceneRefNodeAnimate on SceneRefNode
- ShapeNodeAnimate on ShapeNode
- SurfaceNodeAnimate on SurfaceNode
- TextNodeAnimate on TextNode
- View3DNodeAnimate on View3DNode
-
The typed
animate()a motion file spells — the one place per kind the table cannot write, because it is a Dart signature.
Constants
-
imposedProps
→ const List<
ScenePropSpec> - The imposed vocabulary: every node kind animates these.
-
motionReservedNames
→ const Set<
String> - Names a motion class member may not take: the header's super field, the mandatory arrangement, and the derived copy member.
- sceneArgsPrefix → const String
- The prefix an argument's key carries, because its name is the child's and could be any property's.
-
sceneArgsProps
→ const List<
SceneProp> - What a node that stands for something else passes it. One row, whose PARTS are the child's own parameter names — the only property whose parts this table cannot list, which is why they carry a prefix.
- sceneAxesPrefix → const String
- The prefix an axis's key carries, for the same reason an argument's does: the tags come from the font, not from this table.
-
sceneCommonProps
→ const List<
SceneProp> - Every node's properties, in the order the file writes them.
-
sceneCurvesByName
→ const Map<
String, SceneCurve> -
The same thirteen by name — what JSON reads back, and what the parser
resolves
SceneCurves.<name>through. A test holds this list to Curves. -
sceneFrameProps
→ const List<
SceneProp> -
A frame's own properties, after the common ones.
childrenand the repeat are not here: they are structure, not values. -
sceneShapeProps
→ const List<
SceneProp> -
sceneStyleProps
→ const List<
SceneProp> -
The table's STYLE SUBSET: exactly what a SceneTextStyle carries, and
exactly what
sceneTextStyleFieldsnames — pinned both ways, so a row added here without a field there would be authorable and unshareable. Every one of these is spelled inside the node's onestyle:argument. -
sceneTextOwnProps
→ const List<
SceneProp> - What a text spells for itself, beside its style.
-
sceneTextProps
→ const List<
SceneProp> - Every property a text carries, its own and its style's.
-
sceneTextStyleFields
→ const List<
SceneStyleField> - styleBindingKey → const String
-
The key a StyleRef sits under in SceneNode.bindings — the name the
file spells it with,
style: tokens.title.
Properties
- modelKind → SceneKind
-
One placed asset inside a 3D view.
final
- sceneFlushScheduler ↔ void Function(void flush())
-
How a batch of fx writes schedules its coalesced flush. The default
coalesces on a microtask — right for a headless process, where nothing
frames. A Flutter process installs the frame-aligned one (post-frame
callback + ensureVisualUpdate, the probed 500-writes-to-1-rebuild shape)
via the bridge's installSceneFrameFlush.
getter/setter pair
-
sceneKinds
→ List<
SceneKind> -
Every registered kind. Seeded with the kinds the core ships as data;
a package adds its own with registerSceneKind before a scene is read.
final
-
sceneProps
→ List<
SceneProp> -
The table, whole — the hand-written kinds' rows, plus every registered
kind's.
no setter
- surfaceKind → SceneKind
-
A placed asset with a slot: its first child is drawn onto the mesh named
by
mesh— or, with no asset, onto a quad one unit tall (timessize) whose width follows the child's box.final - view3dKind → SceneKind
-
A 3D view: an orbit camera around a target, drawing its model children.
final
Functions
-
animatableProps(
SceneNode node) → List< ScenePropSpec> - Imposed plus the target kind's intrinsic properties, in canonical emit order.
-
animateNode(
SceneNode node, Map< String, MotionTrack?> tracks) → AnimateGroup -
The door a registered kind's typed
animate()goes through — the same one the hand-written kinds use, named so it can be called from outside. -
applySceneItem(
SceneNode node, String list, SceneItem item) → SceneNode -
Fill in one item's fields across a repeated subtree: every property
bound to
<list>.<field>takes that field's value. Returnsnode, so a copy can be made and filled in one expression. -
bindableKind(
SceneNode node, String prop) → SceneParamKind? -
The parameter kind
propofnodecan read, or null when no parameter can fill it — the table's kind, seen as a parameter's. A nested scene's argument reads a parameter of the kind the child declares it; a side of a quad is a number; a list, a choice and a style are things no parameter holds. -
bindRepeats(
SceneDocument doc) → void - Rebuild the repeat closures of a document that was READ — parsed from source, or decoded from JSON — rather than compiled.
-
deepCopyNode(
SceneNode node, {String rename(String)?}) → SceneNode -
A deep copy of
node's authored plane — every authored property, bindings and children; never fx, measured geometry or the document pointer.renamemaps every name in the subtree (a duplicate needs fresh names — names are field identity, unique per scene); a snapshot passes nothing and keeps them. -
getSceneProperty(
SceneNode node, String prop) → Object? - Read one authored property by the name a SceneNode.bindings entry keys it under — the table's reader, with the two shapes a binding sees differently: edges as their uniform value, a nested argument at its override else the child's default.
-
inheritsFromStyle(
SceneDocument doc, SceneNode node, String prop) → bool -
Whether
propofnodeis what its style says — set by the style and equal to it. "Equal means inherited": there is no override flag, by decision, so a property overridden back to the style's own value is inherited again and follows the style. -
instantiateScene(
SceneDocument template, Map< String, Object?> args) → SceneDocument -
A fresh copy of
templatewithargsapplied to its parameters — what a SceneRefNode.instance is. The copy keeps the template's parameter declarations and bindings, so it can take new args later. -
isSceneDefault(
SceneProp p, Object? value) → bool -
Whether
valueis what the property holds by default — the test that decides whether it is written at all. -
isValidNodeName(
String name) → bool -
motionFromJson(
Map< String, Object?> json, {required String sceneClassName, required SceneDocument scene}) → MotionDocument - The inverse of MotionDocumentJson.toJson.
-
playTimeline(
TimelineExpr expr, {Map< AnimateGroup, BoundGroup> ? into}) → Playable - An arrangement as something that plays.
-
propSpecFor(
SceneNode node, String prop) → ScenePropSpec? - The spec for one property of one node, or null when that node does not animate it.
-
readSceneProps(
SceneNode node, Map< String, Object?> json) → void -
Every table property of
nodeoffjson, the default where the key is absent — shared by the authored plane and the wire, which spell values the same way and differ only in what else they carry. -
reconcileBindings(
SceneDocument doc) → List< String> - Route every edit of a bound property to what it is bound to — the other half of a binding, run by the editor after each mutation.
-
reconcileMotionBindings(
MotionDocument motion) → List< String> - The motion half of the binding rule: a key whose value moved off its parameter's default moves the default, and every other key reading that parameter follows. A key reading a parameter that is no longer declared loses the reference in the same edit, reported by group and property, rather than at save. Run by the editor after each mutation.
-
recordRepeat(
FrameNode frame, String source) → void - Record a repeat the way a reader can: the parameter it draws from, with the cells already in place. bindRepeats turns it into the closure.
-
registerSceneKind(
SceneKind kind) → void -
resolveSceneKey(
SceneNode node, String key) → SceneKey? -
Which SceneKey
keyis onnode, or null when it names nothing the node can hold. -
sceneArgName(
String key) → String? -
The argument's own name when
keynames one, else null. -
sceneAxisTag(
String key) → String? -
The axis's four-letter tag when
keynames one, else null. -
sceneBindSources(
SceneDocument doc, SceneNode node, String key) → SceneBindSources -
sceneFileFromJson(
Map< String, Object?> json) → ({String className, Map<String, MotionDocument> motions, SceneDocument scene}) - The inverse of sceneFileToJson.
-
sceneFileToJson(
SceneDocument doc, {required String className, Map< String, MotionDocument> motions = const {}}) → Map<String, Object?> - A whole file as data: the scene, the class it is named after, and the motions that animate it.
-
sceneFromJson(
Map< String, Object?> json) → SceneDocument -
sceneFromWire(
Map< String, Object?> root) → SceneDocument - Read back what SceneDocument.toWire wrote — a PICTURE, not a document.
-
sceneKindByConstructor(
String constructor) → SceneKind? -
sceneKindNamed(
String name) → SceneKind? -
scenePropNamed(
SceneNode node, String name) → SceneProp? -
One property by name, when
nodecarries it. -
scenePropsOf(
SceneNode node) → List< SceneProp> -
The properties
nodecarries, in file order: its kind's own after the common ones. -
sceneValuesEqual(
Object? a, Object? b) → bool - Whether two property values are the same value.
-
setSceneProperty(
SceneNode node, String prop, Object? value) → void - Write one authored property by the name a SceneNode.bindings entry keys it under. The one place that maps a property name to a slot, so an argument and a repeated item's field land the same way.
-
sizeFromWire(
Object? value) → double? - The inverse of sizeToWire.
-
sizeToWire(
double? size) → Object? - A size on its way out to the wire or a file.
-
styleOf(
SceneDocument doc, SceneNode node) → SceneTextStyle? -
The shared style
nodetakes, when it is bound to one that exists. -
tokenMarker(
String name) → Map< String, Object?> -
The wire's stand-in for an opaque token's value in an external node's
arguments —
{'token': 'ctaStyle'}. The object itself cannot travel and the editor never holds it; the guest, which compiled the declaration, resolves the name at build time (bindExternals). -
tokenMarkerName(
Object? value) → String? - The token a marker names, or null for any other value.
-
videoStops(
{required int durationMs, required int fps}) → List< double> -
The playhead positions a motion of
durationMsshould be rendered at to play back atfps. -
writeStyle(
SceneNode node, SceneTextStyle style) → void -
Writes every property
stylesets ontonode— applying a style, or resetting to it. Properties the style leaves alone are untouched.
Typedefs
- ClipBlend = ({double blend, String clip, String clip2, double time, double time2})
- What a placement plays at one moment: a clip and its time, a second clip and its time when two blocks overlap there, and how far across the overlap the moment is. Empty names mean the placement's own row.
- ClipBlock = MotionClip
- The file's word for one block among several — see ClipBlocks.
-
SceneItem
= Map<
String, Object> - One item of a list parameter: field name to value, and a value is a string or a number — the two kinds a bound property can take.
- SceneWidgetBuilder = Object Function(SceneArgs args)
- What an ExternalNode builds, given the args of the moment.