pub struct MouseSimulator { /* private fields */ }Expand description
Simulates human-like mouse movement via distance-aware Bézier curve trajectories.
Each call to move_to computes a cubic Bézier path
between the current cursor position and the target, then replays it as a sequence
of Input.dispatchMouseEvent CDP commands with randomised inter-event delays
(10–50 ms per segment). Movement speed naturally slows for long distances and
accelerates for short ones — matching human motor-control patterns.
§Example
use stygian_browser::behavior::MouseSimulator;
let mut mouse = MouseSimulator::new();
mouse.move_to(page, 640.0, 400.0).await?;
mouse.click(page, 640.0, 400.0).await?;Implementations§
Source§impl MouseSimulator
impl MouseSimulator
Sourcepub fn new() -> Self
pub fn new() -> Self
Create a simulator seeded from wall-clock time, positioned at (0, 0).
§Example
use stygian_browser::behavior::MouseSimulator;
let mouse = MouseSimulator::new();
assert_eq!(mouse.position(), (0.0, 0.0));Sourcepub const fn with_seed_and_position(seed: u64, x: f64, y: f64) -> Self
pub const fn with_seed_and_position(seed: u64, x: f64, y: f64) -> Self
Create a simulator with a known initial position and deterministic seed.
Useful for unit-testing path generation without CDP.
§Example
use stygian_browser::behavior::MouseSimulator;
let mouse = MouseSimulator::with_seed_and_position(42, 100.0, 200.0);
assert_eq!(mouse.position(), (100.0, 200.0));Sourcepub const fn position(&self) -> (f64, f64)
pub const fn position(&self) -> (f64, f64)
Returns the current cursor position as (x, y).
§Example
use stygian_browser::behavior::MouseSimulator;
let mouse = MouseSimulator::new();
let (x, y) = mouse.position();
assert_eq!((x, y), (0.0, 0.0));Sourcepub fn compute_path(
&mut self,
from_x: f64,
from_y: f64,
to_x: f64,
to_y: f64,
) -> Vec<(f64, f64)>
pub fn compute_path( &mut self, from_x: f64, from_y: f64, to_x: f64, to_y: f64, ) -> Vec<(f64, f64)>
Compute Bézier waypoints for a move from (from_x, from_y) to
(to_x, to_y).
The number of waypoints scales with Euclidean distance — roughly one point every 8 pixels — with a minimum of 12 and maximum of 120 steps. Random perpendicular offsets are applied to the two interior control points to produce natural curved paths. Each waypoint receives sub-pixel jitter (±0.8 px) for micro-tremor realism.
This method is pure (no I/O) and is exposed for testing.
§Example
use stygian_browser::behavior::MouseSimulator;
let mut mouse = MouseSimulator::with_seed_and_position(1, 0.0, 0.0);
let path = mouse.compute_path(0.0, 0.0, 200.0, 0.0);
// always at least 12 steps
assert!(path.len() >= 13);
// starts near origin
assert!((path[0].0).abs() < 5.0);
// ends near target
let last = path[path.len() - 1];
assert!((last.0 - 200.0).abs() < 5.0);Sourcepub async fn move_to(&mut self, page: &Page, to_x: f64, to_y: f64) -> Result<()>
pub async fn move_to(&mut self, page: &Page, to_x: f64, to_y: f64) -> Result<()>
Move the cursor to (to_x, to_y) using a human-like Bézier trajectory.
Dispatches Input.dispatchMouseEvent(mouseMoved) for each waypoint
with randomised 10–50 ms delays. Updates position
on success.
§Errors
Returns BrowserError::CdpError if any CDP event dispatch fails.
Sourcepub async fn click(&mut self, page: &Page, x: f64, y: f64) -> Result<()>
pub async fn click(&mut self, page: &Page, x: f64, y: f64) -> Result<()>
Move to (x, y) then perform a human-like left-click.
After arriving at the target the simulator pauses (20–80 ms), sends
mousePressed, holds (50–150 ms), then sends mouseReleased.
§Errors
Returns BrowserError::CdpError if any CDP event dispatch fails.