Skip to content

AlertDialog

AlertDialog is a lookless ContentControl whose own template is the backdrop plus panel, the same shape NaviusDialog uses: the web family’s Root/Trigger/Portal/Backdrop/Popup/Title/Description/ Action/Cancel parts fold into this one control plus a CloseCommand binding. Unlike Dialog it is always modal and never dismissed by an outside press, and it moves initial focus to whichever child is marked as the cancel action rather than the panel’s first focusable descendant, matching the APG guidance that the least-destructive action should receive focus.

xmlns:navius="clr-namespace:Navius.Wpf.Primitives.Controls;assembly=Navius.Wpf.Primitives"
xmlns:overlay="clr-namespace:Navius.Wpf.Primitives.Controls.OverlaySurface;assembly=Navius.Wpf.Primitives"
xmlns:alertDialog="clr-namespace:Navius.Wpf.Primitives.Controls.AlertDialog;assembly=Navius.Wpf.Primitives"
<Grid>
<!-- app content -->
<navius:NaviusButton Content="Delete" Click="OnOpenAlertDialog" />
<!-- one layer per window, stretched over the root -->
<overlay:NaviusOverlayLayer>
<alertDialog:NaviusAlertDialog x:Name="ConfirmDelete"
Title="Delete this item?"
Description="This cannot be undone.">
<StackPanel Orientation="Horizontal">
<navius:NaviusButton Content="Cancel"
alertDialog:NaviusAlertDialog.IsCancelButton="True"
Command="overlay:NaviusOverlaySurfaceBase.CloseCommand" />
<navius:NaviusButton Content="Delete"
Command="overlay:NaviusOverlaySurfaceBase.CloseCommand" />
</StackPanel>
</alertDialog:NaviusAlertDialog>
</overlay:NaviusOverlayLayer>
</Grid>

Like Dialog, an AlertDialog is declared as a direct XAML child of the layer and stays Collapsed until opened; a window with no NaviusOverlayLayer still parses, but opening logs a Trace.TraceWarning and reverts IsOpen to false.

Property Type Default From Description
IsOpen bool false NaviusOverlaySurfaceBase Open state. Two-way bindable by default. A canceled Closing reverts it to true so the DP never desyncs from the live overlay.
Title string? null NaviusOverlaySurfaceBase Accessible name. Applied via AutomationProperties.Name on engage.
Description string? null NaviusOverlaySurfaceBase Accessible help text. Applied via AutomationProperties.HelpText on engage.
IsCancelButton bool false NaviusAlertDialog (attached) Set on the button that plays the Cancel role. AlertDialogFocus.FindCancelElement walks the logical tree for the first enabled element carrying it and gives it initial focus, the WPF analogue of the web’s InitialFocusSelector => "[data-navius-alert-dialog-cancel]" CSS selector.
Content object - ContentControl The dialog body.

There is no Modal or CloseOnOutsideClick property: ModalEffective is hard-coded true and CloseOnOutsideClickEffective is hard-coded false, both non-overridable, matching the web contract’s “AlertDialog is always modal, never outside-dismissed” rule rather than exposing settable properties a consumer could push out of contract.

Method Description
Open() Sets IsOpen to true via SetCurrentValue, preserving an existing two-way binding.
Close() Sets IsOpen to false via SetCurrentValue, preserving an existing two-way binding.
Command Description
NaviusOverlaySurfaceBase.CloseCommand Bind any element inside Content to request a close, mirroring both the web’s NaviusAlertDialogAction and NaviusAlertDialogCancel parts (there is no separate command per action; a consumer’s own click handler runs destructive logic before or alongside it).
Event Signature Fires when
Opened EventHandler The overlay has engaged: pushed onto the OverlayStack, enter animation started.
Closing EventHandler<OverlayClosingEventArgs> A close was requested (Escape, CloseCommand, or IsOpen = false). Cancelable: set Cancel to keep the dialog open.
Closed EventHandler The exit animation completed and the surface left its layer.
Key Behavior
Escape Closes the dialog. Fixed on, not configurable (CloseOnEscapeEffective is not overridden).
Tab / Shift + Tab Cycles focus among the dialog’s focusable descendants, via KeyboardNavigationMode.Cycle applied by the OverlayStack focus trap (always engaged, since AlertDialog is always modal).

A press outside the panel never closes the dialog (CloseOnOutsideClickEffective is hard-coded false, not a DP).

NaviusAlertDialogAutomationPeer (a FrameworkElementAutomationPeer) reports AutomationControlType.Window, overrides IsDialogCore() to return true, and additionally overrides GetLocalizedControlTypeCore() to return "alert dialog", the closest native UIA mapping to the web’s role="alertdialog". On engage, Title/Description are applied as AutomationProperties.Name/HelpText (inherited NaviusOverlaySurfaceBase.Engage() behavior, shared with Dialog and Drawer). Initial focus is resolved by AlertDialogFocus.FindCancelElement, a pure logical-tree search invoked through the overridable ResolveInitialFocusElement() hook immediately after the OverlayStack focus trap’s own default first-focusable-descendant focus, so the cancel-marked element wins regardless of its position in the visual or logical tree. The unit suite (AlertDialogTests.cs) exercises ModalEffective/ CloseOnOutsideClickEffective being hard-coded, the IsCancelButton logical-tree search, and the peer’s control type, localized control type, and dialog flag.

  • Always modal, no Modal property: unlike NaviusDialog/NaviusDrawer, there is no settable DP a consumer could use to make an AlertDialog non-modal, matching the web contract’s hard constraint rather than defaulting a DP to true.
  • No outside dismissal: CloseOnOutsideClickEffective is hard-coded false (also not a DP), matching NaviusAlertDialogPopup.CloseOnOutside => false in the web source.
  • IsCancelButton is an attached property a consumer sets on the button that plays Cancel’s role, replacing the web’s CSS-selector-based InitialFocusSelector; resolution walks the logical tree (matching NaviusRadioGroup/NaviusCheckboxGroup’s own descendant search) rather than requiring a layout pass.
  • The web’s six cancelable callbacks (OnOpenAutoFocus, OnCloseAutoFocus, OnEscapeKeyDown, OnPointerDownOutside, OnFocusOutside, OnInteractOutside) collapse into the single cancelable Closing event shared with Dialog/Drawer, carrying an OverlayCloseReason. Known residual (M6 audit): this only really collapses the five close-related hooks; there is no cancelable hook at all for the open side (OnOpenAutoFocus’s “keep focus where it is when the popup opens” behavior has no WPF equivalent anywhere in the shared OverlaySession/ OverlayOptions substrate). The “six hooks to one” framing therefore overstates what was ported; the fix would touch every family built on NaviusOverlaySurfaceBase/OverlayStack, not just AlertDialog, so it is reported rather than fixed here.
  • Enter and exit transitions are the same fixed 150ms opacity fade as Dialog/Drawer (NaviusOverlaySurfaceBase’s DoubleAnimation); Navius.Wpf.Primitives does not reference Navius.Wpf.Motion.

The AlertDialog Gallery page rendered at the pinned commit, in each theme.

AlertDialog Gallery page in the light theme

AlertDialog Gallery page in the dark theme

AlertDialog Gallery page in the high contrast theme