Files
David Ortinau c4b6819dda Add 7 core .NET MAUI development skills to dotnet-maui plugin (#456)
* Add 7 core .NET MAUI development skills to dotnet-maui plugin

Add maui-shell-navigation, maui-collectionview, maui-data-binding,
maui-dependency-injection, maui-app-lifecycle, maui-safe-area, and
maui-theming skills with eval.yaml tests and reference docs.

Update plugin.json, marketplace.json (both copies), and CODEOWNERS.

Resolves #455

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>

* Fix cross-skill references to non-existent skills

Replace 10 dangling references to skills not in this repo
(maui-deep-linking, maui-platform-invoke, maui-unit-testing,
maui-maps, maui-animations, maui-accessibility, maui-app-icons-splash,
maui-bootstrap-theme, maui-localization) with plain-English guidance
or references to skills that exist in this PR.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>

* Fix code correctness bugs and remaining cross-references

Address PR review feedback and skeptic review findings:

Code correctness:
- Fix BackgroundColor="Primary" (XAML crash) → use {StaticResource Primary}
- Fix MergedDictionaries.Clear() (nukes all styles) → remove-then-add pattern
- Fix HorizontalStackLayout Fill (no effect) → use Grid with ColumnDefinitions
- Fix AncestorType with ViewModel type → use ContentPage (visual element)
- Fix Frame usage → replace with Border (recommended control)
- Remove redundant MultiBinding StringFormat="{}{0}"
- Fix OnStart reference → use CreateWindow for theme restore
- Soften lifecycle OnStart/OnSleep characterization (compat shims, not absent)
- Qualify ResourceDictionary code-behind requirement (only for x:Class)

Cross-references:
- Remove all remaining body-text refs to non-existent skills
- Replace with Microsoft Learn doc links or generic guidance

Eval:
- Relax SafeAreaRegions assertion to accept SafeAreaEdges or SafeAreaRegions
- Relax theming rubric for ResourceDictionary code-behind

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>

* Restore Clear() theme pattern with clarifying comment

The Clear()+Add() pattern is intentional — theme dictionaries are designed
to be the only merged dictionaries in this architecture. Added comment
explaining the assumption and what to do if non-theme dictionaries exist.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>

* Fix second-pass review findings: API accuracy and eval robustness

Code correctness:
- ScrollView SafeAreaEdges="All" → "Container" (ScrollView only honors
  Container and None; All silently fails for keyboard avoidance)
- DI CreateWindow example: add comment noting AppShell must be registered
- AddHttpClient: add comment noting Microsoft.Extensions.Http NuGet required
- MultiBinding: remove redundant StringFormat from reference doc (matches SKILL.md)
- RelativeSource Self table: Path=Width → Path=WidthRequest (Width is
  read-only -1 before layout; WidthRequest is the correct bindable property)
- CollectionView StackLayout warning: clarify it refers to BindableLayout
  on StackLayout vs CollectionView ItemsLayout types
- SafeAreaEdges: fix "attached property" → "property" (it's a regular property)
- ios:NavigationPage example: add xmlns comment for ios namespace

Eval assertions:
- DI Scoped regex: accept "doesn't"/"lacks"/"without" not just "no"
- CollectionView ViewCell: match negation in either direction around ViewCell
- Lifecycle events: require 3+ distinct events instead of any single one

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>

* Fix final PR review comments

- safe-area eval: tighten Container assertion to require SafeAreaEdges context
- DI: merge #else fallback into single compilable #if block
- lifecycle: behaviour → behavior (American English consistency)
- theming: macOS Catalyst minimum 10.14 → 10.15 (Catalina required)

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>

---------

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
2026-04-02 15:48:30 +02:00

92 lines
4.1 KiB
YAML

scenarios:
- name: "Set up Shell navigation with tabs and flyout"
prompt: |
I'm starting a new .NET MAUI app that needs a flyout menu with two sections:
"Dashboard" (single page) and "Products" (with two sub-tabs: "Active" and
"Archived"). I also need a Settings page accessible from the flyout.
Show me how to set up AppShell.xaml with this structure, including route
registration for a ProductDetailsPage that I'll navigate to from the list.
assertions:
- type: "output_contains"
value: "FlyoutItem"
- type: "output_contains"
value: "ContentTemplate"
- type: "output_matches"
pattern: "Routing\\.RegisterRoute"
- type: "output_matches"
pattern: "(?i)ShellContent"
rubric:
- "Uses ContentTemplate with DataTemplate for lazy page creation, not eager Content"
- "Correctly nests ShellContent inside Tab to produce top tabs for Active/Archived"
- "Registers ProductDetailsPage route in AppShell constructor"
- "Sets FlyoutBehavior on Shell element"
timeout: 120
- name: "Navigate with parameters using GoToAsync"
prompt: |
I have a ProductListPage that shows products in a CollectionView. When the
user taps a product, I need to navigate to ProductDetailsPage and pass the
product ID as a string parameter AND sometimes the full Product object.
Show me both approaches and how to receive the data on the target page
using IQueryAttributable on my ViewModel.
assertions:
- type: "output_contains"
value: "GoToAsync"
- type: "output_contains"
value: "IQueryAttributable"
- type: "output_matches"
pattern: "ShellNavigationQueryParameters"
- type: "output_matches"
pattern: "ApplyQueryAttributes"
rubric:
- "Shows query string approach for the string ID parameter"
- "Shows ShellNavigationQueryParameters for passing the full object"
- "Implements IQueryAttributable on the ViewModel, not the page"
- "Always awaits GoToAsync calls"
timeout: 120
- name: "Handle back navigation and unsaved changes guard"
prompt: |
My EditProductPage has a form with unsaved changes. I need to:
1. Show a confirmation dialog when the user tries to navigate back
2. Cancel navigation if they choose to stay
3. Also provide a custom back button that says "Cancel" instead of the
default back arrow.
How do I implement this in .NET MAUI Shell?
assertions:
- type: "output_matches"
pattern: "(?i)OnNavigating|ShellNavigatingEventArgs"
- type: "output_matches"
pattern: "GetDeferral"
- type: "output_contains"
value: "BackButtonBehavior"
- type: "output_matches"
pattern: "(?i)args\\.Cancel|Cancel\\(\\)"
rubric:
- "Uses GetDeferral/Complete pattern for async confirmation dialog"
- "Checks ShellNavigationSource.Pop to detect back navigation"
- "Shows BackButtonBehavior XAML with TextOverride for custom label"
- "Does not use synchronous blocking for the async dialog check"
timeout: 120
- name: "Diagnose common Shell navigation mistakes"
prompt: |
My .NET MAUI Shell app has these problems:
1. GoToAsync("productdetails") throws an exception
2. GoToAsync("//products/active") navigates but nothing visible changes
3. My app takes 3 seconds to start and I have 12 pages in Shell
What's likely wrong in each case and how do I fix them?
assertions:
- type: "output_matches"
pattern: "(?i)RegisterRoute|register.*route"
- type: "output_matches"
pattern: "(?i)hierarchy|absolute.*route|path"
- type: "output_contains"
value: "ContentTemplate"
rubric:
- "Identifies missing Routing.RegisterRoute for the relative route case"
- "Explains that the absolute route path must match the full visual hierarchy"
- "Recommends ContentTemplate with DataTemplate to fix eager page creation at startup"
- "Does not suggest NavigationPage-based solutions for Shell navigation issues"
timeout: 120