How to Interact with Elements Using Ego-Lite Actions: Click, Fill, and Double-Click

Ego-lite exposes a Playwright-style page API that enables element interaction through high-level helpers like click(), fill(), and dblclick(), which delegate to specialized drivers in pointer.ts and keyboard.ts to dispatch synthetic DOM events and verify actions via click probes.

The citrolabs/ego-lite repository provides a lightweight browser automation framework that abstracts native DOM manipulation into a concise, Playwright-inspired interface. When you interact with elements using ego-lite actions, the framework translates high-level commands into precise synthetic browser events while providing built-in verification mechanisms to ensure reliability.

Understanding the Ego-Lite Action Architecture

Ego-lite surfaces element interaction methods through a façade object called page that is injected into script contexts. According to the source code in package/ego-browser/src/helpers.ts, these helpers are registered into the execution context at lines 30-31 and exported as wrapped methods around lines 560-568. This architecture allows scripts running inside the ego-lite harness to access methods like page.click() or page.fill() without directly managing the underlying browser drivers.

The action system relies on two primary driver modules located in package/ego-browser/src/driver/:

  • pointer.ts: Handles all mouse-based interactions including single and double clicks
  • keyboard.ts: Manages text input, field clearing, and content-editable operations

Both drivers receive resolved DOM elements from the locator system and dispatch native events that mimic genuine user interactions.

How to Click Elements in Ego-Lite

Locator Resolution and the Pointer Driver

When you invoke await page.locator('button').click(), the framework first resolves your selector through package/ego-browser/src/element-resolver.ts to obtain a concrete DOM node. This target is then passed to the pointer driver at package/ego-browser/src/driver/pointer.ts (lines 63-71), which executes the following workflow:

  1. Inject a click probe: The driver temporarily injects a confirmation element to verify the click lands on the intended target (finishClickProbe logic).
  2. Dispatch synthetic events: It fires mousedown, mouseup, and click MouseEvents on the target element with appropriate detail counts (lines 283-287).
  3. Verify success: The promise resolves only after the click probe confirms the action succeeded, guaranteeing the page actually processed the interaction.

Double-Click Implementation

Double-clicking is implemented as a thin wrapper around the standard click mechanism. In pointer.ts at lines 98-103, the dblclick function invokes the core click driver with clickCount: 2, which triggers two sequential click events followed by the native dblclick event. This ensures compatibility with web applications that listen for either single or double-click interactions.

How to Fill and Clear Input Fields

The Keyboard Driver

Text input operations are handled by package/ego-browser/src/driver/keyboard.ts. When you call page.fill(selector, value), the driver executes the routine defined at lines 277-284:

  1. Optional clearing: By default, clearFirst is set to true, which simulates deletion events to empty the field before entering new text.
  2. Value injection: For standard inputs, it sets the element's value property; for contentEditable elements, it updates textContent.
  3. Event dispatch: After setting the value, it fires an InputEvent to ensure any JavaScript listeners attached to the field trigger correctly.

The clear() helper is a convenience method that internally calls fill with an empty string, utilizing the same clearing logic without requiring manual backspace simulation.

Code Examples for Ego-Lite Actions

Click a Button by CSS Selector

await page.locator('button[type=submit]').click();

This resolves the selector via the element resolver, invokes the pointer driver with a click probe, and resolves when the synthetic click events complete successfully.

Double-Click at Specific Coordinates

await page.mouse.dblclick(420, 260);

Direct coordinate targeting bypasses the locator system and uses the pointer driver to dispatch two click events at the specified viewport position.

Fill and Clear an Email Field

// Fill the field with text
await page.getByLabel('Email').fill('me@example.com');

// Clear the field using the helper shortcut
await page.getByLabel('Email').clear();

The fill method uses the keyboard driver to enter text, while clear triggers the deletion routine with an empty string value.

Click by Accessibility Role

await page.getByRole('link', { name: 'Terms of Service' }).click();

Role-based queries are translated into concrete elements by element-resolver.ts before the click driver executes, supporting accessible automation patterns.

Core Source Files for Element Interaction

The following files in the citrolabs/ego-lite repository implement the action system:

Summary

  • Ego-lite provides a Playwright-compatible API through the page object, with methods like click() and fill() available in script contexts.
  • Click actions use the pointer driver (pointer.ts) to dispatch synthetic MouseEvents and verify success via temporary click probes.
  • Fill actions leverage the keyboard driver (keyboard.ts) to clear fields by default, set values (or textContent for content-editable elements), and dispatch input events.
  • Double-click is implemented as a clickCount: 2 variant within the same pointer driver architecture.
  • All helpers are registered in helpers.ts and resolved through element-resolver.ts, creating a reliable abstraction layer over raw DOM manipulation.

Frequently Asked Questions

How does ego-lite verify that a click actually succeeded?

The pointer driver in package/ego-browser/src/driver/pointer.ts injects a temporary click probe into the DOM before dispatching events. After sending the synthetic mousedown, mouseup, and click events (lines 283-287), the driver waits for the probe to confirm the click landed on the intended target before resolving the promise, ensuring the action was processed by the page rather than just fired into the void.

Can I use ego-lite to fill content-editable elements?

Yes. The keyboard driver at package/ego-browser/src/driver/keyboard.ts detects content-editable elements and uses textContent instead of the value property when filling fields. It then dispatches the appropriate input event to trigger any JavaScript listeners, making it compatible with rich text editors and other non-standard input fields.

What is the difference between page.click() and page.mouse.click()?

page.click() accepts a selector string, resolves it to a DOM element via element-resolver.ts, and includes built-in verification via the click probe mechanism. page.mouse.click() accepts raw viewport coordinates and bypasses the locator system, giving you direct control over pointer position without element resolution, but without the automatic success verification that comes with the higher-level API.

Where are the helper methods like fill and dblclick registered?

These methods are registered in package/ego-browser/src/helpers.ts at lines 30-31, where they are injected into the script execution context. The actual export wrappers that expose them on the page object are defined around lines 560-568 of the same file. This registration pattern ensures that scripts running inside the ego-lite harness have immediate access to these automation primitives.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →