-
Notifications
You must be signed in to change notification settings - Fork 13k
feat: add pulsating blue border automation overlay to browser agent #21173
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
gsquared94
merged 12 commits into
google-gemini:main
from
kunal-10-cloud:feat/browser-automation-overlay
Mar 10, 2026
Merged
Changes from 1 commit
Commits
Show all changes
12 commits
Select commit
Hold shift + click to select a range
014d264
feat: add pulsating blue border automation overlay to browser agent
kunal-10-cloud 469c724
Update packages/core/src/agents/browser/automationOverlay.ts
kunal-10-cloud b3a586b
refactor: use composition instead of monkey-patching in mcpToolWrappe…
kunal-10-cloud 0374f3e
Merge branch 'main' into feat/browser-automation-overlay
kunal-10-cloud 80c22ff
fix: rewrite automation overlay to use Web Animations API and correct…
kunal-10-cloud 144a97c
Merge branch 'main' into feat/browser-automation-overlay
kunal-10-cloud abee2ec
fix: implementing gemini suggestion
kunal-10-cloud a40a82f
fix(browser-agent): handle implicit navigations in automation overlay
kunal-10-cloud dc41356
Update packages/core/src/agents/browser/browserManager.ts
kunal-10-cloud 4ab7d46
fix:implementing gemini suggestion
kunal-10-cloud 1dc7af3
Merge branch 'main' into feat/browser-automation-overlay
kunal-10-cloud b25d9e8
Merge branch 'main' into feat/browser-automation-overlay
gsquared94 File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Some comments aren't visible on the classic Files Changed page.
There are no files selected for viewing
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
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,142 @@ | ||
| /** | ||
| * @license | ||
| * Copyright 2026 Google LLC | ||
| * SPDX-License-Identifier: Apache-2.0 | ||
| */ | ||
|
|
||
| /** | ||
| * @fileoverview Automation overlay utilities for visual indication during browser automation. | ||
| * | ||
| * Provides functions to inject and remove a pulsating blue border overlay | ||
| * that indicates when the browser is under AI agent control. | ||
| */ | ||
|
|
||
| import type { BrowserManager } from './browserManager.js'; | ||
| import { debugLogger } from '../../utils/debugLogger.js'; | ||
|
|
||
| const OVERLAY_ELEMENT_ID = '__gemini_automation_overlay'; | ||
| const OVERLAY_STYLE_ID = '__gemini_automation_style'; | ||
|
|
||
| /** | ||
| * JavaScript code to inject the automation overlay | ||
| */ | ||
| const OVERLAY_INJECTION_SCRIPT = ` | ||
| (() => { | ||
| // Remove existing overlay if present | ||
| const existingOverlay = document.getElementById('${OVERLAY_ELEMENT_ID}'); | ||
| if (existingOverlay) { | ||
| existingOverlay.remove(); | ||
| } | ||
|
|
||
| const existingStyle = document.getElementById('${OVERLAY_STYLE_ID}'); | ||
| if (existingStyle) { | ||
| existingStyle.remove(); | ||
| } | ||
|
|
||
| // Create style element with animation | ||
| const style = document.createElement('style'); | ||
| style.id = '${OVERLAY_STYLE_ID}'; | ||
| style.textContent = \` | ||
| @keyframes __gemini_pulse { | ||
| 0%, 100% { | ||
| border-color: rgba(66, 133, 244, 0.2); | ||
| box-shadow: inset 0 0 8px rgba(66, 133, 244, 0.1); | ||
| } | ||
| 50% { | ||
| border-color: rgba(66, 133, 244, 0.6); | ||
| box-shadow: inset 0 0 16px rgba(66, 133, 244, 0.2); | ||
| } | ||
| } | ||
| \`; | ||
| document.head.appendChild(style); | ||
|
|
||
| // Create overlay element | ||
| const overlay = document.createElement('div'); | ||
| overlay.id = '${OVERLAY_ELEMENT_ID}'; | ||
| overlay.setAttribute('aria-hidden', 'true'); | ||
| overlay.setAttribute('role', 'presentation'); | ||
| overlay.style.cssText = \` | ||
| position: fixed; | ||
| inset: 0; | ||
| z-index: 2147483647; | ||
| pointer-events: none; | ||
| border: 3px solid rgba(66, 133, 244, 0.4); | ||
| animation: __gemini_pulse 2s ease-in-out infinite; | ||
| \`; | ||
|
|
||
| document.body.appendChild(overlay); | ||
|
|
||
| return 'Automation overlay injected successfully'; | ||
| })(); | ||
| `; | ||
|
|
||
| /** | ||
| * JavaScript code to remove the automation overlay | ||
| */ | ||
| const OVERLAY_REMOVAL_SCRIPT = ` | ||
| (() => { | ||
| const overlay = document.getElementById('${OVERLAY_ELEMENT_ID}'); | ||
| if (overlay) { | ||
| overlay.remove(); | ||
| } | ||
|
|
||
| const style = document.getElementById('${OVERLAY_STYLE_ID}'); | ||
| if (style) { | ||
| style.remove(); | ||
| } | ||
|
|
||
| return 'Automation overlay removed successfully'; | ||
| })(); | ||
| `; | ||
|
|
||
| /** | ||
| * Injects the automation overlay into the current page | ||
| */ | ||
| export async function injectAutomationOverlay( | ||
| browserManager: BrowserManager, | ||
| signal?: AbortSignal, | ||
| ): Promise<void> { | ||
| try { | ||
| debugLogger.log('Injecting automation overlay...'); | ||
|
|
||
| const result = await browserManager.callTool( | ||
| 'evaluate_script', | ||
| { code: OVERLAY_INJECTION_SCRIPT }, | ||
| signal, | ||
| ); | ||
|
|
||
| if (result.isError) { | ||
| debugLogger.warn('Failed to inject automation overlay:', result); | ||
| } else { | ||
| debugLogger.log('Automation overlay injected successfully'); | ||
| } | ||
| } catch (error) { | ||
| debugLogger.warn('Error injecting automation overlay:', error); | ||
| } | ||
| } | ||
|
|
||
| /** | ||
| * Removes the automation overlay from the current page | ||
| */ | ||
| export async function removeAutomationOverlay( | ||
| browserManager: BrowserManager, | ||
| signal?: AbortSignal, | ||
| ): Promise<void> { | ||
| try { | ||
| debugLogger.log('Removing automation overlay...'); | ||
|
|
||
| const result = await browserManager.callTool( | ||
| 'evaluate_script', | ||
| { code: OVERLAY_REMOVAL_SCRIPT }, | ||
| signal, | ||
| ); | ||
|
|
||
| if (result.isError) { | ||
| debugLogger.warn('Failed to remove automation overlay:', result); | ||
| } else { | ||
| debugLogger.log('Automation overlay removed successfully'); | ||
| } | ||
| } catch (error) { | ||
| debugLogger.warn('Error removing automation overlay:', error); | ||
| } | ||
| } | ||
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
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
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
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
Oops, something went wrong.
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.
Uh oh!
There was an error while loading. Please reload this page.