dotnet/wpf · error · InvalidOperationException

SR.CannotBeInsidePopup

Error message

SR.CannotBeInsidePopup

What it means

WebBrowser throws this InvalidOperationException when it is loaded inside a Popup's visual tree. The WebBrowser control hosts the full HwndSource-based WebBrowser ActiveX control, which cannot function correctly when hosted within a PopupRoot, so WPF explicitly forbids the combination. The check runs in the Loaded handler once the PresentationSource is available.

Solutions

  1. Move the WebBrowser out of the Popup — host it in a separate always-open Window (e.g. borderless, non-activating) positioned over the anchor instead of using a Popup.
  2. Use an overlay Adorner/Panel within the main window visual tree instead of a Popup.
  3. If the content is simple HTML, render it with a Frame/FlowDocument or third-party control that supports Popup hosting.
  4. P/Invoke-based alternatives (e.g. hosting via WindowsFormsHost outside the popup, or WebView2 with proper hwnd placement) that manage their own top-level hwnd.

Example fix

// before
<Popup>
  <WebBrowser Source="https://example.com" />
</Popup>
// after
<Window x:Class="FlyoutWindow" WindowStyle="None" AllowsTransparency="False" ShowInTaskbar="False">
  <WebBrowser Source="https://example.com" />
</Window>
<!-- position FlyoutWindow near the anchor instead of using a Popup -->
Defensive patterns

Strategy: try-catch

Validate before calling

// before loading a WebBrowser, verify it is not inside a Popup visual tree
static bool IsInsidePopup(System.Windows.DependencyObject d)
{
    while (d != null)
    {
        d = System.Windows.Media.VisualTreeHelper.GetParent(d);
        if (d is System.Windows.Controls.Primitives.Popup) return true;
    }
    return false;
}

Type guard

static bool InPopupRoot(Visual v) =>
    (PresentationSource.FromVisual(v)?.RootVisual) is PopupRoot;

Try / catch

try { popup.Child = new WebBrowser(); } catch (InvalidOperationException ex) when (ex.Message.Contains("popup")) { Log.Warn("WebBrowser cannot be hosted in a Popup; use a borderless window instead."); }

Prevention

When it happens

Trigger: Placing a <WebBrowser> element inside a <Popup> (or inside any control whose visual root becomes a PopupRoot) and letting it load; the exception is thrown from the Loaded event handler when pSource.RootVisual is PopupRoot.

Common situations: Developers building tooltip-like or flyout UI containing a WebBrowser; embedding web content in popup-styled custom controls; migrating code that worked with a hidden window into a Popup in .NET 4+.

Understand the failure class

Background: UnsupportedOperationException and "is not supported" errors: when a library deliberately refuses a call — this error's family across 30 libraries.

Related errors


AI-assisted analysis of dotnet/wpf@81131a70a4 (2026-09-14). Data as JSON: /api/errors/a9c896ee4b3e4176. Report an issue: GitHub.

Appendix: source

Thrown at src/Microsoft.DotNet.Wpf/src/PresentationFramework/System/Windows/Controls/WebBrowser.cs:739

        // Private Methods
        //
        //----------------------------------------------

        #region Private Methods
        
        private void LoadedHandler(object sender, RoutedEventArgs args)
        {
            PresentationSource pSource = PresentationSource.CriticalFromVisual(this);

            // Note that we cannot assert this condition here. The reason is that this element might have 
            // been disconnected from the tree through one of its parents even while it waited for the 
            // pending Loaded event to fire. More details for this scenario can be found in the 
            // Windows OS Bug#1981485.
            // Invariant.Assert(pSource != null, "Loaded has fired. PresentationSource shouldn't be null");
            
            if (pSource != null && pSource.RootVisual is PopupRoot)
            {
                throw new InvalidOperationException(SR.CannotBeInsidePopup);
            }
        }


        // Turn on all the WebOC Feature Control Keys implementing various security mitigations. 
        // Whenever possible, we do it programmatically instead of adding reg-keys so that these are on on all WPF apps. 
        // Unfortunately, some FCKs, especially newer ones, work only through the registry.
        [SuppressMessage("Microsoft.Usage", "CA1806:DoNotIgnoreMethodResults", MessageId="MS.Win32.UnsafeNativeMethods.CoInternetSetFeatureEnabled(System.Int32,System.Int32,System.Boolean)", 
            Justification="CoInternetSetFeatureEnabled() returns error for an unknown FCK. We expect this to happen with older versions of IE.")]
        private static void TurnOnFeatureControlKeys()
        {
            Version osver = Environment.OSVersion.Version;
            if (osver.Major == 5 && osver.Minor == 2 && osver.MajorRevision == 0) 
            {
                // XPSP2 mitigations - not available on Server 2003 before SP1. 
                return ; 
            }

View on GitHub (pinned to 81131a70a4)