Skip to content

feat: implement smart scroll for terminal output#506

Merged
lzwind merged 3 commits into
linuxdeepin:masterfrom
dzw1995:develop/snipe
Apr 10, 2026
Merged

feat: implement smart scroll for terminal output#506
lzwind merged 3 commits into
linuxdeepin:masterfrom
dzw1995:develop/snipe

Conversation

@dzw1995
Copy link
Copy Markdown
Contributor

@dzw1995 dzw1995 commented Mar 26, 2026

Implement smart scrolling behavior that only auto-scrolls when user is already at the bottom of the terminal. This allows users to scroll up and view history without being forced back to the bottom when new output arrives.

Changes:

  • Add isAtEndOfOutput() method to QTermWidget
  • Modify onQTermWidgetReceivedData() to check user position before scrolling
  • Improves experience with high-frequency output apps like kimi-cli
  • Enhanced debug logging for scroll behavior

Fixes: Users can now scroll up to view history while output is ongoing

@github-actions
Copy link
Copy Markdown

github-actions Bot commented Mar 26, 2026

CLA Assistant Lite bot All contributors have signed the CLA ✍️ ✅

@deepin-ci-robot
Copy link
Copy Markdown

Hi @dzw1995. Thanks for your PR.

I'm waiting for a linuxdeepin member to verify that this patch is reasonable to test. If it is, they should reply with /ok-to-test on its own line. Until that is done, I will not automatically test new commits in this PR, but the usual testing commands by org members will still work. Regular contributors should join the org to skip this step.

Once the patch is verified, the new status will be reflected by the ok-to-test label.

I understand the commands that are listed here.

Details

Instructions for interacting with me using PR comments are available here. If you have questions or suggestions related to my behavior, please file an issue against the kubernetes/test-infra repository.

@github-actions
Copy link
Copy Markdown

  • 敏感词检查失败, 检测到1个文件存在敏感词
详情
{
    "src/views/termwidget.cpp": [
        {
            "line": "    QString strUrl = \"https://cn.bing.com/search?q=\" + selectedText();",
            "line_number": 701,
            "rule": "S35",
            "reason": "Url link | fd576f862d"
        },
        {
            "line": "    QString strUrl = \"https://www.baidu.com/s?wd=\" + selectedText();",
            "line_number": 708,
            "rule": "S35",
            "reason": "Url link | 6f8d292d20"
        },
        {
            "line": "    QString strUrl = \"https://github.com/search?q=\" + selectedText();",
            "line_number": 715,
            "rule": "S35",
            "reason": "Url link | e1ba2d7c70"
        },
        {
            "line": "    QString strUrl = \"https://stackoverflow.com/search?q=\" + selectedText();",
            "line_number": 722,
            "rule": "S35",
            "reason": "Url link | bd659725f2"
        }
    ]
}

@github-actions
Copy link
Copy Markdown

  • 敏感词检查失败, 检测到1个文件存在敏感词
详情
{
    "src/views/termwidget.cpp": [
        {
            "line": "    QString strUrl = \"https://cn.bing.com/search?q=\" + selectedText();",
            "line_number": 701,
            "rule": "S35",
            "reason": "Url link | fd576f862d"
        },
        {
            "line": "    QString strUrl = \"https://www.baidu.com/s?wd=\" + selectedText();",
            "line_number": 708,
            "rule": "S35",
            "reason": "Url link | 6f8d292d20"
        },
        {
            "line": "    QString strUrl = \"https://github.com/search?q=\" + selectedText();",
            "line_number": 715,
            "rule": "S35",
            "reason": "Url link | e1ba2d7c70"
        },
        {
            "line": "    QString strUrl = \"https://stackoverflow.com/search?q=\" + selectedText();",
            "line_number": 722,
            "rule": "S35",
            "reason": "Url link | bd659725f2"
        }
    ]
}

@wyu71
Copy link
Copy Markdown
Contributor

wyu71 commented Apr 2, 2026

Thanks for the contribution! The smart scroll feature is a reasonable improvement. However, there's a logic issue in the current implementation that prevents it from working correctly. Please revise and resubmit.

Core Issue

In termwidget.cpp onQTermWidgetReceivedData, the setTrackOutput logic is flawed:

