Repository navigation
NTP omnibar: screenshot capture - #3076
Conversation
Adds "Add Screenshot" to the Duck.ai omnibar attach menu and lets images and files be pasted into the prompt, for the Windows NTP. - New `omnibar_captureScreenshot` request: native captures (region overlay or window/display picker) and returns a processed image; the page attaches it through the existing image pipeline at up to 1024px. - Config: `screenshotModes` (menu rows) and `enablePastedAttachments` (paste kill switch). - Paste: clipboard text wins; otherwise bitmaps attach at screenshot size, copied images like picked ones, PDFs as file chips. - Telemetry: omnibar_image_attached / _removed (with source) and omnibar_screenshot_taken / _removed / _failed. - Shared Dropdown gains a DropdownSubmenu primitive (hover, click, Enter/ArrowRight to open; ArrowLeft/Escape to close). Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Native now answers a pending capture as cancelled when a new one replaces it, so the page no longer greys the screenshot rows while a request is pending. Only the latest request may show the capture error. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
[Beta] Generated file diffTime updated: Tue, 06 Oct 2026 07:18:49 GMT Apple
File has changed Integration
File has changed Windows
File has changed |
|
This PR requires a manual review and approval from a member of one of the following teams:
|
|
@claude review |
There was a problem hiding this comment.
Nothing blocking. The comments below are optional suggestions. There is no need to push a fix for them before merging.
Beyond the inline finding, I also checked two other candidates and ruled them out: the paperclip dropdown's file-attach row for screenshot-only users silently no-ops at the image cap the same way the pre-existing tabsEnabled dropdown path already does (not a new regression, just extended to a new entry point); and the screenshot decode path's synchronous atob loop runs before the size/pixel checks, but native is documented to always scale screenshots to at most 1024px, so there's no practical main-thread-freeze risk in the trusted native→page contract.
Extended reasoning...
The diff adds screenshot capture and clipboard paste to the NTP omnibar (new native message, image/file attachment pipeline, a generic dropdown/submenu primitive, telemetry, and integration tests) with no auth/crypto surface; the confirmed inline finding is a real but non-security UX gap (unsupported pasted image MIME types silently drop with no feedback). I independently verified the file-read code path and two other candidate issues (dropdown cap no-op for screenshot-only users, and the screenshotToFile atob loop preceding size checks) and found both to be pre-existing patterns or backed by a trusted native size contract rather than new regressions, so I'm noting them as ruled out rather than raising them.
A pasted BMP, TIFF or GIF was dropped with only a console warning, and the paste itself was swallowed. processFiles now reports format-rejected files with the existing "Failed to process image" error, for paste and picker alike. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Build Branch
Static preview entry points
QR codes (mobile preview)
Integration commandsnpm (Android / Extension): Swift Package Manager (Apple): .package(url: "https://github.com/duckduckgo/content-scope-scripts.git", branch: "pr-releases/feature/anpete/ntp-screenshot")git submodule (Windows): git -C submodules/content-scope-scripts fetch origin pr-releases/feature/anpete/ntp-screenshot
git -C submodules/content-scope-scripts checkout origin/pr-releases/feature/anpete/ntp-screenshotPin to exact commitnpm (Android / Extension): Swift Package Manager (Apple): .package(url: "https://github.com/duckduckgo/content-scope-scripts.git", revision: "64c2d6d4ff0b6f49726551158b1548117ceefdd5")git submodule (Windows): git -C submodules/content-scope-scripts fetch origin pr-releases/feature/anpete/ntp-screenshot
git -C submodules/content-scope-scripts checkout 64c2d6d4ff0b6f49726551158b1548117ceefdd5 |
There was a problem hiding this comment.
Claude Code Review
This repository is configured for manual code reviews. Comment @claude review for a one-time review, or @claude review always to subscribe this PR to a review on every future push.
Tip: disable this comment in your organization's Code Review settings.
…ending" This reverts commit 6f6b627. Windows now draws its own region selector over every monitor, so a second capture can't start while one is up: native is back to one capture at a time and answers a second request as cancelled. The screenshot rows grey out again while a request is pending, and the request-id / stale-reply handling is gone. Docs updated to match. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
|
@anpete nice work! Two points for now:
|
Pasting into the Duck.ai prompt attaches copied images and files when `enablePastedAttachments` is on. Clipboard text wins, so an Office copy pastes its text rather than the picture of the cells; otherwise a bitmap attaches at up to 1024px, copied images like picked ones, and PDFs as file chips. Image chips now record their source and send omnibar_image_attached / omnibar_image_removed. Images in unsupported formats show the existing "Failed to process image" error instead of being dropped silently. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Stacks this branch on feature/anpete/ntp-paste-attachments (#3079), which now carries paste and the image telemetry. Paste moves out of useScreenshotCapture into usePastedAttachments, and its tests into omnibar-paste.spec.js; what remains here is the native screenshot feature. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
|
@sashalavron thanks!
🤖 Posted by Claude Code |
Resolves conflicts with #3072 (file upload privacy disclaimer): the image and file hooks now come from AttachmentsProvider, and the mock transport keeps both the enablePastedAttachments and showAttachmentPrivacyDisclaimer params. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Brings in #3072 (file upload privacy disclaimer) via the paste branch; the image and file hooks now come from AttachmentsProvider. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Docs, schema descriptions and comments now state only the contract and the page's own behaviour (the reply can take as long as the user needs, images are at most 1024px, `error` replies send no page telemetry), not how native captures, scales or limits screenshots. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Drops Dropdown's closeOnArrowLeft prop; DropdownSubmenu's panel wrapper already handles the panel's key events, so it closes on ArrowLeft itself. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Dropdown's onClose now passes `selected: true` when it closes because a row was chosen, so DropdownSubmenu closes the whole menu on a choice and only the submenu otherwise. Drops choseRowRef and the cloning of the submenu's items. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
sashalavron
left a comment
There was a problem hiding this comment.
Looks good. Please test it e2e after the recent changes and address the open comments. Approving in advance - nice work!!
Covers the open "Add Screenshot" submenu, the row disabled without image support, an attached screenshot chip, and the capture error. The darwin baselines are generated by the snapshots-update workflow. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Asana Task/Github Issue: Windows side: duckduckgo/windows-browser#9333 (stacked on duckduckgo/windows-browser#9290 and duckduckgo/windows-browser#9286)
Description
Adds screenshot capture to the Duck.ai omnibar on the NTP. Native (Windows) captures the image and the page attaches it through the existing image pipeline.
omnibar_captureScreenshotrequest. Native returns an image already scaled to at most 1024px; the page keeps that size. Native allows one capture at a time; the screenshot rows grey out while a request is pending.screenshotModesinOmnibarConfig, off when absent. On Windows it sits behindaiChat.ntpScreenshot.omnibar_screenshot_taken/_removed/_failed, andsource: "screenshot"on the image events added in NTP omnibar: paste images and files, with image telemetry #3079.DropdownSubmenuprimitive (hover, click, Enter or ArrowRight opens; ArrowLeft or Escape closes).Message and config docs are in
special-pages/pages/new-tab/app/omnibar/omnibar.md.Testing Steps
?omnibar.mode=ai&omnibar.enableAiChatTools=true&omnibar.screenshotModes=dragToSelect,selectWindowOrDisplay.&omnibar.screenshotResult=errorto see "Couldn't capture screenshot", or=cancelto see that nothing happens.special-pages/pages/new-tab/app/omnibar/integration-tests/omnibar-screenshot.spec.js.Checklist
Please tick all that apply:
🤖 Generated with Claude Code