{"record":{"id":"ecd255e84cc96aaa","repo":"stride3d/stride","slug":"can-only-assign-uielementservice-to-the-root-element","errorCode":null,"errorMessage":"Can only assign UIElementService to the root element!","messagePattern":"Can only assign UIElementService to the root element!","errorType":"exception","errorClass":"InvalidOperationException","httpStatus":null,"severity":"error","filePath":"sources/engine/Stride.UI/UIElement.cs","lineNumber":649,"sourceCode":"                    child.LayoutingContext = value;\n            }\n        }\n\n        private UIElementServices uiElementServices;\n\n        internal UIElementServices UIElementServices\n        {\n            get\n            {\n                if (Parent != null && !Parent.UIElementServices.Equals(ref uiElementServices))\n                    uiElementServices = Parent.UIElementServices;\n\n                return uiElementServices;\n            }\n            set\n            {\n                if (Parent != null)\n                    throw new InvalidOperationException(\"Can only assign UIElementService to the root element!\");\n\n                uiElementServices = value;\n            }\n        }\n\n        /// <summary>\n        /// The visual children of this element.\n        /// </summary>\n        /// <remarks>If the class is inherited it is the responsibility of the descendant class to correctly update this collection</remarks>\n        [DataMemberIgnore]\n        protected internal UIElementCollection VisualChildrenCollection { get; }\n\n        /// <summary>\n        /// Invalidates the arrange state (layout) for the element.\n        /// </summary>\n        protected internal void InvalidateArrange()\n        {\n            ForceArrange(); // force arrange on top hierarchy","sourceCodeStart":631,"sourceCodeEnd":667,"githubUrl":"https://github.com/stride3d/stride/blob/96fad776d210c221682aac1ccdf4c79dc046fc38/sources/engine/Stride.UI/UIElement.cs#L631-L667","documentation":"The UIElementServices property may only be set on the root element of a UI tree. Stride throws InvalidOperationException if a non-root element (one that already has a Parent) is assigned services, because service resolution flows from the root down and per-node assignment would break that invariant.","triggerScenarios":"Setting element.UIElementServices = services on a child element whose Parent is already set; assigning services after the element has been added to a UI tree.","commonSituations":"Looping over all elements in a page and assigning services to each; re-parenting an element then trying to give it its own services instance.","solutions":["Assign UIElementServices only on the root element (e.g. the page or root UIComponent element) before/while building the tree.","Set the property before adding the element as a child of another element.","Let child elements inherit services from the root instead of assigning directly."],"exampleFix":"// before\nforeach (var el in page.Traverse()) el.UIElementServices = services; // throws on children\n// after\nroot.UIElementServices = services; // root only; children inherit","handlingStrategy":"validation","validationCode":"if (element.Parent == null)\n    element.UIElementServices = services;\nelse\n    element.FindRoot()?.UIElementServices = services;","typeGuard":"bool IsRoot(UIElement e) => e.Parent == null;","tryCatchPattern":"try { element.UIElementServices = services; }\ncatch (InvalidOperationException) { element.FindRoot().UIElementServices = services; }","preventionTips":["Assign services once on the root element during page setup","Set UIElementServices before attaching the element into a tree","Rely on service inheritance from the root rather than per-node assignment"],"tags":["invalid-state","ui","root-element","services"],"backgroundTag":"invalid-state-transition","analyzedSha":"96fad776d210c221682aac1ccdf4c79dc046fc38","analyzedAt":"2026-09-14T02:59:31.279Z","contentChangedAt":"2026-09-14T02:59:31.279Z","schemaVersion":2},"datasetVersion":"2026-09-15T23:17:13.987Z"}