Repository navigation
feat(web): visual channel for multimodal web research - #12
Merged
Merged
Conversation
Add a generic visual tool-result channel and web_research screenshot. The viewport is rendered to PNG, OCR text is always returned, and known vision models receive the image once via a synthetic user message. Text models stay on OCR. Images are never persisted or resent on later rounds. Verified on API 35 emulator with CSS chart and canvas-only pages; gate test/lintDebug/assembleDebug green.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Problem
web_researchcould read DOM text but multimodal models could not see the page. Charts, canvas, images, maps and visual layout were invisible.take_screenshotreturned only a file path, and tool results had no image channel.What changed
ToolResult.Successgainsimages: List<ToolImage>(base64 kept in memory only).AgentLoopinserts a synthetic user image message after a tool batch, reusing the existing OpenAI / Anthropic / Gemini user-image serialization. The message is marked as untrusted visual data.web_researchgainsscreenshot:View.draw();vision=true/falseoverrides.VisionModelscovers GPT-4o/4.1/5/6, Claude 3/4/5, Gemini, Grok, Qwen-VL, LLaVA, Pixtral, GLM-V, etc. Unknown models stay OCR-only.web_searchdescription now points toweb_research open + screenshotfor rendered pages.Why
View.draw()instead of the virtual-displayImageReaderOn the API 35 emulator the reader frame contained only the WebView window background (white + scrollbar) while Chromium composited the page on another layer. Drawing the viewport directly produced the real page. A four-attempt retry handles first-draw warmup; completely blank frames return an actionable failure.
Verification
cobalt lantern 47;images=1withvision=true.<canvas>): 76 KB PNG; OCR read31415and the bar values; proves DOM-invisible content now reaches the model.vision=false: same OCR,images=0.ToolResultimage round-trip,VisionModelsdetection, synthetic user image message, and old screenshots not resent on later rounds../gradlew test lintDebug :app:assembleDebuggreen.Limits / follow-ups
View.draw()may miss video/SurfaceView layers; 2D canvas, HTML/CSS and images are covered.show_to_userfirst.take_screenshot/screen_ocr, sensitive-page policy.