{"record":{"id":"300c0ea0207f4aa5","repo":"dotnet/wpf","slug":"sr-format-sr-textschema-cannotsplitelement","errorCode":null,"errorMessage":"SR.Format(SR.TextSchema_CannotSplitElement, nonMergeableAncestor.GetType().Name)","messagePattern":"SR\\.Format\\(SR\\.TextSchema_CannotSplitElement, nonMergeableAncestor\\.GetType\\(\\)\\.Name\\)","errorType":"exception","errorClass":"InvalidOperationException","httpStatus":null,"severity":"error","filePath":"src/Microsoft.DotNet.Wpf/src/PresentationFramework/System/Windows/Documents/Span.cs","lineNumber":116,"sourceCode":"\n            start.TextContainer.BeginChange();\n            try\n            {\n                start = TextRangeEditTables.EnsureInsertionPosition(start);\n                Invariant.Assert(start.Parent is Run);\n                end = TextRangeEditTables.EnsureInsertionPosition(end);\n                Invariant.Assert(end.Parent is Run);\n\n                if (start.Paragraph != end.Paragraph)\n                {\n                    throw new ArgumentException(SR.Format(SR.InDifferentParagraphs, \"start\", \"end\"));\n                }\n\n                // If start or end positions have a Hyperlink ancestor, we cannot split them.\n                Inline nonMergeableAncestor;\n                if ((nonMergeableAncestor = start.GetNonMergeableInlineAncestor()) != null)\n                {\n                    throw new InvalidOperationException(SR.Format(SR.TextSchema_CannotSplitElement, nonMergeableAncestor.GetType().Name));\n                }\n                if ((nonMergeableAncestor = end.GetNonMergeableInlineAncestor()) != null)\n                {\n                    throw new InvalidOperationException(SR.Format(SR.TextSchema_CannotSplitElement, nonMergeableAncestor.GetType().Name));\n                }\n\n                TextElement commonAncestor = TextElement.GetCommonAncestor((TextElement)start.Parent, (TextElement)end.Parent);\n\n                while (start.Parent != commonAncestor)\n                {\n                    start = SplitElement(start);\n                }\n                while (end.Parent != commonAncestor)\n                {\n                    end = SplitElement(end);\n                }\n\n                if (start.Parent is Run)","sourceCodeStart":98,"sourceCodeEnd":134,"githubUrl":"https://github.com/dotnet/wpf/blob/81131a70a4c573cd62748a5c36908fc4d662daa9/src/Microsoft.DotNet.Wpf/src/PresentationFramework/System/Windows/Documents/Span.cs#L98-L134","documentation":"The Span(TextPointer start, TextPointer end) constructor throws InvalidOperationException with SR.TextSchema_CannotSplitElement (containing the element type name, e.g. 'Hyperlink') when either endpoint sits inside a non-mergeable inline element such as a Hyperlink. Creating the Span would require splitting that element, which the text schema forbids, so the constructor refuses regardless of argument order.","triggerScenarios":"new Span(start, end) where start.GetNonMergeableInlineAncestor() (or the same for end) returns non-null - typically a position inside a Hyperlink (or other non-mergeable Inline) in a FlowDocument.","commonSituations":"Programmatically inserting/formatting content within a hyperlink in a RichTextBox/FlowDocument; building a Span whose endpoint lands inside UIElement-anchored or embedded inline content; text processing scripts that walk into hyperlinked text runs.","solutions":["Move the start/end position outside the Hyperlink (e.g. to its ElementStart/ElementEnd) before constructing the Span.","Check GetNonMergeableInlineAncestor() on both endpoints first and reject or adjust positions when non-null.","Split the operation into ranges that exclude the hyperlink, or operate on the Hyperlink element itself instead of positions inside it.","Catch InvalidOperationException and report that the position inside an un-splittable element (name in message) is not allowed."],"exampleFix":"// before\nvar span = new Span(insideHyperlinkPointer, end);\n// after\nif (insideHyperlinkPointer.GetNonMergeableInlineAncestor() != null)\n    insideHyperlinkPointer = insideHyperlinkPointer.GetNonMergeableInlineAncestor().ElementEnd;\nvar span = new Span(insideHyperlinkPointer, end);","handlingStrategy":"validation","validationCode":"if (start.GetNonMergeableInlineAncestor() != null || end.GetNonMergeableInlineAncestor() != null)\n    throw new InvalidOperationException(\"Range endpoints lie inside a non-mergeable inline element (e.g. Hyperlink).\");","typeGuard":"static bool OutsideNonMergeableInline(TextPointer p) => p.GetNonMergeableInlineAncestor() == null;","tryCatchPattern":"try { span = new Span(start, end); }\ncatch (InvalidOperationException ex) when (ex.Message.Contains(\"split\")) { /* move endpoints outside the element and retry */ }","preventionTips":["Snap range endpoints out of Hyperlinks via GetNonMergeableInlineAncestor()/ElementEnd","Disable editing operations inside hyperlinks in UI where Spans are built","Unit-test range creation against documents containing hyperlinks and embedded UIElements"],"tags":["wpf","documents","hyperlink","invalid-operation"],"backgroundTag":"unsupported-operation","analyzedSha":"81131a70a4c573cd62748a5c36908fc4d662daa9","analyzedAt":"2026-09-14T10:12:48.479Z","contentChangedAt":"2026-09-14T10:12:48.479Z","schemaVersion":2},"datasetVersion":"2026-09-21T21:30:21.729Z"}