Commit Graph
22 Commits
Author SHA1 Message Date
f556cf349e Release: chat stream scroll-bounce fix (#6257) (#6993)
* fix(stream): preserve fade nodes while prose is live

* fix(stream): preserve transparent fade nodes like assistant prose

The transparent-activity prose path (transparent_stream mode) kept the
pre-PR fade cleanup: _bindTransparentFadeCleanup() in static/ui.js still
replaced every animated stream-fade-word span with a fresh text node on
animationend, invalidating the native scroll anchor while the row is
still growing.

Mirror the messages.js fix so both live prose paths share one
node-preserving cleanup: remove only the transient is-new class and the
--stream-fade-ms inline property, keeping span identity until final
settlement rebuilds the persisted DOM.

Extend tests/test_smooth_text_fade.py with a sibling regression that
extracts the production _bindTransparentFadeCleanup() from ui.js and
fires animationend, asserting no replacement, is-new removal,
stream-fade-word retention, and timing-override cleanup (plus
source-string guards against replaceWith in the cleanup block). The new
test is red-before-green against the previous ui.js implementation.

* docs(changelog): stamp #6257 (stream fade scroll-bounce fix)

---------

Co-authored-by: Anthony Ruiz <ruizanthony@users.noreply.github.com>
Co-authored-by: nesquena-hermes <nesquena-hermes@users.noreply.github.com>
2026-08-13 17:40:54 +00:00
cabb467b36 fix(stream): stop fade-text effect from re-fading the whole message on tool-call rewinds (#6783)
* fix(stream): stop fade-text effect from re-fading whole message on tool-call rewinds

When the fade-text effect is enabled, Hermes long tasks visibly blink the
entire message on every tool call. Root cause: tool-call XML
(<function_calls>) appears inline in the assistant text stream, and the
unclosed-tag stripping in _stripXmlToolCalls temporarily rewinds
displayText to a strict prefix. That rewind zeroed the fade playout
(_streamFadeNextText) and tripped _smdWrite's self-heal, which cleared
assistantBody.innerHTML and re-created every word as a fresh is-new
span — replaying the fade on all visible text at once.

Fix: on a detected rewind, shrink the playout cursor to the common
prefix instead of resetting to zero, and mute the fade renderer for
that common prefix during any rebuild (both the main smd path and the
anchor prose incremental node) so only the post-rewind tail animates.

Adds regression tests: playout rewind keeps common prefix visible,
rebuild mutes the common prefix, and _smdWrite's self-heal sets the
silent-prefix window.

* fix(#6783): compute rewind mute prefix in rendered-text space

Review feedback (maintainer round on 56c9307f): the silent-prefix budget
was computed in SOURCE-text space (charCodeAt over markdown source), but
the fade add_text hook only receives RENDERED prose. Markdown delimiters,
link destinations and MEDIA token bytes never reach add_text, so the
source-space budget over-muted the first genuinely new word after a
rewind (e.g. '**alpha** beta' -> '**alpha** gamma' muted gamma).

Fix: snapshot the OLD rendered text before the rebuild (assistantBody
textContent / anchor .msg-body textContent), then after parser_write
compare it with the NEW rendered text and strip is-new only from spans
inside the rendered common prefix (_streamFadeMuteRenderedPrefix).

- Rendered-space boundary, scoped to the owning node (no stream-global
  counter that can survive a rebuild without a fade consumer)
- No state left behind on reduced-motion / safe-renderer / empty-text /
  parser-finalization paths: _rewindPrevRendered is a local variable
  consumed right after the rebuild
- Tests: plain-word mute, markdown/MEDIA byte regression (the blocker),
  per-root scoping (main vs anchor), updated _smdWrite self-heal test

Gate: node -c OK; test_smooth_text_fade + test_smd_media_in_stream +
test_svg_audio_video_rendering + test_insights -> 83 passed, 18 subtests.

* fix(#6783): drop f-prefix from _fade_fake_node JS block (F541)

CI lint failure on a6d37b22: tests/test_smooth_text_fade.py:723 F541
f-string without any placeholders. The f-prefix was only used to escape
JS braces ({{ }}) — a plain string with literal braces is equivalent
and passes the ruff E9+F+B gate.

---------

Co-authored-by: silent-reader-cn <silent-reader-cn@users.noreply.github.com>
Co-authored-by: nesquena-hermes <nesquena+hermes@gmail.com>
2026-08-08 23:37:54 +00:00
Rod Boev 0c1bdce023 fix(#5493): honor reduced motion for transparent fade 2026-07-04 10:07:34 -04:00
Rod Boev 45a203b36b fix(#5493): preserve anchor prose before body mount 2026-07-04 10:04:15 -04:00
Rod Boev 3918dd132e Fade transparent prose without preference gate 2026-07-04 10:04:15 -04:00
Rod Boev 86e55c7856 Feed transparent fade rows revealed text 2026-07-04 10:03:35 -04:00
Rod Boev 26eda1adbd Make appended token fade perceptible 2026-07-04 10:02:39 -04:00
Rod Boev 28d058ad2e Start fade spans when appended 2026-07-04 10:02:39 -04:00
Rod Boev af2f534f21 Append fade spans instead of replaying streamed prose 2026-07-04 10:02:39 -04:00
Rod Boev c15cb84867 fix(#5493): restore transparent stream prose fade 2026-07-04 10:02:39 -04:00
Anthony Ruiz 76ae2b795c test(webui): make live-transition guard anchors explicit 2026-07-01 15:50:24 +00:00
ruizanthony 0c13a17231 fix(webui): stop live streaming message flicker
Opt live assistant streaming nodes out of the global theme color/background transitions so token-by-token markdown updates do not flash or fade on light themes.

Adds a targeted regression test in test_smooth_text_fade.py while keeping the opt-in smooth text fade feature intact.
2026-07-01 07:38:44 +00:00
b5caf83ff9 Release v0.51.279 — Release IU (stage-p3h — preserve Activity/streaming turn on mid-stream scroll #3665) (#3686)
* fix(streaming): preserve Activity + streaming turn when loading earlier messages mid-stream (#3665, #3346)

Co-authored-by: mysoul12138 <839465496@qq.com>

* docs(changelog): v0.51.279 — Release IU (stage-p3h)

---------

Co-authored-by: nesquena-hermes <[email protected]>
Co-authored-by: mysoul12138 <839465496@qq.com>
2026-06-05 14:45:31 -07:00
Michael Lam 87e3b4e88e fix: cap stream fade done drain 2026-05-17 00:27:54 -07:00
dobby-d-elf f23ee79938 Scale fade duration with playback speed 2026-05-12 20:50:38 -06:00
dobby-d-elf 0b51245bd3 Optimize smooth fade word append path 2026-05-12 18:20:08 -06:00
dobby-d-elf 5e2350e128 Harden smooth text fade before merge 2026-05-12 18:18:07 -06:00
dobby-d-elf c9c70fc1c5 improve smoothness with punctiotion rules & performance optimizations 2026-05-12 09:06:08 -06:00
dobby-d-elf 9e9ff30c78 adjust stream params 2026-05-11 21:13:31 -06:00
dobby-d-elf 7fa2f70314 optimize performance & tune readability 2026-05-11 18:02:42 -06:00
dobby-d-elf 8ff368fd80 clean up implementation 2026-05-11 17:38:12 -06:00
dobby-d-elf 67e29fa991 feat: add opt-in streaming text fade 2026-05-11 13:13:26 -06:00