Skip to content

codelessly_sdk 8.3.0: charts, API chains, semantics, dialogs, links, styling - #74

Merged
BuildCodelessly merged 28 commits into
masterfrom
claude/affectionate-knuth-n1ntdj
Oct 24, 2026
Merged

BuildCodelessly merged 28 commits into
masterfrom
claude/affectionate-knuth-n1ntdj

Conversation

@BuildCodelessly

@BuildCodelessly BuildCodelessly commented Oct 23, 2026 •

Copy link
Copy Markdown
Contributor

Summary

Runtime fixes and features found while rebuilding a code-built app (Tidepool field guide) in the editor and comparing it screen by screen against the original, released as 8.3.0 on codelessly_api ^6.2.0 (Codelessly/CodelesslyAPI#39). The editor (Codelessly/CodelesslyEditor) and site (Codelessly/CodelesslySite#9) PRs depend on this release.

  • Charts: PassiveLineChartTransformer renders LineChartNode (bands, area, markers, scrub cursor); axis title and readout units bindable.
  • API chains: ${result} holds the response; query params are sent; onSuccess/onError run (also after the calling widget unmounts, e.g. a dialog closed mid-load); load-time calls run in chain order; Codelessly(client:).
  • Formulas: series/text/date helpers (range, interpolate, runs, minBy, obj, slice, now(offset), …) and FormulaClock.pinned for previews and reproducible screenshots.
  • Semantics: bindable semanticLabel/semanticSelected; a labelled button reads only its label and keeps its tap; fields/dropdowns keep their own semantics; toast semantics stable so its button is clickable on the web.
  • Layout: baseline rows get a text baseline; squeezable loose-flexible sizing; responsive dialogs follow the screen and let barrier taps through; expanded dropdowns don't cut their value at the design width.
  • Links: CodelesslyRoute links match screens' URL paths (guide/bat-star → guide/:id), and Codelessly.pathOf writes them; folded into master's route/pendingRoute.
  • Styling: toasts, confirm dialog and dropdown menus take the new API styling; image fills honour saturation; text color bindable.
  • Pop with a destination goes there when there is nothing to pop.

dart format, flutter analyze and flutter test (712) pass locally against the API branch. See CHANGELOG 8.3.0.

Known Issues

  • CI resolves codelessly_api ^6.2.0 from pub.dev, so it stays red until API 6.2.0 is published; re-run it after that.
  • The editor has no UI yet for squeezable.

🤖 Generated with Claude Code

https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4

claude added 25 commits October 23, 2026 16:45
Found rebuilding the Tidepool reference app in CodelesslyEditor.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
- Formulas: range (numbers, or dates by minutes), interpolate, runs, minBy,
  maxBy, obj, slice, substring, replace, split, wallTime, and a UTC offset
  for now()/today().
- callApi leaves its response (or error) as the chain's ${result}, so the
  next action can read it, e.g. inside a forEach.
- Codelessly takes an optional HTTP client.

Found rebuilding the Tidepool reference app in CodelesslyEditor.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
A row or column with crossAxisAlignment baseline built a Flex without
textBaseline, which Flutter asserts against, so the whole screen failed.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
HttpApiData.queryParams were saved by the editor but never added to the
request URL. FunctionsRepository.buildApiUrl adds the used ones, with
inputs and variables substituted.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
onError handles a failed request instead of stopping the chain, so a
screen can show its error state and turn its loading state off. Load-time
API calls take the same path.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
PassiveLineChartTransformer builds PassiveLineChartWidget, which resolves
the node's properties and bindings (data, domain, bands, y ticks, area
bands, reference lines, x ticks, markers, vertical lines, colors and the
semantic label; paths or formulas) into a LineChartSpec and paints it
bottom to top: bands, grid and y labels, gradient area, area bands, the
polyline or Catmull-Rom curve, dashed reference lines, x axis, markers,
vertical lines with tags and curve dots, and the scrub cursor with its
readout card. Hover, tap, horizontal drag and the arrow keys move the
cursor; Esc and mouse exit clear it. Date x values are wall-clock epoch
milliseconds, and the readout formats them like the formatDate formula,
which FormulaEvaluator.formatDate now exposes.

