A discriminated-union reference resolves only when the current value has its matching variant. Observe the discriminator, then render that variant's generated fields; after switching, controls for the old branch no longer resolve. The schema and generated variant model are described in Schema unions.
KeyedFormSelector<ItinerarySchema, String?>(
selector: (form) => fields.getOrNull(form.value)?.kind,
builder: (context, kind, _) => switch (kind) {
'sightseeing' => KeyedFormField.text<ItinerarySchema>(
field: fields.asSightseeing.place,
builder: (context, field, text) => TextField(controller: text),
),
'meal' => KeyedFormField.text<ItinerarySchema>(
field: fields.asMeal.restaurant,
builder: (context, field, text) => TextField(controller: text),
),
_ => const SizedBox.shrink(),
},
)
When a union is inside a keyed list, update the row by clientId and preserve that ID while replacing its variant shape. The selector is important: the row identity remains stable across the variant change, while the selected discriminator changes the rendered branch. Generated APIs such as
asSightseeing and asMeal depend on the declared variant names; use the refs emitted for your schema rather than inventing a variant accessor. See
virtualized lists and selective rebuilds. For a complete repository example, browse the
tour builder source.