// Current code (broken)
if (getIsAllowScroll()) {
    setTrackOutput(Settings::instance()->OutputtingScroll()); // 1. Unconditionally sets true
    if (isAtEndOfOutput()) {
        setTrackOutput(true);   // 2. Redundant
    } else {
        // 3. Missing setTrackOutput(false) — the true from step 1 already took effect
    }
}

Problems:

  1. The first line setTrackOutput(OutputtingScroll()) already sets trackOutput to true
  2. When user is not at the bottom, the else branch doesn't call setTrackOutput(false), so auto-scroll is never actually prevented
  3. When user is at the bottom, setTrackOutput(true) is called twice redundantly

Suggested Fix

if (getIsAllowScroll()) {
    setTrackOutput(isAtEndOfOutput());
    setIsAllowScroll(true);
}

This one-liner setTrackOutput(isAtEndOfOutput()) does the job: auto-scroll when at the bottom, hold position when scrolled up.

Minor Suggestions

  • The 6 qCDebug logs for a simple boolean check are excessive — consider trimming
  • setIsAllowScroll(true) is called in both branches, can be moved outside the if-else
  • The comment style in qtermwidget.h should follow the project's existing full comment block format (with author/date)

@dzw1995 dzw1995 force-pushed the develop/snipe branch 3 times, most recently from 8d56700 to bce585c Compare April 3, 2026 10:10
dzw1995 added 2 commits April 9, 2026 14:07
Implement smart scrolling behavior that only auto-scrolls when user
is already at the bottom of the terminal. This allows users to scroll
up and view history without being forced back to the bottom when
new output arrives.

Changes:
- Add isAtEndOfOutput() method to QTermWidget
- Modify onQTermWidgetReceivedData() to check user position before scrolling
- Improves experience with high-frequency output apps like kimi-cli
- Enhanced debug logging for scroll behavior

Fixes: Users can now scroll up to view history while output is ongoing
…t())

Implement smart scrolling behavior that only auto-scrolls when user
is already at the bottom of the terminal. This allows users to scroll
up and view history without being forced back to the bottom when
new output arrives.

Changes:
- Replace broken logic that didn't call setTrackOutput(false) when scrolled up
- Use setTrackOutput(isAtEndOfOutput()) to properly auto-scroll when at bottom
- Removed 6 excessive qCDebug logs
- Updated comment style in qtermwidget.h to match project format (dzw1995 2026-04-03)

Fixes: Users can now scroll up to view history while output is ongoing
@wyu71
Copy link
Copy Markdown
Contributor

wyu71 commented Apr 9, 2026

Review of fix commit (bce585c)

Thanks for addressing the previous feedback. The one-liner setTrackOutput(isAtEndOfOutput()) is much cleaner and the core smart scroll logic is now correct.

Remaining issue: OutputtingScroll() check was removed

The original code guarded against the user disabling scroll-on-output in settings:

if (!Settings::instance()->OutputtingScroll()) {
    setIsAllowScroll(true);
    return;
}

This was removed in the fix commit, which means smart scrolling now takes effect regardless of the user's OutputtingScroll preference. We should keep this check.

Suggested final version

inline void TermWidget::onQTermWidgetReceivedData(QString value)
{
    qCDebug(views) << "Enter TermWidget::onQTermWidgetReceivedData";
    Q_UNUSED(value)

    if (!Settings::instance()->OutputtingScroll()) {
        setIsAllowScroll(true);
        return;
    }

    // Smart scroll: auto-scroll only when at bottom, hold position when scrolled up
    if (getIsAllowScroll()) {
        setTrackOutput(isAtEndOfOutput());
        setIsAllowScroll(true);
    }
}

Minor: comment date typo

In qtermwidget.cpp, the comment above isAtEndOfOutput() says 2025-03-26, should be 2026-03-26.

@lzwind lzwind merged commit a05bbb1 into linuxdeepin:master Apr 10, 2026
14 of 15 checks passed
@deepin-ci-robot
Copy link
Copy Markdown

[APPROVALNOTIFIER] This PR is NOT APPROVED

This pull-request has been approved by: dzw1995, lzwind

The full list of commands accepted by this bot can be found here.

Details Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants