nandi/oripublic Fork 0
35061753be581c0ba47a3189520d64e7788c183d
Commits
Clone
git clone https://git.rickub.com/nandi/ori.git
git clone ssh://git@rickub.com/nandi/ori.git

Host key fingerprint (ed25519): SHA256:iycHnxEyq0Q7uyVpB7JlznP0G7JrTPXLYRcAU5CSLhc — verify it before your first connect.

forked from bots-garden/ori

Add copy-paste functionality for code blocks and completion widgets 7895c1d · on 35061753be581c0ba47a3189520d64e7788c183d · k33g · yesterday
0021-copy-paste-completions-and-code-blocks.yaml · 187 lines · 7.2 KBYAML Blame HistoryRaw
  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
# Managed by IssueSpec. Hand edits are welcome; keep the schema valid.
id: 21
title: Add copy-paste functionality for completion widgets and code blocks
state: open
author:
  name: k33g
  email: ph.charriere@gmail.com
createdAt: 2026-09-18T00:00:00.000Z
updatedAt: 2026-09-18T00:00:00.000Z
labels:
  - feature
  - enhancement
  - ui
  - usability
body: |
  Add the ability to copy-paste each generated completion widget and code portions/blocks individually.

  ## Problem Statement

  Users need to quickly copy agent responses, code snippets, and individual completion widgets without selecting text manually. This is a common UX pattern in modern AI chat interfaces.

  ## Requirements

  ### Completion Widgets
  - Each completion widget (thought, tool call result, plan, etc.) should have a copy button
  - Copy button appears on hover or always visible (design decision)
  - Clicking copies the entire widget content to clipboard
  - Visual feedback when copied (checkmark, tooltip, color change)
  - Preserve formatting when copying (plain text or markdown)

  ### Code Blocks
  - Every code block should have a dedicated copy button
  - Button positioned in top-right corner of code block (standard pattern)
  - Copy raw code without syntax highlighting markup
  - Support for inline code spans (optional - may be too small for button)
  - Language label displayed alongside copy button

  ### Multi-line Text Blocks
  - Bash command outputs
  - File content previews
  - Error messages
  - Log outputs
  - Any multi-line formatted text

  ## User Experience

  ### Visual Design
  - **Copy button icon**: clipboard icon or "Copy" text
  - **Position**: Top-right corner of widget/block (consistent placement)
  - **Visibility**: 
    - Always visible (simpler)
    - OR show on hover (cleaner UI)
  - **Feedback states**:
    - Default: clipboard icon
    - Hover: subtle highlight
    - Click: changes to checkmark icon
    - After 2s: reverts to clipboard icon
  - **Tooltip**: "Copy" (before), "Copied!" (after)

  ### Interaction Flow
  ```
  User hovers over code block
  → Copy button appears/highlights
  → User clicks copy button
  → Content copied to clipboard
  → Button shows checkmark + "Copied!" tooltip
  → After 2 seconds, button reverts to default
  ```

  ## Implementation Considerations

  ### Frontend (React)
  - Use Clipboard API (`navigator.clipboard.writeText()`)
  - Fallback for older browsers (`document.execCommand('copy')`)
  - Component: `<CopyButton content={text} />`
  - State management for "copied" feedback
  - Debounce multiple rapid clicks

  ### Code Block Integration
  - Monaco editor code blocks: extract raw text
  - Markdown code blocks: access pre-rendered content
  - Syntax highlighted blocks: strip HTML/CSS, keep plain text

  ### Content Processing
  - **Code blocks**: Copy raw code, preserve indentation
  - **Thought widgets**: Copy plain text or markdown?
  - **Tool calls**: Copy JSON formatted or pretty-printed?
  - **Structured output**: Preserve structure (JSON, YAML, etc.)
  - **Tables**: Copy as markdown table or TSV/CSV?

  ### Security & Privacy
  - Only copy visible content (no hidden data)
  - Sanitize content before copying (no script injection)
  - Respect clipboard permissions (prompt if needed)
  - No automatic clipboard access (user-initiated only)

  ## Widget Types to Support

  | Widget Type | Copy Format | Priority |
  |------------|-------------|----------|
  | Code blocks | Raw code | High |
  | Thought bubbles | Plain text | High |
  | Tool call output | Formatted text | High |
  | File previews | Full content | Medium |
  | Error messages | Plain text | Medium |
  | Bash commands | Command only | Medium |
  | Bash output | Output text | Medium |
  | Plans | Markdown | Low |
  | JSON responses | Formatted JSON | Low |
  | Tables | Markdown table | Low |

  ## Example UI Mock

  ```
  ┌─────────────────────────────────────────────┐
  │ Thought: Analyzing the codebase...   [📋]   │
  │                                             │
  │ I'll search for the authentication logic... │
  └─────────────────────────────────────────────┘

  ┌─────────────────────────────────────────────┐
  │ JavaScript                            [📋]   │
  ├─────────────────────────────────────────────┤
  │ function authenticate(user, pass) {         │
  │   return bcrypt.compare(pass, user.hash);   │
  │ }                                           │
  └─────────────────────────────────────────────┘

  ┌─────────────────────────────────────────────┐
  │ Bash Output                           [✓]   │
  ├─────────────────────────────────────────────┤
  │ Tests passed: 42                            │
  │ Coverage: 87%                               │
  └─────────────────────────────────────────────┘
  ```

  ## Accessibility

  - Button has proper ARIA label: `aria-label="Copy code"`
  - Keyboard accessible: Tab to button, Enter/Space to activate
  - Screen reader announces "Copied to clipboard"
  - Focus visible indicator on keyboard navigation
  - Sufficient color contrast for button (WCAG AA)

  ## Testing Considerations

  - Test clipboard API support detection
  - Test fallback mechanism
  - Test with different content types (code, JSON, markdown)
  - Test with large content (>1MB)
  - Test rapid successive clicks
  - Test keyboard navigation
  - Cross-browser testing (Chrome, Firefox, Safari, Edge)
  - Mobile touch interaction testing

  ## Related Features

  - Could add "Copy all" button for entire conversation
  - Export conversation as markdown with all code blocks
  - Share snippet functionality (copy + generate shareable link)
  - Syntax highlighting preservation option

  ## Open Questions

  - Should copy button be always visible or show on hover?
  - Should we support "copy as markdown" vs "copy as plain text" toggle?
  - Should inline code (`inline`) have copy buttons or only blocks?
  - Maximum content size for clipboard operations?
  - Should we track copy events for analytics/UX improvements?
  - Mobile long-press behavior (native context menu vs custom)?

  ## Similar Implementations

  - GitHub code blocks (hover, top-right corner)
  - ChatGPT code blocks (always visible, next to language label)
  - VS Code (inline copy button on hover)
  - Stack Overflow (copy button on code blocks)
  - Claude.ai web interface (copy button on responses)

  ## Priority

  High - Essential usability feature for developer workflows

  ## Related Issues

  - Could integrate with Monaco editor's native copy functionality
  - Related to file tree operations (copy file path, copy file content)