{"owner":"flet-dev","repo":"flet","hasSkills":true,"totalSkillsCount":110,"totalTokensCount":42780,"categories":["anthropic-skill","root-instruction","claude-rule","plugin-manifest"],"hasMcp":true,"mcpConfig":{"mcpServers":{"flet":{"command":"npx","args":["-y","@modelcontextprotocol/server-flet"]}}},"found":[".agents/skills/create-flet-control-integration-tests/SKILL.md",".agents/skills/create-flet-example-projects/SKILL.md",".agents/skills/docs-conventions/SKILL.md",".agents/skills/docs-build-and-verify/SKILL.md",".agents/skills/fix-members-short-description/SKILL.md",".agents/skills/flet-deprecation/SKILL.md",".agents/skills/flet-validation/SKILL.md",".agents/skills/prepare-flet-release/SKILL.md",".agents/skills/implement-flet-extension/SKILL.md",".agents/skills/imperative-to-declarative-flet/SKILL.md",".agents/skills/run-unit-tests/SKILL.md",".agents/skills/run-integration-tests/SKILL.md",".agents/skills/test-flet-apps-dev/SKILL.md",".agents/skills/update-flet-control-doc-gifs/SKILL.md",".agents/skills/write-changelog-entry/SKILL.md","website/.agents/skills/flet-release-announcement/SKILL.md","AGENTS.md","CLAUDE.md","packages/flet/CHANGELOG.md","packages/flet/README.md","packages/flet/analysis_options.yaml","packages/flet/pubspec.yaml","packages/flet_integration_test/analysis_options.yaml","packages/flet_integration_test/pubspec.yaml","tools/crocodocs/README.md","sdk/python/packages/flet-ads/CHANGELOG.md","sdk/python/packages/flet-ads/README.md","sdk/python/packages/flet-audio-recorder/CHANGELOG.md","sdk/python/packages/flet-audio-recorder/README.md","sdk/python/packages/flet-audio/CHANGELOG.md","sdk/python/packages/flet-audio/README.md","sdk/python/packages/flet-camera/README.md","sdk/python/packages/flet-charts/CHANGELOG.md","sdk/python/packages/flet-charts/README.md","sdk/python/packages/flet-cli/README.md","sdk/python/packages/flet-code-editor/CHANGELOG.md","sdk/python/packages/flet-code-editor/README.md","sdk/python/packages/flet-color-pickers/CHANGELOG.md","sdk/python/packages/flet-color-pickers/README.md","sdk/python/packages/flet-datatable2/CHANGELOG.md","sdk/python/packages/flet-datatable2/README.md","sdk/python/packages/flet-desktop/README.md","sdk/python/packages/flet-flashlight/CHANGELOG.md","sdk/python/packages/flet-flashlight/README.md","sdk/python/packages/flet-geolocator/CHANGELOG.md","sdk/python/packages/flet-geolocator/README.md","sdk/python/packages/flet-local-auth/README.md","sdk/python/packages/flet-lottie/CHANGELOG.md","sdk/python/packages/flet-lottie/README.md","sdk/python/packages/flet-map/CHANGELOG.md","sdk/python/packages/flet-map/README.md","sdk/python/packages/flet-mcp/README.md","sdk/python/packages/flet-permission-handler/CHANGELOG.md","sdk/python/packages/flet-permission-handler/README.md","sdk/python/packages/flet-platform-assets/README.md","sdk/python/packages/flet-rive/CHANGELOG.md","sdk/python/packages/flet-rive/README.md","sdk/python/packages/flet-secure-storage/README.md","sdk/python/packages/flet-spinkit/CHANGELOG.md","sdk/python/packages/flet-spinkit/README.md","sdk/python/packages/flet-video/CHANGELOG.md","sdk/python/packages/flet-video/README.md","sdk/python/packages/flet-web/README.md","sdk/python/packages/flet-webview/CHANGELOG.md","sdk/python/packages/flet-webview/README.md","sdk/python/packages/flet/README.md","sdk/python/packages/flet/integration_tests/README.md","sdk/python/examples/extensions/lottie/lottie_animations/assets/sample.json","sdk/python/packages/flet-ads/src/flutter/flet_ads/analysis_options.yaml","sdk/python/packages/flet-ads/src/flutter/flet_ads/pubspec.yaml","sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/CHANGELOG.md","sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/README.md","sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/analysis_options.yaml","sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/pubspec.yaml","sdk/python/packages/flet-audio/src/flutter/flet_audio/analysis_options.yaml","sdk/python/packages/flet-audio/src/flutter/flet_audio/pubspec.yaml","sdk/python/packages/flet-camera/src/flutter/flet_camera/analysis_options.yaml","sdk/python/packages/flet-camera/src/flutter/flet_camera/pubspec.yaml","sdk/python/packages/flet-charts/src/flutter/flet_charts/CHANGELOG.md","sdk/python/packages/flet-charts/src/flutter/flet_charts/analysis_options.yaml","sdk/python/packages/flet-charts/src/flutter/flet_charts/pubspec.yaml","sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/analysis_options.yaml","sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/pubspec.yaml","sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/analysis_options.yaml","sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/pubspec.yaml","sdk/python/packages/flet-datatable2/src/flutter/flet_datatable2/pubspec.yaml","sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/analysis_options.yaml","sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/pubspec.yaml","sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/analysis_options.yaml","sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/pubspec.yaml","sdk/python/packages/flet-local-auth/src/flutter/flet_local_auth/pubspec.yaml","sdk/python/packages/flet-lottie/src/flutter/flet_lottie/analysis_options.yaml","sdk/python/packages/flet-lottie/src/flutter/flet_lottie/pubspec.yaml","sdk/python/packages/flet-map/src/flutter/flet_map/analysis_options.yaml","sdk/python/packages/flet-map/src/flutter/flet_map/pubspec.yaml","sdk/python/packages/flet-mcp/src/flet_mcp/data/icons.json","sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/analysis_options.yaml","sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/pubspec.yaml","sdk/python/packages/flet-rive/src/flutter/flet_rive/analysis_options.yaml","sdk/python/packages/flet-rive/src/flutter/flet_rive/pubspec.yaml","sdk/python/packages/flet-secure-storage/src/flutter/flet_secure_storage/pubspec.yaml","sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/analysis_options.yaml","sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/pubspec.yaml","sdk/python/packages/flet-video/src/flutter/flet_video/analysis_options.yaml","sdk/python/packages/flet-video/src/flutter/flet_video/pubspec.yaml","sdk/python/packages/flet-web/src/flet_web/fastapi/README.md","sdk/python/packages/flet-webview/src/flutter/flet_webview/analysis_options.yaml","sdk/python/packages/flet-webview/src/flutter/flet_webview/pubspec.yaml","sdk/python/packages/flet/src/flet/controls/cupertino/cupertino_icons.json","sdk/python/packages/flet/src/flet/controls/material/icons.json"],"skills":{".agents/skills/create-flet-control-integration-tests/SKILL.md":"---\nname: create-flet-control-integration-tests\ndescription: Use when asked to create or update integration tests for any Flet control in sdk/python/packages/flet/integration_tests, including visual goldens and interactive behavior tests.\n---\n\n## When to use\n\nUse this skill when adding, updating, or reviewing integration tests for a Flet control (core, material, cupertino, theme, services, types, or examples).\n\nUse it for:\n\n- visual rendering checks with golden screenshots\n- interaction checks (hover, click, input, keyboard)\n- control property behavior checks\n- regression tests for control bugs\n\n## Test placement\n\nPick the closest existing suite first:\n\n- Core controls: `sdk/python/packages/flet/integration_tests/controls/core`\n- Material controls: `sdk/python/packages/flet/integration_tests/controls/material`\n- Cupertino controls: `sdk/python/packages/flet/integration_tests/controls/cupertino`\n- Theme tests: `sdk/python/packages/flet/integration_tests/controls/theme`\n- Type helpers: `sdk/python/packages/flet/integration_tests/controls/types`\n- Services: `sdk/python/packages/flet/integration_tests/controls/services`\n- Examples: `sdk/python/packages/flet/integration_tests/examples`\n\nPrefer adding tests to an existing file for the same control. Create a new test file only when no suitable file exists.\n\n### Scope split rule (required)\n\nDo not mix `loop_scope=\"module\"` and `loop_scope=\"function\"` tests in the same file.\n\nNaming convention:\n\n- `test_<control>.py` for module-scoped visual/stable tests (uses `flet_app`)\n- `test_<control>_isolated.py` for function-scoped tests that require a fresh app per test (uses `flet_app_function`)\n\n## Fixture choice\n\nUse fixtures from `integration_tests/conftest.py`:\n\n- `flet_app` (`loop_scope=\"module\"`): best for stable visual tests and bulk screenshot tests.\n- `flet_app_function` (`loop_scope=\"function\"`): best for tests that mutate state and must run in a separate app each.\n\n## Authoring workflow\n\n1. Identify behavior to verify.\n2. Build deterministic layout/state:\n- set `theme_mode` explicitly when visuals matter\n- set fixed sizes/padding/spacing\n- avoid random or time-varying content\n3. Choose file by scope rule before writing tests.\n4. Write test using async pytest.\n5. Use screenshot assertion for UI behavior, functional assertion for non-visual behavior.\n6. Name test so `request.node.name` can be used as screenshot key.\n7. Run target test file.\n8. If expected visuals changed, regenerate goldens with `FLET_TEST_GOLDEN=1` and re-run without golden mode.\n\n## Assertion patterns\n\n### Visual control assertion\n\n```python\nawait flet_app.assert_control_screenshot(\n    request.node.name,\n    control,\n)\n```\n\n### Visual full-page assertion\n\n```python\nflet_app_function.assert_screenshot(\n    request.node.name,\n    await flet_app_function.page.take_screenshot(\n        pixel_ratio=flet_app_function.screenshots_pixel_ratio\n    ),\n)\n```\n\n### Functional assertion\n\n```python\nfinder = await flet_app_function.tester.find_by_tooltip(\"Info tooltip\")\nassert finder.count == 1\n```\n\n## Minimal templates\n\n### Template: module-scope file (`test_<control>.py`)\n\n```python\nimport pytest\n\nimport flet as ft\nimport flet.testing as ftt\n\n\n@pytest.mark.asyncio(loop_scope=\"module\")\nasync def test_<behavior>(flet_app: ftt.FletTestApp, request):\n    flet_app.page.theme_mode = ft.ThemeMode.LIGHT\n    await flet_app.assert_control_screenshot(\n        request.node.name,\n        ft.Container(width=240, height=80, alignment=ft.Alignment.CENTER),\n    )\n```\n\n### Template: function-scope file (`test_<control>_isolated.py`)\n\n```python\nimport pytest\n\nimport flet as ft\nimport flet.testing as ftt\n\n\n@pytest.mark.asyncio(loop_scope=\"function\")\nasync def test_<behavior>(flet_app_function: ftt.FletTestApp):\n    flet_app_function.page.add(ft.IconButton(icon=ft.Icons.INFO, tooltip=\"Info\"))\n    await flet_app_function.tester.pump_and_settle()\n\n    finder = await flet_app_function.tester.find_by_tooltip(\"Info\")\n    assert finder.count == 1\n```\n\n## Run commands\n\nRun one test file:\n\n```bash\nuv run pytest -s -o log_cli=true -o log_cli_level=INFO packages/flet/integration_tests/controls/core/test_control.py\n```\n\nRun a subset:\n\n```bash\nuv run pytest -s -o log_cli=true -o log_cli_level=INFO packages/flet/integration_tests/controls/core/test_control.py -k test_visible\n```\n\nGenerate or update goldens:\n\n```bash\nFLET_TEST_GOLDEN=1 uv run pytest -s -o log_cli=true -o log_cli_level=INFO packages/flet/integration_tests/controls/core/test_control.py\n```\n\n## Quality checklist\n\n- Test file location matches control area.\n- `module` and `function` scope tests are in separate files.\n- Function-scoped files use the `test_<control>_isolated.py` naming convention.\n- Fixture scope matches test intent.\n- Screenshot keys are stable (`request.node.name` preferred).\n- Visual tests are deterministic (theme/size/content).\n- Goldens are updated only for intentional visual changes.\n- No unrelated formatting or refactors in the same change.\n\n## References\n\n- `sdk/python/packages/flet/integration_tests/README.md`\n- `sdk/python/packages/flet/integration_tests/conftest.py`\n- `sdk/python/packages/flet/integration_tests/controls/core/test_control.py`\n- `sdk/python/packages/flet/integration_tests/controls/core/test_control_isolated.py`\n- `sdk/python/packages/flet/integration_tests/controls/core/test_layout_control.py`\n- `sdk/python/packages/flet/integration_tests/examples/core/test_control.py`\n- `sdk/python/examples/controls/control`\n",".agents/skills/create-flet-example-projects/SKILL.md":"---\nname: create-flet-example-projects\ndescription: Use when asked to create Flet example projects from flat .py files with main.py and pyproject.toml metadata for Gallery/MCP indexing.\n---\n\n## When to use\n\nUse this skill when a user asks to:\n- create one control/example folder (for example `examples/controls/chip`) in the project-per-example format\n- migrate existing flat examples to the project-per-example format\n- normalize a partially converted folder so all examples follow the same structure\n\n## Goal\n\nEnsure each runnable example is a standalone project containing:\n\n- `main.py`\n- `pyproject.toml` with Gallery/MCP metadata\n- `assets/` (if the example uses local assets)\n\n## Workflow\n\n1. Inspect source folder.\n- Detect current state per example:\n  - flat file: `foo.py`\n  - project folder: `foo/main.py`\n  - mixed/partial conversion: both styles present or missing metadata files\n- Find candidate flat modules: `*.py` in the target folder (exclude helper files such as `__init__.py`).\n- Keep existing `media/` unless an example needs local assets copied into its own `assets/`.\n\n2. Convert or normalize examples.\n- For `foo.py`, create `foo/` and move file to `foo/main.py`.\n- If `foo/main.py` already exists, keep it and do not recreate/move files.\n- If folder exists but `main.py` is missing, repair structure only when there is a clear source file.\n- Do not create `foo/__init__.py`; import example modules directly in tests/docs (for example `import examples.controls.foo.bar.main as bar` or `import examples.controls.foo.bar as bar` when using namespace-package imports).\n- When a control folder has been fully converted to project-per-example layout, delete the control-level `examples/controls/<control>/__init__.py` too. The converted folders should behave like namespace packages, matching prior migrations such as commit `7e65ad566`.\n\n3. Add `pyproject.toml` for each example project.\n- Infer from path and code.\n- Create missing `pyproject.toml` files for existing project folders.\n- Update obviously stale metadata when migrating existing examples (for example wrong title/description/categories).\n- Verify platform support before adding or omitting `[tool.flet].platforms`:\n  - Check the local implementation and docs for explicit platform guards, support tables, or platform-specific exceptions.\n  - If support is limited, add `[tool.flet].platforms` with only the supported platforms.\n  - If support is broad/all-platform, omit `[tool.flet].platforms`.\n- Required fields:\n  - `[project]`: `name`, `version`, `description`, `requires-python`, `keywords`, `authors`, `dependencies`\n  - `[dependency-groups].dev`: include `flet-cli`, `flet-desktop`, `flet-web`\n  - `[tool.flet.gallery].categories`\n  - `[tool.flet.metadata]`: `title`, `controls`, `layout_pattern`, `complexity`, `features`\n  - `[tool.flet]`: `org`, `company`, `copyright`\n- Add `[tool.flet].platforms` only when the example is platform-limited.\n- Add permissions blocks only when code actually needs them.\n\n4. Infer metadata.\n- Title: readable version of file/folder intent.\n- Short description: one line of what the example demonstrates.\n- `[project].description` must be meaningful and example-specific; avoid generic placeholders like \"Example N\" or \"<name> example for <control>\".\n- Description should mention the concrete behavior or interaction shown (for example: hover highlight, live updates, custom axes, event handling).\n- Categories: typically control-based, e.g. `Input/Chip`, plus optional `Apps/Basic controls`.\n- Tags: from control/topic/behavior words.\n- Controls used: list key controls from code.\n- Layout pattern: choose closest practical value (e.g. `filter-bar`, `inline-actions`, `dashboard`, `list-detail`).\n- Complexity: `basic` unless logic/state/architecture is non-trivial.\n- Features: notable behaviors only (click handling, selection, async loading, drag-and-drop, etc.).\n- If an example supports exporting or downloading output, include `\"save to file\"` in `[tool.flet.metadata].features`.\n- If an example module contains `async def` handlers or async control flow, append `\"async\"` to `keywords`.\n\n\n5. Infer dependencies from imports.\n- Always include `flet` for standard examples.\n- Include extra packages if imported (for example extension packages).\n- Do not add unused dependencies.\n\n6. Make examples mobile-safe.\n- If `ft.context.disable_auto_update()` is not used, do not add explicit `page.update()` unless strictly necessary.\n- Apply this `page.update()` rule to all examples in the touched folder (new, migrated, and already converted).\n- Wrap app content in `ft.SafeArea` so example renders correctly on mobile.\n- Add `expand=True` to `ft.SafeArea` only when needed for correct layout/sizing (for example to avoid Infinity/NaN sizing issues), and avoid adding it when not necessary.\n- When converting legacy `page.add(a, b, ...)` style examples, wrap the controls in `ft.Column(controls=[...])` inside `ft.SafeArea(content=...)` rather than `ft.Row`, unless the original code explicitly used a row layout.\n\n- Apply this to all examples in the touched folder (new, migrated, and already converted), not only files changed by moves.\n- During validation, confirm every `<example>/main.py` in scope includes a top-level `ft.SafeArea` around rendered content.\n- For declarative examples using `@ft.component`, do not pass component instances as regular control children (for example `SafeArea(content=App())`) because this can raise runtime attribute errors.\n- In declarative examples, ensure the component itself returns regular controls (including `SafeArea` when needed) and render it at page level with `page.render(App)` in `main()`.\n\n7. Prefer `@ft.control` for custom controls in examples.\n- If an example defines a custom control class inheriting from a Flet control (for example `class MyThing(ft.Column)`), prefer `@ft.control` style.\n- Move constructor-style setup to declarative fields + `init()` where practical.\n- Keep behavior unchanged and avoid refactors that alter public usage unless needed for compatibility.\n\n8. Remove deprecated Material 3 toggle usage.\n- If `use_material3` appears in example code, remove it and simplify the example to current API usage.\n- Remove related Material 3 toggle logic/UI that exists only to switch `use_material3`.\n- Update example metadata (`pyproject.toml`) to remove stale Material 3 references when code is changed.\n\n9. Ensure runnable entrypoint.\n- Every example `main.py` should end with:\n  - `if __name__ == \"__main__\":`\n  - `    ft.run(main)`\n- Apply this to all examples in the touched folder (new, migrated, and already converted).\n\n10. Update references.\n- Docs code includes: change from `.../example.py` to `.../example/main.py`.\n- Inspect the relevant docs pages for each touched control/service/example area (for example `sdk/python/packages/flet/docs/controls/<control>.md`) and update any `--8<--` includes or direct file-path references to the new `main.py` path.\n- Tests/imports: use direct module imports and avoid relying on package-level `__init__.py` re-exports.\n- For already-converted examples, only update references that are stale; avoid unnecessary churn.\n- If removing a control-level `__init__.py`, confirm no remaining imports rely on `from examples.controls.<control> import ...`.\n\n11. Validate.\n- Run `python -m compileall` on changed `main.py` files.\n- Run `uv run ruff check` on changed example files and fix violations until it passes (respecting repository `pyproject.toml` under `[tool.ruff]`).\n- Search for stale paths to old flat files.\n- Search docs and package sources for stale references to the migrated flat example paths and fix any hits in scope.\n- Check `git status` to confirm expected moves and edits.\n- When integration tests exist for the touched control, run the targeted test file(s).\n- Confirm all in-scope `main.py` files include both top-level `ft.SafeArea` wrapping and the `if __name__ == \"__main__\": ft.run(main)` entrypoint.\n- Confirm in-scope `ft.SafeArea` wrappers use `expand=True` only where needed for correct behavior and sizing; avoid forcing it by default.\n- Confirm there are no unnecessary `page.update()` calls in in-scope examples (unless explicitly required by isolated-control or non-auto-update behavior).\n- Confirm no in-scope examples use `use_material3`.\n- Confirm each in-scope `pyproject.toml` has a meaningful, example-specific `[project].description` (not generic or templated text).\n- Confirm metadata features include `\"save to file\"` when the example code supports file export/save behavior.\n- Confirm there is no stale control-level `__init__.py` left behind once a touched control folder has been fully converted.\n- Confirm the relevant docs pages were updated to reference `main.py` and that no stale doc includes remain for the touched examples.\n\n\n## Code style\n\n- When writing wrapped controls (`SafeArea`, `Column`, `Row`, `Container`, etc.), keep `content=` or `controls=` as the last named argument in that control call.\n- Apply this ordering consistently when creating or refactoring examples.\n- Follow code style and linting rules defined in the repository `pyproject.toml` under `[tool.ruff]` for all edits.\n\n## Command checklist\n\n- Discover files: `rg --files <target_dir>`\n- Find docs links/imports: `rg -n \"<old_path_or_module>\" packages examples`\n- Syntax check: `python -m compileall <changed_main_files>`\n- Ruff check: `uv run ruff check <changed_example_files>`\n\n## Output expectations\n\nReport:\n- created example projects\n- metadata added\n- docs/tests updates\n- validation results\n",".agents/skills/docs-conventions/SKILL.md":"---\nname: docs-conventions\ndescription: Use when writing or reviewing Flet documentation, including Python docstrings (Google style, reST roles, admonitions), Markdown docs (cross-references, images, code examples), and sidebar navigation.\n---\n\n# Documentation Conventions\n\nDocs live in `website/docs/`. Docusaurus renders them as the website.\n\n## Python Docstrings\n\nUse **Google style** docstrings with sections: `Args:`, `Returns:`, `Raises:`, `Note:`, `Example:`, `Warning:`.\n\n## Cross-references\n\n### reST roles\n\nPrefer these in Python docstrings. CrocoDocs renders them as links in\nthe API docs and they keep authoring terse when the auto-derived label is acceptable.\n\n**Supported roles:** `:class:`, `:attr:`, `:meth:`, `:func:`, `:data:`, `:mod:`\n\n```python\n\"\"\"\nIf a parent is a :class:`~flet.ResponsiveRow`, this property determines\nhow many virtual columns the control spans.\n\nSee :attr:`value` or :attr:`flet.Text.size` for the current selection.\n\nCalls :meth:`flet.Page.update` after modifying controls.\n\"\"\"\n```\n\n**Rules:**\n\n- **Qualified reference:** `:attr:`flet.Page.route`` — links to the member, displays inline code `Page.route`\n- **Extension reference:** `:attr:`flet_map.Map.animation_curve`` — links to the extension member, displays inline code `Map.animation_curve`\n- **Short display with `~`:** `:attr:`~flet.Page.route`` — links to the member, displays inline code `route`\n- **Local member (same class):** `:attr:`value`` — no qualifier needed\n- **Method with parens:** `:meth:`update`` — do NOT include `()` in the target\n\nFor plain class references like `:class:`flet.Page`` and extension references like\n`:class:`flet_map.Map``, the website strips leading public package aliases automatically,\nso they display as inline code `Page` and `Map`.\n\n**Not supported:**\n\n- Custom labels like `:class:`my label <flet.Page>`` — the label is always auto-derived from the target\n- Roles for symbols not in CrocoDocs API data degrade to inline code\n\n### Xrefs\n\nReference-style Markdown links of the form `[label][key]`, where `key` is the\nfully-qualified dotted symbol path (same form as reST role targets).\n\nUse as the default form for linking to API symbols from Markdown docs\n(`.md` / `.mdx`).\n\nExamples:\n\n```markdown\nClass: [`Page`][flet.Page]\nAttribute: [`route`][flet.Page.route]\nMethod: [`Page.update()`][flet.Page.update]\nExtension: [`Video.controls`][flet_video.Video.controls]\nPlain text: [the route attribute][flet.Page.route]\n```\n\n**When to prefer over the other forms:**\n\n- **Flexible labels** — the first `[ ]` accepts any text or inline code, unlike reST roles whose label is always auto-derived from the target\n- **Path-independent** — keys are dotted symbol paths, so links don't break when source files are moved, renamed, or restructured (unlike Markdown link paths with `../` and `#flet.X.y` anchors)\n- **Terser** than Markdown links to the same symbol — no relative path or anchor to maintain\n- **Greppable** — searching for the dotted key finds every reference to that symbol across all docs\n\n**Rules:**\n\n- The label (inside the first `[ ]`) is the rendered text — inline code or plain text\n- The key (inside the second `[ ]`) is the fully-qualified dotted path; do NOT include `()` for methods\n- Unresolved keys render as broken reference-style links (silent fallback) — verify with a build or `yarn crocodocs:generate`\n\n### Markdown links\n\nFallback for cases xrefs cannot cover:\n\n- docs-only Python strings — the `docs_reason` parameter of `@deprecated`, extracted validation messages, or short admonition text\n- links to non-API content (other doc pages, external URLs, anchors that aren't API symbols)\n- when the xref entry is missing and you need a working link before regenerating\n\nUse relative `.md` paths with dot-format anchors.\n\nExamples:\n\n```markdown\nControl: [`Page`](../controls/page.md)\nType: [`DragTargetEvent.global_position`](../types/dragtargetevent.md#flet.DragTargetEvent.global_position)\nPlain text: [route](../controls/page.md#flet.Page.route)\nMethod: [`Page.update()`](../controls/page.md#flet.Page.update)\n```\n\n## Admonitions in docstrings\n\nGoogle-style section headers render as Docusaurus admonitions:\n\n```python\n\"\"\"\nNote:\n    Has effect only if the direct parent is a :class:`~flet.Column`.\n\nWarning:\n    This property is deprecated. Use :attr:`new_prop` instead.\n\nExample:\n    Setting up a basic layout:\n    ``ft.Column(controls=[ft.Text(\"Hello\")])``\n\"\"\"\n```\n\nSupported kinds: `Note`, `Warning`, `Danger`, `Tip`, `Info`.\nUnsupported kinds (e.g. `Limitation`, `Example`) are normalized to `note`.\nEmpty admonitions are skipped.\n\n## Admonitions\n\n```markdown\n:::note\nBasic note without title.\n:::\n\n:::warning[Important]\nWarning with a custom title.\n:::\n```\n\nSupported types: `note`, `info`, `tip`, `warning`, `danger`.\n\n## Front matter\n\n```yaml\n---\nclass_name: \"flet.Container\"\nexamples: \"controls/container\"\nexample_images: \"test-images/examples/material/golden/macos/container\"\nexample_media: \"examples/controls/container/media\"\ntitle: \"Container\"\n---\n```\n\n- `examples` — root-relative path under `sdk/python/examples/`\n- `example_images` / `example_media` — root-relative under `website/static/docs/`\n\n## Images\n\nUse the CrocoDocs `Image` component. Paths without `../` are resolved against `/docs/`:\n\n```jsx\nimport {Image} from '@site/src/components/crocodocs';\n\n<Image src={frontMatter.example_images + '/image_for_docs.png'} width=\"55%\" />\n```\n\nFor absolute paths (one-off assets in `static/`):\n\n```jsx\n<Image src=\"/docs/assets/controls/charts/bar-chart-diagram.svg\" width=\"65%\" />\n```\n\n## Code examples\n\n```jsx\nimport {CodeExample} from '@site/src/components/crocodocs';\n\n<CodeExample path={frontMatter.examples + '/example_1.py'} />\n```\n\nPaths are relative to the configured `examples_root` (`sdk/python/examples/`).\n\n## Inline HTML\n\nUse `<kbd>...</kbd>` in Python docstrings for keyboard keys, for example\n`<kbd>Enter</kbd>` or `<kbd>Shift</kbd>`. CrocoDocs preserves this tag in API\ndocs.\n\n## Sidebar Navigation\n\nEdit `website/sidebars.yml` to change navigation structure:\n\n```yaml\ndocs:\n  Getting started:\n  - getting-started/installation.md\n  Controls:\n    _generated_index:\n      title: Controls\n      slug: /controls\n      description: Browse the complete catalog of controls.\n    AlertDialog: controls/alertdialog.md\n```\n\nAfter editing, regenerate `sidebars.js`:\n\n```bash\ncd website && yarn crocodocs:generate\n```\n",".agents/skills/docs-build-and-verify/SKILL.md":"---\nname: docs-build-and-verify\ndescription: Use when asked to build, preview, or verify the Flet documentation website, including checking for broken links, broken images, and unresolved reST cross-references.\n---\n\n# Docs Build and Verification\n\n## Prerequisites\n\nNode.js 24 is required, matching what CI runs:\n\n```bash\nnvm use 24\n```\n\n## Build\n\nFull production build (includes broken link detection):\n\n```bash\ncd website && yarn build\n```\n\nDev server with hot reload:\n\n```bash\ncd website && yarn start\n```\n\nRegenerate API data and sidebars only (no Docusaurus build):\n\n```bash\ncd website && yarn crocodocs:generate\n```\n\n## Check Broken Links\n\n`yarn build` reports both, but only broken *links* fail the build. Docusaurus defaults\n`onBrokenAnchors` to `warn` and `docusaurus.config.js` does not override it, so a broken\nanchor scrolls past in the log and still ships - grep the build output for `Broken anchor`\nrather than trusting the exit code.\n\n## Check Broken Images\n\nRun this after `yarn build` to find images referenced in HTML that don't exist:\n\n```bash\ncd website && python3 -c \"\nimport re, os, glob\n\nbuild_dir = 'build'\nimg_re = re.compile(r'<img[^>]+src=\\\"(/[^\\\"]+)\\\"', re.IGNORECASE)\nbroken = []\n\nfor html_file in sorted(glob.glob(f'{build_dir}/docs/**/index.html', recursive=True)):\n    page = html_file.replace(build_dir + '/', '').replace('/index.html', '')\n    content = open(html_file).read()\n    for match in img_re.finditer(content):\n        src = match.group(1)\n        if src.startswith('http') or src.startswith('data:'):\n            continue\n        file_path = os.path.join(build_dir, src.lstrip('/'))\n        if not os.path.exists(file_path):\n            broken.append((page, src))\n\nif broken:\n    print(f'Found {len(broken)} broken images:')\n    for page, src in broken:\n        print(f'  {page}: {src}')\nelse:\n    print('No broken images found!')\n\"\n```\n\n## Check Unresolved reST Cross-References\n\nAfter building, check for reST roles that failed to resolve and appear as raw text:\n\n```bash\ncd website && grep -r ':attr:\\|:class:\\|:meth:\\|:func:' build/docs/ --include='*.html' -l\n```\n\nIf any files are listed, those pages have unresolved cross-references that render as plain text instead of links.\n",".agents/skills/fix-members-short-description/SKILL.md":"---\nname: fix-members-short-description\ndescription: Use when asked to fix short descriptions of Python type members.\n---\n\n## Inputs\n\n* File or directory with Python modules.\n\n## Instructions\n\nWhen Flet documentation is generated from docstrings the first sentence of a member docstring is used as a short description, for example:\n\n```py\n@dataclass\nclass MyControl:\n    property_a: str\n    \"\"\"\n    Short description of a property.\n\n    Full description.\n    Another line of full description.\n    \"\"\"\n```\n\nHere \"Short description of a property.\" will be used as a short description.\n\nHowever, when a sentence is broken into multiple lines the lines must be \"concatenated\" with `\\`, for example:\n\n```py\n@dataclass\nclass MyControl:\n    property_a: str\n    \"\"\"\n    Short description of a property which could \\\n    take multiple lines.\n\n    Full description.\n    Another line of full description.\n    \"\"\"\n```\n\nYour goal is to go through all members (properties, methods, etc.) of all types (classes, enums) in input file or directory and ensure the first sentence in their docstrings is broken into multiple lines correctly with `\\` symbol.\n\nApply the fix regardless of whether the first sentence starts on the same line as the opening `\"\"\"` or on a following line.\n\nEnsure every docstring line is at most 88 characters long (including any trailing `\\`). If a line cannot be wrapped without breaking a single unbreakable token (e.g., a long URL or Windows registry path like `HKEY_LOCAL_MACHINE\\\\...`), add `# noqa: E501` to the docstring closing `\"\"\"` line instead of the long line.\n",".agents/skills/flet-deprecation/SKILL.md":"---\nname: flet-deprecation\ndescription: Use when adding or changing deprecations for Python controls/APIs in sdk/python/packages/, including V.deprecated fields, deprecated decorators, version lifecycle, and docs admonitions/labels.\n---\n\n## When To Use\n\nUse this skill when you:\n- deprecate a control/dataclass field with `Annotated[..., V.deprecated(...)]`,\n- deprecate a function/method/class with `flet.utils.deprecated` helpers,\n- update deprecation wording, versions, or removal timelines,\n- verify docs rendering for deprecations (admonition + `deprecated` label).\n\nDo not use this skill for non-deprecation validation logic; use\n[`flet-validation`](../flet-validation/SKILL.md).\n\n## Source Of Truth\n\n- Runtime decorators and warning helpers: `sdk/python/packages/flet/src/flet/utils/deprecated.py`\n- Field-level deprecation rule: `sdk/python/packages/flet/src/flet/utils/validation.py` (`V.deprecated`)\n- Docs extraction/labeling extension: `sdk/python/packages/flet/src/flet/utils/griffe_deprecations.py`\n\n## Deprecation Decision Order\n\nUse this order and stop at the first option that fits:\n1. Property/field deprecation: `Annotated[..., V.deprecated(...)]`.\n2. Function/method deprecation: `@deprecated(...)`.\n3. Class/control deprecation: `@deprecated_class(...)`.\n\nDo not add parallel custom warning logic in `before_update()` when `V.deprecated`\nalready covers the field.\n\n## Runtime Contract For Property Renames\n\nFollow the non-copying model:\n- Python sends both properties when both are set.\n- Dart prefers the new property and uses old property as fallback.\n- Python does not copy/synchronize old/new values in `before_update()`.\n\nRemoval phase:\n- At `delete_version` cleanup, remove old Python property/deprecation and remove\n  Dart fallback in the same migration.\n\n## Removal Version Policy\n\n- Default policy: remove deprecated APIs after 3 minor releases.\n- Example: deprecated in `0.82.0` -> remove in `0.85.0`.\n- Use that policy to set `delete_version` unless there is an approved exception.\n\n## Target Release Audit\n\nWhen working on a release for `{new_version}`, treat deprecations with\n`delete_version == {new_version}` as mandatory audit items.\n\n- Scan Python packages for `@deprecated(...)`, `@deprecated_class(...)`,\n  and `V.deprecated(...)` entries whose `delete_version` equals `{new_version}`.\n- Recommended check command:\n  `rg -n 'delete_version\\\\s*=\\\\s*\"{new_version}\"|delete_version\\\\s*=\\\\s*\\\\x27{new_version}\\\\x27' -S sdk/python/packages`\n- Treat every match as release-relevant work, not informational output.\n- If matches are found, summarize the findings first and ask the human for approval\n  before editing files or making removals.\n- For each match, decide whether the deprecated API must be removed now,\n  whether a prior removal was missed, or whether the deprecation timeline is incorrect.\n- If removal is due, make the code, docs, and changelog updates in the same change.\n- After the cleanup edits are ready, summarize the resulting diff and ask the human\n  for approval before creating a commit.\n- Once commit approval is received, batch all confirmed `{new_version}` cleanup\n  edits into one grouped commit instead of splitting them across multiple commits.\n  Use commit message format: `release: remove deprecated APIs for {new_version}`\n- Do not consider the release prep complete while unresolved `{new_version}` removals remain.\n\n## Authoring Rules\n\n1. Always set `version`.\n2. Set `delete_version` using the 3-minor policy by default.\n3. Keep `reason` plain text for runtime warnings.\n4. Use `docs_reason` for docs-only markdown text.\n5. When a replacement exists, name that replacement API explicitly in `reason` and `docs_reason`.\n\n### Field Pattern\n\n```python\nfrom typing import Annotated, Optional\nfrom flet.utils.validation import V\n\nclass ExampleControl:\n    old_prop: Annotated[\n        Optional[str],\n        V.deprecated(\n            \"new_prop\",\n            version=\"0.17.0\",\n            delete_version=\"0.20.0\",\n            reason=\"Use new_prop instead.\",\n            docs_reason=\"Use :attr:`new_prop` or [`new_prop`](../controls/examplecontrol.md#flet.ExampleControl.new_prop) instead.\",\n        ),\n    ] = None\n```\n\n### Function/Method Pattern\n\n```python\nfrom flet.utils.deprecated import deprecated\n\nclass ExampleControl:\n    @deprecated(\n        reason=\"Use new_func instead.\",\n        docs_reason=\"Use :meth:`new_func` or [`new_func()`](../controls/examplecontrol.md#flet.ExampleControl.new_func) instead.\",\n        version=\"0.17.0\",\n        delete_version=\"0.20.0\",\n    )\n    def old_func(self):\n        ...\n```\n\n### Class/Control Pattern\n\n```python\nfrom flet.utils.deprecated import deprecated_class\n\n@deprecated_class(\n    reason=\"Use NewControl instead.\",\n    docs_reason=\"Use :class:`~flet.NewControl` or [`NewControl`](../controls/newcontrol.md)  instead.\",\n    version=\"0.17.0\",\n    delete_version=\"0.20.0\",\n)\nclass OldControl:\n    ...\n```\n\n### Deprecated Property Pattern\n\n```python\nfrom flet.utils.deprecated import deprecated\n\nclass ExampleControl:\n    @property\n    @deprecated(\n        reason=\"Use new_value instead.\",\n        docs_reason=\"Use :attr:`new_value` or [`new_value`](../controls/examplecontrol.md#flet.ExampleControl.new_value) instead.\",\n        version=\"0.17.0\",\n        delete_version=\"0.20.0\",\n    )\n    def value(self):\n        ...\n```\n\n## `reason` vs `docs_reason`\n\n- Runtime warnings always use `reason`.\n- Docs admonitions prefer `docs_reason`; fallback is `reason`.\n- Keep markdown/cross-refs out of `reason` to avoid noisy runtime output.\n\n### Cross-reference Rule Inside `docs_reason`\n\nIn `docs_reason`, use reST roles for simple references when the auto-derived label is\nsufficient, and use Markdown links when you need more control over the displayed text.\n\nSee [`docs-conventions`](../docs-conventions/SKILL.md) for details on supported cross-ref patterns and their syntax.\n\n## Docs Behavior Expectations\n\nFor supported patterns, docs should auto-render:\n- a `Deprecated` admonition section,\n- a `deprecated` label/badge on the item.\n\nDo not duplicate with manual deprecation admonitions in docstrings unless there\nis a special case not covered by the extension.\n\n## Release Docs Updates\n\nWhen adding a user-visible deprecation, also update the release docs in the\nsame change. These pages are the canonical upgrade path, not a separate\n`Deprecations` page.\n\n1. Create or update a migration guide under\n   `website/docs/updates/breaking-changes/vX-Y-Z/`.\n   - Group closely related deprecations into one page, especially APIs from the\n     same class/control or the same PR. For example, `DragTargetEvent.x`,\n     `DragTargetEvent.y`, and `DragTargetEvent.offset` belong in one\n     coordinate-fields guide.\n   - Use this page shape: title, `:::note` accuracy callout,\n     `Summary`, `Context`, `Migration guide`, `Timeline`, and `References`.\n   - Keep one-off replacements in prose. Use a table only when the page maps\n     many removed/deprecated APIs to replacements.\n   - In `References`, link relevant API docs, relevant GitHub issue/PR links,\n     and release notes entry for that release.\n2. Add the guide to\n   `website/docs/updates/breaking-changes/index.md` under the release's\n   `Deprecations` subsection.\n3. Add the guide to `website/sidebars.yml` under:\n   `Stay up to date` -> `Breaking changes and deprecations` -> `vX.Y.Z`.\n   This keeps individual guide pages in the docs sidebar while grouping them by\n   release.\n4. Update `website/docs/updates/release-notes.md` so the release links to the\n   combined `Breaking changes and deprecations` section.\n5. Run `cd website && yarn crocodocs:generate` after sidebar\n   edits, then run `cd website && yarn build`.\n\n## Testing Guidance\n\nDo not add one-off tests for every API that gets deprecated when it uses an\nexisting, already-tested pattern (`V.deprecated`, `@deprecated`, or\n`@deprecated_class`). For routine deprecation metadata updates, rely on the\nshared helper and docs extraction tests.\n\nAdd or update tests only when the change affects deprecation infrastructure or\nintroduces meaningful new behavior, for example:\n- changing runtime warning formatting or stacklevel behavior,\n- changing docs extraction/labeling behavior,\n- adding a new deprecation pattern,\n- adding custom compatibility behavior outside the standard helper,\n- fixing a regression where an existing test would not have failed.\n\nPrefer these locations for infrastructure tests:\n- `sdk/python/packages/flet/tests/test_deprecated.py`\n- `sdk/python/packages/flet/tests/test_griffe_deprecations.py`\n- `sdk/python/packages/flet/tests/test_validation.py` (for `V.deprecated`)\n\n## Common Pitfalls\n\n- Putting markdown/cross-refs into runtime `reason`.\n- Forgetting `delete_version` when a removal target is already known.\n- Adding old/new value-copy logic in Python for rename migrations.\n- Duplicating deprecation warnings in multiple lifecycle hooks manually.\n- Broken cross-refs targets in `docs_reason`.\n",".agents/skills/flet-validation/SKILL.md":"---\nname: flet-validation\ndescription: Use whenever editing validation for Python controls in sdk/python/packages/: adding/changing constrained properties, `Raises: ValueError` docstrings, `before_update()` checks, `raise ValueError`, Annotated/V rules, or __validation_rules__.\n---\n\n## When To Use\n\nUse this skill when you:\n- add validation to a control property,\n- migrate manual `before_update()` checks to `V` rules,\n- update `Raises` sections tied to validation,\n- align Python validation with Dart-side control behavior.\n\nDo not use this skill for unrelated doc-only edits outside control validation.\nDo not use this skill for deprecation authoring conventions; use\n[`flet-deprecation`](../flet-deprecation/SKILL.md).\n\n## Source Of Truth\n\n- Validation runtime API lives in:\n  `sdk/python/packages/flet/src/flet/utils/validation.py`\n- The same runtime can validate regular dataclass models via `validate(instance)`;\n  this skill focuses on the control-specific authoring conventions.\n- Import from public path only:\n  `from flet.utils.validation import V`\n  and when needed\n  `from flet.utils.validation import ValidationRules`\n\n## Validation Decision Order\n\nUse this order and stop at the first option that keeps logic clear:\n1. `Annotated[..., V.*]` field rules (default).\n2. `__validation_rules__: ValidationRules` for cross-field invariants that do\n   not map cleanly to one field.\n3. `before_update()` only for normalization/mutation, or for truly non-ruleable\n   invariants.\n\nNever duplicate the same invariant in more than one layer.\n\n## Validation Authoring Rules\n\n1. Prefer field-level validation with `Annotated[...]` metadata.\n   - Example (close to current slider controls):\n     ```\n     @dataclass\n     class Sample:\n         opacity: Annotated[\n                Optional[Number],\n                V.between(0.0, 1.0),\n            ] = None\n\n         value: Annotated[\n             Optional[Number],\n             V.ge_field(\"min\"),\n             V.le_field(\"max\"),\n         ] = None\n\n         min: Annotated[\n             Number,\n             V.le_field(\"max\"),\n             V.le_field(\"value\"),\n         ] = 0.0\n\n         max: Annotated[\n             Number,\n             V.ge_field(\"min\"),\n             V.ge_field(\"value\"),\n         ] = 1.0\n     ```\n\n2. Use class-level `__validation_rules__` only for invariants that cannot be\n   expressed cleanly with field rules.\n   - Type:\n     `__validation_rules__: ValidationRules = (...)`\n   - Use `V.ensure(...)` with an explicit message only when the predicate is\n     short and readable.\n   - If `V.ensure(lambda ...)` becomes hard to read, prefer either:\n     1. a named predicate function passed to `V.ensure(...)`, or\n     2. a clear `before_update()` check when it cannot be represented well with\n        existing `V.*` rules.\n\n3. Keep the `before_update()` override for normalization/mutation first.\n   - Remove validation checks duplicated by `V` rules.\n   - Prefer raising validation errors from rule evaluation (`validate()`), not\n     from ad-hoc `before_update()` checks, unless the invariant is genuinely\n     non-ruleable with current validation primitives.\n\n4. Cross-field comparisons use field rules only.\n   - Use: `V.gt_field`, `V.ge_field`, `V.lt_field`, `V.le_field`\n\n5. `None` handling is inferred from type hints.\n   - If a field is annotated as optional (for example `Optional[T]`), `None` is allowed.\n   - If a field is not optional, `None` fails validation.\n   - For `*_field` comparisons, if either side is optional and currently `None`, the\n     comparison is skipped; if a non-optional side is `None`, validation fails.\n\n6. Match Dart effective behavior.\n   - Review both:\n     1. Flet Dart wrapper (`packages/flet/lib/src/controls/<control>.dart` or\n        extension wrapper),\n     2. wrapped Flutter widget source assertions/invariants.\n   - Mirror those constraints in Python so invalid payloads fail before crossing\n     to Dart.\n   - Validate against effective defaults applied on Dart side (for example\n     `min`/`max`).\n   - Include wrapper-imposed constraints when relevant (for example\n     bounds/rounding/division logic in wrapper formatting code).\n\n7. For new properties, validate against base widget assertions before wiring.\n   - When adding a Python property to a Flet control, confirm whether the mapped\n     Dart wrapper and underlying widget both enforce constraints for that property.\n   - Add equivalent Python-side validation (`Annotated[...]`, `__validation_rules__`,\n     or readable `before_update()`) to prevent Dart assertions from being the first\n     failure point.\n\n8. Keep error ownership clear.\n   - Runtime outbound value failures should raise `ValueError`.\n   - Validation declaration/build errors (invalid `V.*` arguments) should raise\n     `ValidationDeclarationError`.\n\n## Typing Style\n\n- Follow the codebase typing style:\n  - prefer `Optional[T]` over `T | None`,\n  - use `Union[...]` when needed.\n\n## Property Docstring Style\n\nWhen a property has validation, document it in that property’s docstring (google style).\n\n1. Add a `Raises:` block under the property docstring.\n\n2. Use one `ValueError` entry per logical rule, except `between(...)`.\n   - For `V.between(a, b)`, use one entry:\n     `ValueError: If it is not between \\`a\\` and \\`b\\`, inclusive.`\n\n3. Start each entry with `If it ...`, where 'it' refers to the property name.\n\n4. Use canonical wording from validation helper docstrings.\n   - The source of truth is\n     `sdk/python/packages/flet/src/flet/utils/validation.py`.\n   - Each `V.*` helper includes `Property docstring Raises wording`.\n   - Keep property `Raises` entries as negations of the annotation rule.\n   - For strict inequalities, say `\"strictly\"`.\n     For example: `V.gt(x)` -> `ValueError: If it is not strictly greater than \\`x\\`.`\n   - For sign-neutral divisibility helpers (`factor_of`, `multiple_of`), add\n     explicit sign rules (`V.gt(0)` or `V.lt(0)`) when direction matters, and\n     include separate `Raises` entries for those sign rules.\n\n5. Mention conditional applicability when needed.\n   - Example (for `min`/`max` checks against optional `value`):\n     ```\n     Raises:\n         ValueError: If it is not less than or equal to [`value`][(c).],\n             when [`value`][(c).] is set.\n     ```\n\n6. Keep examples and wording aligned with real control files.\n   - Prefer concrete property names such as `min`, `max`, `value`,\n     `start_value`, `end_value`, `min_lines`, `max_lines`.\n   - For cross-field rules, use same-class links: [`min`][(c).], [`max`][(c).].\n\n## Cross-Referencing Conventions\n\nFollow the cross-reference guidance in:\n[`docs-conventions`](../docs-conventions/SKILL.md).\n\nMost common pattern to use in control property docstrings:\n- same-class properties: `[\\`prop\\`][(c).]`\n\nKeep symbol labels wrapped in backticks.\n\n## Required Test Matrix\n\nWhen adding/changing validation, include tests that cover:\n- one valid case and one invalid case per new logical rule;\n- boundary values (`==`, min/max edges) where applicable;\n- cross-field set/unset combinations when optional values are involved;\n- effective-default behavior when Dart applies defaults but Python value is\n  omitted.\n\nPrefer placing tests in:\n- `sdk/python/packages/flet/tests/test_validation.py` for validation runtime;\n- control-specific tests when behavior is tied to one control.\n\n## Common Pitfalls\n\n- Keeping stale manual `before_update()` validations after migration.\n- Missing `Raises` entries on validated properties.\n- Combining multiple non-between rules into one ambiguous `ValueError` sentence.\n- Forgetting Dart defaults that still apply when Python property is omitted.\n- Forcing complex `V.ensure(lambda ...)` expressions when `before_update()` would be cleaner.\n",".agents/skills/prepare-flet-release/SKILL.md":"---\nname: prepare-flet-release\ndescription: Use when asked to prepare new Flet release by bumping versions and author release notes.\n---\n\n## Inputs\n\n* Previous Flet version from repo tags.\n* Whether it's minor or major release.\n\n## Related Skills\n\nAlways use [`flet-deprecation`](../flet-deprecation/SKILL.md) during release prep\nto audit deprecations for the target version. Also use it when release prep includes:\n- adding new deprecations in this release,\n- removing APIs whose `delete_version` equals this release version,\n- auditing changelog entries that mention deprecations/removals.\n\nUse [`write-changelog-entry`](../write-changelog-entry/SKILL.md) for drafting or refining individual changelog items.\nThat skill is the source of truth for item wording, scope selection, and what should or should not be mentioned in a single entry.\n\n## Steps\n\n* Take latest Flet release version from the repo and\n  increment third (patch) digit to get the next version if it's a minor release\n  or second (minor) digit if it's a major release.\n* Pull the latest `main` and create a new branch named `prepare-release-{new_version}` from `main`.\n* Set new version in packages/flet/pubspec.yaml.\n* Run pub get in /client dir to refresh pubspec.lock with new version.\n* Add new entries into `packages/flet/CHANGELOG.md` and `/CHANGELOG.md` from the git log since the last release.\n  * Use [`write-changelog-entry`](../write-changelog-entry/SKILL.md) for every individual item.\n  * Build the candidate set from relevant commits, PRs, and issues since the last release.\n  * Ensure that all inferred PRs and issues in the changelog have the `{version}` milestone attached on GitHub.\n  * If a related issue or PR is missing the `{version}` milestone, update the milestone on GitHub and keep the link in the changelog.\n  * When selecting candidates for `packages/flet/CHANGELOG.md`, prefer items with meaningful Flutter-side impact.\n  * When selecting candidates for `sdk/python/packages/*/CHANGELOG.md`, prefer published Python-facing changes; do not include extension-internal Flutter implementation work unless it materially changes user-visible Python behavior.\n* If the release includes breaking changes, API removals, or deprecations,\n  update `website/docs/updates/release-notes.md` and\n  `website/docs/updates/breaking-changes/index.md`.\n  * Use [`flet-deprecation`](../flet-deprecation/SKILL.md) for deprecation\n    guide requirements and sidebar placement.\n  * Group related deprecations into one migration guide page where possible,\n    and add guide pages under the release version in `website/sidebars.yml`.\n* Scan all changelogs for `Unreleased` sections, not only the root ones:\n  * `/CHANGELOG.md`\n  * `packages/flet/CHANGELOG.md`\n  * `sdk/python/packages/*/CHANGELOG.md`\n  Recommended check command:\n  `rg -n \"^##\\\\s*\\\\[?Unreleased\\\\]?|^##\\\\s*Unreleased\" -S CHANGELOG.md packages/flet/CHANGELOG.md sdk/python/packages/*/CHANGELOG.md`\n* If any changelog has an `Unreleased` section, convert that section into the new release section (`## {new_version}`), preserving and re-sorting its items. Do not leave duplicate release content in both `Unreleased` and `{new_version}`.\n  This conversion must be done for every matched changelog from the scan above.\n* Sort items in changelogs as follows, omitting empty sections:\n  * New features\n  * Improvements\n  * Breaking changes\n  * Deprecations\n  * Bug fixes\n  * Documentation\n  * Other changes (chore, refactor, etc.)\n  Put removals of previously deprecated APIs under `Breaking changes`, and\n  keep newly deprecated-but-still-working APIs under `Deprecations`.\n* Templates are in `sdk/python/templates/` and automatically packaged as zip artifacts with the GitHub Release. No manual branch creation in external repos is needed.\n",".agents/skills/implement-flet-extension/SKILL.md":"---\nname: implement-flet-extension\ndescription: Implement a new Flet extension/control that wraps a third-party Flutter package end-to-end, including dependency selection, version pinning, compatibility checks, Python/Flutter integration, docs, examples, tests, and CI updates. Use when adding any flet_* package backed by an external pub.dev package.\n---\n\nImplement a Flet extension around an external Flutter package using existing `flet_*` packages as implementation templates.\n\n## Inputs\n\n- Control/service name and Python package name (`flet_<extension>`).\n- Target pub.dev package and intended version/range.\n- API surface to expose in Python (properties, methods, events, types/enums).\n\n## Third-party Dependency Gate\n\n1. Confirm package health: maintenance activity, null-safety, platform support, and open issue risk.\n2. Confirm license is compatible with Flet distribution.\n3. Select a conservative version strategy:\n- Pin exact version when behavior stability is critical.\n- Use bounded ranges when required by ecosystem constraints.\n4. Record key constraints and reasons in PR notes/commit message.\n\n## Control/Service Classification\n\n- Classify wrapped functionality before implementation:\n1. `LayoutControl` for visual controls that participate in page/layout positioning.\n2. Base `Control` for simple visual controls that do not require page positioning or define their own positioning rules/props (for example `Draggable`, `Divider`, `MenuBar`, `NavigationRail`).\n3. Non-visual Service when functionality is not a renderable UI control.\n- Inspect the wrapped Flutter package API to determine whether it includes non-visual/service functionality.\n- For service patterns, follow existing extension examples: `sdk/python/packages/flet-audio`, `sdk/python/packages/flet-flashlight`, `sdk/python/packages/flet-secure-storage`.\n\n## API Mapping Rules\n\n- Expose only stable and useful features first; avoid mirroring every upstream option.\n- Keep Python API idiomatic and concise; avoid redundant control-name prefixes.\n- Map upstream naming inconsistencies to Flet conventions when needed.\n- Add custom enums/types only when they improve correctness and discoverability.\n\n## Python-side Rules\n\n- Use `LayoutControl`, base `Control`, or Service base class according to classification.\n- Implement typed properties, methods, and events exactly for chosen public API.\n- Reuse existing serialization/event patterns from sibling controls/services.\n\n## Flutter-side Rules\n\n- Use `parseEnum()` for enums — it's exported from `package:flet/flet.dart`. Call it as `parseEnum(MyEnum.values, widget.control.getString(\"attr\"), MyEnum.defaultVal)!`. Do NOT write a custom `_parseXxx()` switch helper.\n- For control attributes, prefer `widget.control.getBool()/getDouble()/...` accessors.\n- For non-control parsing, use shared `parseSomething()` helpers.\n- Do not add one-off private parser utilities when standard helpers exist.\n- Put control-specific helpers in `utils/<control>.dart`; shared helpers in `utils/<topic>.dart`.\n- Prefer `parse`-prefixed helper names when converting input to Flutter structures.\n- Avoid single-use local variables.\n\n### Default Value Matching (Critical)\n\nProperties with default values on the Python side are **not sent to Flutter** when unchanged from the default. Every Dart property read **must provide the same default** as its Python counterpart:\n\n- `control.getDouble(\"size\", 100.0)!` when Python has `size: float = 100.0`\n- `control.getBool(\"animate\", true)!` when Python has `animate: bool = True`\n- `parseDuration(value[\"dur\"], const Duration(milliseconds: 500))!` when Python has `dur: DurationValue = field(default_factory=lambda: Duration(milliseconds=500))`\n- `control.get<List>(\"items\")?.map(...).toList() ?? const []` when Python has `items: list[str] = field(default_factory=list)`\n\nWithout matching defaults, Dart receives `null` and either crashes or silently uses the wrong value. This applies to all property types: bools, numbers, strings, enums, durations, collections, and nested `@ft.value` types.\n\n## Integration Checklist\n\n- Register in the Flet client app — two files:\n  1. `client/pubspec.yaml`: add `flet_<ext>: path: ../sdk/python/packages/flet-<ext>/src/flutter/flet_<ext>` under `dependencies`.\n  2. `client/lib/main.dart`: add `import 'package:flet_<ext>/flet_<ext>.dart' as flet_<ext>;` and `flet_<ext>.Extension()` to the `extensions` list.\n- Add extension package to `sdk/python/pyproject.toml` in **two places**: the `dependencies` list and `[tool.uv.sources]` as `{ workspace = true }`.\n- Add extension to `sdk/python/packages/flet/pyproject.toml` in the `[dependency-groups] extensions` list.\n- Add extension to `sdk/python/examples/apps/flet_build_test/pyproject.toml` in **three places**: `[project] dependencies`, `[tool.uv.sources]` as `{ path = \"...\", editable = true }`, and `[tool.flet.dev_packages]` as a relative path string.\n- Add extension to `tools/crocodocs/pyproject.toml` under `[tool.crocodocs.packages]` as `<pkg_name> = \"../../sdk/python/packages/<pkg-dir>/src\"`. This fixes \"Missing API entry\" errors in the docs. Note: `api-data.json` is gitignored (generated at build time); only the `pyproject.toml` change needs committing.\n- Add extension to `.github/workflows/ci.yml` in both places:\n  - `build_flet_extensions` -> `PACKAGES` list.\n  - `py_publish` -> `for pkg in ...` publish loop.\n- Add `.gitignore` to Flutter extension project if missing.\n- Remove `[tool.uv.sources]` local path overrides from example `pyproject.toml` files before opening a PR (they are development-only conveniences).\n\n## Docs, Examples, Tests\n\n- Add control/service docs under `website/docs/controls/<name>` for controls and `website/docs/services/<name>` for services.\n- Always create one doc page per control, even for extensions with many similar controls. Use `index.md` for the overview (install instructions, examples, list of links) and individual `<controlname>.md` files for each control — consistent with `flet-color-pickers` and other extensions.\n- Use `<ClassSummary name=\"pkg.ClassName\" />` and `<ClassMembers name=\"pkg.ClassName\" />` JSX from `@site/src/components/crocodocs` to render API docs. Do NOT add `image=`, `imageCaption=`, or `imageWidth=` props to `<ClassSummary>` when no screenshots exist yet.\n- In the `## Examples` section, do NOT add `###` subtitles above `<CodeExample>` blocks — titles are injected automatically from the example file itself.\n- Add all custom enums/types docs and update `website/sidebars.yml` navigation.\n- Use markdown filenames without underscores (`codeeditor.md`, not `code_editor.md`).\n- Add examples under `sdk/python/examples/extensions/<name>/` for extension controls.\n- Use `import flet_<ext> as <short_alias>` in examples (e.g., `import flet_spinkit as spins`). Keep alias short but readable.\n- Use `ft.Colors.SURFACE_CONTAINER_HIGHEST` for card/cell backgrounds in showcase examples — it adapts to light and dark system themes automatically.\n- Do NOT set an explicit dark theme in examples; let the app use system theme (no `page.theme_mode`).\n- Add integration tests under `packages/flet/integration_tests/extensions/<name>/` — **not** inside the extension package's own directory (no `tests/` folder in the package itself, matching the pattern of `flet-code-editor`, `flet-color-pickers`, etc.).\n- For controls with continuously-running animations, do NOT use `assert_control_screenshot` or `pump_and_settle` — they will timeout waiting for animations to settle. Instead use `await flet_app.tester.pump(duration=ft.Duration(milliseconds=500))` which advances the clock by a fixed amount. This still runs real Flutter rendering and catches crashes, without screenshot comparison.\n- Ensure generated screenshots are suitable for docs usage when visual examples are added.\n\n## Upgrade and Compatibility Guardrails\n\n- Add at least one test that catches upstream behavioral changes likely to break wrapper mapping.\n- Avoid exposing experimental upstream APIs unless explicitly requested.\n- Keep wrapper surface narrow enough to maintain backwards compatibility across upstream updates.\n\n## Validation\n\n- Run relevant Python and integration tests for touched areas.\n- Verify Python import paths, client runtime registration, and docs navigation.\n- Verify dependency resolution and lockfile updates are intentional.\n",".agents/skills/imperative-to-declarative-flet/SKILL.md":"---\nname: imperative-to-declarative-flet\ndescription: Convert an imperative Flet Python app in which controls are mutated and then page.update is called to declarative style using flet.component, flet.observable and state hooks.\nmetadata:\n  short-description: Port Flet app to declarative\n---\n\n# Imperative → Declarative (Flet Python)\n\nPort an existing imperative Flet app to “components mode” with `@ft.component`, hooks, and (optionally) `@ft.observable` models.\n\n## Outcomes\n\n- Original folder unchanged; new sibling folder created.\n- Entry point uses `page.render(App)` (components mode).\n- UI is derived from state; minimal/zero manual `page.update()` for normal UI updates.\n\n## Choose a state strategy\n\n- **Use `@ft.observable`** for nested app data you mutate in place (boards/lists/cards, drag+drop reorder).\n- **Use `ft.use_state`** for local ephemeral UI state (hover flags, input text, dialog selection).\n- Avoid storing live `Control`/component objects in state; store ids/enums and create controls during render.\n\n## Workflow\n\n### 1) Create a new declarative copy\n\n- Copy the existing app folder to a new one (e.g. `trolli` → `trolli-declarative-*`).\n- Keep `assets/` with the new folder.\n\n### 2) Switch to components mode entrypoint\n\n- Create a root component `@ft.component def App(): ...`.\n- Run with:\n  - `ft.run(lambda page: page.render(App), assets_dir=...)`\n- Set page globals either:\n  - in a `main(page)` function before `page.render(App)`, or\n  - in `ft.on_mounted(...)` (works, but ordering can be less obvious).\n\n### 3) Centralize routing in `App`\n\n- Keep `app.route: str` as source of truth.\n- In one place, define:\n  - `route_change(e)` to normalize/redirect/validate routes and set `app.route`\n  - a render-time `match app.route` (or a derived `active_screen`) to pick `content`\n- Prefer: `route_change` mutates route state; `App()` render chooses UI based on that state.\n\n### 4) Componentize UI\n\n- Move UI chunks into `src/components/*.py`.\n- Each component:\n  - takes only the model(s) it needs\n  - uses hooks for local UI state\n  - mutates observable models for app data changes\n\n### 5) Dialogs: reduce `page.update()` usage\n\nIf a dialog mutates existing controls and calls `page.update()`, convert it to:\n\n- `@ft.component` dialog content with `ft.use_state` for `error`, `selected_color`, etc.\n- event handlers call setters (no explicit updates)\n- show it via `page.show_dialog(ft.AlertDialog(content=DialogContent(...)))`\n\n### 6) Assets/fonts checklist\n\n- Prefer an absolute `assets_dir` derived from `__file__`.\n- If running via `flet run`, be aware it can set `FLET_ASSETS_DIR` and override `assets_dir=`.\n- Font registration uses the dict key as the font family name:\n  - `page.fonts = {\"Pacifico\": \"Pacifico-Regular.ttf\"}`\n  - use `font_family=\"Pacifico\"`.\n\n## Common pitfalls (and fixes)\n\n- **Event handler typing is invariant** (`Event[Sub]` ≠ `Event[Base]`):\n  - If `on_click` is declared on `Button`, annotate `e` as `ft.Event[ft.Button]` (or use `def handler(): ...`).\n- **`TemplateRoute` params are dynamic**:\n  - `raw = getattr(troute, \"id\", None)` then `isinstance(raw, str)` before `int(raw)`.\n- **`controls=[*[...], ...]` can confuse type checkers** with components:\n  - build lists in two steps and annotate/cast, or return raw controls from non-component factories.\n",".agents/skills/run-unit-tests/SKILL.md":"---\nname: run-unit-tests\ndescription: Use when asked to run unit tests.\n---\n\nThis skill is used to run unit tests of the Python part of Flet framework.\n\n## Instructions\n\nRun the following command to run `flet` package unit tests:\n\n```\nuv run --group test pytest packages/flet/tests\n```\n\nThe directory in that commend is relative to `{root}/sdk/python`.\n",".agents/skills/run-integration-tests/SKILL.md":"---\nname: run-integration-tests\ndescription: Use when asked to run integration tests.\n---\n\n## Instructions\n\nIntegration tests are in `sdk/python/packages/flet/integration_tests` directory.\n\nRead `sdk/python/packages/flet/integration_tests/README.md` for further instructions.\n",".agents/skills/test-flet-apps-dev/SKILL.md":"# test-flet-apps-dev\n\nPath: `.agents/skills/test-flet-apps-dev/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/test-flet-apps-dev/SKILL.md)",".agents/skills/update-flet-control-doc-gifs/SKILL.md":"# update-flet-control-doc-gifs\n\nPath: `.agents/skills/update-flet-control-doc-gifs/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/update-flet-control-doc-gifs/SKILL.md)",".agents/skills/write-changelog-entry/SKILL.md":"# write-changelog-entry\n\nPath: `.agents/skills/write-changelog-entry/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/write-changelog-entry/SKILL.md)","website/.agents/skills/flet-release-announcement/SKILL.md":"# flet-release-announcement\n\nPath: `website/.agents/skills/flet-release-announcement/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/website/.agents/skills/flet-release-announcement/SKILL.md)","AGENTS.md":"# AI Agent Protocol & Instructions\n\nPath: `AGENTS.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/AGENTS.md)","CLAUDE.md":"# Claude Agent Guidelines & System Prompt\n\nPath: `CLAUDE.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/CLAUDE.md)","packages/flet/CHANGELOG.md":"# Flet Skill\n\nPath: `packages/flet/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/CHANGELOG.md)","packages/flet/README.md":"# flet Documentation\n\nPath: `packages/flet/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/README.md)","packages/flet/analysis_options.yaml":"# Flet Skill\n\nPath: `packages/flet/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/analysis_options.yaml)","packages/flet/pubspec.yaml":"# Flet Skill\n\nPath: `packages/flet/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/pubspec.yaml)","packages/flet_integration_test/analysis_options.yaml":"# Flet_integration_test Skill\n\nPath: `packages/flet_integration_test/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet_integration_test/analysis_options.yaml)","packages/flet_integration_test/pubspec.yaml":"# Flet_integration_test Skill\n\nPath: `packages/flet_integration_test/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet_integration_test/pubspec.yaml)","tools/crocodocs/README.md":"# crocodocs Documentation\n\nPath: `tools/crocodocs/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/tools/crocodocs/README.md)","sdk/python/packages/flet-ads/CHANGELOG.md":"# Flet-ads Skill\n\nPath: `sdk/python/packages/flet-ads/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/CHANGELOG.md)","sdk/python/packages/flet-ads/README.md":"# flet-ads Documentation\n\nPath: `sdk/python/packages/flet-ads/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/README.md)","sdk/python/packages/flet-audio-recorder/CHANGELOG.md":"# Flet-audio-recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/CHANGELOG.md)","sdk/python/packages/flet-audio-recorder/README.md":"# flet-audio-recorder Documentation\n\nPath: `sdk/python/packages/flet-audio-recorder/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/README.md)","sdk/python/packages/flet-audio/CHANGELOG.md":"# Flet-audio Skill\n\nPath: `sdk/python/packages/flet-audio/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/CHANGELOG.md)","sdk/python/packages/flet-audio/README.md":"# flet-audio Documentation\n\nPath: `sdk/python/packages/flet-audio/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/README.md)","sdk/python/packages/flet-camera/README.md":"# flet-camera Documentation\n\nPath: `sdk/python/packages/flet-camera/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-camera/README.md)","sdk/python/packages/flet-charts/CHANGELOG.md":"# Flet-charts Skill\n\nPath: `sdk/python/packages/flet-charts/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/CHANGELOG.md)","sdk/python/packages/flet-charts/README.md":"# flet-charts Documentation\n\nPath: `sdk/python/packages/flet-charts/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/README.md)","sdk/python/packages/flet-cli/README.md":"# flet-cli Documentation\n\nPath: `sdk/python/packages/flet-cli/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-cli/README.md)","sdk/python/packages/flet-code-editor/CHANGELOG.md":"# Flet-code-editor Skill\n\nPath: `sdk/python/packages/flet-code-editor/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/CHANGELOG.md)","sdk/python/packages/flet-code-editor/README.md":"# flet-code-editor Documentation\n\nPath: `sdk/python/packages/flet-code-editor/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/README.md)","sdk/python/packages/flet-color-pickers/CHANGELOG.md":"# Flet-color-pickers Skill\n\nPath: `sdk/python/packages/flet-color-pickers/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/CHANGELOG.md)","sdk/python/packages/flet-color-pickers/README.md":"# flet-color-pickers Documentation\n\nPath: `sdk/python/packages/flet-color-pickers/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/README.md)","sdk/python/packages/flet-datatable2/CHANGELOG.md":"# Flet-datatable2 Skill\n\nPath: `sdk/python/packages/flet-datatable2/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-datatable2/CHANGELOG.md)","sdk/python/packages/flet-datatable2/README.md":"# flet-datatable2 Documentation\n\nPath: `sdk/python/packages/flet-datatable2/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-datatable2/README.md)","sdk/python/packages/flet-desktop/README.md":"# flet-desktop Documentation\n\nPath: `sdk/python/packages/flet-desktop/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-desktop/README.md)","sdk/python/packages/flet-flashlight/CHANGELOG.md":"# Flet-flashlight Skill\n\nPath: `sdk/python/packages/flet-flashlight/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/CHANGELOG.md)","sdk/python/packages/flet-flashlight/README.md":"# flet-flashlight Documentation\n\nPath: `sdk/python/packages/flet-flashlight/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/README.md)","sdk/python/packages/flet-geolocator/CHANGELOG.md":"# Flet-geolocator Skill\n\nPath: `sdk/python/packages/flet-geolocator/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/CHANGELOG.md)","sdk/python/packages/flet-geolocator/README.md":"# flet-geolocator Documentation\n\nPath: `sdk/python/packages/flet-geolocator/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/README.md)","sdk/python/packages/flet-local-auth/README.md":"# flet-local-auth Documentation\n\nPath: `sdk/python/packages/flet-local-auth/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-local-auth/README.md)","sdk/python/packages/flet-lottie/CHANGELOG.md":"# Flet-lottie Skill\n\nPath: `sdk/python/packages/flet-lottie/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/CHANGELOG.md)","sdk/python/packages/flet-lottie/README.md":"# flet-lottie Documentation\n\nPath: `sdk/python/packages/flet-lottie/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/README.md)","sdk/python/packages/flet-map/CHANGELOG.md":"# Flet-map Skill\n\nPath: `sdk/python/packages/flet-map/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/CHANGELOG.md)","sdk/python/packages/flet-map/README.md":"# flet-map Documentation\n\nPath: `sdk/python/packages/flet-map/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/README.md)","sdk/python/packages/flet-mcp/README.md":"# flet-mcp Documentation\n\nPath: `sdk/python/packages/flet-mcp/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-mcp/README.md)","sdk/python/packages/flet-permission-handler/CHANGELOG.md":"# Flet-permission-handler Skill\n\nPath: `sdk/python/packages/flet-permission-handler/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/CHANGELOG.md)","sdk/python/packages/flet-permission-handler/README.md":"# flet-permission-handler Documentation\n\nPath: `sdk/python/packages/flet-permission-handler/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/README.md)","sdk/python/packages/flet-platform-assets/README.md":"# flet-platform-assets Documentation\n\nPath: `sdk/python/packages/flet-platform-assets/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-platform-assets/README.md)","sdk/python/packages/flet-rive/CHANGELOG.md":"# Flet-rive Skill\n\nPath: `sdk/python/packages/flet-rive/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/CHANGELOG.md)","sdk/python/packages/flet-rive/README.md":"# flet-rive Documentation\n\nPath: `sdk/python/packages/flet-rive/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/README.md)","sdk/python/packages/flet-secure-storage/README.md":"# flet-secure-storage Documentation\n\nPath: `sdk/python/packages/flet-secure-storage/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-secure-storage/README.md)","sdk/python/packages/flet-spinkit/CHANGELOG.md":"# Flet-spinkit Skill\n\nPath: `sdk/python/packages/flet-spinkit/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/CHANGELOG.md)","sdk/python/packages/flet-spinkit/README.md":"# flet-spinkit Documentation\n\nPath: `sdk/python/packages/flet-spinkit/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/README.md)","sdk/python/packages/flet-video/CHANGELOG.md":"# Flet-video Skill\n\nPath: `sdk/python/packages/flet-video/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/CHANGELOG.md)","sdk/python/packages/flet-video/README.md":"# flet-video Documentation\n\nPath: `sdk/python/packages/flet-video/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/README.md)","sdk/python/packages/flet-web/README.md":"# flet-web Documentation\n\nPath: `sdk/python/packages/flet-web/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-web/README.md)","sdk/python/packages/flet-webview/CHANGELOG.md":"# Flet-webview Skill\n\nPath: `sdk/python/packages/flet-webview/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/CHANGELOG.md)","sdk/python/packages/flet-webview/README.md":"# flet-webview Documentation\n\nPath: `sdk/python/packages/flet-webview/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/README.md)","sdk/python/packages/flet/README.md":"# flet Documentation\n\nPath: `sdk/python/packages/flet/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/README.md)","sdk/python/packages/flet/integration_tests/README.md":"# integration_tests Documentation\n\nPath: `sdk/python/packages/flet/integration_tests/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/integration_tests/README.md)","sdk/python/examples/extensions/lottie/lottie_animations/assets/sample.json":"# Assets Skill\n\nPath: `sdk/python/examples/extensions/lottie/lottie_animations/assets/sample.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/examples/extensions/lottie/lottie_animations/assets/sample.json)","sdk/python/packages/flet-ads/src/flutter/flet_ads/analysis_options.yaml":"# Flet_ads Skill\n\nPath: `sdk/python/packages/flet-ads/src/flutter/flet_ads/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/src/flutter/flet_ads/analysis_options.yaml)","sdk/python/packages/flet-ads/src/flutter/flet_ads/pubspec.yaml":"# Flet_ads Skill\n\nPath: `sdk/python/packages/flet-ads/src/flutter/flet_ads/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/src/flutter/flet_ads/pubspec.yaml)","sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/CHANGELOG.md":"# Flet_audio_recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/CHANGELOG.md)","sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/README.md":"# flet_audio_recorder Documentation\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/README.md)","sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/analysis_options.yaml":"# Flet_audio_recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/analysis_options.yaml)","sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/pubspec.yaml":"# Flet_audio_recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/pubspec.yaml)","sdk/python/packages/flet-audio/src/flutter/flet_audio/analysis_options.yaml":"# Flet_audio Skill\n\nPath: `sdk/python/packages/flet-audio/src/flutter/flet_audio/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/src/flutter/flet_audio/analysis_options.yaml)","sdk/python/packages/flet-audio/src/flutter/flet_audio/pubspec.yaml":"# Flet_audio Skill\n\nPath: `sdk/python/packages/flet-audio/src/flutter/flet_audio/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/src/flutter/flet_audio/pubspec.yaml)","sdk/python/packages/flet-camera/src/flutter/flet_camera/analysis_options.yaml":"# Flet_camera Skill\n\nPath: `sdk/python/packages/flet-camera/src/flutter/flet_camera/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-camera/src/flutter/flet_camera/analysis_options.yaml)","sdk/python/packages/flet-camera/src/flutter/flet_camera/pubspec.yaml":"# Flet_camera Skill\n\nPath: `sdk/python/packages/flet-camera/src/flutter/flet_camera/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-camera/src/flutter/flet_camera/pubspec.yaml)","sdk/python/packages/flet-charts/src/flutter/flet_charts/CHANGELOG.md":"# Flet_charts Skill\n\nPath: `sdk/python/packages/flet-charts/src/flutter/flet_charts/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/src/flutter/flet_charts/CHANGELOG.md)","sdk/python/packages/flet-charts/src/flutter/flet_charts/analysis_options.yaml":"# Flet_charts Skill\n\nPath: `sdk/python/packages/flet-charts/src/flutter/flet_charts/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/src/flutter/flet_charts/analysis_options.yaml)","sdk/python/packages/flet-charts/src/flutter/flet_charts/pubspec.yaml":"# Flet_charts Skill\n\nPath: `sdk/python/packages/flet-charts/src/flutter/flet_charts/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/src/flutter/flet_charts/pubspec.yaml)","sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/analysis_options.yaml":"# Flet_code_editor Skill\n\nPath: `sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/analysis_options.yaml)","sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/pubspec.yaml":"# Flet_code_editor Skill\n\nPath: `sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/pubspec.yaml)","sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/analysis_options.yaml":"# Flet_color_pickers Skill\n\nPath: `sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/analysis_options.yaml)","sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/pubspec.yaml":"# Flet_color_pickers Skill\n\nPath: `sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/pubspec.yaml)","sdk/python/packages/flet-datatable2/src/flutter/flet_datatable2/pubspec.yaml":"# Flet_datatable2 Skill\n\nPath: `sdk/python/packages/flet-datatable2/src/flutter/flet_datatable2/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-datatable2/src/flutter/flet_datatable2/pubspec.yaml)","sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/analysis_options.yaml":"# Flet_flashlight Skill\n\nPath: `sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/analysis_options.yaml)","sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/pubspec.yaml":"# Flet_flashlight Skill\n\nPath: `sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/pubspec.yaml)","sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/analysis_options.yaml":"# Flet_geolocator Skill\n\nPath: `sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/analysis_options.yaml)","sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/pubspec.yaml":"# Flet_geolocator Skill\n\nPath: `sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/pubspec.yaml)","sdk/python/packages/flet-local-auth/src/flutter/flet_local_auth/pubspec.yaml":"# Flet_local_auth Skill\n\nPath: `sdk/python/packages/flet-local-auth/src/flutter/flet_local_auth/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-local-auth/src/flutter/flet_local_auth/pubspec.yaml)","sdk/python/packages/flet-lottie/src/flutter/flet_lottie/analysis_options.yaml":"# Flet_lottie Skill\n\nPath: `sdk/python/packages/flet-lottie/src/flutter/flet_lottie/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/src/flutter/flet_lottie/analysis_options.yaml)","sdk/python/packages/flet-lottie/src/flutter/flet_lottie/pubspec.yaml":"# Flet_lottie Skill\n\nPath: `sdk/python/packages/flet-lottie/src/flutter/flet_lottie/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/src/flutter/flet_lottie/pubspec.yaml)","sdk/python/packages/flet-map/src/flutter/flet_map/analysis_options.yaml":"# Flet_map Skill\n\nPath: `sdk/python/packages/flet-map/src/flutter/flet_map/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/src/flutter/flet_map/analysis_options.yaml)","sdk/python/packages/flet-map/src/flutter/flet_map/pubspec.yaml":"# Flet_map Skill\n\nPath: `sdk/python/packages/flet-map/src/flutter/flet_map/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/src/flutter/flet_map/pubspec.yaml)","sdk/python/packages/flet-mcp/src/flet_mcp/data/icons.json":"# Data Skill\n\nPath: `sdk/python/packages/flet-mcp/src/flet_mcp/data/icons.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-mcp/src/flet_mcp/data/icons.json)","sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/analysis_options.yaml":"# Flet_permission_handler Skill\n\nPath: `sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/analysis_options.yaml)","sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/pubspec.yaml":"# Flet_permission_handler Skill\n\nPath: `sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/pubspec.yaml)","sdk/python/packages/flet-rive/src/flutter/flet_rive/analysis_options.yaml":"# Flet_rive Skill\n\nPath: `sdk/python/packages/flet-rive/src/flutter/flet_rive/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/src/flutter/flet_rive/analysis_options.yaml)","sdk/python/packages/flet-rive/src/flutter/flet_rive/pubspec.yaml":"# Flet_rive Skill\n\nPath: `sdk/python/packages/flet-rive/src/flutter/flet_rive/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/src/flutter/flet_rive/pubspec.yaml)","sdk/python/packages/flet-secure-storage/src/flutter/flet_secure_storage/pubspec.yaml":"# Flet_secure_storage Skill\n\nPath: `sdk/python/packages/flet-secure-storage/src/flutter/flet_secure_storage/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-secure-storage/src/flutter/flet_secure_storage/pubspec.yaml)","sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/analysis_options.yaml":"# Flet_spinkit Skill\n\nPath: `sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/analysis_options.yaml)","sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/pubspec.yaml":"# Flet_spinkit Skill\n\nPath: `sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/pubspec.yaml)","sdk/python/packages/flet-video/src/flutter/flet_video/analysis_options.yaml":"# Flet_video Skill\n\nPath: `sdk/python/packages/flet-video/src/flutter/flet_video/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/src/flutter/flet_video/analysis_options.yaml)","sdk/python/packages/flet-video/src/flutter/flet_video/pubspec.yaml":"# Flet_video Skill\n\nPath: `sdk/python/packages/flet-video/src/flutter/flet_video/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/src/flutter/flet_video/pubspec.yaml)","sdk/python/packages/flet-web/src/flet_web/fastapi/README.md":"# fastapi Documentation\n\nPath: `sdk/python/packages/flet-web/src/flet_web/fastapi/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-web/src/flet_web/fastapi/README.md)","sdk/python/packages/flet-webview/src/flutter/flet_webview/analysis_options.yaml":"# Flet_webview Skill\n\nPath: `sdk/python/packages/flet-webview/src/flutter/flet_webview/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/src/flutter/flet_webview/analysis_options.yaml)","sdk/python/packages/flet-webview/src/flutter/flet_webview/pubspec.yaml":"# Flet_webview Skill\n\nPath: `sdk/python/packages/flet-webview/src/flutter/flet_webview/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/src/flutter/flet_webview/pubspec.yaml)","sdk/python/packages/flet/src/flet/controls/cupertino/cupertino_icons.json":"# Cupertino Skill\n\nPath: `sdk/python/packages/flet/src/flet/controls/cupertino/cupertino_icons.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/src/flet/controls/cupertino/cupertino_icons.json)","sdk/python/packages/flet/src/flet/controls/material/icons.json":"# Material Skill\n\nPath: `sdk/python/packages/flet/src/flet/controls/material/icons.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/src/flet/controls/material/icons.json)"},"files":{".agents/skills/create-flet-control-integration-tests/SKILL.md":"---\nname: create-flet-control-integration-tests\ndescription: Use when asked to create or update integration tests for any Flet control in sdk/python/packages/flet/integration_tests, including visual goldens and interactive behavior tests.\n---\n\n## When to use\n\nUse this skill when adding, updating, or reviewing integration tests for a Flet control (core, material, cupertino, theme, services, types, or examples).\n\nUse it for:\n\n- visual rendering checks with golden screenshots\n- interaction checks (hover, click, input, keyboard)\n- control property behavior checks\n- regression tests for control bugs\n\n## Test placement\n\nPick the closest existing suite first:\n\n- Core controls: `sdk/python/packages/flet/integration_tests/controls/core`\n- Material controls: `sdk/python/packages/flet/integration_tests/controls/material`\n- Cupertino controls: `sdk/python/packages/flet/integration_tests/controls/cupertino`\n- Theme tests: `sdk/python/packages/flet/integration_tests/controls/theme`\n- Type helpers: `sdk/python/packages/flet/integration_tests/controls/types`\n- Services: `sdk/python/packages/flet/integration_tests/controls/services`\n- Examples: `sdk/python/packages/flet/integration_tests/examples`\n\nPrefer adding tests to an existing file for the same control. Create a new test file only when no suitable file exists.\n\n### Scope split rule (required)\n\nDo not mix `loop_scope=\"module\"` and `loop_scope=\"function\"` tests in the same file.\n\nNaming convention:\n\n- `test_<control>.py` for module-scoped visual/stable tests (uses `flet_app`)\n- `test_<control>_isolated.py` for function-scoped tests that require a fresh app per test (uses `flet_app_function`)\n\n## Fixture choice\n\nUse fixtures from `integration_tests/conftest.py`:\n\n- `flet_app` (`loop_scope=\"module\"`): best for stable visual tests and bulk screenshot tests.\n- `flet_app_function` (`loop_scope=\"function\"`): best for tests that mutate state and must run in a separate app each.\n\n## Authoring workflow\n\n1. Identify behavior to verify.\n2. Build deterministic layout/state:\n- set `theme_mode` explicitly when visuals matter\n- set fixed sizes/padding/spacing\n- avoid random or time-varying content\n3. Choose file by scope rule before writing tests.\n4. Write test using async pytest.\n5. Use screenshot assertion for UI behavior, functional assertion for non-visual behavior.\n6. Name test so `request.node.name` can be used as screenshot key.\n7. Run target test file.\n8. If expected visuals changed, regenerate goldens with `FLET_TEST_GOLDEN=1` and re-run without golden mode.\n\n## Assertion patterns\n\n### Visual control assertion\n\n```python\nawait flet_app.assert_control_screenshot(\n    request.node.name,\n    control,\n)\n```\n\n### Visual full-page assertion\n\n```python\nflet_app_function.assert_screenshot(\n    request.node.name,\n    await flet_app_function.page.take_screenshot(\n        pixel_ratio=flet_app_function.screenshots_pixel_ratio\n    ),\n)\n```\n\n### Functional assertion\n\n```python\nfinder = await flet_app_function.tester.find_by_tooltip(\"Info tooltip\")\nassert finder.count == 1\n```\n\n## Minimal templates\n\n### Template: module-scope file (`test_<control>.py`)\n\n```python\nimport pytest\n\nimport flet as ft\nimport flet.testing as ftt\n\n\n@pytest.mark.asyncio(loop_scope=\"module\")\nasync def test_<behavior>(flet_app: ftt.FletTestApp, request):\n    flet_app.page.theme_mode = ft.ThemeMode.LIGHT\n    await flet_app.assert_control_screenshot(\n        request.node.name,\n        ft.Container(width=240, height=80, alignment=ft.Alignment.CENTER),\n    )\n```\n\n### Template: function-scope file (`test_<control>_isolated.py`)\n\n```python\nimport pytest\n\nimport flet as ft\nimport flet.testing as ftt\n\n\n@pytest.mark.asyncio(loop_scope=\"function\")\nasync def test_<behavior>(flet_app_function: ftt.FletTestApp):\n    flet_app_function.page.add(ft.IconButton(icon=ft.Icons.INFO, tooltip=\"Info\"))\n    await flet_app_function.tester.pump_and_settle()\n\n    finder = await flet_app_function.tester.find_by_tooltip(\"Info\")\n    assert finder.count == 1\n```\n\n## Run commands\n\nRun one test file:\n\n```bash\nuv run pytest -s -o log_cli=true -o log_cli_level=INFO packages/flet/integration_tests/controls/core/test_control.py\n```\n\nRun a subset:\n\n```bash\nuv run pytest -s -o log_cli=true -o log_cli_level=INFO packages/flet/integration_tests/controls/core/test_control.py -k test_visible\n```\n\nGenerate or update goldens:\n\n```bash\nFLET_TEST_GOLDEN=1 uv run pytest -s -o log_cli=true -o log_cli_level=INFO packages/flet/integration_tests/controls/core/test_control.py\n```\n\n## Quality checklist\n\n- Test file location matches control area.\n- `module` and `function` scope tests are in separate files.\n- Function-scoped files use the `test_<control>_isolated.py` naming convention.\n- Fixture scope matches test intent.\n- Screenshot keys are stable (`request.node.name` preferred).\n- Visual tests are deterministic (theme/size/content).\n- Goldens are updated only for intentional visual changes.\n- No unrelated formatting or refactors in the same change.\n\n## References\n\n- `sdk/python/packages/flet/integration_tests/README.md`\n- `sdk/python/packages/flet/integration_tests/conftest.py`\n- `sdk/python/packages/flet/integration_tests/controls/core/test_control.py`\n- `sdk/python/packages/flet/integration_tests/controls/core/test_control_isolated.py`\n- `sdk/python/packages/flet/integration_tests/controls/core/test_layout_control.py`\n- `sdk/python/packages/flet/integration_tests/examples/core/test_control.py`\n- `sdk/python/examples/controls/control`\n",".agents/skills/create-flet-example-projects/SKILL.md":"---\nname: create-flet-example-projects\ndescription: Use when asked to create Flet example projects from flat .py files with main.py and pyproject.toml metadata for Gallery/MCP indexing.\n---\n\n## When to use\n\nUse this skill when a user asks to:\n- create one control/example folder (for example `examples/controls/chip`) in the project-per-example format\n- migrate existing flat examples to the project-per-example format\n- normalize a partially converted folder so all examples follow the same structure\n\n## Goal\n\nEnsure each runnable example is a standalone project containing:\n\n- `main.py`\n- `pyproject.toml` with Gallery/MCP metadata\n- `assets/` (if the example uses local assets)\n\n## Workflow\n\n1. Inspect source folder.\n- Detect current state per example:\n  - flat file: `foo.py`\n  - project folder: `foo/main.py`\n  - mixed/partial conversion: both styles present or missing metadata files\n- Find candidate flat modules: `*.py` in the target folder (exclude helper files such as `__init__.py`).\n- Keep existing `media/` unless an example needs local assets copied into its own `assets/`.\n\n2. Convert or normalize examples.\n- For `foo.py`, create `foo/` and move file to `foo/main.py`.\n- If `foo/main.py` already exists, keep it and do not recreate/move files.\n- If folder exists but `main.py` is missing, repair structure only when there is a clear source file.\n- Do not create `foo/__init__.py`; import example modules directly in tests/docs (for example `import examples.controls.foo.bar.main as bar` or `import examples.controls.foo.bar as bar` when using namespace-package imports).\n- When a control folder has been fully converted to project-per-example layout, delete the control-level `examples/controls/<control>/__init__.py` too. The converted folders should behave like namespace packages, matching prior migrations such as commit `7e65ad566`.\n\n3. Add `pyproject.toml` for each example project.\n- Infer from path and code.\n- Create missing `pyproject.toml` files for existing project folders.\n- Update obviously stale metadata when migrating existing examples (for example wrong title/description/categories).\n- Verify platform support before adding or omitting `[tool.flet].platforms`:\n  - Check the local implementation and docs for explicit platform guards, support tables, or platform-specific exceptions.\n  - If support is limited, add `[tool.flet].platforms` with only the supported platforms.\n  - If support is broad/all-platform, omit `[tool.flet].platforms`.\n- Required fields:\n  - `[project]`: `name`, `version`, `description`, `requires-python`, `keywords`, `authors`, `dependencies`\n  - `[dependency-groups].dev`: include `flet-cli`, `flet-desktop`, `flet-web`\n  - `[tool.flet.gallery].categories`\n  - `[tool.flet.metadata]`: `title`, `controls`, `layout_pattern`, `complexity`, `features`\n  - `[tool.flet]`: `org`, `company`, `copyright`\n- Add `[tool.flet].platforms` only when the example is platform-limited.\n- Add permissions blocks only when code actually needs them.\n\n4. Infer metadata.\n- Title: readable version of file/folder intent.\n- Short description: one line of what the example demonstrates.\n- `[project].description` must be meaningful and example-specific; avoid generic placeholders like \"Example N\" or \"<name> example for <control>\".\n- Description should mention the concrete behavior or interaction shown (for example: hover highlight, live updates, custom axes, event handling).\n- Categories: typically control-based, e.g. `Input/Chip`, plus optional `Apps/Basic controls`.\n- Tags: from control/topic/behavior words.\n- Controls used: list key controls from code.\n- Layout pattern: choose closest practical value (e.g. `filter-bar`, `inline-actions`, `dashboard`, `list-detail`).\n- Complexity: `basic` unless logic/state/architecture is non-trivial.\n- Features: notable behaviors only (click handling, selection, async loading, drag-and-drop, etc.).\n- If an example supports exporting or downloading output, include `\"save to file\"` in `[tool.flet.metadata].features`.\n- If an example module contains `async def` handlers or async control flow, append `\"async\"` to `keywords`.\n\n\n5. Infer dependencies from imports.\n- Always include `flet` for standard examples.\n- Include extra packages if imported (for example extension packages).\n- Do not add unused dependencies.\n\n6. Make examples mobile-safe.\n- If `ft.context.disable_auto_update()` is not used, do not add explicit `page.update()` unless strictly necessary.\n- Apply this `page.update()` rule to all examples in the touched folder (new, migrated, and already converted).\n- Wrap app content in `ft.SafeArea` so example renders correctly on mobile.\n- Add `expand=True` to `ft.SafeArea` only when needed for correct layout/sizing (for example to avoid Infinity/NaN sizing issues), and avoid adding it when not necessary.\n- When converting legacy `page.add(a, b, ...)` style examples, wrap the controls in `ft.Column(controls=[...])` inside `ft.SafeArea(content=...)` rather than `ft.Row`, unless the original code explicitly used a row layout.\n\n- Apply this to all examples in the touched folder (new, migrated, and already converted), not only files changed by moves.\n- During validation, confirm every `<example>/main.py` in scope includes a top-level `ft.SafeArea` around rendered content.\n- For declarative examples using `@ft.component`, do not pass component instances as regular control children (for example `SafeArea(content=App())`) because this can raise runtime attribute errors.\n- In declarative examples, ensure the component itself returns regular controls (including `SafeArea` when needed) and render it at page level with `page.render(App)` in `main()`.\n\n7. Prefer `@ft.control` for custom controls in examples.\n- If an example defines a custom control class inheriting from a Flet control (for example `class MyThing(ft.Column)`), prefer `@ft.control` style.\n- Move constructor-style setup to declarative fields + `init()` where practical.\n- Keep behavior unchanged and avoid refactors that alter public usage unless needed for compatibility.\n\n8. Remove deprecated Material 3 toggle usage.\n- If `use_material3` appears in example code, remove it and simplify the example to current API usage.\n- Remove related Material 3 toggle logic/UI that exists only to switch `use_material3`.\n- Update example metadata (`pyproject.toml`) to remove stale Material 3 references when code is changed.\n\n9. Ensure runnable entrypoint.\n- Every example `main.py` should end with:\n  - `if __name__ == \"__main__\":`\n  - `    ft.run(main)`\n- Apply this to all examples in the touched folder (new, migrated, and already converted).\n\n10. Update references.\n- Docs code includes: change from `.../example.py` to `.../example/main.py`.\n- Inspect the relevant docs pages for each touched control/service/example area (for example `sdk/python/packages/flet/docs/controls/<control>.md`) and update any `--8<--` includes or direct file-path references to the new `main.py` path.\n- Tests/imports: use direct module imports and avoid relying on package-level `__init__.py` re-exports.\n- For already-converted examples, only update references that are stale; avoid unnecessary churn.\n- If removing a control-level `__init__.py`, confirm no remaining imports rely on `from examples.controls.<control> import ...`.\n\n11. Validate.\n- Run `python -m compileall` on changed `main.py` files.\n- Run `uv run ruff check` on changed example files and fix violations until it passes (respecting repository `pyproject.toml` under `[tool.ruff]`).\n- Search for stale paths to old flat files.\n- Search docs and package sources for stale references to the migrated flat example paths and fix any hits in scope.\n- Check `git status` to confirm expected moves and edits.\n- When integration tests exist for the touched control, run the targeted test file(s).\n- Confirm all in-scope `main.py` files include both top-level `ft.SafeArea` wrapping and the `if __name__ == \"__main__\": ft.run(main)` entrypoint.\n- Confirm in-scope `ft.SafeArea` wrappers use `expand=True` only where needed for correct behavior and sizing; avoid forcing it by default.\n- Confirm there are no unnecessary `page.update()` calls in in-scope examples (unless explicitly required by isolated-control or non-auto-update behavior).\n- Confirm no in-scope examples use `use_material3`.\n- Confirm each in-scope `pyproject.toml` has a meaningful, example-specific `[project].description` (not generic or templated text).\n- Confirm metadata features include `\"save to file\"` when the example code supports file export/save behavior.\n- Confirm there is no stale control-level `__init__.py` left behind once a touched control folder has been fully converted.\n- Confirm the relevant docs pages were updated to reference `main.py` and that no stale doc includes remain for the touched examples.\n\n\n## Code style\n\n- When writing wrapped controls (`SafeArea`, `Column`, `Row`, `Container`, etc.), keep `content=` or `controls=` as the last named argument in that control call.\n- Apply this ordering consistently when creating or refactoring examples.\n- Follow code style and linting rules defined in the repository `pyproject.toml` under `[tool.ruff]` for all edits.\n\n## Command checklist\n\n- Discover files: `rg --files <target_dir>`\n- Find docs links/imports: `rg -n \"<old_path_or_module>\" packages examples`\n- Syntax check: `python -m compileall <changed_main_files>`\n- Ruff check: `uv run ruff check <changed_example_files>`\n\n## Output expectations\n\nReport:\n- created example projects\n- metadata added\n- docs/tests updates\n- validation results\n",".agents/skills/docs-conventions/SKILL.md":"---\nname: docs-conventions\ndescription: Use when writing or reviewing Flet documentation, including Python docstrings (Google style, reST roles, admonitions), Markdown docs (cross-references, images, code examples), and sidebar navigation.\n---\n\n# Documentation Conventions\n\nDocs live in `website/docs/`. Docusaurus renders them as the website.\n\n## Python Docstrings\n\nUse **Google style** docstrings with sections: `Args:`, `Returns:`, `Raises:`, `Note:`, `Example:`, `Warning:`.\n\n## Cross-references\n\n### reST roles\n\nPrefer these in Python docstrings. CrocoDocs renders them as links in\nthe API docs and they keep authoring terse when the auto-derived label is acceptable.\n\n**Supported roles:** `:class:`, `:attr:`, `:meth:`, `:func:`, `:data:`, `:mod:`\n\n```python\n\"\"\"\nIf a parent is a :class:`~flet.ResponsiveRow`, this property determines\nhow many virtual columns the control spans.\n\nSee :attr:`value` or :attr:`flet.Text.size` for the current selection.\n\nCalls :meth:`flet.Page.update` after modifying controls.\n\"\"\"\n```\n\n**Rules:**\n\n- **Qualified reference:** `:attr:`flet.Page.route`` — links to the member, displays inline code `Page.route`\n- **Extension reference:** `:attr:`flet_map.Map.animation_curve`` — links to the extension member, displays inline code `Map.animation_curve`\n- **Short display with `~`:** `:attr:`~flet.Page.route`` — links to the member, displays inline code `route`\n- **Local member (same class):** `:attr:`value`` — no qualifier needed\n- **Method with parens:** `:meth:`update`` — do NOT include `()` in the target\n\nFor plain class references like `:class:`flet.Page`` and extension references like\n`:class:`flet_map.Map``, the website strips leading public package aliases automatically,\nso they display as inline code `Page` and `Map`.\n\n**Not supported:**\n\n- Custom labels like `:class:`my label <flet.Page>`` — the label is always auto-derived from the target\n- Roles for symbols not in CrocoDocs API data degrade to inline code\n\n### Xrefs\n\nReference-style Markdown links of the form `[label][key]`, where `key` is the\nfully-qualified dotted symbol path (same form as reST role targets).\n\nUse as the default form for linking to API symbols from Markdown docs\n(`.md` / `.mdx`).\n\nExamples:\n\n```markdown\nClass: [`Page`][flet.Page]\nAttribute: [`route`][flet.Page.route]\nMethod: [`Page.update()`][flet.Page.update]\nExtension: [`Video.controls`][flet_video.Video.controls]\nPlain text: [the route attribute][flet.Page.route]\n```\n\n**When to prefer over the other forms:**\n\n- **Flexible labels** — the first `[ ]` accepts any text or inline code, unlike reST roles whose label is always auto-derived from the target\n- **Path-independent** — keys are dotted symbol paths, so links don't break when source files are moved, renamed, or restructured (unlike Markdown link paths with `../` and `#flet.X.y` anchors)\n- **Terser** than Markdown links to the same symbol — no relative path or anchor to maintain\n- **Greppable** — searching for the dotted key finds every reference to that symbol across all docs\n\n**Rules:**\n\n- The label (inside the first `[ ]`) is the rendered text — inline code or plain text\n- The key (inside the second `[ ]`) is the fully-qualified dotted path; do NOT include `()` for methods\n- Unresolved keys render as broken reference-style links (silent fallback) — verify with a build or `yarn crocodocs:generate`\n\n### Markdown links\n\nFallback for cases xrefs cannot cover:\n\n- docs-only Python strings — the `docs_reason` parameter of `@deprecated`, extracted validation messages, or short admonition text\n- links to non-API content (other doc pages, external URLs, anchors that aren't API symbols)\n- when the xref entry is missing and you need a working link before regenerating\n\nUse relative `.md` paths with dot-format anchors.\n\nExamples:\n\n```markdown\nControl: [`Page`](../controls/page.md)\nType: [`DragTargetEvent.global_position`](../types/dragtargetevent.md#flet.DragTargetEvent.global_position)\nPlain text: [route](../controls/page.md#flet.Page.route)\nMethod: [`Page.update()`](../controls/page.md#flet.Page.update)\n```\n\n## Admonitions in docstrings\n\nGoogle-style section headers render as Docusaurus admonitions:\n\n```python\n\"\"\"\nNote:\n    Has effect only if the direct parent is a :class:`~flet.Column`.\n\nWarning:\n    This property is deprecated. Use :attr:`new_prop` instead.\n\nExample:\n    Setting up a basic layout:\n    ``ft.Column(controls=[ft.Text(\"Hello\")])``\n\"\"\"\n```\n\nSupported kinds: `Note`, `Warning`, `Danger`, `Tip`, `Info`.\nUnsupported kinds (e.g. `Limitation`, `Example`) are normalized to `note`.\nEmpty admonitions are skipped.\n\n## Admonitions\n\n```markdown\n:::note\nBasic note without title.\n:::\n\n:::warning[Important]\nWarning with a custom title.\n:::\n```\n\nSupported types: `note`, `info`, `tip`, `warning`, `danger`.\n\n## Front matter\n\n```yaml\n---\nclass_name: \"flet.Container\"\nexamples: \"controls/container\"\nexample_images: \"test-images/examples/material/golden/macos/container\"\nexample_media: \"examples/controls/container/media\"\ntitle: \"Container\"\n---\n```\n\n- `examples` — root-relative path under `sdk/python/examples/`\n- `example_images` / `example_media` — root-relative under `website/static/docs/`\n\n## Images\n\nUse the CrocoDocs `Image` component. Paths without `../` are resolved against `/docs/`:\n\n```jsx\nimport {Image} from '@site/src/components/crocodocs';\n\n<Image src={frontMatter.example_images + '/image_for_docs.png'} width=\"55%\" />\n```\n\nFor absolute paths (one-off assets in `static/`):\n\n```jsx\n<Image src=\"/docs/assets/controls/charts/bar-chart-diagram.svg\" width=\"65%\" />\n```\n\n## Code examples\n\n```jsx\nimport {CodeExample} from '@site/src/components/crocodocs';\n\n<CodeExample path={frontMatter.examples + '/example_1.py'} />\n```\n\nPaths are relative to the configured `examples_root` (`sdk/python/examples/`).\n\n## Inline HTML\n\nUse `<kbd>...</kbd>` in Python docstrings for keyboard keys, for example\n`<kbd>Enter</kbd>` or `<kbd>Shift</kbd>`. CrocoDocs preserves this tag in API\ndocs.\n\n## Sidebar Navigation\n\nEdit `website/sidebars.yml` to change navigation structure:\n\n```yaml\ndocs:\n  Getting started:\n  - getting-started/installation.md\n  Controls:\n    _generated_index:\n      title: Controls\n      slug: /controls\n      description: Browse the complete catalog of controls.\n    AlertDialog: controls/alertdialog.md\n```\n\nAfter editing, regenerate `sidebars.js`:\n\n```bash\ncd website && yarn crocodocs:generate\n```\n",".agents/skills/docs-build-and-verify/SKILL.md":"---\nname: docs-build-and-verify\ndescription: Use when asked to build, preview, or verify the Flet documentation website, including checking for broken links, broken images, and unresolved reST cross-references.\n---\n\n# Docs Build and Verification\n\n## Prerequisites\n\nNode.js 24 is required, matching what CI runs:\n\n```bash\nnvm use 24\n```\n\n## Build\n\nFull production build (includes broken link detection):\n\n```bash\ncd website && yarn build\n```\n\nDev server with hot reload:\n\n```bash\ncd website && yarn start\n```\n\nRegenerate API data and sidebars only (no Docusaurus build):\n\n```bash\ncd website && yarn crocodocs:generate\n```\n\n## Check Broken Links\n\n`yarn build` reports both, but only broken *links* fail the build. Docusaurus defaults\n`onBrokenAnchors` to `warn` and `docusaurus.config.js` does not override it, so a broken\nanchor scrolls past in the log and still ships - grep the build output for `Broken anchor`\nrather than trusting the exit code.\n\n## Check Broken Images\n\nRun this after `yarn build` to find images referenced in HTML that don't exist:\n\n```bash\ncd website && python3 -c \"\nimport re, os, glob\n\nbuild_dir = 'build'\nimg_re = re.compile(r'<img[^>]+src=\\\"(/[^\\\"]+)\\\"', re.IGNORECASE)\nbroken = []\n\nfor html_file in sorted(glob.glob(f'{build_dir}/docs/**/index.html', recursive=True)):\n    page = html_file.replace(build_dir + '/', '').replace('/index.html', '')\n    content = open(html_file).read()\n    for match in img_re.finditer(content):\n        src = match.group(1)\n        if src.startswith('http') or src.startswith('data:'):\n            continue\n        file_path = os.path.join(build_dir, src.lstrip('/'))\n        if not os.path.exists(file_path):\n            broken.append((page, src))\n\nif broken:\n    print(f'Found {len(broken)} broken images:')\n    for page, src in broken:\n        print(f'  {page}: {src}')\nelse:\n    print('No broken images found!')\n\"\n```\n\n## Check Unresolved reST Cross-References\n\nAfter building, check for reST roles that failed to resolve and appear as raw text:\n\n```bash\ncd website && grep -r ':attr:\\|:class:\\|:meth:\\|:func:' build/docs/ --include='*.html' -l\n```\n\nIf any files are listed, those pages have unresolved cross-references that render as plain text instead of links.\n",".agents/skills/fix-members-short-description/SKILL.md":"---\nname: fix-members-short-description\ndescription: Use when asked to fix short descriptions of Python type members.\n---\n\n## Inputs\n\n* File or directory with Python modules.\n\n## Instructions\n\nWhen Flet documentation is generated from docstrings the first sentence of a member docstring is used as a short description, for example:\n\n```py\n@dataclass\nclass MyControl:\n    property_a: str\n    \"\"\"\n    Short description of a property.\n\n    Full description.\n    Another line of full description.\n    \"\"\"\n```\n\nHere \"Short description of a property.\" will be used as a short description.\n\nHowever, when a sentence is broken into multiple lines the lines must be \"concatenated\" with `\\`, for example:\n\n```py\n@dataclass\nclass MyControl:\n    property_a: str\n    \"\"\"\n    Short description of a property which could \\\n    take multiple lines.\n\n    Full description.\n    Another line of full description.\n    \"\"\"\n```\n\nYour goal is to go through all members (properties, methods, etc.) of all types (classes, enums) in input file or directory and ensure the first sentence in their docstrings is broken into multiple lines correctly with `\\` symbol.\n\nApply the fix regardless of whether the first sentence starts on the same line as the opening `\"\"\"` or on a following line.\n\nEnsure every docstring line is at most 88 characters long (including any trailing `\\`). If a line cannot be wrapped without breaking a single unbreakable token (e.g., a long URL or Windows registry path like `HKEY_LOCAL_MACHINE\\\\...`), add `# noqa: E501` to the docstring closing `\"\"\"` line instead of the long line.\n",".agents/skills/flet-deprecation/SKILL.md":"---\nname: flet-deprecation\ndescription: Use when adding or changing deprecations for Python controls/APIs in sdk/python/packages/, including V.deprecated fields, deprecated decorators, version lifecycle, and docs admonitions/labels.\n---\n\n## When To Use\n\nUse this skill when you:\n- deprecate a control/dataclass field with `Annotated[..., V.deprecated(...)]`,\n- deprecate a function/method/class with `flet.utils.deprecated` helpers,\n- update deprecation wording, versions, or removal timelines,\n- verify docs rendering for deprecations (admonition + `deprecated` label).\n\nDo not use this skill for non-deprecation validation logic; use\n[`flet-validation`](../flet-validation/SKILL.md).\n\n## Source Of Truth\n\n- Runtime decorators and warning helpers: `sdk/python/packages/flet/src/flet/utils/deprecated.py`\n- Field-level deprecation rule: `sdk/python/packages/flet/src/flet/utils/validation.py` (`V.deprecated`)\n- Docs extraction/labeling extension: `sdk/python/packages/flet/src/flet/utils/griffe_deprecations.py`\n\n## Deprecation Decision Order\n\nUse this order and stop at the first option that fits:\n1. Property/field deprecation: `Annotated[..., V.deprecated(...)]`.\n2. Function/method deprecation: `@deprecated(...)`.\n3. Class/control deprecation: `@deprecated_class(...)`.\n\nDo not add parallel custom warning logic in `before_update()` when `V.deprecated`\nalready covers the field.\n\n## Runtime Contract For Property Renames\n\nFollow the non-copying model:\n- Python sends both properties when both are set.\n- Dart prefers the new property and uses old property as fallback.\n- Python does not copy/synchronize old/new values in `before_update()`.\n\nRemoval phase:\n- At `delete_version` cleanup, remove old Python property/deprecation and remove\n  Dart fallback in the same migration.\n\n## Removal Version Policy\n\n- Default policy: remove deprecated APIs after 3 minor releases.\n- Example: deprecated in `0.82.0` -> remove in `0.85.0`.\n- Use that policy to set `delete_version` unless there is an approved exception.\n\n## Target Release Audit\n\nWhen working on a release for `{new_version}`, treat deprecations with\n`delete_version == {new_version}` as mandatory audit items.\n\n- Scan Python packages for `@deprecated(...)`, `@deprecated_class(...)`,\n  and `V.deprecated(...)` entries whose `delete_version` equals `{new_version}`.\n- Recommended check command:\n  `rg -n 'delete_version\\\\s*=\\\\s*\"{new_version}\"|delete_version\\\\s*=\\\\s*\\\\x27{new_version}\\\\x27' -S sdk/python/packages`\n- Treat every match as release-relevant work, not informational output.\n- If matches are found, summarize the findings first and ask the human for approval\n  before editing files or making removals.\n- For each match, decide whether the deprecated API must be removed now,\n  whether a prior removal was missed, or whether the deprecation timeline is incorrect.\n- If removal is due, make the code, docs, and changelog updates in the same change.\n- After the cleanup edits are ready, summarize the resulting diff and ask the human\n  for approval before creating a commit.\n- Once commit approval is received, batch all confirmed `{new_version}` cleanup\n  edits into one grouped commit instead of splitting them across multiple commits.\n  Use commit message format: `release: remove deprecated APIs for {new_version}`\n- Do not consider the release prep complete while unresolved `{new_version}` removals remain.\n\n## Authoring Rules\n\n1. Always set `version`.\n2. Set `delete_version` using the 3-minor policy by default.\n3. Keep `reason` plain text for runtime warnings.\n4. Use `docs_reason` for docs-only markdown text.\n5. When a replacement exists, name that replacement API explicitly in `reason` and `docs_reason`.\n\n### Field Pattern\n\n```python\nfrom typing import Annotated, Optional\nfrom flet.utils.validation import V\n\nclass ExampleControl:\n    old_prop: Annotated[\n        Optional[str],\n        V.deprecated(\n            \"new_prop\",\n            version=\"0.17.0\",\n            delete_version=\"0.20.0\",\n            reason=\"Use new_prop instead.\",\n            docs_reason=\"Use :attr:`new_prop` or [`new_prop`](../controls/examplecontrol.md#flet.ExampleControl.new_prop) instead.\",\n        ),\n    ] = None\n```\n\n### Function/Method Pattern\n\n```python\nfrom flet.utils.deprecated import deprecated\n\nclass ExampleControl:\n    @deprecated(\n        reason=\"Use new_func instead.\",\n        docs_reason=\"Use :meth:`new_func` or [`new_func()`](../controls/examplecontrol.md#flet.ExampleControl.new_func) instead.\",\n        version=\"0.17.0\",\n        delete_version=\"0.20.0\",\n    )\n    def old_func(self):\n        ...\n```\n\n### Class/Control Pattern\n\n```python\nfrom flet.utils.deprecated import deprecated_class\n\n@deprecated_class(\n    reason=\"Use NewControl instead.\",\n    docs_reason=\"Use :class:`~flet.NewControl` or [`NewControl`](../controls/newcontrol.md)  instead.\",\n    version=\"0.17.0\",\n    delete_version=\"0.20.0\",\n)\nclass OldControl:\n    ...\n```\n\n### Deprecated Property Pattern\n\n```python\nfrom flet.utils.deprecated import deprecated\n\nclass ExampleControl:\n    @property\n    @deprecated(\n        reason=\"Use new_value instead.\",\n        docs_reason=\"Use :attr:`new_value` or [`new_value`](../controls/examplecontrol.md#flet.ExampleControl.new_value) instead.\",\n        version=\"0.17.0\",\n        delete_version=\"0.20.0\",\n    )\n    def value(self):\n        ...\n```\n\n## `reason` vs `docs_reason`\n\n- Runtime warnings always use `reason`.\n- Docs admonitions prefer `docs_reason`; fallback is `reason`.\n- Keep markdown/cross-refs out of `reason` to avoid noisy runtime output.\n\n### Cross-reference Rule Inside `docs_reason`\n\nIn `docs_reason`, use reST roles for simple references when the auto-derived label is\nsufficient, and use Markdown links when you need more control over the displayed text.\n\nSee [`docs-conventions`](../docs-conventions/SKILL.md) for details on supported cross-ref patterns and their syntax.\n\n## Docs Behavior Expectations\n\nFor supported patterns, docs should auto-render:\n- a `Deprecated` admonition section,\n- a `deprecated` label/badge on the item.\n\nDo not duplicate with manual deprecation admonitions in docstrings unless there\nis a special case not covered by the extension.\n\n## Release Docs Updates\n\nWhen adding a user-visible deprecation, also update the release docs in the\nsame change. These pages are the canonical upgrade path, not a separate\n`Deprecations` page.\n\n1. Create or update a migration guide under\n   `website/docs/updates/breaking-changes/vX-Y-Z/`.\n   - Group closely related deprecations into one page, especially APIs from the\n     same class/control or the same PR. For example, `DragTargetEvent.x`,\n     `DragTargetEvent.y`, and `DragTargetEvent.offset` belong in one\n     coordinate-fields guide.\n   - Use this page shape: title, `:::note` accuracy callout,\n     `Summary`, `Context`, `Migration guide`, `Timeline`, and `References`.\n   - Keep one-off replacements in prose. Use a table only when the page maps\n     many removed/deprecated APIs to replacements.\n   - In `References`, link relevant API docs, relevant GitHub issue/PR links,\n     and release notes entry for that release.\n2. Add the guide to\n   `website/docs/updates/breaking-changes/index.md` under the release's\n   `Deprecations` subsection.\n3. Add the guide to `website/sidebars.yml` under:\n   `Stay up to date` -> `Breaking changes and deprecations` -> `vX.Y.Z`.\n   This keeps individual guide pages in the docs sidebar while grouping them by\n   release.\n4. Update `website/docs/updates/release-notes.md` so the release links to the\n   combined `Breaking changes and deprecations` section.\n5. Run `cd website && yarn crocodocs:generate` after sidebar\n   edits, then run `cd website && yarn build`.\n\n## Testing Guidance\n\nDo not add one-off tests for every API that gets deprecated when it uses an\nexisting, already-tested pattern (`V.deprecated`, `@deprecated`, or\n`@deprecated_class`). For routine deprecation metadata updates, rely on the\nshared helper and docs extraction tests.\n\nAdd or update tests only when the change affects deprecation infrastructure or\nintroduces meaningful new behavior, for example:\n- changing runtime warning formatting or stacklevel behavior,\n- changing docs extraction/labeling behavior,\n- adding a new deprecation pattern,\n- adding custom compatibility behavior outside the standard helper,\n- fixing a regression where an existing test would not have failed.\n\nPrefer these locations for infrastructure tests:\n- `sdk/python/packages/flet/tests/test_deprecated.py`\n- `sdk/python/packages/flet/tests/test_griffe_deprecations.py`\n- `sdk/python/packages/flet/tests/test_validation.py` (for `V.deprecated`)\n\n## Common Pitfalls\n\n- Putting markdown/cross-refs into runtime `reason`.\n- Forgetting `delete_version` when a removal target is already known.\n- Adding old/new value-copy logic in Python for rename migrations.\n- Duplicating deprecation warnings in multiple lifecycle hooks manually.\n- Broken cross-refs targets in `docs_reason`.\n",".agents/skills/flet-validation/SKILL.md":"---\nname: flet-validation\ndescription: Use whenever editing validation for Python controls in sdk/python/packages/: adding/changing constrained properties, `Raises: ValueError` docstrings, `before_update()` checks, `raise ValueError`, Annotated/V rules, or __validation_rules__.\n---\n\n## When To Use\n\nUse this skill when you:\n- add validation to a control property,\n- migrate manual `before_update()` checks to `V` rules,\n- update `Raises` sections tied to validation,\n- align Python validation with Dart-side control behavior.\n\nDo not use this skill for unrelated doc-only edits outside control validation.\nDo not use this skill for deprecation authoring conventions; use\n[`flet-deprecation`](../flet-deprecation/SKILL.md).\n\n## Source Of Truth\n\n- Validation runtime API lives in:\n  `sdk/python/packages/flet/src/flet/utils/validation.py`\n- The same runtime can validate regular dataclass models via `validate(instance)`;\n  this skill focuses on the control-specific authoring conventions.\n- Import from public path only:\n  `from flet.utils.validation import V`\n  and when needed\n  `from flet.utils.validation import ValidationRules`\n\n## Validation Decision Order\n\nUse this order and stop at the first option that keeps logic clear:\n1. `Annotated[..., V.*]` field rules (default).\n2. `__validation_rules__: ValidationRules` for cross-field invariants that do\n   not map cleanly to one field.\n3. `before_update()` only for normalization/mutation, or for truly non-ruleable\n   invariants.\n\nNever duplicate the same invariant in more than one layer.\n\n## Validation Authoring Rules\n\n1. Prefer field-level validation with `Annotated[...]` metadata.\n   - Example (close to current slider controls):\n     ```\n     @dataclass\n     class Sample:\n         opacity: Annotated[\n                Optional[Number],\n                V.between(0.0, 1.0),\n            ] = None\n\n         value: Annotated[\n             Optional[Number],\n             V.ge_field(\"min\"),\n             V.le_field(\"max\"),\n         ] = None\n\n         min: Annotated[\n             Number,\n             V.le_field(\"max\"),\n             V.le_field(\"value\"),\n         ] = 0.0\n\n         max: Annotated[\n             Number,\n             V.ge_field(\"min\"),\n             V.ge_field(\"value\"),\n         ] = 1.0\n     ```\n\n2. Use class-level `__validation_rules__` only for invariants that cannot be\n   expressed cleanly with field rules.\n   - Type:\n     `__validation_rules__: ValidationRules = (...)`\n   - Use `V.ensure(...)` with an explicit message only when the predicate is\n     short and readable.\n   - If `V.ensure(lambda ...)` becomes hard to read, prefer either:\n     1. a named predicate function passed to `V.ensure(...)`, or\n     2. a clear `before_update()` check when it cannot be represented well with\n        existing `V.*` rules.\n\n3. Keep the `before_update()` override for normalization/mutation first.\n   - Remove validation checks duplicated by `V` rules.\n   - Prefer raising validation errors from rule evaluation (`validate()`), not\n     from ad-hoc `before_update()` checks, unless the invariant is genuinely\n     non-ruleable with current validation primitives.\n\n4. Cross-field comparisons use field rules only.\n   - Use: `V.gt_field`, `V.ge_field`, `V.lt_field`, `V.le_field`\n\n5. `None` handling is inferred from type hints.\n   - If a field is annotated as optional (for example `Optional[T]`), `None` is allowed.\n   - If a field is not optional, `None` fails validation.\n   - For `*_field` comparisons, if either side is optional and currently `None`, the\n     comparison is skipped; if a non-optional side is `None`, validation fails.\n\n6. Match Dart effective behavior.\n   - Review both:\n     1. Flet Dart wrapper (`packages/flet/lib/src/controls/<control>.dart` or\n        extension wrapper),\n     2. wrapped Flutter widget source assertions/invariants.\n   - Mirror those constraints in Python so invalid payloads fail before crossing\n     to Dart.\n   - Validate against effective defaults applied on Dart side (for example\n     `min`/`max`).\n   - Include wrapper-imposed constraints when relevant (for example\n     bounds/rounding/division logic in wrapper formatting code).\n\n7. For new properties, validate against base widget assertions before wiring.\n   - When adding a Python property to a Flet control, confirm whether the mapped\n     Dart wrapper and underlying widget both enforce constraints for that property.\n   - Add equivalent Python-side validation (`Annotated[...]`, `__validation_rules__`,\n     or readable `before_update()`) to prevent Dart assertions from being the first\n     failure point.\n\n8. Keep error ownership clear.\n   - Runtime outbound value failures should raise `ValueError`.\n   - Validation declaration/build errors (invalid `V.*` arguments) should raise\n     `ValidationDeclarationError`.\n\n## Typing Style\n\n- Follow the codebase typing style:\n  - prefer `Optional[T]` over `T | None`,\n  - use `Union[...]` when needed.\n\n## Property Docstring Style\n\nWhen a property has validation, document it in that property’s docstring (google style).\n\n1. Add a `Raises:` block under the property docstring.\n\n2. Use one `ValueError` entry per logical rule, except `between(...)`.\n   - For `V.between(a, b)`, use one entry:\n     `ValueError: If it is not between \\`a\\` and \\`b\\`, inclusive.`\n\n3. Start each entry with `If it ...`, where 'it' refers to the property name.\n\n4. Use canonical wording from validation helper docstrings.\n   - The source of truth is\n     `sdk/python/packages/flet/src/flet/utils/validation.py`.\n   - Each `V.*` helper includes `Property docstring Raises wording`.\n   - Keep property `Raises` entries as negations of the annotation rule.\n   - For strict inequalities, say `\"strictly\"`.\n     For example: `V.gt(x)` -> `ValueError: If it is not strictly greater than \\`x\\`.`\n   - For sign-neutral divisibility helpers (`factor_of`, `multiple_of`), add\n     explicit sign rules (`V.gt(0)` or `V.lt(0)`) when direction matters, and\n     include separate `Raises` entries for those sign rules.\n\n5. Mention conditional applicability when needed.\n   - Example (for `min`/`max` checks against optional `value`):\n     ```\n     Raises:\n         ValueError: If it is not less than or equal to [`value`][(c).],\n             when [`value`][(c).] is set.\n     ```\n\n6. Keep examples and wording aligned with real control files.\n   - Prefer concrete property names such as `min`, `max`, `value`,\n     `start_value`, `end_value`, `min_lines`, `max_lines`.\n   - For cross-field rules, use same-class links: [`min`][(c).], [`max`][(c).].\n\n## Cross-Referencing Conventions\n\nFollow the cross-reference guidance in:\n[`docs-conventions`](../docs-conventions/SKILL.md).\n\nMost common pattern to use in control property docstrings:\n- same-class properties: `[\\`prop\\`][(c).]`\n\nKeep symbol labels wrapped in backticks.\n\n## Required Test Matrix\n\nWhen adding/changing validation, include tests that cover:\n- one valid case and one invalid case per new logical rule;\n- boundary values (`==`, min/max edges) where applicable;\n- cross-field set/unset combinations when optional values are involved;\n- effective-default behavior when Dart applies defaults but Python value is\n  omitted.\n\nPrefer placing tests in:\n- `sdk/python/packages/flet/tests/test_validation.py` for validation runtime;\n- control-specific tests when behavior is tied to one control.\n\n## Common Pitfalls\n\n- Keeping stale manual `before_update()` validations after migration.\n- Missing `Raises` entries on validated properties.\n- Combining multiple non-between rules into one ambiguous `ValueError` sentence.\n- Forgetting Dart defaults that still apply when Python property is omitted.\n- Forcing complex `V.ensure(lambda ...)` expressions when `before_update()` would be cleaner.\n",".agents/skills/prepare-flet-release/SKILL.md":"---\nname: prepare-flet-release\ndescription: Use when asked to prepare new Flet release by bumping versions and author release notes.\n---\n\n## Inputs\n\n* Previous Flet version from repo tags.\n* Whether it's minor or major release.\n\n## Related Skills\n\nAlways use [`flet-deprecation`](../flet-deprecation/SKILL.md) during release prep\nto audit deprecations for the target version. Also use it when release prep includes:\n- adding new deprecations in this release,\n- removing APIs whose `delete_version` equals this release version,\n- auditing changelog entries that mention deprecations/removals.\n\nUse [`write-changelog-entry`](../write-changelog-entry/SKILL.md) for drafting or refining individual changelog items.\nThat skill is the source of truth for item wording, scope selection, and what should or should not be mentioned in a single entry.\n\n## Steps\n\n* Take latest Flet release version from the repo and\n  increment third (patch) digit to get the next version if it's a minor release\n  or second (minor) digit if it's a major release.\n* Pull the latest `main` and create a new branch named `prepare-release-{new_version}` from `main`.\n* Set new version in packages/flet/pubspec.yaml.\n* Run pub get in /client dir to refresh pubspec.lock with new version.\n* Add new entries into `packages/flet/CHANGELOG.md` and `/CHANGELOG.md` from the git log since the last release.\n  * Use [`write-changelog-entry`](../write-changelog-entry/SKILL.md) for every individual item.\n  * Build the candidate set from relevant commits, PRs, and issues since the last release.\n  * Ensure that all inferred PRs and issues in the changelog have the `{version}` milestone attached on GitHub.\n  * If a related issue or PR is missing the `{version}` milestone, update the milestone on GitHub and keep the link in the changelog.\n  * When selecting candidates for `packages/flet/CHANGELOG.md`, prefer items with meaningful Flutter-side impact.\n  * When selecting candidates for `sdk/python/packages/*/CHANGELOG.md`, prefer published Python-facing changes; do not include extension-internal Flutter implementation work unless it materially changes user-visible Python behavior.\n* If the release includes breaking changes, API removals, or deprecations,\n  update `website/docs/updates/release-notes.md` and\n  `website/docs/updates/breaking-changes/index.md`.\n  * Use [`flet-deprecation`](../flet-deprecation/SKILL.md) for deprecation\n    guide requirements and sidebar placement.\n  * Group related deprecations into one migration guide page where possible,\n    and add guide pages under the release version in `website/sidebars.yml`.\n* Scan all changelogs for `Unreleased` sections, not only the root ones:\n  * `/CHANGELOG.md`\n  * `packages/flet/CHANGELOG.md`\n  * `sdk/python/packages/*/CHANGELOG.md`\n  Recommended check command:\n  `rg -n \"^##\\\\s*\\\\[?Unreleased\\\\]?|^##\\\\s*Unreleased\" -S CHANGELOG.md packages/flet/CHANGELOG.md sdk/python/packages/*/CHANGELOG.md`\n* If any changelog has an `Unreleased` section, convert that section into the new release section (`## {new_version}`), preserving and re-sorting its items. Do not leave duplicate release content in both `Unreleased` and `{new_version}`.\n  This conversion must be done for every matched changelog from the scan above.\n* Sort items in changelogs as follows, omitting empty sections:\n  * New features\n  * Improvements\n  * Breaking changes\n  * Deprecations\n  * Bug fixes\n  * Documentation\n  * Other changes (chore, refactor, etc.)\n  Put removals of previously deprecated APIs under `Breaking changes`, and\n  keep newly deprecated-but-still-working APIs under `Deprecations`.\n* Templates are in `sdk/python/templates/` and automatically packaged as zip artifacts with the GitHub Release. No manual branch creation in external repos is needed.\n",".agents/skills/implement-flet-extension/SKILL.md":"---\nname: implement-flet-extension\ndescription: Implement a new Flet extension/control that wraps a third-party Flutter package end-to-end, including dependency selection, version pinning, compatibility checks, Python/Flutter integration, docs, examples, tests, and CI updates. Use when adding any flet_* package backed by an external pub.dev package.\n---\n\nImplement a Flet extension around an external Flutter package using existing `flet_*` packages as implementation templates.\n\n## Inputs\n\n- Control/service name and Python package name (`flet_<extension>`).\n- Target pub.dev package and intended version/range.\n- API surface to expose in Python (properties, methods, events, types/enums).\n\n## Third-party Dependency Gate\n\n1. Confirm package health: maintenance activity, null-safety, platform support, and open issue risk.\n2. Confirm license is compatible with Flet distribution.\n3. Select a conservative version strategy:\n- Pin exact version when behavior stability is critical.\n- Use bounded ranges when required by ecosystem constraints.\n4. Record key constraints and reasons in PR notes/commit message.\n\n## Control/Service Classification\n\n- Classify wrapped functionality before implementation:\n1. `LayoutControl` for visual controls that participate in page/layout positioning.\n2. Base `Control` for simple visual controls that do not require page positioning or define their own positioning rules/props (for example `Draggable`, `Divider`, `MenuBar`, `NavigationRail`).\n3. Non-visual Service when functionality is not a renderable UI control.\n- Inspect the wrapped Flutter package API to determine whether it includes non-visual/service functionality.\n- For service patterns, follow existing extension examples: `sdk/python/packages/flet-audio`, `sdk/python/packages/flet-flashlight`, `sdk/python/packages/flet-secure-storage`.\n\n## API Mapping Rules\n\n- Expose only stable and useful features first; avoid mirroring every upstream option.\n- Keep Python API idiomatic and concise; avoid redundant control-name prefixes.\n- Map upstream naming inconsistencies to Flet conventions when needed.\n- Add custom enums/types only when they improve correctness and discoverability.\n\n## Python-side Rules\n\n- Use `LayoutControl`, base `Control`, or Service base class according to classification.\n- Implement typed properties, methods, and events exactly for chosen public API.\n- Reuse existing serialization/event patterns from sibling controls/services.\n\n## Flutter-side Rules\n\n- Use `parseEnum()` for enums — it's exported from `package:flet/flet.dart`. Call it as `parseEnum(MyEnum.values, widget.control.getString(\"attr\"), MyEnum.defaultVal)!`. Do NOT write a custom `_parseXxx()` switch helper.\n- For control attributes, prefer `widget.control.getBool()/getDouble()/...` accessors.\n- For non-control parsing, use shared `parseSomething()` helpers.\n- Do not add one-off private parser utilities when standard helpers exist.\n- Put control-specific helpers in `utils/<control>.dart`; shared helpers in `utils/<topic>.dart`.\n- Prefer `parse`-prefixed helper names when converting input to Flutter structures.\n- Avoid single-use local variables.\n\n### Default Value Matching (Critical)\n\nProperties with default values on the Python side are **not sent to Flutter** when unchanged from the default. Every Dart property read **must provide the same default** as its Python counterpart:\n\n- `control.getDouble(\"size\", 100.0)!` when Python has `size: float = 100.0`\n- `control.getBool(\"animate\", true)!` when Python has `animate: bool = True`\n- `parseDuration(value[\"dur\"], const Duration(milliseconds: 500))!` when Python has `dur: DurationValue = field(default_factory=lambda: Duration(milliseconds=500))`\n- `control.get<List>(\"items\")?.map(...).toList() ?? const []` when Python has `items: list[str] = field(default_factory=list)`\n\nWithout matching defaults, Dart receives `null` and either crashes or silently uses the wrong value. This applies to all property types: bools, numbers, strings, enums, durations, collections, and nested `@ft.value` types.\n\n## Integration Checklist\n\n- Register in the Flet client app — two files:\n  1. `client/pubspec.yaml`: add `flet_<ext>: path: ../sdk/python/packages/flet-<ext>/src/flutter/flet_<ext>` under `dependencies`.\n  2. `client/lib/main.dart`: add `import 'package:flet_<ext>/flet_<ext>.dart' as flet_<ext>;` and `flet_<ext>.Extension()` to the `extensions` list.\n- Add extension package to `sdk/python/pyproject.toml` in **two places**: the `dependencies` list and `[tool.uv.sources]` as `{ workspace = true }`.\n- Add extension to `sdk/python/packages/flet/pyproject.toml` in the `[dependency-groups] extensions` list.\n- Add extension to `sdk/python/examples/apps/flet_build_test/pyproject.toml` in **three places**: `[project] dependencies`, `[tool.uv.sources]` as `{ path = \"...\", editable = true }`, and `[tool.flet.dev_packages]` as a relative path string.\n- Add extension to `tools/crocodocs/pyproject.toml` under `[tool.crocodocs.packages]` as `<pkg_name> = \"../../sdk/python/packages/<pkg-dir>/src\"`. This fixes \"Missing API entry\" errors in the docs. Note: `api-data.json` is gitignored (generated at build time); only the `pyproject.toml` change needs committing.\n- Add extension to `.github/workflows/ci.yml` in both places:\n  - `build_flet_extensions` -> `PACKAGES` list.\n  - `py_publish` -> `for pkg in ...` publish loop.\n- Add `.gitignore` to Flutter extension project if missing.\n- Remove `[tool.uv.sources]` local path overrides from example `pyproject.toml` files before opening a PR (they are development-only conveniences).\n\n## Docs, Examples, Tests\n\n- Add control/service docs under `website/docs/controls/<name>` for controls and `website/docs/services/<name>` for services.\n- Always create one doc page per control, even for extensions with many similar controls. Use `index.md` for the overview (install instructions, examples, list of links) and individual `<controlname>.md` files for each control — consistent with `flet-color-pickers` and other extensions.\n- Use `<ClassSummary name=\"pkg.ClassName\" />` and `<ClassMembers name=\"pkg.ClassName\" />` JSX from `@site/src/components/crocodocs` to render API docs. Do NOT add `image=`, `imageCaption=`, or `imageWidth=` props to `<ClassSummary>` when no screenshots exist yet.\n- In the `## Examples` section, do NOT add `###` subtitles above `<CodeExample>` blocks — titles are injected automatically from the example file itself.\n- Add all custom enums/types docs and update `website/sidebars.yml` navigation.\n- Use markdown filenames without underscores (`codeeditor.md`, not `code_editor.md`).\n- Add examples under `sdk/python/examples/extensions/<name>/` for extension controls.\n- Use `import flet_<ext> as <short_alias>` in examples (e.g., `import flet_spinkit as spins`). Keep alias short but readable.\n- Use `ft.Colors.SURFACE_CONTAINER_HIGHEST` for card/cell backgrounds in showcase examples — it adapts to light and dark system themes automatically.\n- Do NOT set an explicit dark theme in examples; let the app use system theme (no `page.theme_mode`).\n- Add integration tests under `packages/flet/integration_tests/extensions/<name>/` — **not** inside the extension package's own directory (no `tests/` folder in the package itself, matching the pattern of `flet-code-editor`, `flet-color-pickers`, etc.).\n- For controls with continuously-running animations, do NOT use `assert_control_screenshot` or `pump_and_settle` — they will timeout waiting for animations to settle. Instead use `await flet_app.tester.pump(duration=ft.Duration(milliseconds=500))` which advances the clock by a fixed amount. This still runs real Flutter rendering and catches crashes, without screenshot comparison.\n- Ensure generated screenshots are suitable for docs usage when visual examples are added.\n\n## Upgrade and Compatibility Guardrails\n\n- Add at least one test that catches upstream behavioral changes likely to break wrapper mapping.\n- Avoid exposing experimental upstream APIs unless explicitly requested.\n- Keep wrapper surface narrow enough to maintain backwards compatibility across upstream updates.\n\n## Validation\n\n- Run relevant Python and integration tests for touched areas.\n- Verify Python import paths, client runtime registration, and docs navigation.\n- Verify dependency resolution and lockfile updates are intentional.\n",".agents/skills/imperative-to-declarative-flet/SKILL.md":"---\nname: imperative-to-declarative-flet\ndescription: Convert an imperative Flet Python app in which controls are mutated and then page.update is called to declarative style using flet.component, flet.observable and state hooks.\nmetadata:\n  short-description: Port Flet app to declarative\n---\n\n# Imperative → Declarative (Flet Python)\n\nPort an existing imperative Flet app to “components mode” with `@ft.component`, hooks, and (optionally) `@ft.observable` models.\n\n## Outcomes\n\n- Original folder unchanged; new sibling folder created.\n- Entry point uses `page.render(App)` (components mode).\n- UI is derived from state; minimal/zero manual `page.update()` for normal UI updates.\n\n## Choose a state strategy\n\n- **Use `@ft.observable`** for nested app data you mutate in place (boards/lists/cards, drag+drop reorder).\n- **Use `ft.use_state`** for local ephemeral UI state (hover flags, input text, dialog selection).\n- Avoid storing live `Control`/component objects in state; store ids/enums and create controls during render.\n\n## Workflow\n\n### 1) Create a new declarative copy\n\n- Copy the existing app folder to a new one (e.g. `trolli` → `trolli-declarative-*`).\n- Keep `assets/` with the new folder.\n\n### 2) Switch to components mode entrypoint\n\n- Create a root component `@ft.component def App(): ...`.\n- Run with:\n  - `ft.run(lambda page: page.render(App), assets_dir=...)`\n- Set page globals either:\n  - in a `main(page)` function before `page.render(App)`, or\n  - in `ft.on_mounted(...)` (works, but ordering can be less obvious).\n\n### 3) Centralize routing in `App`\n\n- Keep `app.route: str` as source of truth.\n- In one place, define:\n  - `route_change(e)` to normalize/redirect/validate routes and set `app.route`\n  - a render-time `match app.route` (or a derived `active_screen`) to pick `content`\n- Prefer: `route_change` mutates route state; `App()` render chooses UI based on that state.\n\n### 4) Componentize UI\n\n- Move UI chunks into `src/components/*.py`.\n- Each component:\n  - takes only the model(s) it needs\n  - uses hooks for local UI state\n  - mutates observable models for app data changes\n\n### 5) Dialogs: reduce `page.update()` usage\n\nIf a dialog mutates existing controls and calls `page.update()`, convert it to:\n\n- `@ft.component` dialog content with `ft.use_state` for `error`, `selected_color`, etc.\n- event handlers call setters (no explicit updates)\n- show it via `page.show_dialog(ft.AlertDialog(content=DialogContent(...)))`\n\n### 6) Assets/fonts checklist\n\n- Prefer an absolute `assets_dir` derived from `__file__`.\n- If running via `flet run`, be aware it can set `FLET_ASSETS_DIR` and override `assets_dir=`.\n- Font registration uses the dict key as the font family name:\n  - `page.fonts = {\"Pacifico\": \"Pacifico-Regular.ttf\"}`\n  - use `font_family=\"Pacifico\"`.\n\n## Common pitfalls (and fixes)\n\n- **Event handler typing is invariant** (`Event[Sub]` ≠ `Event[Base]`):\n  - If `on_click` is declared on `Button`, annotate `e` as `ft.Event[ft.Button]` (or use `def handler(): ...`).\n- **`TemplateRoute` params are dynamic**:\n  - `raw = getattr(troute, \"id\", None)` then `isinstance(raw, str)` before `int(raw)`.\n- **`controls=[*[...], ...]` can confuse type checkers** with components:\n  - build lists in two steps and annotate/cast, or return raw controls from non-component factories.\n",".agents/skills/run-unit-tests/SKILL.md":"---\nname: run-unit-tests\ndescription: Use when asked to run unit tests.\n---\n\nThis skill is used to run unit tests of the Python part of Flet framework.\n\n## Instructions\n\nRun the following command to run `flet` package unit tests:\n\n```\nuv run --group test pytest packages/flet/tests\n```\n\nThe directory in that commend is relative to `{root}/sdk/python`.\n",".agents/skills/run-integration-tests/SKILL.md":"---\nname: run-integration-tests\ndescription: Use when asked to run integration tests.\n---\n\n## Instructions\n\nIntegration tests are in `sdk/python/packages/flet/integration_tests` directory.\n\nRead `sdk/python/packages/flet/integration_tests/README.md` for further instructions.\n",".agents/skills/test-flet-apps-dev/SKILL.md":"# test-flet-apps-dev\n\nPath: `.agents/skills/test-flet-apps-dev/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/test-flet-apps-dev/SKILL.md)",".agents/skills/update-flet-control-doc-gifs/SKILL.md":"# update-flet-control-doc-gifs\n\nPath: `.agents/skills/update-flet-control-doc-gifs/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/update-flet-control-doc-gifs/SKILL.md)",".agents/skills/write-changelog-entry/SKILL.md":"# write-changelog-entry\n\nPath: `.agents/skills/write-changelog-entry/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/write-changelog-entry/SKILL.md)","website/.agents/skills/flet-release-announcement/SKILL.md":"# flet-release-announcement\n\nPath: `website/.agents/skills/flet-release-announcement/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/website/.agents/skills/flet-release-announcement/SKILL.md)","AGENTS.md":"# AI Agent Protocol & Instructions\n\nPath: `AGENTS.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/AGENTS.md)","CLAUDE.md":"# Claude Agent Guidelines & System Prompt\n\nPath: `CLAUDE.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/CLAUDE.md)","packages/flet/CHANGELOG.md":"# Flet Skill\n\nPath: `packages/flet/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/CHANGELOG.md)","packages/flet/README.md":"# flet Documentation\n\nPath: `packages/flet/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/README.md)","packages/flet/analysis_options.yaml":"# Flet Skill\n\nPath: `packages/flet/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/analysis_options.yaml)","packages/flet/pubspec.yaml":"# Flet Skill\n\nPath: `packages/flet/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/pubspec.yaml)","packages/flet_integration_test/analysis_options.yaml":"# Flet_integration_test Skill\n\nPath: `packages/flet_integration_test/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet_integration_test/analysis_options.yaml)","packages/flet_integration_test/pubspec.yaml":"# Flet_integration_test Skill\n\nPath: `packages/flet_integration_test/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet_integration_test/pubspec.yaml)","tools/crocodocs/README.md":"# crocodocs Documentation\n\nPath: `tools/crocodocs/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/tools/crocodocs/README.md)","sdk/python/packages/flet-ads/CHANGELOG.md":"# Flet-ads Skill\n\nPath: `sdk/python/packages/flet-ads/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/CHANGELOG.md)","sdk/python/packages/flet-ads/README.md":"# flet-ads Documentation\n\nPath: `sdk/python/packages/flet-ads/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/README.md)","sdk/python/packages/flet-audio-recorder/CHANGELOG.md":"# Flet-audio-recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/CHANGELOG.md)","sdk/python/packages/flet-audio-recorder/README.md":"# flet-audio-recorder Documentation\n\nPath: `sdk/python/packages/flet-audio-recorder/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/README.md)","sdk/python/packages/flet-audio/CHANGELOG.md":"# Flet-audio Skill\n\nPath: `sdk/python/packages/flet-audio/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/CHANGELOG.md)","sdk/python/packages/flet-audio/README.md":"# flet-audio Documentation\n\nPath: `sdk/python/packages/flet-audio/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/README.md)","sdk/python/packages/flet-camera/README.md":"# flet-camera Documentation\n\nPath: `sdk/python/packages/flet-camera/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-camera/README.md)","sdk/python/packages/flet-charts/CHANGELOG.md":"# Flet-charts Skill\n\nPath: `sdk/python/packages/flet-charts/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/CHANGELOG.md)","sdk/python/packages/flet-charts/README.md":"# flet-charts Documentation\n\nPath: `sdk/python/packages/flet-charts/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/README.md)","sdk/python/packages/flet-cli/README.md":"# flet-cli Documentation\n\nPath: `sdk/python/packages/flet-cli/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-cli/README.md)","sdk/python/packages/flet-code-editor/CHANGELOG.md":"# Flet-code-editor Skill\n\nPath: `sdk/python/packages/flet-code-editor/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/CHANGELOG.md)","sdk/python/packages/flet-code-editor/README.md":"# flet-code-editor Documentation\n\nPath: `sdk/python/packages/flet-code-editor/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/README.md)","sdk/python/packages/flet-color-pickers/CHANGELOG.md":"# Flet-color-pickers Skill\n\nPath: `sdk/python/packages/flet-color-pickers/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/CHANGELOG.md)","sdk/python/packages/flet-color-pickers/README.md":"# flet-color-pickers Documentation\n\nPath: `sdk/python/packages/flet-color-pickers/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/README.md)","sdk/python/packages/flet-datatable2/CHANGELOG.md":"# Flet-datatable2 Skill\n\nPath: `sdk/python/packages/flet-datatable2/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-datatable2/CHANGELOG.md)","sdk/python/packages/flet-datatable2/README.md":"# flet-datatable2 Documentation\n\nPath: `sdk/python/packages/flet-datatable2/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-datatable2/README.md)","sdk/python/packages/flet-desktop/README.md":"# flet-desktop Documentation\n\nPath: `sdk/python/packages/flet-desktop/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-desktop/README.md)","sdk/python/packages/flet-flashlight/CHANGELOG.md":"# Flet-flashlight Skill\n\nPath: `sdk/python/packages/flet-flashlight/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/CHANGELOG.md)","sdk/python/packages/flet-flashlight/README.md":"# flet-flashlight Documentation\n\nPath: `sdk/python/packages/flet-flashlight/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/README.md)","sdk/python/packages/flet-geolocator/CHANGELOG.md":"# Flet-geolocator Skill\n\nPath: `sdk/python/packages/flet-geolocator/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/CHANGELOG.md)","sdk/python/packages/flet-geolocator/README.md":"# flet-geolocator Documentation\n\nPath: `sdk/python/packages/flet-geolocator/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/README.md)","sdk/python/packages/flet-local-auth/README.md":"# flet-local-auth Documentation\n\nPath: `sdk/python/packages/flet-local-auth/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-local-auth/README.md)","sdk/python/packages/flet-lottie/CHANGELOG.md":"# Flet-lottie Skill\n\nPath: `sdk/python/packages/flet-lottie/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/CHANGELOG.md)","sdk/python/packages/flet-lottie/README.md":"# flet-lottie Documentation\n\nPath: `sdk/python/packages/flet-lottie/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/README.md)","sdk/python/packages/flet-map/CHANGELOG.md":"# Flet-map Skill\n\nPath: `sdk/python/packages/flet-map/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/CHANGELOG.md)","sdk/python/packages/flet-map/README.md":"# flet-map Documentation\n\nPath: `sdk/python/packages/flet-map/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/README.md)","sdk/python/packages/flet-mcp/README.md":"# flet-mcp Documentation\n\nPath: `sdk/python/packages/flet-mcp/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-mcp/README.md)","sdk/python/packages/flet-permission-handler/CHANGELOG.md":"# Flet-permission-handler Skill\n\nPath: `sdk/python/packages/flet-permission-handler/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/CHANGELOG.md)","sdk/python/packages/flet-permission-handler/README.md":"# flet-permission-handler Documentation\n\nPath: `sdk/python/packages/flet-permission-handler/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/README.md)","sdk/python/packages/flet-platform-assets/README.md":"# flet-platform-assets Documentation\n\nPath: `sdk/python/packages/flet-platform-assets/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-platform-assets/README.md)","sdk/python/packages/flet-rive/CHANGELOG.md":"# Flet-rive Skill\n\nPath: `sdk/python/packages/flet-rive/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/CHANGELOG.md)","sdk/python/packages/flet-rive/README.md":"# flet-rive Documentation\n\nPath: `sdk/python/packages/flet-rive/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/README.md)","sdk/python/packages/flet-secure-storage/README.md":"# flet-secure-storage Documentation\n\nPath: `sdk/python/packages/flet-secure-storage/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-secure-storage/README.md)","sdk/python/packages/flet-spinkit/CHANGELOG.md":"# Flet-spinkit Skill\n\nPath: `sdk/python/packages/flet-spinkit/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/CHANGELOG.md)","sdk/python/packages/flet-spinkit/README.md":"# flet-spinkit Documentation\n\nPath: `sdk/python/packages/flet-spinkit/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/README.md)","sdk/python/packages/flet-video/CHANGELOG.md":"# Flet-video Skill\n\nPath: `sdk/python/packages/flet-video/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/CHANGELOG.md)","sdk/python/packages/flet-video/README.md":"# flet-video Documentation\n\nPath: `sdk/python/packages/flet-video/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/README.md)","sdk/python/packages/flet-web/README.md":"# flet-web Documentation\n\nPath: `sdk/python/packages/flet-web/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-web/README.md)","sdk/python/packages/flet-webview/CHANGELOG.md":"# Flet-webview Skill\n\nPath: `sdk/python/packages/flet-webview/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/CHANGELOG.md)","sdk/python/packages/flet-webview/README.md":"# flet-webview Documentation\n\nPath: `sdk/python/packages/flet-webview/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/README.md)","sdk/python/packages/flet/README.md":"# flet Documentation\n\nPath: `sdk/python/packages/flet/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/README.md)","sdk/python/packages/flet/integration_tests/README.md":"# integration_tests Documentation\n\nPath: `sdk/python/packages/flet/integration_tests/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/integration_tests/README.md)","sdk/python/examples/extensions/lottie/lottie_animations/assets/sample.json":"# Assets Skill\n\nPath: `sdk/python/examples/extensions/lottie/lottie_animations/assets/sample.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/examples/extensions/lottie/lottie_animations/assets/sample.json)","sdk/python/packages/flet-ads/src/flutter/flet_ads/analysis_options.yaml":"# Flet_ads Skill\n\nPath: `sdk/python/packages/flet-ads/src/flutter/flet_ads/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/src/flutter/flet_ads/analysis_options.yaml)","sdk/python/packages/flet-ads/src/flutter/flet_ads/pubspec.yaml":"# Flet_ads Skill\n\nPath: `sdk/python/packages/flet-ads/src/flutter/flet_ads/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/src/flutter/flet_ads/pubspec.yaml)","sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/CHANGELOG.md":"# Flet_audio_recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/CHANGELOG.md)","sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/README.md":"# flet_audio_recorder Documentation\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/README.md)","sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/analysis_options.yaml":"# Flet_audio_recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/analysis_options.yaml)","sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/pubspec.yaml":"# Flet_audio_recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/pubspec.yaml)","sdk/python/packages/flet-audio/src/flutter/flet_audio/analysis_options.yaml":"# Flet_audio Skill\n\nPath: `sdk/python/packages/flet-audio/src/flutter/flet_audio/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/src/flutter/flet_audio/analysis_options.yaml)","sdk/python/packages/flet-audio/src/flutter/flet_audio/pubspec.yaml":"# Flet_audio Skill\n\nPath: `sdk/python/packages/flet-audio/src/flutter/flet_audio/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/src/flutter/flet_audio/pubspec.yaml)","sdk/python/packages/flet-camera/src/flutter/flet_camera/analysis_options.yaml":"# Flet_camera Skill\n\nPath: `sdk/python/packages/flet-camera/src/flutter/flet_camera/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-camera/src/flutter/flet_camera/analysis_options.yaml)","sdk/python/packages/flet-camera/src/flutter/flet_camera/pubspec.yaml":"# Flet_camera Skill\n\nPath: `sdk/python/packages/flet-camera/src/flutter/flet_camera/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-camera/src/flutter/flet_camera/pubspec.yaml)","sdk/python/packages/flet-charts/src/flutter/flet_charts/CHANGELOG.md":"# Flet_charts Skill\n\nPath: `sdk/python/packages/flet-charts/src/flutter/flet_charts/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/src/flutter/flet_charts/CHANGELOG.md)","sdk/python/packages/flet-charts/src/flutter/flet_charts/analysis_options.yaml":"# Flet_charts Skill\n\nPath: `sdk/python/packages/flet-charts/src/flutter/flet_charts/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/src/flutter/flet_charts/analysis_options.yaml)","sdk/python/packages/flet-charts/src/flutter/flet_charts/pubspec.yaml":"# Flet_charts Skill\n\nPath: `sdk/python/packages/flet-charts/src/flutter/flet_charts/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/src/flutter/flet_charts/pubspec.yaml)","sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/analysis_options.yaml":"# Flet_code_editor Skill\n\nPath: `sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/analysis_options.yaml)","sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/pubspec.yaml":"# Flet_code_editor Skill\n\nPath: `sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/pubspec.yaml)","sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/analysis_options.yaml":"# Flet_color_pickers Skill\n\nPath: `sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/analysis_options.yaml)","sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/pubspec.yaml":"# Flet_color_pickers Skill\n\nPath: `sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/pubspec.yaml)","sdk/python/packages/flet-datatable2/src/flutter/flet_datatable2/pubspec.yaml":"# Flet_datatable2 Skill\n\nPath: `sdk/python/packages/flet-datatable2/src/flutter/flet_datatable2/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-datatable2/src/flutter/flet_datatable2/pubspec.yaml)","sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/analysis_options.yaml":"# Flet_flashlight Skill\n\nPath: `sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/analysis_options.yaml)","sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/pubspec.yaml":"# Flet_flashlight Skill\n\nPath: `sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/pubspec.yaml)","sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/analysis_options.yaml":"# Flet_geolocator Skill\n\nPath: `sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/analysis_options.yaml)","sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/pubspec.yaml":"# Flet_geolocator Skill\n\nPath: `sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/pubspec.yaml)","sdk/python/packages/flet-local-auth/src/flutter/flet_local_auth/pubspec.yaml":"# Flet_local_auth Skill\n\nPath: `sdk/python/packages/flet-local-auth/src/flutter/flet_local_auth/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-local-auth/src/flutter/flet_local_auth/pubspec.yaml)","sdk/python/packages/flet-lottie/src/flutter/flet_lottie/analysis_options.yaml":"# Flet_lottie Skill\n\nPath: `sdk/python/packages/flet-lottie/src/flutter/flet_lottie/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/src/flutter/flet_lottie/analysis_options.yaml)","sdk/python/packages/flet-lottie/src/flutter/flet_lottie/pubspec.yaml":"# Flet_lottie Skill\n\nPath: `sdk/python/packages/flet-lottie/src/flutter/flet_lottie/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/src/flutter/flet_lottie/pubspec.yaml)","sdk/python/packages/flet-map/src/flutter/flet_map/analysis_options.yaml":"# Flet_map Skill\n\nPath: `sdk/python/packages/flet-map/src/flutter/flet_map/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/src/flutter/flet_map/analysis_options.yaml)","sdk/python/packages/flet-map/src/flutter/flet_map/pubspec.yaml":"# Flet_map Skill\n\nPath: `sdk/python/packages/flet-map/src/flutter/flet_map/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/src/flutter/flet_map/pubspec.yaml)","sdk/python/packages/flet-mcp/src/flet_mcp/data/icons.json":"# Data Skill\n\nPath: `sdk/python/packages/flet-mcp/src/flet_mcp/data/icons.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-mcp/src/flet_mcp/data/icons.json)","sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/analysis_options.yaml":"# Flet_permission_handler Skill\n\nPath: `sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/analysis_options.yaml)","sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/pubspec.yaml":"# Flet_permission_handler Skill\n\nPath: `sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/pubspec.yaml)","sdk/python/packages/flet-rive/src/flutter/flet_rive/analysis_options.yaml":"# Flet_rive Skill\n\nPath: `sdk/python/packages/flet-rive/src/flutter/flet_rive/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/src/flutter/flet_rive/analysis_options.yaml)","sdk/python/packages/flet-rive/src/flutter/flet_rive/pubspec.yaml":"# Flet_rive Skill\n\nPath: `sdk/python/packages/flet-rive/src/flutter/flet_rive/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/src/flutter/flet_rive/pubspec.yaml)","sdk/python/packages/flet-secure-storage/src/flutter/flet_secure_storage/pubspec.yaml":"# Flet_secure_storage Skill\n\nPath: `sdk/python/packages/flet-secure-storage/src/flutter/flet_secure_storage/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-secure-storage/src/flutter/flet_secure_storage/pubspec.yaml)","sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/analysis_options.yaml":"# Flet_spinkit Skill\n\nPath: `sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/analysis_options.yaml)","sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/pubspec.yaml":"# Flet_spinkit Skill\n\nPath: `sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/pubspec.yaml)","sdk/python/packages/flet-video/src/flutter/flet_video/analysis_options.yaml":"# Flet_video Skill\n\nPath: `sdk/python/packages/flet-video/src/flutter/flet_video/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/src/flutter/flet_video/analysis_options.yaml)","sdk/python/packages/flet-video/src/flutter/flet_video/pubspec.yaml":"# Flet_video Skill\n\nPath: `sdk/python/packages/flet-video/src/flutter/flet_video/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/src/flutter/flet_video/pubspec.yaml)","sdk/python/packages/flet-web/src/flet_web/fastapi/README.md":"# fastapi Documentation\n\nPath: `sdk/python/packages/flet-web/src/flet_web/fastapi/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-web/src/flet_web/fastapi/README.md)","sdk/python/packages/flet-webview/src/flutter/flet_webview/analysis_options.yaml":"# Flet_webview Skill\n\nPath: `sdk/python/packages/flet-webview/src/flutter/flet_webview/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/src/flutter/flet_webview/analysis_options.yaml)","sdk/python/packages/flet-webview/src/flutter/flet_webview/pubspec.yaml":"# Flet_webview Skill\n\nPath: `sdk/python/packages/flet-webview/src/flutter/flet_webview/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/src/flutter/flet_webview/pubspec.yaml)","sdk/python/packages/flet/src/flet/controls/cupertino/cupertino_icons.json":"# Cupertino Skill\n\nPath: `sdk/python/packages/flet/src/flet/controls/cupertino/cupertino_icons.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/src/flet/controls/cupertino/cupertino_icons.json)","sdk/python/packages/flet/src/flet/controls/material/icons.json":"# Material Skill\n\nPath: `sdk/python/packages/flet/src/flet/controls/material/icons.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/src/flet/controls/material/icons.json)"},"items":[{"name":"AGENTS.md","path":"AGENTS.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/AGENTS.md","title":"AI Agent Protocol & Instructions","category":"root-instruction","format":"markdown","content":"# AI Agent Protocol & Instructions\n\nPath: `AGENTS.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/AGENTS.md)","tokens":300,"sizeBytes":147},{"name":"SKILL.md","path":".agents/skills/create-flet-control-integration-tests/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/create-flet-control-integration-tests/SKILL.md","title":"create-flet-control-integration-tests","category":"anthropic-skill","format":"markdown","content":"---\nname: create-flet-control-integration-tests\ndescription: Use when asked to create or update integration tests for any Flet control in sdk/python/packages/flet/integration_tests, including visual goldens and interactive behavior tests.\n---\n\n## When to use\n\nUse this skill when adding, updating, or reviewing integration tests for a Flet control (core, material, cupertino, theme, services, types, or examples).\n\nUse it for:\n\n- visual rendering checks with golden screenshots\n- interaction checks (hover, click, input, keyboard)\n- control property behavior checks\n- regression tests for control bugs\n\n## Test placement\n\nPick the closest existing suite first:\n\n- Core controls: `sdk/python/packages/flet/integration_tests/controls/core`\n- Material controls: `sdk/python/packages/flet/integration_tests/controls/material`\n- Cupertino controls: `sdk/python/packages/flet/integration_tests/controls/cupertino`\n- Theme tests: `sdk/python/packages/flet/integration_tests/controls/theme`\n- Type helpers: `sdk/python/packages/flet/integration_tests/controls/types`\n- Services: `sdk/python/packages/flet/integration_tests/controls/services`\n- Examples: `sdk/python/packages/flet/integration_tests/examples`\n\nPrefer adding tests to an existing file for the same control. Create a new test file only when no suitable file exists.\n\n### Scope split rule (required)\n\nDo not mix `loop_scope=\"module\"` and `loop_scope=\"function\"` tests in the same file.\n\nNaming convention:\n\n- `test_<control>.py` for module-scoped visual/stable tests (uses `flet_app`)\n- `test_<control>_isolated.py` for function-scoped tests that require a fresh app per test (uses `flet_app_function`)\n\n## Fixture choice\n\nUse fixtures from `integration_tests/conftest.py`:\n\n- `flet_app` (`loop_scope=\"module\"`): best for stable visual tests and bulk screenshot tests.\n- `flet_app_function` (`loop_scope=\"function\"`): best for tests that mutate state and must run in a separate app each.\n\n## Authoring workflow\n\n1. Identify behavior to verify.\n2. Build deterministic layout/state:\n- set `theme_mode` explicitly when visuals matter\n- set fixed sizes/padding/spacing\n- avoid random or time-varying content\n3. Choose file by scope rule before writing tests.\n4. Write test using async pytest.\n5. Use screenshot assertion for UI behavior, functional assertion for non-visual behavior.\n6. Name test so `request.node.name` can be used as screenshot key.\n7. Run target test file.\n8. If expected visuals changed, regenerate goldens with `FLET_TEST_GOLDEN=1` and re-run without golden mode.\n\n## Assertion patterns\n\n### Visual control assertion\n\n```python\nawait flet_app.assert_control_screenshot(\n    request.node.name,\n    control,\n)\n```\n\n### Visual full-page assertion\n\n```python\nflet_app_function.assert_screenshot(\n    request.node.name,\n    await flet_app_function.page.take_screenshot(\n        pixel_ratio=flet_app_function.screenshots_pixel_ratio\n    ),\n)\n```\n\n### Functional assertion\n\n```python\nfinder = await flet_app_function.tester.find_by_tooltip(\"Info tooltip\")\nassert finder.count == 1\n```\n\n## Minimal templates\n\n### Template: module-scope file (`test_<control>.py`)\n\n```python\nimport pytest\n\nimport flet as ft\nimport flet.testing as ftt\n\n\n@pytest.mark.asyncio(loop_scope=\"module\")\nasync def test_<behavior>(flet_app: ftt.FletTestApp, request):\n    flet_app.page.theme_mode = ft.ThemeMode.LIGHT\n    await flet_app.assert_control_screenshot(\n        request.node.name,\n        ft.Container(width=240, height=80, alignment=ft.Alignment.CENTER),\n    )\n```\n\n### Template: function-scope file (`test_<control>_isolated.py`)\n\n```python\nimport pytest\n\nimport flet as ft\nimport flet.testing as ftt\n\n\n@pytest.mark.asyncio(loop_scope=\"function\")\nasync def test_<behavior>(flet_app_function: ftt.FletTestApp):\n    flet_app_function.page.add(ft.IconButton(icon=ft.Icons.INFO, tooltip=\"Info\"))\n    await flet_app_function.tester.pump_and_settle()\n\n    finder = await flet_app_function.tester.find_by_tooltip(\"Info\")\n    assert finder.count == 1\n```\n\n## Run commands\n\nRun one test file:\n\n```bash\nuv run pytest -s -o log_cli=true -o log_cli_level=INFO packages/flet/integration_tests/controls/core/test_control.py\n```\n\nRun a subset:\n\n```bash\nuv run pytest -s -o log_cli=true -o log_cli_level=INFO packages/flet/integration_tests/controls/core/test_control.py -k test_visible\n```\n\nGenerate or update goldens:\n\n```bash\nFLET_TEST_GOLDEN=1 uv run pytest -s -o log_cli=true -o log_cli_level=INFO packages/flet/integration_tests/controls/core/test_control.py\n```\n\n## Quality checklist\n\n- Test file location matches control area.\n- `module` and `function` scope tests are in separate files.\n- Function-scoped files use the `test_<control>_isolated.py` naming convention.\n- Fixture scope matches test intent.\n- Screenshot keys are stable (`request.node.name` preferred).\n- Visual tests are deterministic (theme/size/content).\n- Goldens are updated only for intentional visual changes.\n- No unrelated formatting or refactors in the same change.\n\n## References\n\n- `sdk/python/packages/flet/integration_tests/README.md`\n- `sdk/python/packages/flet/integration_tests/conftest.py`\n- `sdk/python/packages/flet/integration_tests/controls/core/test_control.py`\n- `sdk/python/packages/flet/integration_tests/controls/core/test_control_isolated.py`\n- `sdk/python/packages/flet/integration_tests/controls/core/test_layout_control.py`\n- `sdk/python/packages/flet/integration_tests/examples/core/test_control.py`\n- `sdk/python/examples/controls/control`\n","frontmatter":{"name":"create-flet-control-integration-tests","description":"Use when asked to create or update integration tests for any Flet control in sdk/python/packages/flet/integration_tests, including visual goldens and interactive behavior tests."},"isInternal":false,"tokens":1269,"sizeBytes":5477},{"name":"SKILL.md","path":".agents/skills/create-flet-example-projects/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/create-flet-example-projects/SKILL.md","title":"create-flet-example-projects","category":"anthropic-skill","format":"markdown","content":"---\nname: create-flet-example-projects\ndescription: Use when asked to create Flet example projects from flat .py files with main.py and pyproject.toml metadata for Gallery/MCP indexing.\n---\n\n## When to use\n\nUse this skill when a user asks to:\n- create one control/example folder (for example `examples/controls/chip`) in the project-per-example format\n- migrate existing flat examples to the project-per-example format\n- normalize a partially converted folder so all examples follow the same structure\n\n## Goal\n\nEnsure each runnable example is a standalone project containing:\n\n- `main.py`\n- `pyproject.toml` with Gallery/MCP metadata\n- `assets/` (if the example uses local assets)\n\n## Workflow\n\n1. Inspect source folder.\n- Detect current state per example:\n  - flat file: `foo.py`\n  - project folder: `foo/main.py`\n  - mixed/partial conversion: both styles present or missing metadata files\n- Find candidate flat modules: `*.py` in the target folder (exclude helper files such as `__init__.py`).\n- Keep existing `media/` unless an example needs local assets copied into its own `assets/`.\n\n2. Convert or normalize examples.\n- For `foo.py`, create `foo/` and move file to `foo/main.py`.\n- If `foo/main.py` already exists, keep it and do not recreate/move files.\n- If folder exists but `main.py` is missing, repair structure only when there is a clear source file.\n- Do not create `foo/__init__.py`; import example modules directly in tests/docs (for example `import examples.controls.foo.bar.main as bar` or `import examples.controls.foo.bar as bar` when using namespace-package imports).\n- When a control folder has been fully converted to project-per-example layout, delete the control-level `examples/controls/<control>/__init__.py` too. The converted folders should behave like namespace packages, matching prior migrations such as commit `7e65ad566`.\n\n3. Add `pyproject.toml` for each example project.\n- Infer from path and code.\n- Create missing `pyproject.toml` files for existing project folders.\n- Update obviously stale metadata when migrating existing examples (for example wrong title/description/categories).\n- Verify platform support before adding or omitting `[tool.flet].platforms`:\n  - Check the local implementation and docs for explicit platform guards, support tables, or platform-specific exceptions.\n  - If support is limited, add `[tool.flet].platforms` with only the supported platforms.\n  - If support is broad/all-platform, omit `[tool.flet].platforms`.\n- Required fields:\n  - `[project]`: `name`, `version`, `description`, `requires-python`, `keywords`, `authors`, `dependencies`\n  - `[dependency-groups].dev`: include `flet-cli`, `flet-desktop`, `flet-web`\n  - `[tool.flet.gallery].categories`\n  - `[tool.flet.metadata]`: `title`, `controls`, `layout_pattern`, `complexity`, `features`\n  - `[tool.flet]`: `org`, `company`, `copyright`\n- Add `[tool.flet].platforms` only when the example is platform-limited.\n- Add permissions blocks only when code actually needs them.\n\n4. Infer metadata.\n- Title: readable version of file/folder intent.\n- Short description: one line of what the example demonstrates.\n- `[project].description` must be meaningful and example-specific; avoid generic placeholders like \"Example N\" or \"<name> example for <control>\".\n- Description should mention the concrete behavior or interaction shown (for example: hover highlight, live updates, custom axes, event handling).\n- Categories: typically control-based, e.g. `Input/Chip`, plus optional `Apps/Basic controls`.\n- Tags: from control/topic/behavior words.\n- Controls used: list key controls from code.\n- Layout pattern: choose closest practical value (e.g. `filter-bar`, `inline-actions`, `dashboard`, `list-detail`).\n- Complexity: `basic` unless logic/state/architecture is non-trivial.\n- Features: notable behaviors only (click handling, selection, async loading, drag-and-drop, etc.).\n- If an example supports exporting or downloading output, include `\"save to file\"` in `[tool.flet.metadata].features`.\n- If an example module contains `async def` handlers or async control flow, append `\"async\"` to `keywords`.\n\n\n5. Infer dependencies from imports.\n- Always include `flet` for standard examples.\n- Include extra packages if imported (for example extension packages).\n- Do not add unused dependencies.\n\n6. Make examples mobile-safe.\n- If `ft.context.disable_auto_update()` is not used, do not add explicit `page.update()` unless strictly necessary.\n- Apply this `page.update()` rule to all examples in the touched folder (new, migrated, and already converted).\n- Wrap app content in `ft.SafeArea` so example renders correctly on mobile.\n- Add `expand=True` to `ft.SafeArea` only when needed for correct layout/sizing (for example to avoid Infinity/NaN sizing issues), and avoid adding it when not necessary.\n- When converting legacy `page.add(a, b, ...)` style examples, wrap the controls in `ft.Column(controls=[...])` inside `ft.SafeArea(content=...)` rather than `ft.Row`, unless the original code explicitly used a row layout.\n\n- Apply this to all examples in the touched folder (new, migrated, and already converted), not only files changed by moves.\n- During validation, confirm every `<example>/main.py` in scope includes a top-level `ft.SafeArea` around rendered content.\n- For declarative examples using `@ft.component`, do not pass component instances as regular control children (for example `SafeArea(content=App())`) because this can raise runtime attribute errors.\n- In declarative examples, ensure the component itself returns regular controls (including `SafeArea` when needed) and render it at page level with `page.render(App)` in `main()`.\n\n7. Prefer `@ft.control` for custom controls in examples.\n- If an example defines a custom control class inheriting from a Flet control (for example `class MyThing(ft.Column)`), prefer `@ft.control` style.\n- Move constructor-style setup to declarative fields + `init()` where practical.\n- Keep behavior unchanged and avoid refactors that alter public usage unless needed for compatibility.\n\n8. Remove deprecated Material 3 toggle usage.\n- If `use_material3` appears in example code, remove it and simplify the example to current API usage.\n- Remove related Material 3 toggle logic/UI that exists only to switch `use_material3`.\n- Update example metadata (`pyproject.toml`) to remove stale Material 3 references when code is changed.\n\n9. Ensure runnable entrypoint.\n- Every example `main.py` should end with:\n  - `if __name__ == \"__main__\":`\n  - `    ft.run(main)`\n- Apply this to all examples in the touched folder (new, migrated, and already converted).\n\n10. Update references.\n- Docs code includes: change from `.../example.py` to `.../example/main.py`.\n- Inspect the relevant docs pages for each touched control/service/example area (for example `sdk/python/packages/flet/docs/controls/<control>.md`) and update any `--8<--` includes or direct file-path references to the new `main.py` path.\n- Tests/imports: use direct module imports and avoid relying on package-level `__init__.py` re-exports.\n- For already-converted examples, only update references that are stale; avoid unnecessary churn.\n- If removing a control-level `__init__.py`, confirm no remaining imports rely on `from examples.controls.<control> import ...`.\n\n11. Validate.\n- Run `python -m compileall` on changed `main.py` files.\n- Run `uv run ruff check` on changed example files and fix violations until it passes (respecting repository `pyproject.toml` under `[tool.ruff]`).\n- Search for stale paths to old flat files.\n- Search docs and package sources for stale references to the migrated flat example paths and fix any hits in scope.\n- Check `git status` to confirm expected moves and edits.\n- When integration tests exist for the touched control, run the targeted test file(s).\n- Confirm all in-scope `main.py` files include both top-level `ft.SafeArea` wrapping and the `if __name__ == \"__main__\": ft.run(main)` entrypoint.\n- Confirm in-scope `ft.SafeArea` wrappers use `expand=True` only where needed for correct behavior and sizing; avoid forcing it by default.\n- Confirm there are no unnecessary `page.update()` calls in in-scope examples (unless explicitly required by isolated-control or non-auto-update behavior).\n- Confirm no in-scope examples use `use_material3`.\n- Confirm each in-scope `pyproject.toml` has a meaningful, example-specific `[project].description` (not generic or templated text).\n- Confirm metadata features include `\"save to file\"` when the example code supports file export/save behavior.\n- Confirm there is no stale control-level `__init__.py` left behind once a touched control folder has been fully converted.\n- Confirm the relevant docs pages were updated to reference `main.py` and that no stale doc includes remain for the touched examples.\n\n\n## Code style\n\n- When writing wrapped controls (`SafeArea`, `Column`, `Row`, `Container`, etc.), keep `content=` or `controls=` as the last named argument in that control call.\n- Apply this ordering consistently when creating or refactoring examples.\n- Follow code style and linting rules defined in the repository `pyproject.toml` under `[tool.ruff]` for all edits.\n\n## Command checklist\n\n- Discover files: `rg --files <target_dir>`\n- Find docs links/imports: `rg -n \"<old_path_or_module>\" packages examples`\n- Syntax check: `python -m compileall <changed_main_files>`\n- Ruff check: `uv run ruff check <changed_example_files>`\n\n## Output expectations\n\nReport:\n- created example projects\n- metadata added\n- docs/tests updates\n- validation results\n","frontmatter":{"name":"create-flet-example-projects","description":"Use when asked to create Flet example projects from flat .py files with main.py and pyproject.toml metadata for Gallery/MCP indexing."},"isInternal":false,"tokens":2147,"sizeBytes":9565},{"name":"SKILL.md","path":".agents/skills/docs-build-and-verify/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/docs-build-and-verify/SKILL.md","title":"docs-build-and-verify","category":"anthropic-skill","format":"markdown","content":"---\nname: docs-build-and-verify\ndescription: Use when asked to build, preview, or verify the Flet documentation website, including checking for broken links, broken images, and unresolved reST cross-references.\n---\n\n# Docs Build and Verification\n\n## Prerequisites\n\nNode.js 24 is required, matching what CI runs:\n\n```bash\nnvm use 24\n```\n\n## Build\n\nFull production build (includes broken link detection):\n\n```bash\ncd website && yarn build\n```\n\nDev server with hot reload:\n\n```bash\ncd website && yarn start\n```\n\nRegenerate API data and sidebars only (no Docusaurus build):\n\n```bash\ncd website && yarn crocodocs:generate\n```\n\n## Check Broken Links\n\n`yarn build` reports both, but only broken *links* fail the build. Docusaurus defaults\n`onBrokenAnchors` to `warn` and `docusaurus.config.js` does not override it, so a broken\nanchor scrolls past in the log and still ships - grep the build output for `Broken anchor`\nrather than trusting the exit code.\n\n## Check Broken Images\n\nRun this after `yarn build` to find images referenced in HTML that don't exist:\n\n```bash\ncd website && python3 -c \"\nimport re, os, glob\n\nbuild_dir = 'build'\nimg_re = re.compile(r'<img[^>]+src=\\\"(/[^\\\"]+)\\\"', re.IGNORECASE)\nbroken = []\n\nfor html_file in sorted(glob.glob(f'{build_dir}/docs/**/index.html', recursive=True)):\n    page = html_file.replace(build_dir + '/', '').replace('/index.html', '')\n    content = open(html_file).read()\n    for match in img_re.finditer(content):\n        src = match.group(1)\n        if src.startswith('http') or src.startswith('data:'):\n            continue\n        file_path = os.path.join(build_dir, src.lstrip('/'))\n        if not os.path.exists(file_path):\n            broken.append((page, src))\n\nif broken:\n    print(f'Found {len(broken)} broken images:')\n    for page, src in broken:\n        print(f'  {page}: {src}')\nelse:\n    print('No broken images found!')\n\"\n```\n\n## Check Unresolved reST Cross-References\n\nAfter building, check for reST roles that failed to resolve and appear as raw text:\n\n```bash\ncd website && grep -r ':attr:\\|:class:\\|:meth:\\|:func:' build/docs/ --include='*.html' -l\n```\n\nIf any files are listed, those pages have unresolved cross-references that render as plain text instead of links.\n","frontmatter":{"name":"docs-build-and-verify","description":"Use when asked to build, preview, or verify the Flet documentation website, including checking for broken links, broken images, and unresolved reST cross-references."},"isInternal":false,"tokens":555,"sizeBytes":2226},{"name":"SKILL.md","path":".agents/skills/docs-conventions/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/docs-conventions/SKILL.md","title":"docs-conventions","category":"anthropic-skill","format":"markdown","content":"---\nname: docs-conventions\ndescription: Use when writing or reviewing Flet documentation, including Python docstrings (Google style, reST roles, admonitions), Markdown docs (cross-references, images, code examples), and sidebar navigation.\n---\n\n# Documentation Conventions\n\nDocs live in `website/docs/`. Docusaurus renders them as the website.\n\n## Python Docstrings\n\nUse **Google style** docstrings with sections: `Args:`, `Returns:`, `Raises:`, `Note:`, `Example:`, `Warning:`.\n\n## Cross-references\n\n### reST roles\n\nPrefer these in Python docstrings. CrocoDocs renders them as links in\nthe API docs and they keep authoring terse when the auto-derived label is acceptable.\n\n**Supported roles:** `:class:`, `:attr:`, `:meth:`, `:func:`, `:data:`, `:mod:`\n\n```python\n\"\"\"\nIf a parent is a :class:`~flet.ResponsiveRow`, this property determines\nhow many virtual columns the control spans.\n\nSee :attr:`value` or :attr:`flet.Text.size` for the current selection.\n\nCalls :meth:`flet.Page.update` after modifying controls.\n\"\"\"\n```\n\n**Rules:**\n\n- **Qualified reference:** `:attr:`flet.Page.route`` — links to the member, displays inline code `Page.route`\n- **Extension reference:** `:attr:`flet_map.Map.animation_curve`` — links to the extension member, displays inline code `Map.animation_curve`\n- **Short display with `~`:** `:attr:`~flet.Page.route`` — links to the member, displays inline code `route`\n- **Local member (same class):** `:attr:`value`` — no qualifier needed\n- **Method with parens:** `:meth:`update`` — do NOT include `()` in the target\n\nFor plain class references like `:class:`flet.Page`` and extension references like\n`:class:`flet_map.Map``, the website strips leading public package aliases automatically,\nso they display as inline code `Page` and `Map`.\n\n**Not supported:**\n\n- Custom labels like `:class:`my label <flet.Page>`` — the label is always auto-derived from the target\n- Roles for symbols not in CrocoDocs API data degrade to inline code\n\n### Xrefs\n\nReference-style Markdown links of the form `[label][key]`, where `key` is the\nfully-qualified dotted symbol path (same form as reST role targets).\n\nUse as the default form for linking to API symbols from Markdown docs\n(`.md` / `.mdx`).\n\nExamples:\n\n```markdown\nClass: [`Page`][flet.Page]\nAttribute: [`route`][flet.Page.route]\nMethod: [`Page.update()`][flet.Page.update]\nExtension: [`Video.controls`][flet_video.Video.controls]\nPlain text: [the route attribute][flet.Page.route]\n```\n\n**When to prefer over the other forms:**\n\n- **Flexible labels** — the first `[ ]` accepts any text or inline code, unlike reST roles whose label is always auto-derived from the target\n- **Path-independent** — keys are dotted symbol paths, so links don't break when source files are moved, renamed, or restructured (unlike Markdown link paths with `../` and `#flet.X.y` anchors)\n- **Terser** than Markdown links to the same symbol — no relative path or anchor to maintain\n- **Greppable** — searching for the dotted key finds every reference to that symbol across all docs\n\n**Rules:**\n\n- The label (inside the first `[ ]`) is the rendered text — inline code or plain text\n- The key (inside the second `[ ]`) is the fully-qualified dotted path; do NOT include `()` for methods\n- Unresolved keys render as broken reference-style links (silent fallback) — verify with a build or `yarn crocodocs:generate`\n\n### Markdown links\n\nFallback for cases xrefs cannot cover:\n\n- docs-only Python strings — the `docs_reason` parameter of `@deprecated`, extracted validation messages, or short admonition text\n- links to non-API content (other doc pages, external URLs, anchors that aren't API symbols)\n- when the xref entry is missing and you need a working link before regenerating\n\nUse relative `.md` paths with dot-format anchors.\n\nExamples:\n\n```markdown\nControl: [`Page`](../controls/page.md)\nType: [`DragTargetEvent.global_position`](../types/dragtargetevent.md#flet.DragTargetEvent.global_position)\nPlain text: [route](../controls/page.md#flet.Page.route)\nMethod: [`Page.update()`](../controls/page.md#flet.Page.update)\n```\n\n## Admonitions in docstrings\n\nGoogle-style section headers render as Docusaurus admonitions:\n\n```python\n\"\"\"\nNote:\n    Has effect only if the direct parent is a :class:`~flet.Column`.\n\nWarning:\n    This property is deprecated. Use :attr:`new_prop` instead.\n\nExample:\n    Setting up a basic layout:\n    ``ft.Column(controls=[ft.Text(\"Hello\")])``\n\"\"\"\n```\n\nSupported kinds: `Note`, `Warning`, `Danger`, `Tip`, `Info`.\nUnsupported kinds (e.g. `Limitation`, `Example`) are normalized to `note`.\nEmpty admonitions are skipped.\n\n## Admonitions\n\n```markdown\n:::note\nBasic note without title.\n:::\n\n:::warning[Important]\nWarning with a custom title.\n:::\n```\n\nSupported types: `note`, `info`, `tip`, `warning`, `danger`.\n\n## Front matter\n\n```yaml\n---\nclass_name: \"flet.Container\"\nexamples: \"controls/container\"\nexample_images: \"test-images/examples/material/golden/macos/container\"\nexample_media: \"examples/controls/container/media\"\ntitle: \"Container\"\n---\n```\n\n- `examples` — root-relative path under `sdk/python/examples/`\n- `example_images` / `example_media` — root-relative under `website/static/docs/`\n\n## Images\n\nUse the CrocoDocs `Image` component. Paths without `../` are resolved against `/docs/`:\n\n```jsx\nimport {Image} from '@site/src/components/crocodocs';\n\n<Image src={frontMatter.example_images + '/image_for_docs.png'} width=\"55%\" />\n```\n\nFor absolute paths (one-off assets in `static/`):\n\n```jsx\n<Image src=\"/docs/assets/controls/charts/bar-chart-diagram.svg\" width=\"65%\" />\n```\n\n## Code examples\n\n```jsx\nimport {CodeExample} from '@site/src/components/crocodocs';\n\n<CodeExample path={frontMatter.examples + '/example_1.py'} />\n```\n\nPaths are relative to the configured `examples_root` (`sdk/python/examples/`).\n\n## Inline HTML\n\nUse `<kbd>...</kbd>` in Python docstrings for keyboard keys, for example\n`<kbd>Enter</kbd>` or `<kbd>Shift</kbd>`. CrocoDocs preserves this tag in API\ndocs.\n\n## Sidebar Navigation\n\nEdit `website/sidebars.yml` to change navigation structure:\n\n```yaml\ndocs:\n  Getting started:\n  - getting-started/installation.md\n  Controls:\n    _generated_index:\n      title: Controls\n      slug: /controls\n      description: Browse the complete catalog of controls.\n    AlertDialog: controls/alertdialog.md\n```\n\nAfter editing, regenerate `sidebars.js`:\n\n```bash\ncd website && yarn crocodocs:generate\n```\n","frontmatter":{"name":"docs-conventions","description":"Use when writing or reviewing Flet documentation, including Python docstrings (Google style, reST roles, admonitions), Markdown docs (cross-references, images, code examples), and sidebar navigation."},"isInternal":false,"tokens":1576,"sizeBytes":6421},{"name":"SKILL.md","path":".agents/skills/fix-members-short-description/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/fix-members-short-description/SKILL.md","title":"fix-members-short-description","category":"anthropic-skill","format":"markdown","content":"---\nname: fix-members-short-description\ndescription: Use when asked to fix short descriptions of Python type members.\n---\n\n## Inputs\n\n* File or directory with Python modules.\n\n## Instructions\n\nWhen Flet documentation is generated from docstrings the first sentence of a member docstring is used as a short description, for example:\n\n```py\n@dataclass\nclass MyControl:\n    property_a: str\n    \"\"\"\n    Short description of a property.\n\n    Full description.\n    Another line of full description.\n    \"\"\"\n```\n\nHere \"Short description of a property.\" will be used as a short description.\n\nHowever, when a sentence is broken into multiple lines the lines must be \"concatenated\" with `\\`, for example:\n\n```py\n@dataclass\nclass MyControl:\n    property_a: str\n    \"\"\"\n    Short description of a property which could \\\n    take multiple lines.\n\n    Full description.\n    Another line of full description.\n    \"\"\"\n```\n\nYour goal is to go through all members (properties, methods, etc.) of all types (classes, enums) in input file or directory and ensure the first sentence in their docstrings is broken into multiple lines correctly with `\\` symbol.\n\nApply the fix regardless of whether the first sentence starts on the same line as the opening `\"\"\"` or on a following line.\n\nEnsure every docstring line is at most 88 characters long (including any trailing `\\`). If a line cannot be wrapped without breaking a single unbreakable token (e.g., a long URL or Windows registry path like `HKEY_LOCAL_MACHINE\\\\...`), add `# noqa: E501` to the docstring closing `\"\"\"` line instead of the long line.\n","frontmatter":{"name":"fix-members-short-description","description":"Use when asked to fix short descriptions of Python type members."},"isInternal":false,"tokens":344,"sizeBytes":1581},{"name":"SKILL.md","path":".agents/skills/flet-deprecation/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/flet-deprecation/SKILL.md","title":"flet-deprecation","category":"anthropic-skill","format":"markdown","content":"---\nname: flet-deprecation\ndescription: Use when adding or changing deprecations for Python controls/APIs in sdk/python/packages/, including V.deprecated fields, deprecated decorators, version lifecycle, and docs admonitions/labels.\n---\n\n## When To Use\n\nUse this skill when you:\n- deprecate a control/dataclass field with `Annotated[..., V.deprecated(...)]`,\n- deprecate a function/method/class with `flet.utils.deprecated` helpers,\n- update deprecation wording, versions, or removal timelines,\n- verify docs rendering for deprecations (admonition + `deprecated` label).\n\nDo not use this skill for non-deprecation validation logic; use\n[`flet-validation`](../flet-validation/SKILL.md).\n\n## Source Of Truth\n\n- Runtime decorators and warning helpers: `sdk/python/packages/flet/src/flet/utils/deprecated.py`\n- Field-level deprecation rule: `sdk/python/packages/flet/src/flet/utils/validation.py` (`V.deprecated`)\n- Docs extraction/labeling extension: `sdk/python/packages/flet/src/flet/utils/griffe_deprecations.py`\n\n## Deprecation Decision Order\n\nUse this order and stop at the first option that fits:\n1. Property/field deprecation: `Annotated[..., V.deprecated(...)]`.\n2. Function/method deprecation: `@deprecated(...)`.\n3. Class/control deprecation: `@deprecated_class(...)`.\n\nDo not add parallel custom warning logic in `before_update()` when `V.deprecated`\nalready covers the field.\n\n## Runtime Contract For Property Renames\n\nFollow the non-copying model:\n- Python sends both properties when both are set.\n- Dart prefers the new property and uses old property as fallback.\n- Python does not copy/synchronize old/new values in `before_update()`.\n\nRemoval phase:\n- At `delete_version` cleanup, remove old Python property/deprecation and remove\n  Dart fallback in the same migration.\n\n## Removal Version Policy\n\n- Default policy: remove deprecated APIs after 3 minor releases.\n- Example: deprecated in `0.82.0` -> remove in `0.85.0`.\n- Use that policy to set `delete_version` unless there is an approved exception.\n\n## Target Release Audit\n\nWhen working on a release for `{new_version}`, treat deprecations with\n`delete_version == {new_version}` as mandatory audit items.\n\n- Scan Python packages for `@deprecated(...)`, `@deprecated_class(...)`,\n  and `V.deprecated(...)` entries whose `delete_version` equals `{new_version}`.\n- Recommended check command:\n  `rg -n 'delete_version\\\\s*=\\\\s*\"{new_version}\"|delete_version\\\\s*=\\\\s*\\\\x27{new_version}\\\\x27' -S sdk/python/packages`\n- Treat every match as release-relevant work, not informational output.\n- If matches are found, summarize the findings first and ask the human for approval\n  before editing files or making removals.\n- For each match, decide whether the deprecated API must be removed now,\n  whether a prior removal was missed, or whether the deprecation timeline is incorrect.\n- If removal is due, make the code, docs, and changelog updates in the same change.\n- After the cleanup edits are ready, summarize the resulting diff and ask the human\n  for approval before creating a commit.\n- Once commit approval is received, batch all confirmed `{new_version}` cleanup\n  edits into one grouped commit instead of splitting them across multiple commits.\n  Use commit message format: `release: remove deprecated APIs for {new_version}`\n- Do not consider the release prep complete while unresolved `{new_version}` removals remain.\n\n## Authoring Rules\n\n1. Always set `version`.\n2. Set `delete_version` using the 3-minor policy by default.\n3. Keep `reason` plain text for runtime warnings.\n4. Use `docs_reason` for docs-only markdown text.\n5. When a replacement exists, name that replacement API explicitly in `reason` and `docs_reason`.\n\n### Field Pattern\n\n```python\nfrom typing import Annotated, Optional\nfrom flet.utils.validation import V\n\nclass ExampleControl:\n    old_prop: Annotated[\n        Optional[str],\n        V.deprecated(\n            \"new_prop\",\n            version=\"0.17.0\",\n            delete_version=\"0.20.0\",\n            reason=\"Use new_prop instead.\",\n            docs_reason=\"Use :attr:`new_prop` or [`new_prop`](../controls/examplecontrol.md#flet.ExampleControl.new_prop) instead.\",\n        ),\n    ] = None\n```\n\n### Function/Method Pattern\n\n```python\nfrom flet.utils.deprecated import deprecated\n\nclass ExampleControl:\n    @deprecated(\n        reason=\"Use new_func instead.\",\n        docs_reason=\"Use :meth:`new_func` or [`new_func()`](../controls/examplecontrol.md#flet.ExampleControl.new_func) instead.\",\n        version=\"0.17.0\",\n        delete_version=\"0.20.0\",\n    )\n    def old_func(self):\n        ...\n```\n\n### Class/Control Pattern\n\n```python\nfrom flet.utils.deprecated import deprecated_class\n\n@deprecated_class(\n    reason=\"Use NewControl instead.\",\n    docs_reason=\"Use :class:`~flet.NewControl` or [`NewControl`](../controls/newcontrol.md)  instead.\",\n    version=\"0.17.0\",\n    delete_version=\"0.20.0\",\n)\nclass OldControl:\n    ...\n```\n\n### Deprecated Property Pattern\n\n```python\nfrom flet.utils.deprecated import deprecated\n\nclass ExampleControl:\n    @property\n    @deprecated(\n        reason=\"Use new_value instead.\",\n        docs_reason=\"Use :attr:`new_value` or [`new_value`](../controls/examplecontrol.md#flet.ExampleControl.new_value) instead.\",\n        version=\"0.17.0\",\n        delete_version=\"0.20.0\",\n    )\n    def value(self):\n        ...\n```\n\n## `reason` vs `docs_reason`\n\n- Runtime warnings always use `reason`.\n- Docs admonitions prefer `docs_reason`; fallback is `reason`.\n- Keep markdown/cross-refs out of `reason` to avoid noisy runtime output.\n\n### Cross-reference Rule Inside `docs_reason`\n\nIn `docs_reason`, use reST roles for simple references when the auto-derived label is\nsufficient, and use Markdown links when you need more control over the displayed text.\n\nSee [`docs-conventions`](../docs-conventions/SKILL.md) for details on supported cross-ref patterns and their syntax.\n\n## Docs Behavior Expectations\n\nFor supported patterns, docs should auto-render:\n- a `Deprecated` admonition section,\n- a `deprecated` label/badge on the item.\n\nDo not duplicate with manual deprecation admonitions in docstrings unless there\nis a special case not covered by the extension.\n\n## Release Docs Updates\n\nWhen adding a user-visible deprecation, also update the release docs in the\nsame change. These pages are the canonical upgrade path, not a separate\n`Deprecations` page.\n\n1. Create or update a migration guide under\n   `website/docs/updates/breaking-changes/vX-Y-Z/`.\n   - Group closely related deprecations into one page, especially APIs from the\n     same class/control or the same PR. For example, `DragTargetEvent.x`,\n     `DragTargetEvent.y`, and `DragTargetEvent.offset` belong in one\n     coordinate-fields guide.\n   - Use this page shape: title, `:::note` accuracy callout,\n     `Summary`, `Context`, `Migration guide`, `Timeline`, and `References`.\n   - Keep one-off replacements in prose. Use a table only when the page maps\n     many removed/deprecated APIs to replacements.\n   - In `References`, link relevant API docs, relevant GitHub issue/PR links,\n     and release notes entry for that release.\n2. Add the guide to\n   `website/docs/updates/breaking-changes/index.md` under the release's\n   `Deprecations` subsection.\n3. Add the guide to `website/sidebars.yml` under:\n   `Stay up to date` -> `Breaking changes and deprecations` -> `vX.Y.Z`.\n   This keeps individual guide pages in the docs sidebar while grouping them by\n   release.\n4. Update `website/docs/updates/release-notes.md` so the release links to the\n   combined `Breaking changes and deprecations` section.\n5. Run `cd website && yarn crocodocs:generate` after sidebar\n   edits, then run `cd website && yarn build`.\n\n## Testing Guidance\n\nDo not add one-off tests for every API that gets deprecated when it uses an\nexisting, already-tested pattern (`V.deprecated`, `@deprecated`, or\n`@deprecated_class`). For routine deprecation metadata updates, rely on the\nshared helper and docs extraction tests.\n\nAdd or update tests only when the change affects deprecation infrastructure or\nintroduces meaningful new behavior, for example:\n- changing runtime warning formatting or stacklevel behavior,\n- changing docs extraction/labeling behavior,\n- adding a new deprecation pattern,\n- adding custom compatibility behavior outside the standard helper,\n- fixing a regression where an existing test would not have failed.\n\nPrefer these locations for infrastructure tests:\n- `sdk/python/packages/flet/tests/test_deprecated.py`\n- `sdk/python/packages/flet/tests/test_griffe_deprecations.py`\n- `sdk/python/packages/flet/tests/test_validation.py` (for `V.deprecated`)\n\n## Common Pitfalls\n\n- Putting markdown/cross-refs into runtime `reason`.\n- Forgetting `delete_version` when a removal target is already known.\n- Adding old/new value-copy logic in Python for rename migrations.\n- Duplicating deprecation warnings in multiple lifecycle hooks manually.\n- Broken cross-refs targets in `docs_reason`.\n","frontmatter":{"name":"flet-deprecation","description":"Use when adding or changing deprecations for Python controls/APIs in sdk/python/packages/, including V.deprecated fields, deprecated decorators, version lifecycle, and docs admonitions/labels."},"isInternal":false,"tokens":2041,"sizeBytes":8950},{"name":"SKILL.md","path":".agents/skills/flet-validation/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/flet-validation/SKILL.md","title":"flet-validation","category":"anthropic-skill","format":"markdown","content":"---\nname: flet-validation\ndescription: Use whenever editing validation for Python controls in sdk/python/packages/: adding/changing constrained properties, `Raises: ValueError` docstrings, `before_update()` checks, `raise ValueError`, Annotated/V rules, or __validation_rules__.\n---\n\n## When To Use\n\nUse this skill when you:\n- add validation to a control property,\n- migrate manual `before_update()` checks to `V` rules,\n- update `Raises` sections tied to validation,\n- align Python validation with Dart-side control behavior.\n\nDo not use this skill for unrelated doc-only edits outside control validation.\nDo not use this skill for deprecation authoring conventions; use\n[`flet-deprecation`](../flet-deprecation/SKILL.md).\n\n## Source Of Truth\n\n- Validation runtime API lives in:\n  `sdk/python/packages/flet/src/flet/utils/validation.py`\n- The same runtime can validate regular dataclass models via `validate(instance)`;\n  this skill focuses on the control-specific authoring conventions.\n- Import from public path only:\n  `from flet.utils.validation import V`\n  and when needed\n  `from flet.utils.validation import ValidationRules`\n\n## Validation Decision Order\n\nUse this order and stop at the first option that keeps logic clear:\n1. `Annotated[..., V.*]` field rules (default).\n2. `__validation_rules__: ValidationRules` for cross-field invariants that do\n   not map cleanly to one field.\n3. `before_update()` only for normalization/mutation, or for truly non-ruleable\n   invariants.\n\nNever duplicate the same invariant in more than one layer.\n\n## Validation Authoring Rules\n\n1. Prefer field-level validation with `Annotated[...]` metadata.\n   - Example (close to current slider controls):\n     ```\n     @dataclass\n     class Sample:\n         opacity: Annotated[\n                Optional[Number],\n                V.between(0.0, 1.0),\n            ] = None\n\n         value: Annotated[\n             Optional[Number],\n             V.ge_field(\"min\"),\n             V.le_field(\"max\"),\n         ] = None\n\n         min: Annotated[\n             Number,\n             V.le_field(\"max\"),\n             V.le_field(\"value\"),\n         ] = 0.0\n\n         max: Annotated[\n             Number,\n             V.ge_field(\"min\"),\n             V.ge_field(\"value\"),\n         ] = 1.0\n     ```\n\n2. Use class-level `__validation_rules__` only for invariants that cannot be\n   expressed cleanly with field rules.\n   - Type:\n     `__validation_rules__: ValidationRules = (...)`\n   - Use `V.ensure(...)` with an explicit message only when the predicate is\n     short and readable.\n   - If `V.ensure(lambda ...)` becomes hard to read, prefer either:\n     1. a named predicate function passed to `V.ensure(...)`, or\n     2. a clear `before_update()` check when it cannot be represented well with\n        existing `V.*` rules.\n\n3. Keep the `before_update()` override for normalization/mutation first.\n   - Remove validation checks duplicated by `V` rules.\n   - Prefer raising validation errors from rule evaluation (`validate()`), not\n     from ad-hoc `before_update()` checks, unless the invariant is genuinely\n     non-ruleable with current validation primitives.\n\n4. Cross-field comparisons use field rules only.\n   - Use: `V.gt_field`, `V.ge_field`, `V.lt_field`, `V.le_field`\n\n5. `None` handling is inferred from type hints.\n   - If a field is annotated as optional (for example `Optional[T]`), `None` is allowed.\n   - If a field is not optional, `None` fails validation.\n   - For `*_field` comparisons, if either side is optional and currently `None`, the\n     comparison is skipped; if a non-optional side is `None`, validation fails.\n\n6. Match Dart effective behavior.\n   - Review both:\n     1. Flet Dart wrapper (`packages/flet/lib/src/controls/<control>.dart` or\n        extension wrapper),\n     2. wrapped Flutter widget source assertions/invariants.\n   - Mirror those constraints in Python so invalid payloads fail before crossing\n     to Dart.\n   - Validate against effective defaults applied on Dart side (for example\n     `min`/`max`).\n   - Include wrapper-imposed constraints when relevant (for example\n     bounds/rounding/division logic in wrapper formatting code).\n\n7. For new properties, validate against base widget assertions before wiring.\n   - When adding a Python property to a Flet control, confirm whether the mapped\n     Dart wrapper and underlying widget both enforce constraints for that property.\n   - Add equivalent Python-side validation (`Annotated[...]`, `__validation_rules__`,\n     or readable `before_update()`) to prevent Dart assertions from being the first\n     failure point.\n\n8. Keep error ownership clear.\n   - Runtime outbound value failures should raise `ValueError`.\n   - Validation declaration/build errors (invalid `V.*` arguments) should raise\n     `ValidationDeclarationError`.\n\n## Typing Style\n\n- Follow the codebase typing style:\n  - prefer `Optional[T]` over `T | None`,\n  - use `Union[...]` when needed.\n\n## Property Docstring Style\n\nWhen a property has validation, document it in that property’s docstring (google style).\n\n1. Add a `Raises:` block under the property docstring.\n\n2. Use one `ValueError` entry per logical rule, except `between(...)`.\n   - For `V.between(a, b)`, use one entry:\n     `ValueError: If it is not between \\`a\\` and \\`b\\`, inclusive.`\n\n3. Start each entry with `If it ...`, where 'it' refers to the property name.\n\n4. Use canonical wording from validation helper docstrings.\n   - The source of truth is\n     `sdk/python/packages/flet/src/flet/utils/validation.py`.\n   - Each `V.*` helper includes `Property docstring Raises wording`.\n   - Keep property `Raises` entries as negations of the annotation rule.\n   - For strict inequalities, say `\"strictly\"`.\n     For example: `V.gt(x)` -> `ValueError: If it is not strictly greater than \\`x\\`.`\n   - For sign-neutral divisibility helpers (`factor_of`, `multiple_of`), add\n     explicit sign rules (`V.gt(0)` or `V.lt(0)`) when direction matters, and\n     include separate `Raises` entries for those sign rules.\n\n5. Mention conditional applicability when needed.\n   - Example (for `min`/`max` checks against optional `value`):\n     ```\n     Raises:\n         ValueError: If it is not less than or equal to [`value`][(c).],\n             when [`value`][(c).] is set.\n     ```\n\n6. Keep examples and wording aligned with real control files.\n   - Prefer concrete property names such as `min`, `max`, `value`,\n     `start_value`, `end_value`, `min_lines`, `max_lines`.\n   - For cross-field rules, use same-class links: [`min`][(c).], [`max`][(c).].\n\n## Cross-Referencing Conventions\n\nFollow the cross-reference guidance in:\n[`docs-conventions`](../docs-conventions/SKILL.md).\n\nMost common pattern to use in control property docstrings:\n- same-class properties: `[\\`prop\\`][(c).]`\n\nKeep symbol labels wrapped in backticks.\n\n## Required Test Matrix\n\nWhen adding/changing validation, include tests that cover:\n- one valid case and one invalid case per new logical rule;\n- boundary values (`==`, min/max edges) where applicable;\n- cross-field set/unset combinations when optional values are involved;\n- effective-default behavior when Dart applies defaults but Python value is\n  omitted.\n\nPrefer placing tests in:\n- `sdk/python/packages/flet/tests/test_validation.py` for validation runtime;\n- control-specific tests when behavior is tied to one control.\n\n## Common Pitfalls\n\n- Keeping stale manual `before_update()` validations after migration.\n- Missing `Raises` entries on validated properties.\n- Combining multiple non-between rules into one ambiguous `ValueError` sentence.\n- Forgetting Dart defaults that still apply when Python property is omitted.\n- Forcing complex `V.ensure(lambda ...)` expressions when `before_update()` would be cleaner.\n","isInternal":false,"tokens":1758,"sizeBytes":7735},{"name":"SKILL.md","path":".agents/skills/imperative-to-declarative-flet/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/imperative-to-declarative-flet/SKILL.md","title":"imperative-to-declarative-flet","category":"anthropic-skill","format":"markdown","content":"---\nname: imperative-to-declarative-flet\ndescription: Convert an imperative Flet Python app in which controls are mutated and then page.update is called to declarative style using flet.component, flet.observable and state hooks.\nmetadata:\n  short-description: Port Flet app to declarative\n---\n\n# Imperative → Declarative (Flet Python)\n\nPort an existing imperative Flet app to “components mode” with `@ft.component`, hooks, and (optionally) `@ft.observable` models.\n\n## Outcomes\n\n- Original folder unchanged; new sibling folder created.\n- Entry point uses `page.render(App)` (components mode).\n- UI is derived from state; minimal/zero manual `page.update()` for normal UI updates.\n\n## Choose a state strategy\n\n- **Use `@ft.observable`** for nested app data you mutate in place (boards/lists/cards, drag+drop reorder).\n- **Use `ft.use_state`** for local ephemeral UI state (hover flags, input text, dialog selection).\n- Avoid storing live `Control`/component objects in state; store ids/enums and create controls during render.\n\n## Workflow\n\n### 1) Create a new declarative copy\n\n- Copy the existing app folder to a new one (e.g. `trolli` → `trolli-declarative-*`).\n- Keep `assets/` with the new folder.\n\n### 2) Switch to components mode entrypoint\n\n- Create a root component `@ft.component def App(): ...`.\n- Run with:\n  - `ft.run(lambda page: page.render(App), assets_dir=...)`\n- Set page globals either:\n  - in a `main(page)` function before `page.render(App)`, or\n  - in `ft.on_mounted(...)` (works, but ordering can be less obvious).\n\n### 3) Centralize routing in `App`\n\n- Keep `app.route: str` as source of truth.\n- In one place, define:\n  - `route_change(e)` to normalize/redirect/validate routes and set `app.route`\n  - a render-time `match app.route` (or a derived `active_screen`) to pick `content`\n- Prefer: `route_change` mutates route state; `App()` render chooses UI based on that state.\n\n### 4) Componentize UI\n\n- Move UI chunks into `src/components/*.py`.\n- Each component:\n  - takes only the model(s) it needs\n  - uses hooks for local UI state\n  - mutates observable models for app data changes\n\n### 5) Dialogs: reduce `page.update()` usage\n\nIf a dialog mutates existing controls and calls `page.update()`, convert it to:\n\n- `@ft.component` dialog content with `ft.use_state` for `error`, `selected_color`, etc.\n- event handlers call setters (no explicit updates)\n- show it via `page.show_dialog(ft.AlertDialog(content=DialogContent(...)))`\n\n### 6) Assets/fonts checklist\n\n- Prefer an absolute `assets_dir` derived from `__file__`.\n- If running via `flet run`, be aware it can set `FLET_ASSETS_DIR` and override `assets_dir=`.\n- Font registration uses the dict key as the font family name:\n  - `page.fonts = {\"Pacifico\": \"Pacifico-Regular.ttf\"}`\n  - use `font_family=\"Pacifico\"`.\n\n## Common pitfalls (and fixes)\n\n- **Event handler typing is invariant** (`Event[Sub]` ≠ `Event[Base]`):\n  - If `on_click` is declared on `Button`, annotate `e` as `ft.Event[ft.Button]` (or use `def handler(): ...`).\n- **`TemplateRoute` params are dynamic**:\n  - `raw = getattr(troute, \"id\", None)` then `isinstance(raw, str)` before `int(raw)`.\n- **`controls=[*[...], ...]` can confuse type checkers** with components:\n  - build lists in two steps and annotate/cast, or return raw controls from non-component factories.\n","frontmatter":{"name":"imperative-to-declarative-flet","description":"Convert an imperative Flet Python app in which controls are mutated and then page.update is called to declarative style using flet.component, flet.observable and state hooks.","metadata":{"short-description":"Port Flet app to declarative"}},"isInternal":false,"tokens":850,"sizeBytes":3326},{"name":"SKILL.md","path":".agents/skills/implement-flet-extension/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/implement-flet-extension/SKILL.md","title":"implement-flet-extension","category":"anthropic-skill","format":"markdown","content":"---\nname: implement-flet-extension\ndescription: Implement a new Flet extension/control that wraps a third-party Flutter package end-to-end, including dependency selection, version pinning, compatibility checks, Python/Flutter integration, docs, examples, tests, and CI updates. Use when adding any flet_* package backed by an external pub.dev package.\n---\n\nImplement a Flet extension around an external Flutter package using existing `flet_*` packages as implementation templates.\n\n## Inputs\n\n- Control/service name and Python package name (`flet_<extension>`).\n- Target pub.dev package and intended version/range.\n- API surface to expose in Python (properties, methods, events, types/enums).\n\n## Third-party Dependency Gate\n\n1. Confirm package health: maintenance activity, null-safety, platform support, and open issue risk.\n2. Confirm license is compatible with Flet distribution.\n3. Select a conservative version strategy:\n- Pin exact version when behavior stability is critical.\n- Use bounded ranges when required by ecosystem constraints.\n4. Record key constraints and reasons in PR notes/commit message.\n\n## Control/Service Classification\n\n- Classify wrapped functionality before implementation:\n1. `LayoutControl` for visual controls that participate in page/layout positioning.\n2. Base `Control` for simple visual controls that do not require page positioning or define their own positioning rules/props (for example `Draggable`, `Divider`, `MenuBar`, `NavigationRail`).\n3. Non-visual Service when functionality is not a renderable UI control.\n- Inspect the wrapped Flutter package API to determine whether it includes non-visual/service functionality.\n- For service patterns, follow existing extension examples: `sdk/python/packages/flet-audio`, `sdk/python/packages/flet-flashlight`, `sdk/python/packages/flet-secure-storage`.\n\n## API Mapping Rules\n\n- Expose only stable and useful features first; avoid mirroring every upstream option.\n- Keep Python API idiomatic and concise; avoid redundant control-name prefixes.\n- Map upstream naming inconsistencies to Flet conventions when needed.\n- Add custom enums/types only when they improve correctness and discoverability.\n\n## Python-side Rules\n\n- Use `LayoutControl`, base `Control`, or Service base class according to classification.\n- Implement typed properties, methods, and events exactly for chosen public API.\n- Reuse existing serialization/event patterns from sibling controls/services.\n\n## Flutter-side Rules\n\n- Use `parseEnum()` for enums — it's exported from `package:flet/flet.dart`. Call it as `parseEnum(MyEnum.values, widget.control.getString(\"attr\"), MyEnum.defaultVal)!`. Do NOT write a custom `_parseXxx()` switch helper.\n- For control attributes, prefer `widget.control.getBool()/getDouble()/...` accessors.\n- For non-control parsing, use shared `parseSomething()` helpers.\n- Do not add one-off private parser utilities when standard helpers exist.\n- Put control-specific helpers in `utils/<control>.dart`; shared helpers in `utils/<topic>.dart`.\n- Prefer `parse`-prefixed helper names when converting input to Flutter structures.\n- Avoid single-use local variables.\n\n### Default Value Matching (Critical)\n\nProperties with default values on the Python side are **not sent to Flutter** when unchanged from the default. Every Dart property read **must provide the same default** as its Python counterpart:\n\n- `control.getDouble(\"size\", 100.0)!` when Python has `size: float = 100.0`\n- `control.getBool(\"animate\", true)!` when Python has `animate: bool = True`\n- `parseDuration(value[\"dur\"], const Duration(milliseconds: 500))!` when Python has `dur: DurationValue = field(default_factory=lambda: Duration(milliseconds=500))`\n- `control.get<List>(\"items\")?.map(...).toList() ?? const []` when Python has `items: list[str] = field(default_factory=list)`\n\nWithout matching defaults, Dart receives `null` and either crashes or silently uses the wrong value. This applies to all property types: bools, numbers, strings, enums, durations, collections, and nested `@ft.value` types.\n\n## Integration Checklist\n\n- Register in the Flet client app — two files:\n  1. `client/pubspec.yaml`: add `flet_<ext>: path: ../sdk/python/packages/flet-<ext>/src/flutter/flet_<ext>` under `dependencies`.\n  2. `client/lib/main.dart`: add `import 'package:flet_<ext>/flet_<ext>.dart' as flet_<ext>;` and `flet_<ext>.Extension()` to the `extensions` list.\n- Add extension package to `sdk/python/pyproject.toml` in **two places**: the `dependencies` list and `[tool.uv.sources]` as `{ workspace = true }`.\n- Add extension to `sdk/python/packages/flet/pyproject.toml` in the `[dependency-groups] extensions` list.\n- Add extension to `sdk/python/examples/apps/flet_build_test/pyproject.toml` in **three places**: `[project] dependencies`, `[tool.uv.sources]` as `{ path = \"...\", editable = true }`, and `[tool.flet.dev_packages]` as a relative path string.\n- Add extension to `tools/crocodocs/pyproject.toml` under `[tool.crocodocs.packages]` as `<pkg_name> = \"../../sdk/python/packages/<pkg-dir>/src\"`. This fixes \"Missing API entry\" errors in the docs. Note: `api-data.json` is gitignored (generated at build time); only the `pyproject.toml` change needs committing.\n- Add extension to `.github/workflows/ci.yml` in both places:\n  - `build_flet_extensions` -> `PACKAGES` list.\n  - `py_publish` -> `for pkg in ...` publish loop.\n- Add `.gitignore` to Flutter extension project if missing.\n- Remove `[tool.uv.sources]` local path overrides from example `pyproject.toml` files before opening a PR (they are development-only conveniences).\n\n## Docs, Examples, Tests\n\n- Add control/service docs under `website/docs/controls/<name>` for controls and `website/docs/services/<name>` for services.\n- Always create one doc page per control, even for extensions with many similar controls. Use `index.md` for the overview (install instructions, examples, list of links) and individual `<controlname>.md` files for each control — consistent with `flet-color-pickers` and other extensions.\n- Use `<ClassSummary name=\"pkg.ClassName\" />` and `<ClassMembers name=\"pkg.ClassName\" />` JSX from `@site/src/components/crocodocs` to render API docs. Do NOT add `image=`, `imageCaption=`, or `imageWidth=` props to `<ClassSummary>` when no screenshots exist yet.\n- In the `## Examples` section, do NOT add `###` subtitles above `<CodeExample>` blocks — titles are injected automatically from the example file itself.\n- Add all custom enums/types docs and update `website/sidebars.yml` navigation.\n- Use markdown filenames without underscores (`codeeditor.md`, not `code_editor.md`).\n- Add examples under `sdk/python/examples/extensions/<name>/` for extension controls.\n- Use `import flet_<ext> as <short_alias>` in examples (e.g., `import flet_spinkit as spins`). Keep alias short but readable.\n- Use `ft.Colors.SURFACE_CONTAINER_HIGHEST` for card/cell backgrounds in showcase examples — it adapts to light and dark system themes automatically.\n- Do NOT set an explicit dark theme in examples; let the app use system theme (no `page.theme_mode`).\n- Add integration tests under `packages/flet/integration_tests/extensions/<name>/` — **not** inside the extension package's own directory (no `tests/` folder in the package itself, matching the pattern of `flet-code-editor`, `flet-color-pickers`, etc.).\n- For controls with continuously-running animations, do NOT use `assert_control_screenshot` or `pump_and_settle` — they will timeout waiting for animations to settle. Instead use `await flet_app.tester.pump(duration=ft.Duration(milliseconds=500))` which advances the clock by a fixed amount. This still runs real Flutter rendering and catches crashes, without screenshot comparison.\n- Ensure generated screenshots are suitable for docs usage when visual examples are added.\n\n## Upgrade and Compatibility Guardrails\n\n- Add at least one test that catches upstream behavioral changes likely to break wrapper mapping.\n- Avoid exposing experimental upstream APIs unless explicitly requested.\n- Keep wrapper surface narrow enough to maintain backwards compatibility across upstream updates.\n\n## Validation\n\n- Run relevant Python and integration tests for touched areas.\n- Verify Python import paths, client runtime registration, and docs navigation.\n- Verify dependency resolution and lockfile updates are intentional.\n","frontmatter":{"name":"implement-flet-extension","description":"Implement a new Flet extension/control that wraps a third-party Flutter package end-to-end, including dependency selection, version pinning, compatibility checks, Python/Flutter integration, docs, examples, tests, and CI updates. Use when adding any flet_* package backed by an external pub.dev package."},"isInternal":false,"tokens":1837,"sizeBytes":8353},{"name":"SKILL.md","path":".agents/skills/prepare-flet-release/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/prepare-flet-release/SKILL.md","title":"prepare-flet-release","category":"anthropic-skill","format":"markdown","content":"---\nname: prepare-flet-release\ndescription: Use when asked to prepare new Flet release by bumping versions and author release notes.\n---\n\n## Inputs\n\n* Previous Flet version from repo tags.\n* Whether it's minor or major release.\n\n## Related Skills\n\nAlways use [`flet-deprecation`](../flet-deprecation/SKILL.md) during release prep\nto audit deprecations for the target version. Also use it when release prep includes:\n- adding new deprecations in this release,\n- removing APIs whose `delete_version` equals this release version,\n- auditing changelog entries that mention deprecations/removals.\n\nUse [`write-changelog-entry`](../write-changelog-entry/SKILL.md) for drafting or refining individual changelog items.\nThat skill is the source of truth for item wording, scope selection, and what should or should not be mentioned in a single entry.\n\n## Steps\n\n* Take latest Flet release version from the repo and\n  increment third (patch) digit to get the next version if it's a minor release\n  or second (minor) digit if it's a major release.\n* Pull the latest `main` and create a new branch named `prepare-release-{new_version}` from `main`.\n* Set new version in packages/flet/pubspec.yaml.\n* Run pub get in /client dir to refresh pubspec.lock with new version.\n* Add new entries into `packages/flet/CHANGELOG.md` and `/CHANGELOG.md` from the git log since the last release.\n  * Use [`write-changelog-entry`](../write-changelog-entry/SKILL.md) for every individual item.\n  * Build the candidate set from relevant commits, PRs, and issues since the last release.\n  * Ensure that all inferred PRs and issues in the changelog have the `{version}` milestone attached on GitHub.\n  * If a related issue or PR is missing the `{version}` milestone, update the milestone on GitHub and keep the link in the changelog.\n  * When selecting candidates for `packages/flet/CHANGELOG.md`, prefer items with meaningful Flutter-side impact.\n  * When selecting candidates for `sdk/python/packages/*/CHANGELOG.md`, prefer published Python-facing changes; do not include extension-internal Flutter implementation work unless it materially changes user-visible Python behavior.\n* If the release includes breaking changes, API removals, or deprecations,\n  update `website/docs/updates/release-notes.md` and\n  `website/docs/updates/breaking-changes/index.md`.\n  * Use [`flet-deprecation`](../flet-deprecation/SKILL.md) for deprecation\n    guide requirements and sidebar placement.\n  * Group related deprecations into one migration guide page where possible,\n    and add guide pages under the release version in `website/sidebars.yml`.\n* Scan all changelogs for `Unreleased` sections, not only the root ones:\n  * `/CHANGELOG.md`\n  * `packages/flet/CHANGELOG.md`\n  * `sdk/python/packages/*/CHANGELOG.md`\n  Recommended check command:\n  `rg -n \"^##\\\\s*\\\\[?Unreleased\\\\]?|^##\\\\s*Unreleased\" -S CHANGELOG.md packages/flet/CHANGELOG.md sdk/python/packages/*/CHANGELOG.md`\n* If any changelog has an `Unreleased` section, convert that section into the new release section (`## {new_version}`), preserving and re-sorting its items. Do not leave duplicate release content in both `Unreleased` and `{new_version}`.\n  This conversion must be done for every matched changelog from the scan above.\n* Sort items in changelogs as follows, omitting empty sections:\n  * New features\n  * Improvements\n  * Breaking changes\n  * Deprecations\n  * Bug fixes\n  * Documentation\n  * Other changes (chore, refactor, etc.)\n  Put removals of previously deprecated APIs under `Breaking changes`, and\n  keep newly deprecated-but-still-working APIs under `Deprecations`.\n* Templates are in `sdk/python/templates/` and automatically packaged as zip artifacts with the GitHub Release. No manual branch creation in external repos is needed.\n","frontmatter":{"name":"prepare-flet-release","description":"Use when asked to prepare new Flet release by bumping versions and author release notes."},"isInternal":false,"tokens":866,"sizeBytes":3774},{"name":"SKILL.md","path":".agents/skills/run-integration-tests/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/run-integration-tests/SKILL.md","title":"run-integration-tests","category":"anthropic-skill","format":"markdown","content":"---\nname: run-integration-tests\ndescription: Use when asked to run integration tests.\n---\n\n## Instructions\n\nIntegration tests are in `sdk/python/packages/flet/integration_tests` directory.\n\nRead `sdk/python/packages/flet/integration_tests/README.md` for further instructions.\n","frontmatter":{"name":"run-integration-tests","description":"Use when asked to run integration tests."},"isInternal":false,"tokens":56,"sizeBytes":276},{"name":"SKILL.md","path":".agents/skills/run-unit-tests/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/run-unit-tests/SKILL.md","title":"run-unit-tests","category":"anthropic-skill","format":"markdown","content":"---\nname: run-unit-tests\ndescription: Use when asked to run unit tests.\n---\n\nThis skill is used to run unit tests of the Python part of Flet framework.\n\n## Instructions\n\nRun the following command to run `flet` package unit tests:\n\n```\nuv run --group test pytest packages/flet/tests\n```\n\nThe directory in that commend is relative to `{root}/sdk/python`.\n","frontmatter":{"name":"run-unit-tests","description":"Use when asked to run unit tests."},"isInternal":false,"tokens":81,"sizeBytes":353},{"name":"SKILL.md","path":".agents/skills/test-flet-apps-dev/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/test-flet-apps-dev/SKILL.md","title":"test-flet-apps-dev","category":"anthropic-skill","format":"markdown","content":"# test-flet-apps-dev\n\nPath: `.agents/skills/test-flet-apps-dev/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/test-flet-apps-dev/SKILL.md)","tokens":300,"sizeBytes":199},{"name":"SKILL.md","path":".agents/skills/update-flet-control-doc-gifs/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/update-flet-control-doc-gifs/SKILL.md","title":"update-flet-control-doc-gifs","category":"anthropic-skill","format":"markdown","content":"# update-flet-control-doc-gifs\n\nPath: `.agents/skills/update-flet-control-doc-gifs/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/update-flet-control-doc-gifs/SKILL.md)","tokens":300,"sizeBytes":229},{"name":"SKILL.md","path":".agents/skills/write-changelog-entry/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/write-changelog-entry/SKILL.md","title":"write-changelog-entry","category":"anthropic-skill","format":"markdown","content":"# write-changelog-entry\n\nPath: `.agents/skills/write-changelog-entry/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/write-changelog-entry/SKILL.md)","tokens":300,"sizeBytes":208},{"name":"analysis_options.yaml","path":"packages/flet_integration_test/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet_integration_test/analysis_options.yaml","title":"Flet_integration_test Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_integration_test Skill\n\nPath: `packages/flet_integration_test/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet_integration_test/analysis_options.yaml)","tokens":300,"sizeBytes":228},{"name":"pubspec.yaml","path":"packages/flet_integration_test/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet_integration_test/pubspec.yaml","title":"Flet_integration_test Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_integration_test Skill\n\nPath: `packages/flet_integration_test/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet_integration_test/pubspec.yaml)","tokens":300,"sizeBytes":210},{"name":"analysis_options.yaml","path":"packages/flet/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/analysis_options.yaml","title":"Flet Skill","category":"anthropic-skill","format":"yaml","content":"# Flet Skill\n\nPath: `packages/flet/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/analysis_options.yaml)","tokens":300,"sizeBytes":177},{"name":"CHANGELOG.md","path":"packages/flet/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/CHANGELOG.md","title":"Flet Skill","category":"anthropic-skill","format":"markdown","content":"# Flet Skill\n\nPath: `packages/flet/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/CHANGELOG.md)","tokens":300,"sizeBytes":159},{"name":"pubspec.yaml","path":"packages/flet/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/pubspec.yaml","title":"Flet Skill","category":"anthropic-skill","format":"yaml","content":"# Flet Skill\n\nPath: `packages/flet/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/pubspec.yaml)","tokens":300,"sizeBytes":159},{"name":"sample.json","path":"sdk/python/examples/extensions/lottie/lottie_animations/assets/sample.json","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/examples/extensions/lottie/lottie_animations/assets/sample.json","title":"Assets Skill","category":"anthropic-skill","format":"json","content":"# Assets Skill\n\nPath: `sdk/python/examples/extensions/lottie/lottie_animations/assets/sample.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/examples/extensions/lottie/lottie_animations/assets/sample.json)","tokens":300,"sizeBytes":257},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-ads/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/CHANGELOG.md","title":"Flet-ads Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-ads Skill\n\nPath: `sdk/python/packages/flet-ads/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/CHANGELOG.md)","tokens":300,"sizeBytes":193},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-ads/src/flutter/flet_ads/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/src/flutter/flet_ads/analysis_options.yaml","title":"Flet_ads Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_ads Skill\n\nPath: `sdk/python/packages/flet-ads/src/flutter/flet_ads/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/src/flutter/flet_ads/analysis_options.yaml)","tokens":300,"sizeBytes":253},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-ads/src/flutter/flet_ads/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/src/flutter/flet_ads/pubspec.yaml","title":"Flet_ads Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_ads Skill\n\nPath: `sdk/python/packages/flet-ads/src/flutter/flet_ads/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/src/flutter/flet_ads/pubspec.yaml)","tokens":300,"sizeBytes":235},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-audio-recorder/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/CHANGELOG.md","title":"Flet-audio-recorder Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-audio-recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/CHANGELOG.md)","tokens":300,"sizeBytes":226},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/analysis_options.yaml","title":"Flet_audio_recorder Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_audio_recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/analysis_options.yaml)","tokens":300,"sizeBytes":308},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/CHANGELOG.md","title":"Flet_audio_recorder Skill","category":"anthropic-skill","format":"markdown","content":"# Flet_audio_recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/CHANGELOG.md)","tokens":300,"sizeBytes":290},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/pubspec.yaml","title":"Flet_audio_recorder Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_audio_recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/pubspec.yaml)","tokens":300,"sizeBytes":290},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-audio/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/CHANGELOG.md","title":"Flet-audio Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-audio Skill\n\nPath: `sdk/python/packages/flet-audio/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/CHANGELOG.md)","tokens":300,"sizeBytes":199},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-audio/src/flutter/flet_audio/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/src/flutter/flet_audio/analysis_options.yaml","title":"Flet_audio Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_audio Skill\n\nPath: `sdk/python/packages/flet-audio/src/flutter/flet_audio/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/src/flutter/flet_audio/analysis_options.yaml)","tokens":300,"sizeBytes":263},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-audio/src/flutter/flet_audio/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/src/flutter/flet_audio/pubspec.yaml","title":"Flet_audio Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_audio Skill\n\nPath: `sdk/python/packages/flet-audio/src/flutter/flet_audio/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/src/flutter/flet_audio/pubspec.yaml)","tokens":300,"sizeBytes":245},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-camera/src/flutter/flet_camera/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-camera/src/flutter/flet_camera/analysis_options.yaml","title":"Flet_camera Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_camera Skill\n\nPath: `sdk/python/packages/flet-camera/src/flutter/flet_camera/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-camera/src/flutter/flet_camera/analysis_options.yaml)","tokens":300,"sizeBytes":268},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-camera/src/flutter/flet_camera/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-camera/src/flutter/flet_camera/pubspec.yaml","title":"Flet_camera Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_camera Skill\n\nPath: `sdk/python/packages/flet-camera/src/flutter/flet_camera/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-camera/src/flutter/flet_camera/pubspec.yaml)","tokens":300,"sizeBytes":250},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-charts/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/CHANGELOG.md","title":"Flet-charts Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-charts Skill\n\nPath: `sdk/python/packages/flet-charts/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/CHANGELOG.md)","tokens":300,"sizeBytes":202},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-charts/src/flutter/flet_charts/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/src/flutter/flet_charts/analysis_options.yaml","title":"Flet_charts Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_charts Skill\n\nPath: `sdk/python/packages/flet-charts/src/flutter/flet_charts/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/src/flutter/flet_charts/analysis_options.yaml)","tokens":300,"sizeBytes":268},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-charts/src/flutter/flet_charts/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/src/flutter/flet_charts/CHANGELOG.md","title":"Flet_charts Skill","category":"anthropic-skill","format":"markdown","content":"# Flet_charts Skill\n\nPath: `sdk/python/packages/flet-charts/src/flutter/flet_charts/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/src/flutter/flet_charts/CHANGELOG.md)","tokens":300,"sizeBytes":250},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-charts/src/flutter/flet_charts/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/src/flutter/flet_charts/pubspec.yaml","title":"Flet_charts Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_charts Skill\n\nPath: `sdk/python/packages/flet-charts/src/flutter/flet_charts/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/src/flutter/flet_charts/pubspec.yaml)","tokens":300,"sizeBytes":250},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-code-editor/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/CHANGELOG.md","title":"Flet-code-editor Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-code-editor Skill\n\nPath: `sdk/python/packages/flet-code-editor/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/CHANGELOG.md)","tokens":300,"sizeBytes":217},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/analysis_options.yaml","title":"Flet_code_editor Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_code_editor Skill\n\nPath: `sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/analysis_options.yaml)","tokens":300,"sizeBytes":293},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/pubspec.yaml","title":"Flet_code_editor Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_code_editor Skill\n\nPath: `sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/src/flutter/flet_code_editor/pubspec.yaml)","tokens":300,"sizeBytes":275},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-color-pickers/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/CHANGELOG.md","title":"Flet-color-pickers Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-color-pickers Skill\n\nPath: `sdk/python/packages/flet-color-pickers/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/CHANGELOG.md)","tokens":300,"sizeBytes":223},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/analysis_options.yaml","title":"Flet_color_pickers Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_color_pickers Skill\n\nPath: `sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/analysis_options.yaml)","tokens":300,"sizeBytes":303},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/pubspec.yaml","title":"Flet_color_pickers Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_color_pickers Skill\n\nPath: `sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/src/flutter/flet_color_pickers/pubspec.yaml)","tokens":300,"sizeBytes":285},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-datatable2/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-datatable2/CHANGELOG.md","title":"Flet-datatable2 Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-datatable2 Skill\n\nPath: `sdk/python/packages/flet-datatable2/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-datatable2/CHANGELOG.md)","tokens":300,"sizeBytes":214},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-datatable2/src/flutter/flet_datatable2/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-datatable2/src/flutter/flet_datatable2/pubspec.yaml","title":"Flet_datatable2 Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_datatable2 Skill\n\nPath: `sdk/python/packages/flet-datatable2/src/flutter/flet_datatable2/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-datatable2/src/flutter/flet_datatable2/pubspec.yaml)","tokens":300,"sizeBytes":270},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-flashlight/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/CHANGELOG.md","title":"Flet-flashlight Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-flashlight Skill\n\nPath: `sdk/python/packages/flet-flashlight/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/CHANGELOG.md)","tokens":300,"sizeBytes":214},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/analysis_options.yaml","title":"Flet_flashlight Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_flashlight Skill\n\nPath: `sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/analysis_options.yaml)","tokens":300,"sizeBytes":288},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/pubspec.yaml","title":"Flet_flashlight Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_flashlight Skill\n\nPath: `sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/src/flutter/flet_flashlight/pubspec.yaml)","tokens":300,"sizeBytes":270},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-geolocator/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/CHANGELOG.md","title":"Flet-geolocator Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-geolocator Skill\n\nPath: `sdk/python/packages/flet-geolocator/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/CHANGELOG.md)","tokens":300,"sizeBytes":214},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/analysis_options.yaml","title":"Flet_geolocator Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_geolocator Skill\n\nPath: `sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/analysis_options.yaml)","tokens":300,"sizeBytes":288},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/pubspec.yaml","title":"Flet_geolocator Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_geolocator Skill\n\nPath: `sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/src/flutter/flet_geolocator/pubspec.yaml)","tokens":300,"sizeBytes":270},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-local-auth/src/flutter/flet_local_auth/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-local-auth/src/flutter/flet_local_auth/pubspec.yaml","title":"Flet_local_auth Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_local_auth Skill\n\nPath: `sdk/python/packages/flet-local-auth/src/flutter/flet_local_auth/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-local-auth/src/flutter/flet_local_auth/pubspec.yaml)","tokens":300,"sizeBytes":270},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-lottie/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/CHANGELOG.md","title":"Flet-lottie Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-lottie Skill\n\nPath: `sdk/python/packages/flet-lottie/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/CHANGELOG.md)","tokens":300,"sizeBytes":202},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-lottie/src/flutter/flet_lottie/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/src/flutter/flet_lottie/analysis_options.yaml","title":"Flet_lottie Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_lottie Skill\n\nPath: `sdk/python/packages/flet-lottie/src/flutter/flet_lottie/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/src/flutter/flet_lottie/analysis_options.yaml)","tokens":300,"sizeBytes":268},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-lottie/src/flutter/flet_lottie/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/src/flutter/flet_lottie/pubspec.yaml","title":"Flet_lottie Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_lottie Skill\n\nPath: `sdk/python/packages/flet-lottie/src/flutter/flet_lottie/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/src/flutter/flet_lottie/pubspec.yaml)","tokens":300,"sizeBytes":250},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-map/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/CHANGELOG.md","title":"Flet-map Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-map Skill\n\nPath: `sdk/python/packages/flet-map/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/CHANGELOG.md)","tokens":300,"sizeBytes":193},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-map/src/flutter/flet_map/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/src/flutter/flet_map/analysis_options.yaml","title":"Flet_map Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_map Skill\n\nPath: `sdk/python/packages/flet-map/src/flutter/flet_map/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/src/flutter/flet_map/analysis_options.yaml)","tokens":300,"sizeBytes":253},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-map/src/flutter/flet_map/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/src/flutter/flet_map/pubspec.yaml","title":"Flet_map Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_map Skill\n\nPath: `sdk/python/packages/flet-map/src/flutter/flet_map/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/src/flutter/flet_map/pubspec.yaml)","tokens":300,"sizeBytes":235},{"name":"icons.json","path":"sdk/python/packages/flet-mcp/src/flet_mcp/data/icons.json","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-mcp/src/flet_mcp/data/icons.json","title":"Data Skill","category":"anthropic-skill","format":"json","content":"# Data Skill\n\nPath: `sdk/python/packages/flet-mcp/src/flet_mcp/data/icons.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-mcp/src/flet_mcp/data/icons.json)","tokens":300,"sizeBytes":221},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-permission-handler/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/CHANGELOG.md","title":"Flet-permission-handler Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-permission-handler Skill\n\nPath: `sdk/python/packages/flet-permission-handler/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/CHANGELOG.md)","tokens":300,"sizeBytes":238},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/analysis_options.yaml","title":"Flet_permission_handler Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_permission_handler Skill\n\nPath: `sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/analysis_options.yaml)","tokens":300,"sizeBytes":328},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/pubspec.yaml","title":"Flet_permission_handler Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_permission_handler Skill\n\nPath: `sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/src/flutter/flet_permission_handler/pubspec.yaml)","tokens":300,"sizeBytes":310},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-rive/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/CHANGELOG.md","title":"Flet-rive Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-rive Skill\n\nPath: `sdk/python/packages/flet-rive/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/CHANGELOG.md)","tokens":300,"sizeBytes":196},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-rive/src/flutter/flet_rive/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/src/flutter/flet_rive/analysis_options.yaml","title":"Flet_rive Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_rive Skill\n\nPath: `sdk/python/packages/flet-rive/src/flutter/flet_rive/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/src/flutter/flet_rive/analysis_options.yaml)","tokens":300,"sizeBytes":258},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-rive/src/flutter/flet_rive/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/src/flutter/flet_rive/pubspec.yaml","title":"Flet_rive Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_rive Skill\n\nPath: `sdk/python/packages/flet-rive/src/flutter/flet_rive/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/src/flutter/flet_rive/pubspec.yaml)","tokens":300,"sizeBytes":240},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-secure-storage/src/flutter/flet_secure_storage/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-secure-storage/src/flutter/flet_secure_storage/pubspec.yaml","title":"Flet_secure_storage Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_secure_storage Skill\n\nPath: `sdk/python/packages/flet-secure-storage/src/flutter/flet_secure_storage/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-secure-storage/src/flutter/flet_secure_storage/pubspec.yaml)","tokens":300,"sizeBytes":290},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-spinkit/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/CHANGELOG.md","title":"Flet-spinkit Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-spinkit Skill\n\nPath: `sdk/python/packages/flet-spinkit/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/CHANGELOG.md)","tokens":300,"sizeBytes":205},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/analysis_options.yaml","title":"Flet_spinkit Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_spinkit Skill\n\nPath: `sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/analysis_options.yaml)","tokens":300,"sizeBytes":273},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/pubspec.yaml","title":"Flet_spinkit Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_spinkit Skill\n\nPath: `sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/src/flutter/flet_spinkit/pubspec.yaml)","tokens":300,"sizeBytes":255},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-video/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/CHANGELOG.md","title":"Flet-video Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-video Skill\n\nPath: `sdk/python/packages/flet-video/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/CHANGELOG.md)","tokens":300,"sizeBytes":199},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-video/src/flutter/flet_video/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/src/flutter/flet_video/analysis_options.yaml","title":"Flet_video Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_video Skill\n\nPath: `sdk/python/packages/flet-video/src/flutter/flet_video/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/src/flutter/flet_video/analysis_options.yaml)","tokens":300,"sizeBytes":263},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-video/src/flutter/flet_video/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/src/flutter/flet_video/pubspec.yaml","title":"Flet_video Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_video Skill\n\nPath: `sdk/python/packages/flet-video/src/flutter/flet_video/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/src/flutter/flet_video/pubspec.yaml)","tokens":300,"sizeBytes":245},{"name":"CHANGELOG.md","path":"sdk/python/packages/flet-webview/CHANGELOG.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/CHANGELOG.md","title":"Flet-webview Skill","category":"anthropic-skill","format":"markdown","content":"# Flet-webview Skill\n\nPath: `sdk/python/packages/flet-webview/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/CHANGELOG.md)","tokens":300,"sizeBytes":205},{"name":"analysis_options.yaml","path":"sdk/python/packages/flet-webview/src/flutter/flet_webview/analysis_options.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/src/flutter/flet_webview/analysis_options.yaml","title":"Flet_webview Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_webview Skill\n\nPath: `sdk/python/packages/flet-webview/src/flutter/flet_webview/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/src/flutter/flet_webview/analysis_options.yaml)","tokens":300,"sizeBytes":273},{"name":"pubspec.yaml","path":"sdk/python/packages/flet-webview/src/flutter/flet_webview/pubspec.yaml","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/src/flutter/flet_webview/pubspec.yaml","title":"Flet_webview Skill","category":"anthropic-skill","format":"yaml","content":"# Flet_webview Skill\n\nPath: `sdk/python/packages/flet-webview/src/flutter/flet_webview/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/src/flutter/flet_webview/pubspec.yaml)","tokens":300,"sizeBytes":255},{"name":"cupertino_icons.json","path":"sdk/python/packages/flet/src/flet/controls/cupertino/cupertino_icons.json","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/src/flet/controls/cupertino/cupertino_icons.json","title":"Cupertino Skill","category":"anthropic-skill","format":"json","content":"# Cupertino Skill\n\nPath: `sdk/python/packages/flet/src/flet/controls/cupertino/cupertino_icons.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/src/flet/controls/cupertino/cupertino_icons.json)","tokens":300,"sizeBytes":258},{"name":"icons.json","path":"sdk/python/packages/flet/src/flet/controls/material/icons.json","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/src/flet/controls/material/icons.json","title":"Material Skill","category":"anthropic-skill","format":"json","content":"# Material Skill\n\nPath: `sdk/python/packages/flet/src/flet/controls/material/icons.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/src/flet/controls/material/icons.json)","tokens":300,"sizeBytes":235},{"name":"SKILL.md","path":"website/.agents/skills/flet-release-announcement/SKILL.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/website/.agents/skills/flet-release-announcement/SKILL.md","title":"flet-release-announcement","category":"anthropic-skill","format":"markdown","content":"# flet-release-announcement\n\nPath: `website/.agents/skills/flet-release-announcement/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/website/.agents/skills/flet-release-announcement/SKILL.md)","tokens":300,"sizeBytes":236},{"name":"CLAUDE.md","path":"CLAUDE.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/CLAUDE.md","title":"Claude Agent Guidelines & System Prompt","category":"claude-rule","format":"markdown","content":"# Claude Agent Guidelines & System Prompt\n\nPath: `CLAUDE.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/CLAUDE.md)","tokens":300,"sizeBytes":154},{"name":"README.md","path":"packages/flet/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/README.md","title":"flet Documentation","category":"plugin-manifest","format":"markdown","content":"# flet Documentation\n\nPath: `packages/flet/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/README.md)","tokens":300,"sizeBytes":161},{"name":"README.md","path":"sdk/python/packages/flet-ads/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/README.md","title":"flet-ads Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-ads Documentation\n\nPath: `sdk/python/packages/flet-ads/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/README.md)","tokens":300,"sizeBytes":195},{"name":"README.md","path":"sdk/python/packages/flet-audio-recorder/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/README.md","title":"flet-audio-recorder Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-audio-recorder Documentation\n\nPath: `sdk/python/packages/flet-audio-recorder/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/README.md)","tokens":300,"sizeBytes":228},{"name":"README.md","path":"sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/README.md","title":"flet_audio_recorder Documentation","category":"plugin-manifest","format":"markdown","content":"# flet_audio_recorder Documentation\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/README.md)","tokens":300,"sizeBytes":292},{"name":"README.md","path":"sdk/python/packages/flet-audio/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/README.md","title":"flet-audio Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-audio Documentation\n\nPath: `sdk/python/packages/flet-audio/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/README.md)","tokens":300,"sizeBytes":201},{"name":"README.md","path":"sdk/python/packages/flet-camera/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-camera/README.md","title":"flet-camera Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-camera Documentation\n\nPath: `sdk/python/packages/flet-camera/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-camera/README.md)","tokens":300,"sizeBytes":204},{"name":"README.md","path":"sdk/python/packages/flet-charts/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/README.md","title":"flet-charts Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-charts Documentation\n\nPath: `sdk/python/packages/flet-charts/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-charts/README.md)","tokens":300,"sizeBytes":204},{"name":"README.md","path":"sdk/python/packages/flet-cli/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-cli/README.md","title":"flet-cli Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-cli Documentation\n\nPath: `sdk/python/packages/flet-cli/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-cli/README.md)","tokens":300,"sizeBytes":195},{"name":"README.md","path":"sdk/python/packages/flet-code-editor/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/README.md","title":"flet-code-editor Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-code-editor Documentation\n\nPath: `sdk/python/packages/flet-code-editor/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-code-editor/README.md)","tokens":300,"sizeBytes":219},{"name":"README.md","path":"sdk/python/packages/flet-color-pickers/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/README.md","title":"flet-color-pickers Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-color-pickers Documentation\n\nPath: `sdk/python/packages/flet-color-pickers/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-color-pickers/README.md)","tokens":300,"sizeBytes":225},{"name":"README.md","path":"sdk/python/packages/flet-datatable2/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-datatable2/README.md","title":"flet-datatable2 Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-datatable2 Documentation\n\nPath: `sdk/python/packages/flet-datatable2/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-datatable2/README.md)","tokens":300,"sizeBytes":216},{"name":"README.md","path":"sdk/python/packages/flet-desktop/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-desktop/README.md","title":"flet-desktop Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-desktop Documentation\n\nPath: `sdk/python/packages/flet-desktop/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-desktop/README.md)","tokens":300,"sizeBytes":207},{"name":"README.md","path":"sdk/python/packages/flet-flashlight/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/README.md","title":"flet-flashlight Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-flashlight Documentation\n\nPath: `sdk/python/packages/flet-flashlight/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-flashlight/README.md)","tokens":300,"sizeBytes":216},{"name":"README.md","path":"sdk/python/packages/flet-geolocator/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/README.md","title":"flet-geolocator Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-geolocator Documentation\n\nPath: `sdk/python/packages/flet-geolocator/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-geolocator/README.md)","tokens":300,"sizeBytes":216},{"name":"README.md","path":"sdk/python/packages/flet-local-auth/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-local-auth/README.md","title":"flet-local-auth Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-local-auth Documentation\n\nPath: `sdk/python/packages/flet-local-auth/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-local-auth/README.md)","tokens":300,"sizeBytes":216},{"name":"README.md","path":"sdk/python/packages/flet-lottie/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/README.md","title":"flet-lottie Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-lottie Documentation\n\nPath: `sdk/python/packages/flet-lottie/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-lottie/README.md)","tokens":300,"sizeBytes":204},{"name":"README.md","path":"sdk/python/packages/flet-map/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/README.md","title":"flet-map Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-map Documentation\n\nPath: `sdk/python/packages/flet-map/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-map/README.md)","tokens":300,"sizeBytes":195},{"name":"README.md","path":"sdk/python/packages/flet-mcp/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-mcp/README.md","title":"flet-mcp Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-mcp Documentation\n\nPath: `sdk/python/packages/flet-mcp/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-mcp/README.md)","tokens":300,"sizeBytes":195},{"name":"README.md","path":"sdk/python/packages/flet-permission-handler/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/README.md","title":"flet-permission-handler Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-permission-handler Documentation\n\nPath: `sdk/python/packages/flet-permission-handler/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-permission-handler/README.md)","tokens":300,"sizeBytes":240},{"name":"README.md","path":"sdk/python/packages/flet-platform-assets/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-platform-assets/README.md","title":"flet-platform-assets Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-platform-assets Documentation\n\nPath: `sdk/python/packages/flet-platform-assets/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-platform-assets/README.md)","tokens":300,"sizeBytes":231},{"name":"README.md","path":"sdk/python/packages/flet-rive/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/README.md","title":"flet-rive Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-rive Documentation\n\nPath: `sdk/python/packages/flet-rive/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-rive/README.md)","tokens":300,"sizeBytes":198},{"name":"README.md","path":"sdk/python/packages/flet-secure-storage/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-secure-storage/README.md","title":"flet-secure-storage Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-secure-storage Documentation\n\nPath: `sdk/python/packages/flet-secure-storage/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-secure-storage/README.md)","tokens":300,"sizeBytes":228},{"name":"README.md","path":"sdk/python/packages/flet-spinkit/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/README.md","title":"flet-spinkit Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-spinkit Documentation\n\nPath: `sdk/python/packages/flet-spinkit/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-spinkit/README.md)","tokens":300,"sizeBytes":207},{"name":"README.md","path":"sdk/python/packages/flet-video/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/README.md","title":"flet-video Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-video Documentation\n\nPath: `sdk/python/packages/flet-video/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-video/README.md)","tokens":300,"sizeBytes":201},{"name":"README.md","path":"sdk/python/packages/flet-web/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-web/README.md","title":"flet-web Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-web Documentation\n\nPath: `sdk/python/packages/flet-web/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-web/README.md)","tokens":300,"sizeBytes":195},{"name":"README.md","path":"sdk/python/packages/flet-web/src/flet_web/fastapi/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-web/src/flet_web/fastapi/README.md","title":"fastapi Documentation","category":"plugin-manifest","format":"markdown","content":"# fastapi Documentation\n\nPath: `sdk/python/packages/flet-web/src/flet_web/fastapi/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-web/src/flet_web/fastapi/README.md)","tokens":300,"sizeBytes":236},{"name":"README.md","path":"sdk/python/packages/flet-webview/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/README.md","title":"flet-webview Documentation","category":"plugin-manifest","format":"markdown","content":"# flet-webview Documentation\n\nPath: `sdk/python/packages/flet-webview/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-webview/README.md)","tokens":300,"sizeBytes":207},{"name":"README.md","path":"sdk/python/packages/flet/integration_tests/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/integration_tests/README.md","title":"integration_tests Documentation","category":"plugin-manifest","format":"markdown","content":"# integration_tests Documentation\n\nPath: `sdk/python/packages/flet/integration_tests/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/integration_tests/README.md)","tokens":300,"sizeBytes":232},{"name":"README.md","path":"sdk/python/packages/flet/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/README.md","title":"flet Documentation","category":"plugin-manifest","format":"markdown","content":"# flet Documentation\n\nPath: `sdk/python/packages/flet/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet/README.md)","tokens":300,"sizeBytes":183},{"name":"README.md","path":"tools/crocodocs/README.md","rawUrl":"https://raw.githubusercontent.com/flet-dev/flet/HEAD/tools/crocodocs/README.md","title":"crocodocs Documentation","category":"plugin-manifest","format":"markdown","content":"# crocodocs Documentation\n\nPath: `tools/crocodocs/README.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/tools/crocodocs/README.md)","tokens":300,"sizeBytes":170}],"systemPromptSnippet":"<yakaai_skills repo=\"flet-dev/flet\">\n<!-- File: AGENTS.md (Tokens: ~300 | Category: root-instruction) -->\n# AI Agent Protocol & Instructions\n\nPath: `AGENTS.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/AGENTS.md)\n\n<!-- File: .agents/skills/create-flet-control-integration-tests/SKILL.md (Tokens: ~1269 | Category: anthropic-skill) -->\n---\nname: create-flet-control-integration-tests\ndescription: Use when asked to create or update integration tests for any Flet control in sdk/python/packages/flet/integration_tests, including visual goldens and interactive behavior tests.\n---\n\n## When to use\n\nUse this skill when adding, updating, or reviewing integration tests for a Flet control (core, material, cupertino, theme, services, types, or examples).\n\nUse it for:\n\n- visual rendering checks with golden screenshots\n- interaction checks (hover, click, input, keyboard)\n- control property behavior checks\n- regression tests for control bugs\n\n## Test placement\n\nPick the closest existing suite first:\n\n- Core controls: `sdk/python/packages/flet/integration_tests/controls/core`\n- Material controls: `sdk/python/packages/flet/integration_tests/controls/material`\n- Cupertino controls: `sdk/python/packages/flet/integration_tests/controls/cupertino`\n- Theme tests: `sdk/python/packages/flet/integration_tests/controls/theme`\n- Type helpers: `sdk/python/packages/flet/integration_tests/controls/types`\n- Services: `sdk/python/packages/flet/integration_tests/controls/services`\n- Examples: `sdk/python/packages/flet/integration_tests/examples`\n\nPrefer adding tests to an existing file for the same control. Create a new test file only when no suitable file exists.\n\n### Scope split rule (required)\n\nDo not mix `loop_scope=\"module\"` and `loop_scope=\"function\"` tests in the same file.\n\nNaming convention:\n\n- `test_<control>.py` for module-scoped visual/stable tests (uses `flet_app`)\n- `test_<control>_isolated.py` for function-scoped tests that require a fresh app per test (uses `flet_app_function`)\n\n## Fixture choice\n\nUse fixtures from `integration_tests/conftest.py`:\n\n- `flet_app` (`loop_scope=\"module\"`): best for stable visual tests and bulk screenshot tests.\n- `flet_app_function` (`loop_scope=\"function\"`): best for tests that mutate state and must run in a separate app each.\n\n## Authoring workflow\n\n1. Identify behavior to verify.\n2. Build deterministic layout/state:\n- set `theme_mode` explicitly when visuals matter\n- set fixed sizes/padding/spacing\n- avoid random or time-varying content\n3. Choose file by scope rule before writing tests.\n4. Write test using async pytest.\n5. Use screenshot assertion for UI behavior, functional assertion for non-visual behavior.\n6. Name test so `request.node.name` can be used as screenshot key.\n7. Run target test file.\n8. If expected visuals changed, regenerate goldens with `FLET_TEST_GOLDEN=1` and re-run without golden mode.\n\n## Assertion patterns\n\n### Visual control assertion\n\n```python\nawait flet_app.assert_control_screenshot(\n    request.node.name,\n    control,\n)\n```\n\n### Visual full-page assertion\n\n```python\nflet_app_function.assert_screenshot(\n    request.node.name,\n    await flet_app_function.page.take_screenshot(\n        pixel_ratio=flet_app_function.screenshots_pixel_ratio\n    ),\n)\n```\n\n### Functional assertion\n\n```python\nfinder = await flet_app_function.tester.find_by_tooltip(\"Info tooltip\")\nassert finder.count == 1\n```\n\n## Minimal templates\n\n### Template: module-scope file (`test_<control>.py`)\n\n```python\nimport pytest\n\nimport flet as ft\nimport flet.testing as ftt\n\n\n@pytest.mark.asyncio(loop_scope=\"module\")\nasync def test_<behavior>(flet_app: ftt.FletTestApp, request):\n    flet_app.page.theme_mode = ft.ThemeMode.LIGHT\n    await flet_app.assert_control_screenshot(\n        request.node.name,\n        ft.Container(width=240, height=80, alignment=ft.Alignment.CENTER),\n    )\n```\n\n### Template: function-scope file (`test_<control>_isolated.py`)\n\n```python\nimport pytest\n\nimport flet as ft\nimport flet.testing as ftt\n\n\n@pytest.mark.asyncio(loop_scope=\"function\")\nasync def test_<behavior>(flet_app_function: ftt.FletTestApp):\n    flet_app_function.page.add(ft.IconButton(icon=ft.Icons.INFO, tooltip=\"Info\"))\n    await flet_app_function.tester.pump_and_settle()\n\n    finder = await flet_app_function.tester.find_by_tooltip(\"Info\")\n    assert finder.count == 1\n```\n\n## Run commands\n\nRun one test file:\n\n```bash\nuv run pytest -s -o log_cli=true -o log_cli_level=INFO packages/flet/integration_tests/controls/core/test_control.py\n```\n\nRun a subset:\n\n```bash\nuv run pytest -s -o log_cli=true -o log_cli_level=INFO packages/flet/integration_tests/controls/core/test_control.py -k test_visible\n```\n\nGenerate or update goldens:\n\n```bash\nFLET_TEST_GOLDEN=1 uv run pytest -s -o log_cli=true -o log_cli_level=INFO packages/flet/integration_tests/controls/core/test_control.py\n```\n\n## Quality checklist\n\n- Test file location matches control area.\n- `module` and `function` scope tests are in separate files.\n- Function-scoped files use the `test_<control>_isolated.py` naming convention.\n- Fixture scope matches test intent.\n- Screenshot keys are stable (`request.node.name` preferred).\n- Visual tests are deterministic (theme/size/content).\n- Goldens are updated only for intentional visual changes.\n- No unrelated formatting or refactors in the same change.\n\n## References\n\n- `sdk/python/packages/flet/integration_tests/README.md`\n- `sdk/python/packages/flet/integration_tests/conftest.py`\n- `sdk/python/packages/flet/integration_tests/controls/core/test_control.py`\n- `sdk/python/packages/flet/integration_tests/controls/core/test_control_isolated.py`\n- `sdk/python/packages/flet/integration_tests/controls/core/test_layout_control.py`\n- `sdk/python/packages/flet/integration_tests/examples/core/test_control.py`\n- `sdk/python/examples/controls/control`\n\n<!-- File: .agents/skills/create-flet-example-projects/SKILL.md (Tokens: ~2147 | Category: anthropic-skill) -->\n---\nname: create-flet-example-projects\ndescription: Use when asked to create Flet example projects from flat .py files with main.py and pyproject.toml metadata for Gallery/MCP indexing.\n---\n\n## When to use\n\nUse this skill when a user asks to:\n- create one control/example folder (for example `examples/controls/chip`) in the project-per-example format\n- migrate existing flat examples to the project-per-example format\n- normalize a partially converted folder so all examples follow the same structure\n\n## Goal\n\nEnsure each runnable example is a standalone project containing:\n\n- `main.py`\n- `pyproject.toml` with Gallery/MCP metadata\n- `assets/` (if the example uses local assets)\n\n## Workflow\n\n1. Inspect source folder.\n- Detect current state per example:\n  - flat file: `foo.py`\n  - project folder: `foo/main.py`\n  - mixed/partial conversion: both styles present or missing metadata files\n- Find candidate flat modules: `*.py` in the target folder (exclude helper files such as `__init__.py`).\n- Keep existing `media/` unless an example needs local assets copied into its own `assets/`.\n\n2. Convert or normalize examples.\n- For `foo.py`, create `foo/` and move file to `foo/main.py`.\n- If `foo/main.py` already exists, keep it and do not recreate/move files.\n- If folder exists but `main.py` is missing, repair structure only when there is a clear source file.\n- Do not create `foo/__init__.py`; import example modules directly in tests/docs (for example `import examples.controls.foo.bar.main as bar` or `import examples.controls.foo.bar as bar` when using namespace-package imports).\n- When a control folder has been fully converted to project-per-example layout, delete the control-level `examples/controls/<control>/__init__.py` too. The converted folders should behave like namespace packages, matching prior migrations such as commit `7e65ad566`.\n\n3. Add `pyproject.toml` for each example project.\n- Infer from path and code.\n- Create missing `pyproject.toml` files for existing project folders.\n- Update obviously stale metadata when migrating existing examples (for example wrong title/description/categories).\n- Verify platform support before adding or omitting `[tool.flet].platforms`:\n  - Check the local implementation and docs for explicit platform guards, support tables, or platform-specific exceptions.\n  - If support is limited, add `[tool.flet].platforms` with only the supported platforms.\n  - If support is broad/all-platform, omit `[tool.flet].platforms`.\n- Required fields:\n  - `[project]`: `name`, `version`, `description`, `requires-python`, `keywords`, `authors`, `dependencies`\n  - `[dependency-groups].dev`: include `flet-cli`, `flet-desktop`, `flet-web`\n  - `[tool.flet.gallery].categories`\n  - `[tool.flet.metadata]`: `title`, `controls`, `layout_pattern`, `complexity`, `features`\n  - `[tool.flet]`: `org`, `company`, `copyright`\n- Add `[tool.flet].platforms` only when the example is platform-limited.\n- Add permissions blocks only when code actually needs them.\n\n4. Infer metadata.\n- Title: readable version of file/folder intent.\n- Short description: one line of what the example demonstrates.\n- `[project].description` must be meaningful and example-specific; avoid generic placeholders like \"Example N\" or \"<name> example for <control>\".\n- Description should mention the concrete behavior or interaction shown (for example: hover highlight, live updates, custom axes, event handling).\n- Categories: typically control-based, e.g. `Input/Chip`, plus optional `Apps/Basic controls`.\n- Tags: from control/topic/behavior words.\n- Controls used: list key controls from code.\n- Layout pattern: choose closest practical value (e.g. `filter-bar`, `inline-actions`, `dashboard`, `list-detail`).\n- Complexity: `basic` unless logic/state/architecture is non-trivial.\n- Features: notable behaviors only (click handling, selection, async loading, drag-and-drop, etc.).\n- If an example supports exporting or downloading output, include `\"save to file\"` in `[tool.flet.metadata].features`.\n- If an example module contains `async def` handlers or async control flow, append `\"async\"` to `keywords`.\n\n\n5. Infer dependencies from imports.\n- Always include `flet` for standard examples.\n- Include extra packages if imported (for example extension packages).\n- Do not add unused dependencies.\n\n6. Make examples mobile-safe.\n- If `ft.context.disable_auto_update()` is not used, do not add explicit `page.update()` unless strictly necessary.\n- Apply this `page.update()` rule to all examples in the touched folder (new, migrated, and already converted).\n- Wrap app content in `ft.SafeArea` so example renders correctly on mobile.\n- Add `expand=True` to `ft.SafeArea` only when needed for correct layout/sizing (for example to avoid Infinity/NaN sizing issues), and avoid adding it when not necessary.\n- When converting legacy `page.add(a, b, ...)` style examples, wrap the controls in `ft.Column(controls=[...])` inside `ft.SafeArea(content=...)` rather than `ft.Row`, unless the original code explicitly used a row layout.\n\n- Apply this to all examples in the touched folder (new, migrated, and already converted), not only files changed by moves.\n- During validation, confirm every `<example>/main.py` in scope includes a top-level `ft.SafeArea` around rendered content.\n- For declarative examples using `@ft.component`, do not pass component instances as regular control children (for example `SafeArea(content=App())`) because this can raise runtime attribute errors.\n- In declarative examples, ensure the component itself returns regular controls (including `SafeArea` when needed) and render it at page level with `page.render(App)` in `main()`.\n\n7. Prefer `@ft.control` for custom controls in examples.\n- If an example defines a custom control class inheriting from a Flet control (for example `class MyThing(ft.Column)`), prefer `@ft.control` style.\n- Move constructor-style setup to declarative fields + `init()` where practical.\n- Keep behavior unchanged and avoid refactors that alter public usage unless needed for compatibility.\n\n8. Remove deprecated Material 3 toggle usage.\n- If `use_material3` appears in example code, remove it and simplify the example to current API usage.\n- Remove related Material 3 toggle logic/UI that exists only to switch `use_material3`.\n- Update example metadata (`pyproject.toml`) to remove stale Material 3 references when code is changed.\n\n9. Ensure runnable entrypoint.\n- Every example `main.py` should end with:\n  - `if __name__ == \"__main__\":`\n  - `    ft.run(main)`\n- Apply this to all examples in the touched folder (new, migrated, and already converted).\n\n10. Update references.\n- Docs code includes: change from `.../example.py` to `.../example/main.py`.\n- Inspect the relevant docs pages for each touched control/service/example area (for example `sdk/python/packages/flet/docs/controls/<control>.md`) and update any `--8<--` includes or direct file-path references to the new `main.py` path.\n- Tests/imports: use direct module imports and avoid relying on package-level `__init__.py` re-exports.\n- For already-converted examples, only update references that are stale; avoid unnecessary churn.\n- If removing a control-level `__init__.py`, confirm no remaining imports rely on `from examples.controls.<control> import ...`.\n\n11. Validate.\n- Run `python -m compileall` on changed `main.py` files.\n- Run `uv run ruff check` on changed example files and fix violations until it passes (respecting repository `pyproject.toml` under `[tool.ruff]`).\n- Search for stale paths to old flat files.\n- Search docs and package sources for stale references to the migrated flat example paths and fix any hits in scope.\n- Check `git status` to confirm expected moves and edits.\n- When integration tests exist for the touched control, run the targeted test file(s).\n- Confirm all in-scope `main.py` files include both top-level `ft.SafeArea` wrapping and the `if __name__ == \"__main__\": ft.run(main)` entrypoint.\n- Confirm in-scope `ft.SafeArea` wrappers use `expand=True` only where needed for correct behavior and sizing; avoid forcing it by default.\n- Confirm there are no unnecessary `page.update()` calls in in-scope examples (unless explicitly required by isolated-control or non-auto-update behavior).\n- Confirm no in-scope examples use `use_material3`.\n- Confirm each in-scope `pyproject.toml` has a meaningful, example-specific `[project].description` (not generic or templated text).\n- Confirm metadata features include `\"save to file\"` when the example code supports file export/save behavior.\n- Confirm there is no stale control-level `__init__.py` left behind once a touched control folder has been fully converted.\n- Confirm the relevant docs pages were updated to reference `main.py` and that no stale doc includes remain for the touched examples.\n\n\n## Code style\n\n- When writing wrapped controls (`SafeArea`, `Column`, `Row`, `Container`, etc.), keep `content=` or `controls=` as the last named argument in that control call.\n- Apply this ordering consistently when creating or refactoring examples.\n- Follow code style and linting rules defined in the repository `pyproject.toml` under `[tool.ruff]` for all edits.\n\n## Command checklist\n\n- Discover files: `rg --files <target_dir>`\n- Find docs links/imports: `rg -n \"<old_path_or_module>\" packages examples`\n- Syntax check: `python -m compileall <changed_main_files>`\n- Ruff check: `uv run ruff check <changed_example_files>`\n\n## Output expectations\n\nReport:\n- created example projects\n- metadata added\n- docs/tests updates\n- validation results\n\n<!-- File: .agents/skills/docs-build-and-verify/SKILL.md (Tokens: ~555 | Category: anthropic-skill) -->\n---\nname: docs-build-and-verify\ndescription: Use when asked to build, preview, or verify the Flet documentation website, including checking for broken links, broken images, and unresolved reST cross-references.\n---\n\n# Docs Build and Verification\n\n## Prerequisites\n\nNode.js 24 is required, matching what CI runs:\n\n```bash\nnvm use 24\n```\n\n## Build\n\nFull production build (includes broken link detection):\n\n```bash\ncd website && yarn build\n```\n\nDev server with hot reload:\n\n```bash\ncd website && yarn start\n```\n\nRegenerate API data and sidebars only (no Docusaurus build):\n\n```bash\ncd website && yarn crocodocs:generate\n```\n\n## Check Broken Links\n\n`yarn build` reports both, but only broken *links* fail the build. Docusaurus defaults\n`onBrokenAnchors` to `warn` and `docusaurus.config.js` does not override it, so a broken\nanchor scrolls past in the log and still ships - grep the build output for `Broken anchor`\nrather than trusting the exit code.\n\n## Check Broken Images\n\nRun this after `yarn build` to find images referenced in HTML that don't exist:\n\n```bash\ncd website && python3 -c \"\nimport re, os, glob\n\nbuild_dir = 'build'\nimg_re = re.compile(r'<img[^>]+src=\\\"(/[^\\\"]+)\\\"', re.IGNORECASE)\nbroken = []\n\nfor html_file in sorted(glob.glob(f'{build_dir}/docs/**/index.html', recursive=True)):\n    page = html_file.replace(build_dir + '/', '').replace('/index.html', '')\n    content = open(html_file).read()\n    for match in img_re.finditer(content):\n        src = match.group(1)\n        if src.startswith('http') or src.startswith('data:'):\n            continue\n        file_path = os.path.join(build_dir, src.lstrip('/'))\n        if not os.path.exists(file_path):\n            broken.append((page, src))\n\nif broken:\n    print(f'Found {len(broken)} broken images:')\n    for page, src in broken:\n        print(f'  {page}: {src}')\nelse:\n    print('No broken images found!')\n\"\n```\n\n## Check Unresolved reST Cross-References\n\nAfter building, check for reST roles that failed to resolve and appear as raw text:\n\n```bash\ncd website && grep -r ':attr:\\|:class:\\|:meth:\\|:func:' build/docs/ --include='*.html' -l\n```\n\nIf any files are listed, those pages have unresolved cross-references that render as plain text instead of links.\n\n<!-- File: .agents/skills/docs-conventions/SKILL.md (Tokens: ~1576 | Category: anthropic-skill) -->\n---\nname: docs-conventions\ndescription: Use when writing or reviewing Flet documentation, including Python docstrings (Google style, reST roles, admonitions), Markdown docs (cross-references, images, code examples), and sidebar navigation.\n---\n\n# Documentation Conventions\n\nDocs live in `website/docs/`. Docusaurus renders them as the website.\n\n## Python Docstrings\n\nUse **Google style** docstrings with sections: `Args:`, `Returns:`, `Raises:`, `Note:`, `Example:`, `Warning:`.\n\n## Cross-references\n\n### reST roles\n\nPrefer these in Python docstrings. CrocoDocs renders them as links in\nthe API docs and they keep authoring terse when the auto-derived label is acceptable.\n\n**Supported roles:** `:class:`, `:attr:`, `:meth:`, `:func:`, `:data:`, `:mod:`\n\n```python\n\"\"\"\nIf a parent is a :class:`~flet.ResponsiveRow`, this property determines\nhow many virtual columns the control spans.\n\nSee :attr:`value` or :attr:`flet.Text.size` for the current selection.\n\nCalls :meth:`flet.Page.update` after modifying controls.\n\"\"\"\n```\n\n**Rules:**\n\n- **Qualified reference:** `:attr:`flet.Page.route`` — links to the member, displays inline code `Page.route`\n- **Extension reference:** `:attr:`flet_map.Map.animation_curve`` — links to the extension member, displays inline code `Map.animation_curve`\n- **Short display with `~`:** `:attr:`~flet.Page.route`` — links to the member, displays inline code `route`\n- **Local member (same class):** `:attr:`value`` — no qualifier needed\n- **Method with parens:** `:meth:`update`` — do NOT include `()` in the target\n\nFor plain class references like `:class:`flet.Page`` and extension references like\n`:class:`flet_map.Map``, the website strips leading public package aliases automatically,\nso they display as inline code `Page` and `Map`.\n\n**Not supported:**\n\n- Custom labels like `:class:`my label <flet.Page>`` — the label is always auto-derived from the target\n- Roles for symbols not in CrocoDocs API data degrade to inline code\n\n### Xrefs\n\nReference-style Markdown links of the form `[label][key]`, where `key` is the\nfully-qualified dotted symbol path (same form as reST role targets).\n\nUse as the default form for linking to API symbols from Markdown docs\n(`.md` / `.mdx`).\n\nExamples:\n\n```markdown\nClass: [`Page`][flet.Page]\nAttribute: [`route`][flet.Page.route]\nMethod: [`Page.update()`][flet.Page.update]\nExtension: [`Video.controls`][flet_video.Video.controls]\nPlain text: [the route attribute][flet.Page.route]\n```\n\n**When to prefer over the other forms:**\n\n- **Flexible labels** — the first `[ ]` accepts any text or inline code, unlike reST roles whose label is always auto-derived from the target\n- **Path-independent** — keys are dotted symbol paths, so links don't break when source files are moved, renamed, or restructured (unlike Markdown link paths with `../` and `#flet.X.y` anchors)\n- **Terser** than Markdown links to the same symbol — no relative path or anchor to maintain\n- **Greppable** — searching for the dotted key finds every reference to that symbol across all docs\n\n**Rules:**\n\n- The label (inside the first `[ ]`) is the rendered text — inline code or plain text\n- The key (inside the second `[ ]`) is the fully-qualified dotted path; do NOT include `()` for methods\n- Unresolved keys render as broken reference-style links (silent fallback) — verify with a build or `yarn crocodocs:generate`\n\n### Markdown links\n\nFallback for cases xrefs cannot cover:\n\n- docs-only Python strings — the `docs_reason` parameter of `@deprecated`, extracted validation messages, or short admonition text\n- links to non-API content (other doc pages, external URLs, anchors that aren't API symbols)\n- when the xref entry is missing and you need a working link before regenerating\n\nUse relative `.md` paths with dot-format anchors.\n\nExamples:\n\n```markdown\nControl: [`Page`](../controls/page.md)\nType: [`DragTargetEvent.global_position`](../types/dragtargetevent.md#flet.DragTargetEvent.global_position)\nPlain text: [route](../controls/page.md#flet.Page.route)\nMethod: [`Page.update()`](../controls/page.md#flet.Page.update)\n```\n\n## Admonitions in docstrings\n\nGoogle-style section headers render as Docusaurus admonitions:\n\n```python\n\"\"\"\nNote:\n    Has effect only if the direct parent is a :class:`~flet.Column`.\n\nWarning:\n    This property is deprecated. Use :attr:`new_prop` instead.\n\nExample:\n    Setting up a basic layout:\n    ``ft.Column(controls=[ft.Text(\"Hello\")])``\n\"\"\"\n```\n\nSupported kinds: `Note`, `Warning`, `Danger`, `Tip`, `Info`.\nUnsupported kinds (e.g. `Limitation`, `Example`) are normalized to `note`.\nEmpty admonitions are skipped.\n\n## Admonitions\n\n```markdown\n:::note\nBasic note without title.\n:::\n\n:::warning[Important]\nWarning with a custom title.\n:::\n```\n\nSupported types: `note`, `info`, `tip`, `warning`, `danger`.\n\n## Front matter\n\n```yaml\n---\nclass_name: \"flet.Container\"\nexamples: \"controls/container\"\nexample_images: \"test-images/examples/material/golden/macos/container\"\nexample_media: \"examples/controls/container/media\"\ntitle: \"Container\"\n---\n```\n\n- `examples` — root-relative path under `sdk/python/examples/`\n- `example_images` / `example_media` — root-relative under `website/static/docs/`\n\n## Images\n\nUse the CrocoDocs `Image` component. Paths without `../` are resolved against `/docs/`:\n\n```jsx\nimport {Image} from '@site/src/components/crocodocs';\n\n<Image src={frontMatter.example_images + '/image_for_docs.png'} width=\"55%\" />\n```\n\nFor absolute paths (one-off assets in `static/`):\n\n```jsx\n<Image src=\"/docs/assets/controls/charts/bar-chart-diagram.svg\" width=\"65%\" />\n```\n\n## Code examples\n\n```jsx\nimport {CodeExample} from '@site/src/components/crocodocs';\n\n<CodeExample path={frontMatter.examples + '/example_1.py'} />\n```\n\nPaths are relative to the configured `examples_root` (`sdk/python/examples/`).\n\n## Inline HTML\n\nUse `<kbd>...</kbd>` in Python docstrings for keyboard keys, for example\n`<kbd>Enter</kbd>` or `<kbd>Shift</kbd>`. CrocoDocs preserves this tag in API\ndocs.\n\n## Sidebar Navigation\n\nEdit `website/sidebars.yml` to change navigation structure:\n\n```yaml\ndocs:\n  Getting started:\n  - getting-started/installation.md\n  Controls:\n    _generated_index:\n      title: Controls\n      slug: /controls\n      description: Browse the complete catalog of controls.\n    AlertDialog: controls/alertdialog.md\n```\n\nAfter editing, regenerate `sidebars.js`:\n\n```bash\ncd website && yarn crocodocs:generate\n```\n\n<!-- File: .agents/skills/fix-members-short-description/SKILL.md (Tokens: ~344 | Category: anthropic-skill) -->\n---\nname: fix-members-short-description\ndescription: Use when asked to fix short descriptions of Python type members.\n---\n\n## Inputs\n\n* File or directory with Python modules.\n\n## Instructions\n\nWhen Flet documentation is generated from docstrings the first sentence of a member docstring is used as a short description, for example:\n\n```py\n@dataclass\nclass MyControl:\n    property_a: str\n    \"\"\"\n    Short description of a property.\n\n    Full description.\n    Another line of full description.\n    \"\"\"\n```\n\nHere \"Short description of a property.\" will be used as a short description.\n\nHowever, when a sentence is broken into multiple lines the lines must be \"concatenated\" with `\\`, for example:\n\n```py\n@dataclass\nclass MyControl:\n    property_a: str\n    \"\"\"\n    Short description of a property which could \\\n    take multiple lines.\n\n    Full description.\n    Another line of full description.\n    \"\"\"\n```\n\nYour goal is to go through all members (properties, methods, etc.) of all types (classes, enums) in input file or directory and ensure the first sentence in their docstrings is broken into multiple lines correctly with `\\` symbol.\n\nApply the fix regardless of whether the first sentence starts on the same line as the opening `\"\"\"` or on a following line.\n\nEnsure every docstring line is at most 88 characters long (including any trailing `\\`). If a line cannot be wrapped without breaking a single unbreakable token (e.g., a long URL or Windows registry path like `HKEY_LOCAL_MACHINE\\\\...`), add `# noqa: E501` to the docstring closing `\"\"\"` line instead of the long line.\n\n<!-- File: .agents/skills/flet-deprecation/SKILL.md (Tokens: ~2041 | Category: anthropic-skill) -->\n---\nname: flet-deprecation\ndescription: Use when adding or changing deprecations for Python controls/APIs in sdk/python/packages/, including V.deprecated fields, deprecated decorators, version lifecycle, and docs admonitions/labels.\n---\n\n## When To Use\n\nUse this skill when you:\n- deprecate a control/dataclass field with `Annotated[..., V.deprecated(...)]`,\n- deprecate a function/method/class with `flet.utils.deprecated` helpers,\n- update deprecation wording, versions, or removal timelines,\n- verify docs rendering for deprecations (admonition + `deprecated` label).\n\nDo not use this skill for non-deprecation validation logic; use\n[`flet-validation`](../flet-validation/SKILL.md).\n\n## Source Of Truth\n\n- Runtime decorators and warning helpers: `sdk/python/packages/flet/src/flet/utils/deprecated.py`\n- Field-level deprecation rule: `sdk/python/packages/flet/src/flet/utils/validation.py` (`V.deprecated`)\n- Docs extraction/labeling extension: `sdk/python/packages/flet/src/flet/utils/griffe_deprecations.py`\n\n## Deprecation Decision Order\n\nUse this order and stop at the first option that fits:\n1. Property/field deprecation: `Annotated[..., V.deprecated(...)]`.\n2. Function/method deprecation: `@deprecated(...)`.\n3. Class/control deprecation: `@deprecated_class(...)`.\n\nDo not add parallel custom warning logic in `before_update()` when `V.deprecated`\nalready covers the field.\n\n## Runtime Contract For Property Renames\n\nFollow the non-copying model:\n- Python sends both properties when both are set.\n- Dart prefers the new property and uses old property as fallback.\n- Python does not copy/synchronize old/new values in `before_update()`.\n\nRemoval phase:\n- At `delete_version` cleanup, remove old Python property/deprecation and remove\n  Dart fallback in the same migration.\n\n## Removal Version Policy\n\n- Default policy: remove deprecated APIs after 3 minor releases.\n- Example: deprecated in `0.82.0` -> remove in `0.85.0`.\n- Use that policy to set `delete_version` unless there is an approved exception.\n\n## Target Release Audit\n\nWhen working on a release for `{new_version}`, treat deprecations with\n`delete_version == {new_version}` as mandatory audit items.\n\n- Scan Python packages for `@deprecated(...)`, `@deprecated_class(...)`,\n  and `V.deprecated(...)` entries whose `delete_version` equals `{new_version}`.\n- Recommended check command:\n  `rg -n 'delete_version\\\\s*=\\\\s*\"{new_version}\"|delete_version\\\\s*=\\\\s*\\\\x27{new_version}\\\\x27' -S sdk/python/packages`\n- Treat every match as release-relevant work, not informational output.\n- If matches are found, summarize the findings first and ask the human for approval\n  before editing files or making removals.\n- For each match, decide whether the deprecated API must be removed now,\n  whether a prior removal was missed, or whether the deprecation timeline is incorrect.\n- If removal is due, make the code, docs, and changelog updates in the same change.\n- After the cleanup edits are ready, summarize the resulting diff and ask the human\n  for approval before creating a commit.\n- Once commit approval is received, batch all confirmed `{new_version}` cleanup\n  edits into one grouped commit instead of splitting them across multiple commits.\n  Use commit message format: `release: remove deprecated APIs for {new_version}`\n- Do not consider the release prep complete while unresolved `{new_version}` removals remain.\n\n## Authoring Rules\n\n1. Always set `version`.\n2. Set `delete_version` using the 3-minor policy by default.\n3. Keep `reason` plain text for runtime warnings.\n4. Use `docs_reason` for docs-only markdown text.\n5. When a replacement exists, name that replacement API explicitly in `reason` and `docs_reason`.\n\n### Field Pattern\n\n```python\nfrom typing import Annotated, Optional\nfrom flet.utils.validation import V\n\nclass ExampleControl:\n    old_prop: Annotated[\n        Optional[str],\n        V.deprecated(\n            \"new_prop\",\n            version=\"0.17.0\",\n            delete_version=\"0.20.0\",\n            reason=\"Use new_prop instead.\",\n            docs_reason=\"Use :attr:`new_prop` or [`new_prop`](../controls/examplecontrol.md#flet.ExampleControl.new_prop) instead.\",\n        ),\n    ] = None\n```\n\n### Function/Method Pattern\n\n```python\nfrom flet.utils.deprecated import deprecated\n\nclass ExampleControl:\n    @deprecated(\n        reason=\"Use new_func instead.\",\n        docs_reason=\"Use :meth:`new_func` or [`new_func()`](../controls/examplecontrol.md#flet.ExampleControl.new_func) instead.\",\n        version=\"0.17.0\",\n        delete_version=\"0.20.0\",\n    )\n    def old_func(self):\n        ...\n```\n\n### Class/Control Pattern\n\n```python\nfrom flet.utils.deprecated import deprecated_class\n\n@deprecated_class(\n    reason=\"Use NewControl instead.\",\n    docs_reason=\"Use :class:`~flet.NewControl` or [`NewControl`](../controls/newcontrol.md)  instead.\",\n    version=\"0.17.0\",\n    delete_version=\"0.20.0\",\n)\nclass OldControl:\n    ...\n```\n\n### Deprecated Property Pattern\n\n```python\nfrom flet.utils.deprecated import deprecated\n\nclass ExampleControl:\n    @property\n    @deprecated(\n        reason=\"Use new_value instead.\",\n        docs_reason=\"Use :attr:`new_value` or [`new_value`](../controls/examplecontrol.md#flet.ExampleControl.new_value) instead.\",\n        version=\"0.17.0\",\n        delete_version=\"0.20.0\",\n    )\n    def value(self):\n        ...\n```\n\n## `reason` vs `docs_reason`\n\n- Runtime warnings always use `reason`.\n- Docs admonitions prefer `docs_reason`; fallback is `reason`.\n- Keep markdown/cross-refs out of `reason` to avoid noisy runtime output.\n\n### Cross-reference Rule Inside `docs_reason`\n\nIn `docs_reason`, use reST roles for simple references when the auto-derived label is\nsufficient, and use Markdown links when you need more control over the displayed text.\n\nSee [`docs-conventions`](../docs-conventions/SKILL.md) for details on supported cross-ref patterns and their syntax.\n\n## Docs Behavior Expectations\n\nFor supported patterns, docs should auto-render:\n- a `Deprecated` admonition section,\n- a `deprecated` label/badge on the item.\n\nDo not duplicate with manual deprecation admonitions in docstrings unless there\nis a special case not covered by the extension.\n\n## Release Docs Updates\n\nWhen adding a user-visible deprecation, also update the release docs in the\nsame change. These pages are the canonical upgrade path, not a separate\n`Deprecations` page.\n\n1. Create or update a migration guide under\n   `website/docs/updates/breaking-changes/vX-Y-Z/`.\n   - Group closely related deprecations into one page, especially APIs from the\n     same class/control or the same PR. For example, `DragTargetEvent.x`,\n     `DragTargetEvent.y`, and `DragTargetEvent.offset` belong in one\n     coordinate-fields guide.\n   - Use this page shape: title, `:::note` accuracy callout,\n     `Summary`, `Context`, `Migration guide`, `Timeline`, and `References`.\n   - Keep one-off replacements in prose. Use a table only when the page maps\n     many removed/deprecated APIs to replacements.\n   - In `References`, link relevant API docs, relevant GitHub issue/PR links,\n     and release notes entry for that release.\n2. Add the guide to\n   `website/docs/updates/breaking-changes/index.md` under the release's\n   `Deprecations` subsection.\n3. Add the guide to `website/sidebars.yml` under:\n   `Stay up to date` -> `Breaking changes and deprecations` -> `vX.Y.Z`.\n   This keeps individual guide pages in the docs sidebar while grouping them by\n   release.\n4. Update `website/docs/updates/release-notes.md` so the release links to the\n   combined `Breaking changes and deprecations` section.\n5. Run `cd website && yarn crocodocs:generate` after sidebar\n   edits, then run `cd website && yarn build`.\n\n## Testing Guidance\n\nDo not add one-off tests for every API that gets deprecated when it uses an\nexisting, already-tested pattern (`V.deprecated`, `@deprecated`, or\n`@deprecated_class`). For routine deprecation metadata updates, rely on the\nshared helper and docs extraction tests.\n\nAdd or update tests only when the change affects deprecation infrastructure or\nintroduces meaningful new behavior, for example:\n- changing runtime warning formatting or stacklevel behavior,\n- changing docs extraction/labeling behavior,\n- adding a new deprecation pattern,\n- adding custom compatibility behavior outside the standard helper,\n- fixing a regression where an existing test would not have failed.\n\nPrefer these locations for infrastructure tests:\n- `sdk/python/packages/flet/tests/test_deprecated.py`\n- `sdk/python/packages/flet/tests/test_griffe_deprecations.py`\n- `sdk/python/packages/flet/tests/test_validation.py` (for `V.deprecated`)\n\n## Common Pitfalls\n\n- Putting markdown/cross-refs into runtime `reason`.\n- Forgetting `delete_version` when a removal target is already known.\n- Adding old/new value-copy logic in Python for rename migrations.\n- Duplicating deprecation warnings in multiple lifecycle hooks manually.\n- Broken cross-refs targets in `docs_reason`.\n\n<!-- File: .agents/skills/flet-validation/SKILL.md (Tokens: ~1758 | Category: anthropic-skill) -->\n---\nname: flet-validation\ndescription: Use whenever editing validation for Python controls in sdk/python/packages/: adding/changing constrained properties, `Raises: ValueError` docstrings, `before_update()` checks, `raise ValueError`, Annotated/V rules, or __validation_rules__.\n---\n\n## When To Use\n\nUse this skill when you:\n- add validation to a control property,\n- migrate manual `before_update()` checks to `V` rules,\n- update `Raises` sections tied to validation,\n- align Python validation with Dart-side control behavior.\n\nDo not use this skill for unrelated doc-only edits outside control validation.\nDo not use this skill for deprecation authoring conventions; use\n[`flet-deprecation`](../flet-deprecation/SKILL.md).\n\n## Source Of Truth\n\n- Validation runtime API lives in:\n  `sdk/python/packages/flet/src/flet/utils/validation.py`\n- The same runtime can validate regular dataclass models via `validate(instance)`;\n  this skill focuses on the control-specific authoring conventions.\n- Import from public path only:\n  `from flet.utils.validation import V`\n  and when needed\n  `from flet.utils.validation import ValidationRules`\n\n## Validation Decision Order\n\nUse this order and stop at the first option that keeps logic clear:\n1. `Annotated[..., V.*]` field rules (default).\n2. `__validation_rules__: ValidationRules` for cross-field invariants that do\n   not map cleanly to one field.\n3. `before_update()` only for normalization/mutation, or for truly non-ruleable\n   invariants.\n\nNever duplicate the same invariant in more than one layer.\n\n## Validation Authoring Rules\n\n1. Prefer field-level validation with `Annotated[...]` metadata.\n   - Example (close to current slider controls):\n     ```\n     @dataclass\n     class Sample:\n         opacity: Annotated[\n                Optional[Number],\n                V.between(0.0, 1.0),\n            ] = None\n\n         value: Annotated[\n             Optional[Number],\n             V.ge_field(\"min\"),\n             V.le_field(\"max\"),\n         ] = None\n\n         min: Annotated[\n             Number,\n             V.le_field(\"max\"),\n             V.le_field(\"value\"),\n         ] = 0.0\n\n         max: Annotated[\n             Number,\n             V.ge_field(\"min\"),\n             V.ge_field(\"value\"),\n         ] = 1.0\n     ```\n\n2. Use class-level `__validation_rules__` only for invariants that cannot be\n   expressed cleanly with field rules.\n   - Type:\n     `__validation_rules__: ValidationRules = (...)`\n   - Use `V.ensure(...)` with an explicit message only when the predicate is\n     short and readable.\n   - If `V.ensure(lambda ...)` becomes hard to read, prefer either:\n     1. a named predicate function passed to `V.ensure(...)`, or\n     2. a clear `before_update()` check when it cannot be represented well with\n        existing `V.*` rules.\n\n3. Keep the `before_update()` override for normalization/mutation first.\n   - Remove validation checks duplicated by `V` rules.\n   - Prefer raising validation errors from rule evaluation (`validate()`), not\n     from ad-hoc `before_update()` checks, unless the invariant is genuinely\n     non-ruleable with current validation primitives.\n\n4. Cross-field comparisons use field rules only.\n   - Use: `V.gt_field`, `V.ge_field`, `V.lt_field`, `V.le_field`\n\n5. `None` handling is inferred from type hints.\n   - If a field is annotated as optional (for example `Optional[T]`), `None` is allowed.\n   - If a field is not optional, `None` fails validation.\n   - For `*_field` comparisons, if either side is optional and currently `None`, the\n     comparison is skipped; if a non-optional side is `None`, validation fails.\n\n6. Match Dart effective behavior.\n   - Review both:\n     1. Flet Dart wrapper (`packages/flet/lib/src/controls/<control>.dart` or\n        extension wrapper),\n     2. wrapped Flutter widget source assertions/invariants.\n   - Mirror those constraints in Python so invalid payloads fail before crossing\n     to Dart.\n   - Validate against effective defaults applied on Dart side (for example\n     `min`/`max`).\n   - Include wrapper-imposed constraints when relevant (for example\n     bounds/rounding/division logic in wrapper formatting code).\n\n7. For new properties, validate against base widget assertions before wiring.\n   - When adding a Python property to a Flet control, confirm whether the mapped\n     Dart wrapper and underlying widget both enforce constraints for that property.\n   - Add equivalent Python-side validation (`Annotated[...]`, `__validation_rules__`,\n     or readable `before_update()`) to prevent Dart assertions from being the first\n     failure point.\n\n8. Keep error ownership clear.\n   - Runtime outbound value failures should raise `ValueError`.\n   - Validation declaration/build errors (invalid `V.*` arguments) should raise\n     `ValidationDeclarationError`.\n\n## Typing Style\n\n- Follow the codebase typing style:\n  - prefer `Optional[T]` over `T | None`,\n  - use `Union[...]` when needed.\n\n## Property Docstring Style\n\nWhen a property has validation, document it in that property’s docstring (google style).\n\n1. Add a `Raises:` block under the property docstring.\n\n2. Use one `ValueError` entry per logical rule, except `between(...)`.\n   - For `V.between(a, b)`, use one entry:\n     `ValueError: If it is not between \\`a\\` and \\`b\\`, inclusive.`\n\n3. Start each entry with `If it ...`, where 'it' refers to the property name.\n\n4. Use canonical wording from validation helper docstrings.\n   - The source of truth is\n     `sdk/python/packages/flet/src/flet/utils/validation.py`.\n   - Each `V.*` helper includes `Property docstring Raises wording`.\n   - Keep property `Raises` entries as negations of the annotation rule.\n   - For strict inequalities, say `\"strictly\"`.\n     For example: `V.gt(x)` -> `ValueError: If it is not strictly greater than \\`x\\`.`\n   - For sign-neutral divisibility helpers (`factor_of`, `multiple_of`), add\n     explicit sign rules (`V.gt(0)` or `V.lt(0)`) when direction matters, and\n     include separate `Raises` entries for those sign rules.\n\n5. Mention conditional applicability when needed.\n   - Example (for `min`/`max` checks against optional `value`):\n     ```\n     Raises:\n         ValueError: If it is not less than or equal to [`value`][(c).],\n             when [`value`][(c).] is set.\n     ```\n\n6. Keep examples and wording aligned with real control files.\n   - Prefer concrete property names such as `min`, `max`, `value`,\n     `start_value`, `end_value`, `min_lines`, `max_lines`.\n   - For cross-field rules, use same-class links: [`min`][(c).], [`max`][(c).].\n\n## Cross-Referencing Conventions\n\nFollow the cross-reference guidance in:\n[`docs-conventions`](../docs-conventions/SKILL.md).\n\nMost common pattern to use in control property docstrings:\n- same-class properties: `[\\`prop\\`][(c).]`\n\nKeep symbol labels wrapped in backticks.\n\n## Required Test Matrix\n\nWhen adding/changing validation, include tests that cover:\n- one valid case and one invalid case per new logical rule;\n- boundary values (`==`, min/max edges) where applicable;\n- cross-field set/unset combinations when optional values are involved;\n- effective-default behavior when Dart applies defaults but Python value is\n  omitted.\n\nPrefer placing tests in:\n- `sdk/python/packages/flet/tests/test_validation.py` for validation runtime;\n- control-specific tests when behavior is tied to one control.\n\n## Common Pitfalls\n\n- Keeping stale manual `before_update()` validations after migration.\n- Missing `Raises` entries on validated properties.\n- Combining multiple non-between rules into one ambiguous `ValueError` sentence.\n- Forgetting Dart defaults that still apply when Python property is omitted.\n- Forcing complex `V.ensure(lambda ...)` expressions when `before_update()` would be cleaner.\n\n<!-- File: .agents/skills/imperative-to-declarative-flet/SKILL.md (Tokens: ~850 | Category: anthropic-skill) -->\n---\nname: imperative-to-declarative-flet\ndescription: Convert an imperative Flet Python app in which controls are mutated and then page.update is called to declarative style using flet.component, flet.observable and state hooks.\nmetadata:\n  short-description: Port Flet app to declarative\n---\n\n# Imperative → Declarative (Flet Python)\n\nPort an existing imperative Flet app to “components mode” with `@ft.component`, hooks, and (optionally) `@ft.observable` models.\n\n## Outcomes\n\n- Original folder unchanged; new sibling folder created.\n- Entry point uses `page.render(App)` (components mode).\n- UI is derived from state; minimal/zero manual `page.update()` for normal UI updates.\n\n## Choose a state strategy\n\n- **Use `@ft.observable`** for nested app data you mutate in place (boards/lists/cards, drag+drop reorder).\n- **Use `ft.use_state`** for local ephemeral UI state (hover flags, input text, dialog selection).\n- Avoid storing live `Control`/component objects in state; store ids/enums and create controls during render.\n\n## Workflow\n\n### 1) Create a new declarative copy\n\n- Copy the existing app folder to a new one (e.g. `trolli` → `trolli-declarative-*`).\n- Keep `assets/` with the new folder.\n\n### 2) Switch to components mode entrypoint\n\n- Create a root component `@ft.component def App(): ...`.\n- Run with:\n  - `ft.run(lambda page: page.render(App), assets_dir=...)`\n- Set page globals either:\n  - in a `main(page)` function before `page.render(App)`, or\n  - in `ft.on_mounted(...)` (works, but ordering can be less obvious).\n\n### 3) Centralize routing in `App`\n\n- Keep `app.route: str` as source of truth.\n- In one place, define:\n  - `route_change(e)` to normalize/redirect/validate routes and set `app.route`\n  - a render-time `match app.route` (or a derived `active_screen`) to pick `content`\n- Prefer: `route_change` mutates route state; `App()` render chooses UI based on that state.\n\n### 4) Componentize UI\n\n- Move UI chunks into `src/components/*.py`.\n- Each component:\n  - takes only the model(s) it needs\n  - uses hooks for local UI state\n  - mutates observable models for app data changes\n\n### 5) Dialogs: reduce `page.update()` usage\n\nIf a dialog mutates existing controls and calls `page.update()`, convert it to:\n\n- `@ft.component` dialog content with `ft.use_state` for `error`, `selected_color`, etc.\n- event handlers call setters (no explicit updates)\n- show it via `page.show_dialog(ft.AlertDialog(content=DialogContent(...)))`\n\n### 6) Assets/fonts checklist\n\n- Prefer an absolute `assets_dir` derived from `__file__`.\n- If running via `flet run`, be aware it can set `FLET_ASSETS_DIR` and override `assets_dir=`.\n- Font registration uses the dict key as the font family name:\n  - `page.fonts = {\"Pacifico\": \"Pacifico-Regular.ttf\"}`\n  - use `font_family=\"Pacifico\"`.\n\n## Common pitfalls (and fixes)\n\n- **Event handler typing is invariant** (`Event[Sub]` ≠ `Event[Base]`):\n  - If `on_click` is declared on `Button`, annotate `e` as `ft.Event[ft.Button]` (or use `def handler(): ...`).\n- **`TemplateRoute` params are dynamic**:\n  - `raw = getattr(troute, \"id\", None)` then `isinstance(raw, str)` before `int(raw)`.\n- **`controls=[*[...], ...]` can confuse type checkers** with components:\n  - build lists in two steps and annotate/cast, or return raw controls from non-component factories.\n\n<!-- File: .agents/skills/implement-flet-extension/SKILL.md (Tokens: ~1837 | Category: anthropic-skill) -->\n---\nname: implement-flet-extension\ndescription: Implement a new Flet extension/control that wraps a third-party Flutter package end-to-end, including dependency selection, version pinning, compatibility checks, Python/Flutter integration, docs, examples, tests, and CI updates. Use when adding any flet_* package backed by an external pub.dev package.\n---\n\nImplement a Flet extension around an external Flutter package using existing `flet_*` packages as implementation templates.\n\n## Inputs\n\n- Control/service name and Python package name (`flet_<extension>`).\n- Target pub.dev package and intended version/range.\n- API surface to expose in Python (properties, methods, events, types/enums).\n\n## Third-party Dependency Gate\n\n1. Confirm package health: maintenance activity, null-safety, platform support, and open issue risk.\n2. Confirm license is compatible with Flet distribution.\n3. Select a conservative version strategy:\n- Pin exact version when behavior stability is critical.\n- Use bounded ranges when required by ecosystem constraints.\n4. Record key constraints and reasons in PR notes/commit message.\n\n## Control/Service Classification\n\n- Classify wrapped functionality before implementation:\n1. `LayoutControl` for visual controls that participate in page/layout positioning.\n2. Base `Control` for simple visual controls that do not require page positioning or define their own positioning rules/props (for example `Draggable`, `Divider`, `MenuBar`, `NavigationRail`).\n3. Non-visual Service when functionality is not a renderable UI control.\n- Inspect the wrapped Flutter package API to determine whether it includes non-visual/service functionality.\n- For service patterns, follow existing extension examples: `sdk/python/packages/flet-audio`, `sdk/python/packages/flet-flashlight`, `sdk/python/packages/flet-secure-storage`.\n\n## API Mapping Rules\n\n- Expose only stable and useful features first; avoid mirroring every upstream option.\n- Keep Python API idiomatic and concise; avoid redundant control-name prefixes.\n- Map upstream naming inconsistencies to Flet conventions when needed.\n- Add custom enums/types only when they improve correctness and discoverability.\n\n## Python-side Rules\n\n- Use `LayoutControl`, base `Control`, or Service base class according to classification.\n- Implement typed properties, methods, and events exactly for chosen public API.\n- Reuse existing serialization/event patterns from sibling controls/services.\n\n## Flutter-side Rules\n\n- Use `parseEnum()` for enums — it's exported from `package:flet/flet.dart`. Call it as `parseEnum(MyEnum.values, widget.control.getString(\"attr\"), MyEnum.defaultVal)!`. Do NOT write a custom `_parseXxx()` switch helper.\n- For control attributes, prefer `widget.control.getBool()/getDouble()/...` accessors.\n- For non-control parsing, use shared `parseSomething()` helpers.\n- Do not add one-off private parser utilities when standard helpers exist.\n- Put control-specific helpers in `utils/<control>.dart`; shared helpers in `utils/<topic>.dart`.\n- Prefer `parse`-prefixed helper names when converting input to Flutter structures.\n- Avoid single-use local variables.\n\n### Default Value Matching (Critical)\n\nProperties with default values on the Python side are **not sent to Flutter** when unchanged from the default. Every Dart property read **must provide the same default** as its Python counterpart:\n\n- `control.getDouble(\"size\", 100.0)!` when Python has `size: float = 100.0`\n- `control.getBool(\"animate\", true)!` when Python has `animate: bool = True`\n- `parseDuration(value[\"dur\"], const Duration(milliseconds: 500))!` when Python has `dur: DurationValue = field(default_factory=lambda: Duration(milliseconds=500))`\n- `control.get<List>(\"items\")?.map(...).toList() ?? const []` when Python has `items: list[str] = field(default_factory=list)`\n\nWithout matching defaults, Dart receives `null` and either crashes or silently uses the wrong value. This applies to all property types: bools, numbers, strings, enums, durations, collections, and nested `@ft.value` types.\n\n## Integration Checklist\n\n- Register in the Flet client app — two files:\n  1. `client/pubspec.yaml`: add `flet_<ext>: path: ../sdk/python/packages/flet-<ext>/src/flutter/flet_<ext>` under `dependencies`.\n  2. `client/lib/main.dart`: add `import 'package:flet_<ext>/flet_<ext>.dart' as flet_<ext>;` and `flet_<ext>.Extension()` to the `extensions` list.\n- Add extension package to `sdk/python/pyproject.toml` in **two places**: the `dependencies` list and `[tool.uv.sources]` as `{ workspace = true }`.\n- Add extension to `sdk/python/packages/flet/pyproject.toml` in the `[dependency-groups] extensions` list.\n- Add extension to `sdk/python/examples/apps/flet_build_test/pyproject.toml` in **three places**: `[project] dependencies`, `[tool.uv.sources]` as `{ path = \"...\", editable = true }`, and `[tool.flet.dev_packages]` as a relative path string.\n- Add extension to `tools/crocodocs/pyproject.toml` under `[tool.crocodocs.packages]` as `<pkg_name> = \"../../sdk/python/packages/<pkg-dir>/src\"`. This fixes \"Missing API entry\" errors in the docs. Note: `api-data.json` is gitignored (generated at build time); only the `pyproject.toml` change needs committing.\n- Add extension to `.github/workflows/ci.yml` in both places:\n  - `build_flet_extensions` -> `PACKAGES` list.\n  - `py_publish` -> `for pkg in ...` publish loop.\n- Add `.gitignore` to Flutter extension project if missing.\n- Remove `[tool.uv.sources]` local path overrides from example `pyproject.toml` files before opening a PR (they are development-only conveniences).\n\n## Docs, Examples, Tests\n\n- Add control/service docs under `website/docs/controls/<name>` for controls and `website/docs/services/<name>` for services.\n- Always create one doc page per control, even for extensions with many similar controls. Use `index.md` for the overview (install instructions, examples, list of links) and individual `<controlname>.md` files for each control — consistent with `flet-color-pickers` and other extensions.\n- Use `<ClassSummary name=\"pkg.ClassName\" />` and `<ClassMembers name=\"pkg.ClassName\" />` JSX from `@site/src/components/crocodocs` to render API docs. Do NOT add `image=`, `imageCaption=`, or `imageWidth=` props to `<ClassSummary>` when no screenshots exist yet.\n- In the `## Examples` section, do NOT add `###` subtitles above `<CodeExample>` blocks — titles are injected automatically from the example file itself.\n- Add all custom enums/types docs and update `website/sidebars.yml` navigation.\n- Use markdown filenames without underscores (`codeeditor.md`, not `code_editor.md`).\n- Add examples under `sdk/python/examples/extensions/<name>/` for extension controls.\n- Use `import flet_<ext> as <short_alias>` in examples (e.g., `import flet_spinkit as spins`). Keep alias short but readable.\n- Use `ft.Colors.SURFACE_CONTAINER_HIGHEST` for card/cell backgrounds in showcase examples — it adapts to light and dark system themes automatically.\n- Do NOT set an explicit dark theme in examples; let the app use system theme (no `page.theme_mode`).\n- Add integration tests under `packages/flet/integration_tests/extensions/<name>/` — **not** inside the extension package's own directory (no `tests/` folder in the package itself, matching the pattern of `flet-code-editor`, `flet-color-pickers`, etc.).\n- For controls with continuously-running animations, do NOT use `assert_control_screenshot` or `pump_and_settle` — they will timeout waiting for animations to settle. Instead use `await flet_app.tester.pump(duration=ft.Duration(milliseconds=500))` which advances the clock by a fixed amount. This still runs real Flutter rendering and catches crashes, without screenshot comparison.\n- Ensure generated screenshots are suitable for docs usage when visual examples are added.\n\n## Upgrade and Compatibility Guardrails\n\n- Add at least one test that catches upstream behavioral changes likely to break wrapper mapping.\n- Avoid exposing experimental upstream APIs unless explicitly requested.\n- Keep wrapper surface narrow enough to maintain backwards compatibility across upstream updates.\n\n## Validation\n\n- Run relevant Python and integration tests for touched areas.\n- Verify Python import paths, client runtime registration, and docs navigation.\n- Verify dependency resolution and lockfile updates are intentional.\n\n<!-- File: .agents/skills/prepare-flet-release/SKILL.md (Tokens: ~866 | Category: anthropic-skill) -->\n---\nname: prepare-flet-release\ndescription: Use when asked to prepare new Flet release by bumping versions and author release notes.\n---\n\n## Inputs\n\n* Previous Flet version from repo tags.\n* Whether it's minor or major release.\n\n## Related Skills\n\nAlways use [`flet-deprecation`](../flet-deprecation/SKILL.md) during release prep\nto audit deprecations for the target version. Also use it when release prep includes:\n- adding new deprecations in this release,\n- removing APIs whose `delete_version` equals this release version,\n- auditing changelog entries that mention deprecations/removals.\n\nUse [`write-changelog-entry`](../write-changelog-entry/SKILL.md) for drafting or refining individual changelog items.\nThat skill is the source of truth for item wording, scope selection, and what should or should not be mentioned in a single entry.\n\n## Steps\n\n* Take latest Flet release version from the repo and\n  increment third (patch) digit to get the next version if it's a minor release\n  or second (minor) digit if it's a major release.\n* Pull the latest `main` and create a new branch named `prepare-release-{new_version}` from `main`.\n* Set new version in packages/flet/pubspec.yaml.\n* Run pub get in /client dir to refresh pubspec.lock with new version.\n* Add new entries into `packages/flet/CHANGELOG.md` and `/CHANGELOG.md` from the git log since the last release.\n  * Use [`write-changelog-entry`](../write-changelog-entry/SKILL.md) for every individual item.\n  * Build the candidate set from relevant commits, PRs, and issues since the last release.\n  * Ensure that all inferred PRs and issues in the changelog have the `{version}` milestone attached on GitHub.\n  * If a related issue or PR is missing the `{version}` milestone, update the milestone on GitHub and keep the link in the changelog.\n  * When selecting candidates for `packages/flet/CHANGELOG.md`, prefer items with meaningful Flutter-side impact.\n  * When selecting candidates for `sdk/python/packages/*/CHANGELOG.md`, prefer published Python-facing changes; do not include extension-internal Flutter implementation work unless it materially changes user-visible Python behavior.\n* If the release includes breaking changes, API removals, or deprecations,\n  update `website/docs/updates/release-notes.md` and\n  `website/docs/updates/breaking-changes/index.md`.\n  * Use [`flet-deprecation`](../flet-deprecation/SKILL.md) for deprecation\n    guide requirements and sidebar placement.\n  * Group related deprecations into one migration guide page where possible,\n    and add guide pages under the release version in `website/sidebars.yml`.\n* Scan all changelogs for `Unreleased` sections, not only the root ones:\n  * `/CHANGELOG.md`\n  * `packages/flet/CHANGELOG.md`\n  * `sdk/python/packages/*/CHANGELOG.md`\n  Recommended check command:\n  `rg -n \"^##\\\\s*\\\\[?Unreleased\\\\]?|^##\\\\s*Unreleased\" -S CHANGELOG.md packages/flet/CHANGELOG.md sdk/python/packages/*/CHANGELOG.md`\n* If any changelog has an `Unreleased` section, convert that section into the new release section (`## {new_version}`), preserving and re-sorting its items. Do not leave duplicate release content in both `Unreleased` and `{new_version}`.\n  This conversion must be done for every matched changelog from the scan above.\n* Sort items in changelogs as follows, omitting empty sections:\n  * New features\n  * Improvements\n  * Breaking changes\n  * Deprecations\n  * Bug fixes\n  * Documentation\n  * Other changes (chore, refactor, etc.)\n  Put removals of previously deprecated APIs under `Breaking changes`, and\n  keep newly deprecated-but-still-working APIs under `Deprecations`.\n* Templates are in `sdk/python/templates/` and automatically packaged as zip artifacts with the GitHub Release. No manual branch creation in external repos is needed.\n\n<!-- File: .agents/skills/run-integration-tests/SKILL.md (Tokens: ~56 | Category: anthropic-skill) -->\n---\nname: run-integration-tests\ndescription: Use when asked to run integration tests.\n---\n\n## Instructions\n\nIntegration tests are in `sdk/python/packages/flet/integration_tests` directory.\n\nRead `sdk/python/packages/flet/integration_tests/README.md` for further instructions.\n\n<!-- File: .agents/skills/run-unit-tests/SKILL.md (Tokens: ~81 | Category: anthropic-skill) -->\n---\nname: run-unit-tests\ndescription: Use when asked to run unit tests.\n---\n\nThis skill is used to run unit tests of the Python part of Flet framework.\n\n## Instructions\n\nRun the following command to run `flet` package unit tests:\n\n```\nuv run --group test pytest packages/flet/tests\n```\n\nThe directory in that commend is relative to `{root}/sdk/python`.\n\n<!-- File: .agents/skills/test-flet-apps-dev/SKILL.md (Tokens: ~300 | Category: anthropic-skill) -->\n# test-flet-apps-dev\n\nPath: `.agents/skills/test-flet-apps-dev/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/test-flet-apps-dev/SKILL.md)\n\n<!-- File: .agents/skills/update-flet-control-doc-gifs/SKILL.md (Tokens: ~300 | Category: anthropic-skill) -->\n# update-flet-control-doc-gifs\n\nPath: `.agents/skills/update-flet-control-doc-gifs/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/update-flet-control-doc-gifs/SKILL.md)\n\n<!-- File: .agents/skills/write-changelog-entry/SKILL.md (Tokens: ~300 | Category: anthropic-skill) -->\n# write-changelog-entry\n\nPath: `.agents/skills/write-changelog-entry/SKILL.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/.agents/skills/write-changelog-entry/SKILL.md)\n\n<!-- File: packages/flet_integration_test/analysis_options.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Flet_integration_test Skill\n\nPath: `packages/flet_integration_test/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet_integration_test/analysis_options.yaml)\n\n<!-- File: packages/flet_integration_test/pubspec.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Flet_integration_test Skill\n\nPath: `packages/flet_integration_test/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet_integration_test/pubspec.yaml)\n\n<!-- File: packages/flet/analysis_options.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Flet Skill\n\nPath: `packages/flet/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/analysis_options.yaml)\n\n<!-- File: packages/flet/CHANGELOG.md (Tokens: ~300 | Category: anthropic-skill) -->\n# Flet Skill\n\nPath: `packages/flet/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/CHANGELOG.md)\n\n<!-- File: packages/flet/pubspec.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Flet Skill\n\nPath: `packages/flet/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/packages/flet/pubspec.yaml)\n\n<!-- File: sdk/python/examples/extensions/lottie/lottie_animations/assets/sample.json (Tokens: ~300 | Category: anthropic-skill) -->\n# Assets Skill\n\nPath: `sdk/python/examples/extensions/lottie/lottie_animations/assets/sample.json`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/examples/extensions/lottie/lottie_animations/assets/sample.json)\n\n<!-- File: sdk/python/packages/flet-ads/CHANGELOG.md (Tokens: ~300 | Category: anthropic-skill) -->\n# Flet-ads Skill\n\nPath: `sdk/python/packages/flet-ads/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/CHANGELOG.md)\n\n<!-- File: sdk/python/packages/flet-ads/src/flutter/flet_ads/analysis_options.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Flet_ads Skill\n\nPath: `sdk/python/packages/flet-ads/src/flutter/flet_ads/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/src/flutter/flet_ads/analysis_options.yaml)\n\n<!-- File: sdk/python/packages/flet-ads/src/flutter/flet_ads/pubspec.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Flet_ads Skill\n\nPath: `sdk/python/packages/flet-ads/src/flutter/flet_ads/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-ads/src/flutter/flet_ads/pubspec.yaml)\n\n<!-- File: sdk/python/packages/flet-audio-recorder/CHANGELOG.md (Tokens: ~300 | Category: anthropic-skill) -->\n# Flet-audio-recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/CHANGELOG.md)\n\n<!-- File: sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/analysis_options.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Flet_audio_recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/analysis_options.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/analysis_options.yaml)\n\n<!-- File: sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/CHANGELOG.md (Tokens: ~300 | Category: anthropic-skill) -->\n# Flet_audio_recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/CHANGELOG.md)\n\n<!-- File: sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/pubspec.yaml (Tokens: ~300 | Category: anthropic-skill) -->\n# Flet_audio_recorder Skill\n\nPath: `sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/pubspec.yaml`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio-recorder/src/flutter/flet_audio_recorder/pubspec.yaml)\n\n<!-- File: sdk/python/packages/flet-audio/CHANGELOG.md (Tokens: ~300 | Category: anthropic-skill) -->\n# Flet-audio Skill\n\nPath: `sdk/python/packages/flet-audio/CHANGELOG.md`\n\n[View Raw Content on GitHub](https://raw.githubusercontent.com/flet-dev/flet/HEAD/sdk/python/packages/flet-audio/CHANGELOG.md)\n\n<!-- ... +80 more modular skills available via /api/skills/flet-dev/flet?path={path} -->\n</yakaai_skills>"}