{"record":{"id":"f996e78d3b7145e4","repo":"dotnet/maui","slug":"reuse-of-the-shell-renderer-is-not-supported","errorCode":null,"errorMessage":"Reuse of the Shell Renderer is not supported","messagePattern":"Reuse of the Shell Renderer is not supported","errorType":"exception","errorClass":"NotSupportedException","httpStatus":null,"severity":"error","filePath":"src/Controls/src/Core/Compatibility/Handlers/Shell/iOS/ShellRenderer.cs","lineNumber":126,"sourceCode":"\t\t\t\t\tFlyoutRenderer = CreateFlyoutRenderer();\n\t\t\t\t\tFlyoutRenderer.AttachFlyout(this, this);\n\t\t\t\t}\n\t\t\t\treturn _flyoutRenderer;\n\t\t\t}\n\t\t\tset { _flyoutRenderer = value; }\n\t\t}\n\n\t\tpublic event EventHandler<VisualElementChangedEventArgs> ElementChanged;\n\n\t\tpublic VisualElement Element { get; private set; }\n\t\tpublic UIView NativeView => FlyoutRenderer.View;\n\t\tpublic Shell Shell => (Shell)Element;\n\t\tpublic UIViewController ViewController => FlyoutRenderer.ViewController;\n\n\t\tpublic void SetElement(VisualElement element)\n\t\t{\n\t\t\tif (Element != null)\n\t\t\t\tthrow new NotSupportedException(\"Reuse of the Shell Renderer is not supported\");\n\t\t\tElement = element;\n\t\t\tOnElementSet((Shell)Element);\n\n\t\t\tElementChanged?.Invoke(this, new VisualElementChangedEventArgs(null, Element));\n\t\t\tMapper.UpdateProperties(this, Element);\n\t\t}\n\n\t\t[Obsolete]\n\t\tpublic virtual void SetElementSize(Size size)\n\t\t{\n\t\t}\n\n\t\tpublic override void ViewDidLayoutSubviews()\n\t\t{\n\t\t\tbase.ViewDidLayoutSubviews();\n\t\t\tif (_currentShellItemRenderer != null)\n\t\t\t\t_currentShellItemRenderer.ViewController.View.Frame = View.Bounds;\n\t\t}","sourceCodeStart":108,"sourceCodeEnd":144,"githubUrl":"https://github.com/dotnet/maui/blob/f377ff1c5ee04d334d8a925f50c83a6b7afddf03/src/Controls/src/Core/Compatibility/Handlers/Shell/iOS/ShellRenderer.cs#L108-L144","documentation":"Thrown by the iOS ShellRenderer.SetElement when SetElement is called on a renderer that already has an Element assigned. ShellRenderer is designed for single-use — once a Shell is bound to a renderer instance, it cannot be rebound. The check is `if (Element != null) throw new NotSupportedException`. This prevents reuse which would cause state corruption in the flyout/navigation infrastructure.","triggerScenarios":"At line 126: `if (Element != null) throw`. SetElement is called by the MAUI handler/framework when associating a virtual element with a platform renderer. A second call to SetElement on the same renderer instance triggers this. This is typically caused by: (1) the framework attempting to reuse a disposed/cached renderer; (2) manually calling SetElement on a renderer that was already used; (3) a handler lifecycle bug where the renderer wasn't properly disposed before reuse; (4) Shell being reassigned as MainPage without proper teardown.","commonSituations":"1) Setting MainPage to a new Shell instance after a previous Shell was already rendered (if the renderer pool tries to reuse). 2) Custom handler registration that incorrectly pools or reuses ShellRenderer instances. 3) Framework lifecycle bugs in specific MAUI versions where renderer disposal is skipped. 4) Hot reload or live visual tree triggering re-rendering of the Shell.","solutions":["Ensure the Shell is set as MainPage once and not reassigned to a different Shell instance at runtime — use Shell navigation (GoToAsync) instead of swapping the MainPage.","Update to the latest MAUI version where renderer lifecycle issues may be fixed.","If swapping Shells is necessary, ensure the old Shell's renderer is fully disposed before creating a new one.","Avoid custom handler factories that cache or pool ShellRenderer instances.","File a bug if this occurs under normal single-Shell usage (likely a framework lifecycle regression)."],"exampleFix":"// before\nMainPage = new AppShell();\n// later...\nMainPage = new AppShell(); // may reuse renderer on iOS\n\n// after — use Shell navigation, don't swap Shell instances\nMainPage = new AppShell();\n// navigate within the same Shell:\nawait Shell.Current.GoToAsync(\"//login\");","handlingStrategy":"validation","validationCode":"// Ensure Shell renderer is not reused\nif (shellRenderer.Element != null)\n    throw new NotSupportedException(\"ShellRenderer already has an element — create a new instance.\");\nshellRenderer.SetElement(shell);","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Never swap MainPage between different Shell instances — use GoToAsync for navigation.","Avoid custom handler factories that pool or cache ShellRenderer instances.","Update MAUI to the latest stable version for renderer lifecycle fixes."],"tags":["maui","ios","shell","renderer","lifecycle"],"backgroundTag":null,"analyzedSha":"f377ff1c5ee04d334d8a925f50c83a6b7afddf03","analyzedAt":"2026-08-13T14:26:18.069Z","schemaVersion":2},"datasetVersion":"2026-08-13T19:17:28.613Z"}