Skip to content

Fix crash when rendering the wallpaper preview bubbles - #3327

Merged
FrayxRulez merged 2 commits into
developfrom
fasttext-fontsize-zero
Aug 10, 2026
Merged

Fix crash when rendering the wallpaper preview bubbles#3327
FrayxRulez merged 2 commits into
developfrom
fasttext-fontsize-zero

Conversation

@FrayxRulez

@FrayxRulez FrayxRulez commented Aug 10, 2026

Copy link
Copy Markdown
Collaborator

Crash

ArgumentException: Value does not fall within the expected range.

Reported by crash telemetry on 12.9.0.0, as three groups sharing one anchor.

2  Windows.UI.Xaml.Core.Direct.IXamlDirect.SetDoubleProperty
3  Telegram.Controls.FormattedTextBlock.SetText
   Telegram/Controls/FormattedTextBlock.cs:986
4  Telegram.Controls.Messages.MessageTextBlock.SetText
   Telegram/Controls/Messages/MessageTextBlock.cs:202

Reached two ways — from the wallpaper picker:

5  MessageBubble.Mockup                     MessageBubble.xaml.cs:3183
6  BackgroundPopup.UpdateBackground
7  BackgroundViewModel.set_SelectedPattern

and from an ordinary message in the chat:

5  MessageBubble.UpdateMessageText          MessageBubble.xaml.cs:2184
6  MessageBubble.UpdateMessageContent       MessageBubble.xaml.cs:1839
7  MessageBubble.UpdateMessage

Cause

SetText keeps the raw argument in _fontSize, then resolves it:

_fontSize = fontSize;
...
if (AutoFontSize && fontSize == 0)
{
    fontSize = Theme.Current.MessageFontSize;
}

The slow path passes the resolved fontSize to GetOrCreateRun. The plain-run fast path
instead reads _fontSize back:

if (_fontSize != prevFontSize)
{
    direct.SetDoubleProperty(_fastRun, XamlPropertyIndex.TextElement_FontSize, _fontSize);
}

Every SetText overload declares double fontSize = 0, and callers that don't specify a size
rely on AutoFontSize to resolve it. The fast path bypasses that resolution and writes the
raw 0, which XAML rejects with E_INVALIDARG. The guard is on change, so it is the
transition from a real size to 0 that performs the invalid write.

Fix

Write the resolved fontSize, matching what the slow path already passes to GetOrCreateRun.

The first commit here guarded the value and cleared the property instead; that stops the crash
but inherits the parent's size rather than applying the theme size, so it is replaced by the
one-word fix in the follow-up commit.

Verification

Not built or run — a UWP/.NET Native build is not available in the environment this was
prepared in. The edited file was checked with Roslyn (CSharpSyntaxTree.ParseText) and
parses with no syntax errors; that confirms syntax only, not type checking.

🤖 Generated with Claude Code

The plain-run fast path wrote whatever font size had changed, including 0, and
XAML rejects a FontSize of 0 with E_INVALIDARG. GetOrCreateRun already treats
non-positive as "inherit" and clears the property instead; the fast path now
does the same.

MessageBubble.Mockup reaches this: it calls SetText without a font size, so the
default of 0 replaces the size the bubble was previously rendered with, and the
transition is exactly what triggers the write.

Reported by crash telemetry on 12.9.0.0.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@FrayxRulez

Copy link
Copy Markdown
Collaborator Author

I don't think the fix is correct here. I'd rather keep the code as before, but use fontSize rather than _fontSize, as the latter is the raw value, while the first one is the computed font size.

Per review: _fontSize is the raw value, fontSize is what AutoFontSize resolved
it to, and the slow path already passes the resolved one to GetOrCreateRun. The
fast path writing the raw value is the actual defect, so write the resolved one
instead of clearing the property — clearing would inherit the parent's size
rather than applying the theme size.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@FrayxRulez

FrayxRulez commented Aug 10, 2026

Copy link
Copy Markdown
Collaborator Author

You're right, and my version would have been wrong in a way the crash wouldn't have shown.

_fontSize is assigned the raw argument, and a few lines later AutoFontSize resolves it:

_fontSize = fontSize;
...
if (AutoFontSize && fontSize == 0)
{
    fontSize = Theme.Current.MessageFontSize;
}

The slow path already passes the resolved fontSize to GetOrCreateRun; only the fast path
reads _fontSize back. So writing the raw value is the defect itself, not just an unguarded
zero — clearing the property would have stopped the crash while silently inheriting the
parent's size instead of applying the theme size, on exactly the messages AutoFontSize exists
to size.

Pushed as a follow-up commit rather than a force-push, so the original is still visible.

One thing worth recording: a further group has the same anchor but comes through
MessageBubble.UpdateMessageText on a normal message, not Mockup. So the mockup path in the
description above is one trigger rather than the cause; resolving the size covers all of them.
I've updated the description accordingly.

@FrayxRulez
FrayxRulez merged commit 1088776 into develop Aug 10, 2026
1 check passed
@FrayxRulez
FrayxRulez deleted the fasttext-fontsize-zero branch August 10, 2026 12:46
FrayxRulez added a commit that referenced this pull request Aug 10, 2026
* Fix crash when rendering the wallpaper preview bubbles

The plain-run fast path wrote whatever font size had changed, including 0, and
XAML rejects a FontSize of 0 with E_INVALIDARG. GetOrCreateRun already treats
non-positive as "inherit" and clears the property instead; the fast path now
does the same.

MessageBubble.Mockup reaches this: it calls SetText without a font size, so the
default of 0 replaces the size the bubble was previously rendered with, and the
transition is exactly what triggers the write.

Reported by crash telemetry on 12.9.0.0.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

* Use the computed font size in the fast path

Per review: _fontSize is the raw value, fontSize is what AutoFontSize resolved
it to, and the slow path already passes the resolved one to GetOrCreateRun. The
fast path writing the raw value is the actual defect, so write the resolved one
instead of clearing the property — clearing would inherit the parent's size
rather than applying the theme size.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant