stride3d/stride · error · InvalidOperationException
An error occurred while disposing the window manager.
Error message
An error occurred while disposing the window manager.
What it means
Dispose unhooks the native WinEvent hook via NativeHelper.UnhookWinEvent. If the unhook call returns false, cleanup failed and the method throws InvalidOperationException so callers know the manager was not fully torn down and native resources may still be hooked.
Solutions
- Dispose on the same thread that constructed the WindowManager (the dispatcher thread)
- Ensure Dispose is called exactly once (guard with a disposed flag or use try/finally)
- If unhook fails on shutdown, log and continue — wrap Dispose in try/catch since the process is tearing down anyway
Example fix
// before
manager.Dispose(); manager.Dispose(); // second call: hook already zeroed/invalid
// after
if (manager != null) { manager.Dispose(); manager = null; } Defensive patterns
Strategy: try-catch
Validate before calling
if (manager == null || manager.IsDisposed) return;
Try / catch
try { manager.Dispose(); } catch (InvalidOperationException ex) when (ex.Message.Contains("disposing the window manager")) { /* log; shutdown race */ } Prevention
- Dispose on the constructing thread only
- Dispose exactly once
- Treat dispose failures during shutdown as non-fatal
When it happens
Trigger: Calling Dispose after the hook was already invalidated or the native unhook failed (invalid hook handle, wrong thread context, or double-dispose scenarios where the handle is stale).
Common situations: Disposing from a different thread/context than the hook was installed on; double disposal or disposing after hook corruption; native layer returning failure under shutdown races.
Understand the failure class
Background: "Invalid state transition" errors: "status must be X, actually Y", "already rejected/charging/uninstalled", "cannot ... while running" — what they mean when a library rejects your call — this error's family across 31 libraries.
Related errors
- The hwnd cannot be null
- Unable to initialize the window manager.
- A dependency object is already attached to this instance of…
- A dependency object must be attached in order to register a…
- A dependency object must be attached in order to unregister…
AI-assisted analysis of stride3d/stride@96fad776d2 (2026-09-14).
Data as JSON: /api/errors/af3dd070d874b21b.
Report an issue: GitHub.
Appendix: source
Thrown at sources/presentation/Stride.Core.Presentation.Wpf/Windows/WindowManager.cs:77
/// Gets the current main window.
/// </summary>
public static WindowInfo MainWindow { get; private set; }
/// <summary>
/// Gets the collection of currently visible modal windows.
/// </summary>
public static IReadOnlyList<WindowInfo> ModalWindows => ModalWindowsList;
/// <summary>
/// Gets the collection of currently visible blocking windows.
/// </summary>
public static IReadOnlyList<WindowInfo> BlockingWindows => BlockingWindowsList;
/// <inheritdoc/>
public void Dispose()
{
if (!NativeHelper.UnhookWinEvent(hook))
throw new InvalidOperationException("An error occurred while disposing the window manager.");
hook = IntPtr.Zero;
winEventProc = null;
dispatcher = null;
MainWindow = null;
AllWindowsList.Clear();
ModalWindowsList.Clear();
BlockingWindowsList.Clear();
Logger.Info($"{nameof(WindowManager)} disposed");
initialized = false;
}
/// <summary>
/// Shows the given window as the main window of the application. It is mandatory to use this method for the main window to use features of the <see cref="WindowManager"/>.
/// </summary>
/// <param name="window">The main window to show.</param>
public static void ShowMainWindow([NotNull] Window window)View on GitHub (pinned to 96fad776d2)