)]}'
{
  "commit": "2c5681ff38a9e1f1cdf078c0345899c80ce1388d",
  "tree": "a47d4e15379e4eb7b86d4ab985242d13987dcf98",
  "parents": [
    "25971ecc364ed4740f4de88925cd97510a97c762"
  ],
  "author": {
    "name": "HayesGordon",
    "email": "hello@rive.app",
    "time": "Fri Jun 26 15:52:36 2026 +0000"
  },
  "committer": {
    "name": "HayesGordon",
    "email": "hello@rive.app",
    "time": "Fri Jun 26 15:52:36 2026 +0000"
  },
  "message": "feat(runtime): add semantics command queue api (#12198) bd587cb83f\n* wip: semantic system\n\n* feat: semantic state (#11888)\n\n* wip: semantic state\n\n* docs: semantic steps\n\n* test: initial state tests\n\n* chore: live region sample and set on inferred text component\n\n* fix: component list propegation\n\n* fix: visiblity changes exclude semantics and list examples\n\n* chore: update keys\n\n* refactor: remove semantic cursor and query artboard directly\n\n* refactor(flutter): semantic painter mixin\n\n* chore: remove redundant semanticsChanged call\n\n* chore: clangy clank\n\n* docs: cleanup\n\n* refactor: atomic node id\n\n* refactor: remove node id type alias\n\n* feat: focus and semantic handshake\n\n* refactor: opt in semantics for flutter\n\n* chore: cleanup\n\n* fix: tmp step around failing editor tests\n\n* chore: clang clank\n\n* refactor: cleanup public API\n\n* feat: add focusable as a state\n\n* chore: TEMP REMOVE TESTS RESTORE LATER\n\n* feat: semantic inference from subtree\n\n* refactor: expanded definition and state changes\n\n* feat: add support for passthrough bit flags (#11992)\n\n* add support for passthrough bit flags\n\n(cherry picked from commit de4a5504a448df8f051fadae2abf154ea1fad9fd)\n\n* chore: post cherry pick rerun code generator\n\n* feat: expose more passthrough properties\n\n* feat: add all passthrough properties as editor options and labels\n\n* chore: update keys after merge\n\n* chore: resolve merge issues and other post merge updates\n\n* chore: updated example with new core props\n\n* chore: remove expanded from state\n\n* feat: phase2 semantic roles and states\n\n* chore: clang clank\n\n* feat: add semantic actions\n\n* refactor: remove numericX\n\n* refactor: remove heading and progressIndicator from Roles\n\n* fix: missing potential semantic configurations\n\n* feat: add semantic traits for accessibility tristate support (#12148)\n\n* feat: add semantic traits\n\n* fix: semantic action dispatch for listeners targeting nested shapes\n\n* fix: core generator call onPropertyChanged to update editor state\n\n* refactor: editor UI for trait selection\n\n* chore: updated tests and examples\n\n* chore: clang clank\n\n* chore: updated tests\n\n* fix: pass correct from/to mask values in bitmask passthrough notifications\n\n* feat: add semantic artboard boundary (#12180)\n\n* feat: add semantic artboard boundary nodes for targeted collapse and bounds dirtying\n\n* fix: copy vector before iterating\n\n* feat: make semantics runtime opt-in\n\n* refactor: move around the entry point for semantics\n\n* fix: flutter check attach, correct comments, expanded test\n\n* fix(flutter): radio button isButton true (untested)\n\n* chore: additional null checks\n\n* chore: format def file\n\n* chore: uint32 for traits and states diff\n\n* feat: add semantics command queue api\n\n* fix(semantics): order nodes by visual position instead of static graph order (#12200)\n\n* fix(semantics): order nodes by visual position instead of static graph order\n\n* fix: use isBoundaryNode() instead of semanticData() for container bounds check\n\n* perf(semantics): specialize updatedGeometry as POD bounds struct (#12205)\n\n* refactor: dedicated SemanticBoundsUpdate struct\n\n* perf(semantics): tighten FFI diff readers and lock WASM layouts\n\n* chore: update code comment\n\n* chore(semantics): test and sample cleanup\n\n* chore(flutter): other cleanup and analyzer fixes\n\n* fix(semantics): emit diff arrays in deterministic tree pre-order\n\n* fix(semantics): scope semantic node id allocation per-manager\n\n* fix(semantics): static_assert FFI struct sizes on 64-bit native\n\n* test(semantic): SemanticTreeModel.applyDiff and the incremental refresh() paths\n\n* docs(semantics): document Mixed-wins precedence for Checked state\n\n* refactor(semantics): derive trait/state bit constants from JSON\n\n* refactor(semantics): tighten SemanticNode encapsulation\n\n* fix(semantics): (refactor) route fireSemanticAction through the manager index\n\n* refactor(semantics): bind semantic listeners strictly to target\u0027s SD\n\n* test: update .riv files to have listener on SD\n\n* perf(semantics): drop std::function closure in label derivation\n\n* perf(semantics): fuse post-order bounds walk with reorder check\n\n* chore(semantics): simplify and tighten the /simplify review findings\n\nAggregated review cleanups from three parallel audits of this session\u0027s work. No behaviour changes outside the applyDiff no-op guard (which tightens defense-in-depth without changing semantics for correctly-formed diffs).\n\nReuse\n- SemanticManager::reconcileBoundsForSubtree: replace field-by-field bounds compare with AABB::operator!\u003d.\n- Delete unused C++ effectiveChecked/effectiveMixed helpers from semantic_state.hpp; rewrite the Mixed-precedence docstring as plain prose. Dart helpers stay (used by the Flutter overlay).\n\nEfficiency\n- SemanticTreeModel.applyDiff: thread a `changed` flag through all six mutation loops so no-op diffs (identical payload) no longer bump version or notify listeners. New unit test pins the behaviour across updatedSemantic, updatedGeometry, and childrenUpdated.\n- SemanticManager::refresh() incremental path: when containerBoundsChangedIds is empty (common case), skip building the boundsDirtyUnion hashset and check m_dirtyBoundsNodes directly.\n- deriveLabelVisit: introduce LabelDerivationScratch struct owned at the top-level call and clear()-ed between interactive nodes, so per-node set and string allocations are reused across the walk.\n\nComment hygiene\n- Strip narration / session / what-describing comments across semantic_manager.cpp, semantic_data.cpp, state_machine_instance.cpp,\n  rive_semantics_overlay.dart, and rive_binding.cpp.\n- Trim the speculative 32-bit Dart FFI sizing note and the redundant inline \"see precedence note below\" breadcrumb on SemanticState.\n\n* chore(semantics): apply /simplify review findings across runtime and FFI\n\nPer-frame wins:\n- Return nullptr from stateMachineSemanticsTakeDiff when the diff is empty so idle frames skip the FFI struct allocation (Dart/WASM already handle null).\n- Skip markNodeDirty(Bounds) in updateWorldBounds when the computed AABB matches the cached value.\n- Short-circuit applyInferredSemanticsIfNeeded when the inferred role+label are unchanged.\n- Guard every *Changed() handler (role/label/stateFlags/traitFlags/value/hint/headingLevel) so same-value writes don\u0027t dirty the node.\n- Drop ComponentDirt::Paint from the visibility re-sync; opacity does not affect tree membership (per shouldExcludeFromSemanticTree).\n- toSemanticNodeFFI emits nullptr for empty value/hint instead of a 1-byte \"\\0\" buffer each.\n\nReuse:\n- SemanticDirt now uses RIVE_MAKE_ENUM_BITSET; hand-rolled |, \u0026, and hasSemanticDirt removed.\n- Replace hand-rolled \"find first child of T\" loops with ContainerComponent::firstChild\u003cT\u003e() (semantic_data.cpp, semantic_manager.cpp, focus_data.cpp, semantic_provider.cpp).\n- Replace two hasChildBounds two-branch merges with AABB::expand().\n- Dart _mapToWidgetRect uses AABB.transform() (four-corner transform) — also a correctness fix under rotation/skew.\n- Dart _listEquals -\u003e foundation.listEquas.\n\nCleanup:\n- Delete dead m_dirtyStructureNodes field (written, never read).\n- Fix SemanticsChildrenUpdateFFI.childCount from @Int32 to @Uint32 to match the C++ uint32_t.\n- Trim the inference registry: drop redundant null-checks on table entries, drop per-rule type re-check inside the infer fn, drop the POD struct constructor. Registry shape preserved for upcoming rules.\n- Remove a commented-out dropdown_list demo line.\n\n* chore: clang clank\n\n* chore: address copilot review comments\n\n* chore(semantics): update core definitions after merge\n\n* chore: update to new enum util functions after merge\n\n* chore: updated .riv files after merge new prop keys\n\n* chore: clang clank\n\n* chore: remove accessibility_tools package\n\n* test(semantic): expanded c++ test suite\n\n* test: simpsons list filtering test\n\n* test(semantic): fixed list scroll focus\n\n* chore: clang clank\n\n* fix: clang\n\n* chore: test cleanup\n\n* chore: cleanup before merge\n\n* wip: tmp integration guides\n\n* fix(semantics): tear down old painter when RiveSemanticsWidget swaps painter/artboard\n\n* fix(semantics): gate Text inference registry on WITH_RIVE_TEXT\n\n* docs(semantics): clarify that semanticBounds walks the full subtree\n\n* feat(rive_native): expose frame/tree debugger\n\n* perf(rive_native): hoist artboard→widget transform onto a single SemanticsNode\n\n* refactor(flutter): rename public API to \u0027drainSemanticsDiff\u0027 and \u0027focusSemanticNode\u0027\n\n* refactor!(semantics): rename \u0027takeDiff\u0027 to \u0027drainDiff\u0027\n\n* chore(editor): use uistrings for semantics\n\n* feat: Add drainSemanticsDiff operation to command queue (#12247)\n\n* fix: Use new drainDiff function\n\n* chore(flutter): rename ffi bindings to match C++ names exactly\n\n* feat(editor): show warning on role change\n\n* chore(semantics): change warning icon\n\n* chore: cleanup\n\n* chore: readd lost files after merge\n\n* chore: clang formating\n\n* docs: update guides on latest changes\n\n* fix(command-queue): consistent semantic error handling + harden drain\n\n* fix(command-queue): lock per-state-machine mutex for semantic commands\n\n* perf(command-queue): move semantics diff to global listener when sole recipient\n\n* fix(command-queue): map semantics bounds with the real transform, not bounds-equality)\n\n* chore:  per-state-machine lock now covers only what needs the instance and comment cleanup\n\n* chore: more comment cleanup\n\n* chore: move docs to semantics subfolder\n\nCo-authored-by: David Skuza \u003cdavid@rive.app\u003e\nCo-authored-by: Erik \u003cerik@rive.app\u003e\nCo-authored-by: Gordon \u003cpggordonhayes@gmail.com\u003e\nCo-authored-by: Hernan Torrisi \u003chernantorrisi@gmail.com\u003e\n",
  "tree_diff": [
    {
      "type": "modify",
      "old_id": "71e5f7a7ad74072d33c4da4b7cd6c6798dc2aa43",
      "old_mode": 33188,
      "old_path": ".rive_head",
      "new_id": "1819944531f20fd8042a745b4bb98f6e7b0e0fa5",
      "new_mode": 33188,
      "new_path": ".rive_head"
    },
    {
      "type": "modify",
      "old_id": "4a3ebb7550581f0edb44078054d3ad6fba0fb477",
      "old_mode": 33188,
      "old_path": "include/rive/command_queue.hpp",
      "new_id": "8208facfbb51384e4cd5392a3eca9b53a5a452d6",
      "new_mode": 33188,
      "new_path": "include/rive/command_queue.hpp"
    },
    {
      "type": "modify",
      "old_id": "c90534eb24da6a7be038feae0613de5ec4425522",
      "old_mode": 33188,
      "old_path": "include/rive/semantic/semantic_snapshot.hpp",
      "new_id": "0db95cadd9179955a86047a0f559f606aa8af536",
      "new_mode": 33188,
      "new_path": "include/rive/semantic/semantic_snapshot.hpp"
    },
    {
      "type": "modify",
      "old_id": "cbf1bac14b88f19d92fb7d9c793cc4a7a123fcdd",
      "old_mode": 33188,
      "old_path": "src/command_queue.cpp",
      "new_id": "54f4220367b96c44d8a37498dcf8cd059d465f66",
      "new_mode": 33188,
      "new_path": "src/command_queue.cpp"
    },
    {
      "type": "modify",
      "old_id": "7ee51898b8436cdfc4438d8f4a4704591ed1f014",
      "old_mode": 33188,
      "old_path": "src/command_server.cpp",
      "new_id": "c272c51f293249da59d54723748a1988d8feed76",
      "new_mode": 33188,
      "new_path": "src/command_server.cpp"
    },
    {
      "type": "modify",
      "old_id": "6efb0d93a13c27496d7f673b98663e3046d7b580",
      "old_mode": 33188,
      "old_path": "tests/unit_tests/runtime/command_queue_test.cpp",
      "new_id": "b5e4e159a5134dcbc50d51651ce6109cb859ce5a",
      "new_mode": 33188,
      "new_path": "tests/unit_tests/runtime/command_queue_test.cpp"
    }
  ]
}
