Skip to content

fix: improve large-document scroll performance - #107

Merged
heckmon merged 6 commits into
heckmon:mainfrom
zundaren:fix/code-forge-scroll-performance
Sep 2, 2026
Merged

fix: improve large-document scroll performance#107
heckmon merged 6 commits into
heckmon:mainfrom
zundaren:fix/code-forge-scroll-performance

Conversation

@zundaren

Copy link
Copy Markdown
Contributor
  1. Syntax highlighting is removed from the rendered frame.
    Previously, when scrolling to the uncached area, paint() would synchronously call re_highlight. Now, the first frame is drawn as regular text first, and then highlighted in the isolate background; as a result, only the color of this area is redrawn upon returning.

  2. Line height establishment for line breaks is queryable
    After a line break, each line height is different. The original implementation continuously accumulates from the 0th line, and locating the 6000th line is O(n). Now, the average height of the sampled area is used as an estimate for the unknown line, and the actual measured height is used as an increment, placed in the Fenwick tree; by binary search/prefix sum O(log n), the first visible line is found.

  3. Gutter must also reuse the same index
    After optimizing the main text area, the gutter still scans from the first line once, causing line breaks to still be laggy. It is also changed to use the height index.

  4. Features are classified by cost
    Collapsing and indentation lines are not basic text rendering. The folding range of JSON parentheses may scan to the end of the document, and fast scrolling will trigger synchronous calculation. Therefore, JSON tools should first disable these two features; if they need to be retained later, they should be changed to background, lazy-loaded folding range.

  5. Independent performance page verification:
    flutter run -t lib/scroll_performance_main.dart

@heckmon

heckmon commented Aug 28, 2026

Copy link
Copy Markdown
Owner

I'll review and merge it soon 👍

@heckmon

heckmon commented Aug 28, 2026

Copy link
Copy Markdown
Owner

@zundaren Now, the lineWrap=true is smooth even in large files (tested on a 150k line code, as in the picture below), but the syntax highlighting is not working.

Screenshot from 2026-08-28 22-28-16

@zundaren

Copy link
Copy Markdown
Contributor Author

@zundaren Now, the lineWrap=true is smooth even in large files (tested on a 150k line code, as in the picture below), but the syntax highlighting is not working.现在,当 lineWrap 设置为 true 时,即使处理大型文件时,效果也很流畅(如下图所示,测试的是包含 15 万行的代码)。不过,语法高亮功能却无法正常使用。

Screenshot from 2026-08-28 22-28-16

I'll adjust the highlighting effect and then test it. I have only tested 4 languages so far and haven't conducted extensive testing.

@heckmon

heckmon commented Aug 29, 2026

Copy link
Copy Markdown
Owner

@zundaren When typing on a line, the colour of that line flickers. And if lineWrap=true, on pressing backspace or Enter, the whole syntax highlight flickers.

Screencast.from.2026-08-29.11-12-32.webm

@zundaren

Copy link
Copy Markdown
Contributor Author

@zundaren When typing on a line, the colour of that line flickers. And if lineWrap=true, on pressing backspace or Enter, the whole syntax highlight flickers.在输入文字时,所输入的那一行的颜色会闪烁。如果设置了 lineWrap=true,那么在按下退格键或回车键时,整个被高亮显示的语法结构都会闪烁。

Screencast.from.2026-08-29.11-12-32.webm

@zundaren When typing on a line, the colour of that line flickers. And if lineWrap=true, on pressing backspace or Enter, the whole syntax highlight flickers.

Screencast.from.2026-08-29.11-12-32.webm

@zundaren When typing on a line, the colour of that line flickers. And if lineWrap=true, on pressing backspace or Enter, the whole syntax highlight flickers.

Screencast.from.2026-08-29.11-12-32.webm

The core corrections are as follows:

  • When switching languages, CodeForge previously cached the initial _language / _editorTheme. The dropdown was changed, but the internal highlighter did not update accordingly.
  • When the text changes, the page previously used a full-page setState to rebuild the scroll view and the highlight tree, which could easily cause the state to become messy.

The approach I took was:

  • In CodeForge's didUpdateWidget, synchronize _language, _editorTheme, and _readOnly
  • Change _language and _editorTheme from late final to updatable fields
  • Make the text refresh on the example page only affect the right statistics/reference panel, and no longer rebuild the left editor
  • Additionally, I fixed the inheritance of the nested styles for SyntaxHighlighter to avoid losing parent styles in child spans

@zundaren When typing on a line, the colour of that line flickers. And if lineWrap=true, on pressing backspace or Enter, the whole syntax highlight flickers.

Screencast.from.2026-08-29.11-12-32.webm

The core corrections are as follows:

1.Latest submission, The input test did not observe any flickering.

  1. During language switching, CodeForge had been caching the initial _language / _editorTheme values. After the dropdown was changed, the internal highlighter did not update accordingly.
  • When the text changes, the page previously used a full-page setState to rebuild the scroll view and the highlight tree, which can easily cause the state to be messed up.

The approach I took was:

  • In CodeForge's didUpdateWidget, synchronize _language, _editorTheme, and _readOnly
  • Change _language and _editorTheme from late final to updatable fields.
  • Additionally, I supplemented the inheritance of the nested styles of SyntaxHighlighter to avoid losing the parent styles of the child spans.

@heckmon

heckmon commented Aug 30, 2026

Copy link
Copy Markdown
Owner

I'll review it soon, I was very busy.

@heckmon
heckmon merged commit 5231185 into heckmon:main Sep 2, 2026
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.

2 participants