{"record":{"id":"03b69928615cf359","repo":"EllanJiang/GameFramework","slug":"ui-group-is-invalid","errorCode":null,"errorMessage":"UI group is invalid.","messagePattern":"UI group is invalid\\.","errorType":"exception","errorClass":"GameFrameworkException","httpStatus":null,"severity":"error","filePath":"GameFramework/UI/UIManager.cs","lineNumber":822,"sourceCode":"            CloseUIForm(uiForm, null);\n        }\n\n        /// <summary>\n        /// 关闭界面。\n        /// </summary>\n        /// <param name=\"uiForm\">要关闭的界面。</param>\n        /// <param name=\"userData\">用户自定义数据。</param>\n        public void CloseUIForm(IUIForm uiForm, object userData)\n        {\n            if (uiForm == null)\n            {\n                throw new GameFrameworkException(\"UI form is invalid.\");\n            }\n\n            UIGroup uiGroup = (UIGroup)uiForm.UIGroup;\n            if (uiGroup == null)\n            {\n                throw new GameFrameworkException(\"UI group is invalid.\");\n            }\n\n            uiGroup.RemoveUIForm(uiForm);\n            uiForm.OnClose(m_IsShutdown, userData);\n            uiGroup.Refresh();\n\n            if (m_CloseUIFormCompleteEventHandler != null)\n            {\n                CloseUIFormCompleteEventArgs closeUIFormCompleteEventArgs = CloseUIFormCompleteEventArgs.Create(uiForm.SerialId, uiForm.UIFormAssetName, uiGroup, userData);\n                m_CloseUIFormCompleteEventHandler(this, closeUIFormCompleteEventArgs);\n                ReferencePool.Release(closeUIFormCompleteEventArgs);\n            }\n\n            m_RecycleQueue.Enqueue(uiForm);\n        }\n\n        /// <summary>\n        /// 关闭所有已加载的界面。","sourceCodeStart":804,"sourceCodeEnd":840,"githubUrl":"https://github.com/EllanJiang/GameFramework/blob/d0c010b05167c58e92350449d04864a91ca13fd2/GameFramework/UI/UIManager.cs#L804-L840","documentation":"Thrown by UIManager.CloseUIForm when the form is non-null but its UIGroup property is null, i.e. the form was never added to a UI group (never fully opened) or was already detached. Casting uiForm.UIGroup to UIGroup and finding null means the form is not in a valid managed state.","triggerScenarios":"Closing an IUIForm that was instantiated manually (not via OpenUIForm) so it never received a group; or closing a form twice where the first close removed it from its group.","commonSituations":"Double-close on rapid hide/show input; forms created via helper InstantiateUIForm without opening; shutdown-order bugs where forms outlive their groups.","solutions":["Ensure the form was opened through OpenUIForm/OpenUIFormAsync before closing","Guard against double close by checking the form's own state flag before calling CloseUIForm","Check uiForm.UIGroup != null before closing"],"exampleFix":"// before\nUI.CloseUIForm(form);\n// after\nif (form.UIGroup != null)\n{\n    UI.CloseUIForm(form);\n}","handlingStrategy":"validation","validationCode":"if (form == null || form.UIGroup == null) { Log.Warning(\"Form not openable/closeable\"); return; }","typeGuard":"bool IsFormAttached(IUIForm f) => f != null && f.UIGroup != null;","tryCatchPattern":"try { UI.CloseUIForm(form, userData); } catch (GameFrameworkException ex) { Log.Warning(\"Form already detached: {0}\", ex.Message); }","preventionTips":["Track open/closed state with a bool flag to prevent double close","Only close forms obtained from OpenUIForm callbacks","Serialize UI operations instead of closing from multiple systems"],"tags":["unity","gameframework","ui","invalid-state"],"backgroundTag":"invalid-state-transition","analyzedSha":"d0c010b05167c58e92350449d04864a91ca13fd2","analyzedAt":"2026-09-15T13:37:15.352Z","contentChangedAt":"2026-09-15T13:37:15.352Z","schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}