LineChartGeometry holds the pure parts: date and number parsing, domain,
pixel scale, linear interpolation, Catmull-Rom control points, readout
text, trend and card placement. Tests cover them, a bound data list from
a formula, and scrubbing with hover and keys.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
Nodes can bind node.variables['semanticLabel'] and ['semanticSelected'] to
give a custom accessible label and selected state. Tappable nodes merge
the label with their children's semantics so the tap action is kept.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
LayoutBuilder used to fire a canvas's load callApi reactions itself when
the layout loaded, before the rest of the load chain, so a sequence like
set loading -> call API -> read result ran out of order. It now only puts
those APIs' variables in the loading state and the canvas calls them in
its load chain.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
A screen opened directly (a deep link, the first route) can't pop; a pop
action with a destination now replaces it with that screen, as a back link
to a parent screen should.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
A label on a field, dropdown or other widget used to replace its
semantics, so a screen reader lost the text field or button. Widgets now
merge the label with their own semantics, as tappable nodes do.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
CodelesslyWidgetController.initialLocation opens the canvas whose path
matches it (guide/bat-star opens guide/:id) with the path and query params as
route params. onLocationChanged tells the host the location of the screen a
navigation action opens or goes back to, so a site can keep its URL in sync.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
- A dialog whose responsive canvas holds a responsive layout (a variance
  node with breakpoints) fills the screen, so its variant follows the
  screen width: a full-screen sheet on mobile, a centered card on desktop.
  Plain fixed-size dialog canvases keep their design size.
- In a dialog, taps where nothing paints or reacts (a canvas without a
  background, an empty frame) reach the barrier, so a dismissible
  full-screen dialog closes on them.
- A squeezable shrink-wrapped node in a Row/Column is wrapped in a loose
  Flexible: it hugs its content and shrinks to the room left.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
- Toasts take the action's button color, an optional close (x) button,
  corner radius, border, shadows (e.g. a hard stamped shadow), padding,
  max width, message and button fonts, icon size and a bottom offset per
  screen size.
- The built-in confirm dialog takes a border and shadows in place of its
  elevation, title/message/button fonts, and outlined buttons with their
  own radius, colors and shadows (a filled cancel button included).
- FeedbackTheme gains border, shadows, buttonBorder and buttonShadows;
  fromNodes reads the outline and shadow most tappable shapes share.
- A dropdown with a menuStyle opens a card anchored under the field: color,
  border, radius, shadows, offset, row height and padding, a highlighted,
  bolder selected row with a check mark. Rows (and the field) can show a
  per-item image from an itemImage template like ${item.image}.
- A data-source dropdown finds its selected item by content.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
FormulaClock.pinned sets the instant now() and today() (and relative
times) take, so a host can show an app at a given moment: previews of a
given day and reproducible screenshots of date-dependent screens.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
yAxisTitle and the cursor readout's scale, decimals and suffix read their
bindings, so a chart can follow a units setting (feet or metres).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
Master added Codelessly.route and pendingRoute (links by screen id); the
canvas URL paths added on this branch duplicated that with a controller
API. The controller API is gone: a link's path is now matched against
the screens' URL paths (guide/bat-star opens the screen at guide/:id with
id=bat-star) before it's read as a screen id, and Codelessly.pathOf gives
the address for a route, the screen's URL path when it has one.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
A semanticLabel on a tappable node was merged with the children's text
("Settings ft · ≤1.0"), so the button couldn't be named as designed. The
label now replaces the children, and the node's semantics carry its tap
and long press (the gesture handler below is excluded with the children).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
The selected value was capped at the node's stored design width minus the
icon, so a dropdown laid out wider than its design box (a station picker
in a wider header) cut its value short. An expanded dropdown already
gives the value the field's width.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
The toast left the accessibility tree while transparent and ignored taps
until it had faded in, so its semantics node changed after it was added.
The web engine stacks a node only when its siblings change, so the
changed node lost its stacking and sat under the screen: a click on Undo
landed on the list behind it. The toast now keeps its semantics and takes
taps from its first frame, and ignores them only while it fades out.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
callApi returned without running onSuccess/onError when the widget that
started the call had unmounted meanwhile, e.g. a settings dialog closed
while a reload it started was loading: the rest of the reload was lost
and the screen stayed loading. The handlers now run on a mounted context
of the chain (its opener), as the chain's other actions do.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
Depends on codelessly_api 6.2.0.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
@BuildCodelessly BuildCodelessly changed the title Runtime gaps from the Tidepool rebuild: charts, API chains, semantics, dialogs, links, styling codelessly_sdk 8.3.0: charts, API chains, semantics, dialogs, links, styling Oct 23, 2026
A RowColumnNode with wrap builds a Wrap in its direction, aligned by its
main and cross axis alignments and runAlignment, runSpacing apart. Items
can't share free space in a run: an expanded child takes its design size on
the main axis and a flex spacer keeps its design size. Margins still apply.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
…e ours

range(start, end, step) includes its end; range(n) stays n items from 0.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01F3B1XCZZ7QGvZLUGgSG5H4
@BuildCodelessly
BuildCodelessly merged commit 6e7e98b into master Oct 24, 2026
0 of 2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants