lepoco/wpfui · error · InvalidOperationException
Only one ContentDialogHost instance is allowed per Window.
Error message
Only one ContentDialogHost instance is allowed per Window.
What it means
Thrown by ContentDialogHost.RegisterHost when a second, distinct ContentDialogHost instance tries to register itself for the same Window. The library keeps a single-slot-per-window map (WindowHosts) because only one host can own the overlay layer for a window; registering a different instance is treated as a programming error rather than silently replacing the first.
Source
Thrown at src/Wpf.Ui/Controls/ContentDialog/ContentDialogHost.cs:220
private void RegisterHostForWindow()
{
var window = Window.GetWindow(this);
if (window != null)
{
RegisterHost(window);
}
}
private void RegisterHost(Window window)
{
lock (WindowHostsLock)
{
if (WindowHosts.TryGetValue(window, out var existing))
{
if (!ReferenceEquals(existing, this))
{
throw new InvalidOperationException(
"Only one ContentDialogHost instance is allowed per Window."
);
}
// already registered for this window and it's this instance
return;
}
WindowHosts.Add(window, this);
}
}
}
#pragma warning restore IDE0008 // Use explicit type instead of 'var'
View on GitHub (pinned to ffebacd610)
Solutions
- Keep exactly one ContentDialogHost per Window — typically at the root of the window's content.
- If you need hosts in multiple user controls, remove the duplicates and let them share the window-level host.
- Ensure the previous host is properly unloaded (removed from the visual tree) before adding a new one.
- Check WindowHosts registrations during debugging if you suspect a stale entry.
Example fix
<!-- before -->
<Window>
<StackPanel>
<ui:ContentDialogHost x:Name="host1"/>
<ui:ContentDialogHost x:Name="host2"/> <!-- throws on load -->
</StackPanel>
</Window>
<!-- after -->
<Window>
<ui:ContentDialogHost x:Name="host"/>
</Window> Defensive patterns
Strategy: validation
Validate before calling
// In a window, ensure only one host exists
var hosts = FindVisualChildren<ContentDialogHost>(this).ToList();
Debug.Assert(hosts.Count <= 1, $"{hosts.Count} ContentDialogHosts in window"); Prevention
- Place a single ContentDialogHost at the window content root.
- Do not ship ContentDialogHost inside reusable user controls that get composed into the same window.
- Audit XAML for duplicate hosts when merging user controls.
When it happens
Trigger: Placing two <ui:ContentDialogHost> elements in the same Window's visual tree; adding a second host dynamically after one is already loaded; re-hosting on a window that still holds a previously-loaded host that was never unloaded.
Common situations: Migrating an app to WPF UI and leaving an old ContentDialogHost in XAML while adding another in a user control that lives in the same window; merging two user controls each of which ships its own host into one window; a host whose Unloaded handler did not fire (e.g. window closed via ShutdownMode) leaving a stale registration.
Related errors
- DialogHost was not set
- Unable to find the base directory of the application.
- Cannot change DialogHostEx while the dialog is being shown.
- Cannot apply backdrop effect if ExtendsContentIntoTitleBar i
- The {nameof(viewItem)}.{nameof(viewItem.TargetPageType)} pro
AI-assisted analysis of lepoco/wpfui@ffebacd610 (2026-08-13).
Data as JSON: /api/errors/227ae3fd6d172f65.
Report an issue: GitHub.