fix(web): improve code block copy button for mobile and add position setting#2092
fix(web): improve code block copy button for mobile and add position setting#2092roni-estein wants to merge 6 commits intopingdotgg:mainfrom
Conversation
…setting Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
|
Important Review skippedAuto reviews are disabled on this repository. Please check the settings in the CodeRabbit UI or the ⚙️ Run configurationConfiguration used: Repository UI Review profile: CHILL Plan: Pro Run ID: You can disable this status message by setting the Use the checkbox below for a quick retry:
✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
ApprovabilityVerdict: Approved Low-risk UI enhancement adding a configurable copy button position setting for mobile users and a clipboard fallback for non-HTTPS contexts. Changes are self-contained to the code block component with tests included, no sensitive areas touched. You can customize Macroscope's approvability policy. Learn more. |
Incorporate upstream's sidebarProjectGroupingMode and refactored test fixtures alongside copyButtonPosition field. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Dismissing prior approval to re-evaluate 07d8ca7
The document.execCommand("copy") fallback was calling onSuccess()
unconditionally. Now gates the success indicator on the boolean return
value so users aren't shown "Copied" when the browser blocked the
operation.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
There was a problem hiding this comment.
Cursor Bugbot has reviewed your changes and found 1 potential issue.
❌ Bugbot Autofix is OFF. To automatically fix reported issues with cloud agents, enable autofix in the Cursor dashboard.
Reviewed by Cursor Bugbot for commit b94c26c. Configure here.
Move removeChild into a finally block so the hidden textarea is always cleaned up, even if select() or execCommand() throws. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

What Changed
Three focused improvements to the code block copy button, primarily for mobile and remote (HTTP) usage:
@media (hover: none)rule shows the button without requiring hoverdocument.execCommand("copy")fallback whennavigator.clipboardis unavailable (HTTP over Tailscale, etc.)Why
When using T3 Code remotely on a phone (via
t3 serveover Tailscale), the code block copy button has two problems:Position: Generated code blocks and explanations are often long. On mobile, the copy button sits at the top-right corner, requiring the user to scroll back up past the entire block to reach it. A "bottom" option places it at the end where you naturally finish reading.
Visibility: The button relies on
:hoverto appear (opacity: 0→opacity: 1). Touch devices don't have hover, so the button never becomes visible or interactive — it renders as an inert SVG icon withpointer-events: none.Clipboard API:
navigator.clipboard.writeText()requires a secure context (HTTPS). Remote T3 Code sessions served over plain HTTP (common with Tailscale) silently fail because the API isn't available. The fallback uses the legacyexecCommand("copy")path.Why not existing PRs
Files changed
packages/contracts/src/settings.tscopyButtonPositiontoClientSettingsSchemaapps/web/src/components/ChatMarkdown.tsxapps/web/src/components/settings/SettingsPanels.tsxapps/web/src/index.css@media (hover: none)rule for touch devicesapps/web/src/components/ChatMarkdown.logic.test.tsapps/desktop/src/clientPersistence.test.tsapps/web/src/localApi.test.tsUI Changes
Settings → General — new "Copy button position" dropdown:
Default is "Top" (preserves existing behavior). "Bottom" places the button at the bottom-right corner of the code block.
Touch devices — copy button always visible:
On devices without hover (phones, tablets), the button renders at 70% opacity and goes to full opacity on tap, instead of being permanently hidden.
Checklist
bun run typecheck,bun run test— 865/865 passing)Note
Medium Risk
Touches user interaction and clipboard behavior (including a legacy
execCommandpath) and adds a new persisted client setting, which could affect cross-platform copying and settings migration if edge cases exist.Overview
Improves the chat Markdown code-block copy button for mobile and non-HTTPS deployments.
Adds a new client setting
copyButtonPosition(top/bottom) to the shared settings contracts and exposes it in the General settings panel (including restore-defaults dirty-state tracking), then applies it via inline positioning inMarkdownCodeBlock.Updates copy behavior to use
navigator.clipboard.writeTextwhen available and fall back to a hiddentextarea+document.execCommand("copy")when Clipboard API isn’t present, and adjusts CSS to keep the copy button visible on touch devices (@media (hover: none)). Tests/fixtures are updated and a small logic test file is added to cover the positioning/clipboard guards.Reviewed by Cursor Bugbot for commit 8c911b5. Bugbot is set up for automated code reviews on this repo. Configure here.
Note
Add copy button position setting and mobile visibility fix for code blocks
copyButtonPositionsetting (top/bottom) toClientSettingsSchemawith a default oftop, and exposes a UI control in the General settings panel to configure it.ChatMarkdown.tsx, overriding the CSS default.execCommand('copy')textarea fallback in the copy handler for environments wherenavigator.clipboardis unavailable (common on mobile).(hover: none)media query inindex.cssinstead of appearing only on hover.Macroscope summarized 8c911b5.