Remove at from mouse instructions in Ice syntax

This commit is contained in:
Héctor Ramón Jiménez 2025-09-20 17:33:57 +02:00
parent 364b68f030
commit 79d501f9a5
No known key found for this signature in database
GPG key ID: 7CC46565708259A7
5 changed files with 89 additions and 52 deletions

View file

@ -1,4 +1,5 @@
use iced::keyboard;
use iced::time::milliseconds;
use iced::widget::{
self, Text, button, center, center_x, checkbox, column, keyed_column,
operation, row, scrollable, text, text_input,
@ -544,8 +545,8 @@ impl SavedState {
.map_err(|_| SaveError::Write)?;
}
// This is a simple way to save at most once every couple seconds
tokio::time::sleep(std::time::Duration::from_secs(2)).await;
// This is a simple way to save at most twice every second
tokio::time::sleep(milliseconds(500)).await;
Ok(())
}

View file

@ -2,13 +2,13 @@ viewport: 500x800
mode: Immediate
preset: Empty
-----
click at "What needs to be done?"
click "What needs to be done?"
type "Create the universe"
type enter
type "Make an apple pie"
type enter
expect "2 tasks left"
click at "Create the universe"
click "Create the universe"
expect "1 task left"
click at "Make an apple pie"
click "Make an apple pie"
expect "0 tasks left"

View file

@ -54,11 +54,11 @@ impl Interaction {
}
mouse::Event::ButtonPressed(button) => Mouse::Press {
button: *button,
at: None,
target: None,
},
mouse::Event::ButtonReleased(button) => Mouse::Release {
button: *button,
at: None,
target: None,
},
_ => None?,
}),
@ -117,28 +117,40 @@ impl Interaction {
(Mouse::Move(_), Mouse::Move(to)) => {
(Self::Mouse(Mouse::Move(to)), None)
}
(Mouse::Move(to), Mouse::Press { button, at: None }) => (
(
Mouse::Move(to),
Mouse::Press {
button,
target: None,
},
) => (
Self::Mouse(Mouse::Press {
button,
at: Some(to),
target: Some(to),
}),
None,
),
(Mouse::Move(to), Mouse::Release { button, at: None }) => (
(
Mouse::Move(to),
Mouse::Release {
button,
target: None,
},
) => (
Self::Mouse(Mouse::Release {
button,
at: Some(to),
target: Some(to),
}),
None,
),
(
Mouse::Press {
button: press,
at: press_at,
target: press_at,
},
Mouse::Release {
button: release,
at: release_at,
target: release_at,
},
) if press == release
&& release_at.as_ref().is_none_or(|release_at| {
@ -148,7 +160,7 @@ impl Interaction {
(
Self::Mouse(Mouse::Click {
button: press,
at: press_at,
target: press_at,
}),
None,
)
@ -156,26 +168,26 @@ impl Interaction {
(
Mouse::Press {
button,
at: Some(press_at),
target: Some(press_at),
},
Mouse::Move(move_at),
) if press_at == move_at => (
Self::Mouse(Mouse::Press {
button,
at: Some(press_at),
target: Some(press_at),
}),
None,
),
(
Mouse::Click {
button,
at: Some(click_at),
target: Some(click_at),
},
Mouse::Move(move_at),
) if click_at == move_at => (
Self::Mouse(Mouse::Click {
button,
at: Some(click_at),
target: Some(click_at),
}),
None,
),
@ -235,23 +247,29 @@ impl Interaction {
Mouse::Move(to) => vec![mouse_move_(find_target(to)?)],
Mouse::Press {
button,
at: Some(at),
target: Some(at),
} => vec![mouse_move_(find_target(at)?), mouse_press(*button)],
Mouse::Press { button, at: None } => {
Mouse::Press {
button,
target: None,
} => {
vec![mouse_press(*button)]
}
Mouse::Release {
button,
at: Some(at),
target: Some(at),
} => {
vec![mouse_move_(find_target(at)?), mouse_release(*button)]
}
Mouse::Release { button, at: None } => {
Mouse::Release {
button,
target: None,
} => {
vec![mouse_release(*button)]
}
Mouse::Click {
button,
at: Some(at),
target: Some(at),
} => {
vec![
mouse_move_(find_target(at)?),
@ -259,7 +277,10 @@ impl Interaction {
mouse_release(*button),
]
}
Mouse::Click { button, at: None } => {
Mouse::Click {
button,
target: None,
} => {
vec![mouse_press(*button), mouse_release(*button)]
}
},
@ -294,21 +315,21 @@ pub enum Mouse {
/// The button.
button: mouse::Button,
/// The location of the press.
at: Option<Target>,
target: Option<Target>,
},
/// A button was released.
Release {
/// The button.
button: mouse::Button,
/// The location of the release.
at: Option<Target>,
target: Option<Target>,
},
/// A button was clicked.
Click {
/// The button.
button: mouse::Button,
/// The location of the click.
at: Option<Target>,
target: Option<Target>,
},
}
@ -318,14 +339,26 @@ impl fmt::Display for Mouse {
Mouse::Move(target) => {
write!(f, "move cursor to {}", target)
}
Mouse::Press { button, at } => {
write!(f, "press {}", format::button_at(*button, at.as_ref()))
Mouse::Press { button, target } => {
write!(
f,
"press {}",
format::button_at(*button, target.as_ref())
)
}
Mouse::Release { button, at } => {
write!(f, "release {}", format::button_at(*button, at.as_ref()))
Mouse::Release { button, target } => {
write!(
f,
"release {}",
format::button_at(*button, target.as_ref())
)
}
Mouse::Click { button, at } => {
write!(f, "click {}", format::button_at(*button, at.as_ref()))
Mouse::Click { button, target } => {
write!(
f,
"click {}",
format::button_at(*button, target.as_ref())
)
}
}
}
@ -412,9 +445,9 @@ mod format {
if let Some(at) = at {
if button.is_empty() {
format!("at {}", at)
at.to_string()
} else {
format!("{} at {}", button, at)
format!("{} {}", button, at)
}
} else {
button.to_owned()
@ -479,9 +512,7 @@ mod parser {
use nom::bytes::complete::tag;
use nom::bytes::{is_not, take_while_m_n};
use nom::character::complete::{char, multispace0, multispace1};
use nom::combinator::{
cut, map, map_opt, map_res, opt, success, value, verify,
};
use nom::combinator::{map, map_opt, map_res, opt, success, value, verify};
use nom::error::ParseError;
use nom::multi::fold;
use nom::number::float;
@ -526,9 +557,9 @@ mod parser {
fn mouse_click(input: &str) -> IResult<&str, Mouse> {
let (input, _) = tag("click ")(input)?;
let (input, (button, at)) = mouse_button_at(input)?;
let (input, (button, target)) = mouse_button_at(input)?;
Ok((input, Mouse::Click { button, at }))
Ok((input, Mouse::Click { button, target }))
}
fn mouse_button_at(
@ -541,11 +572,7 @@ mod parser {
}
fn target(input: &str) -> IResult<&str, Target> {
preceded(
whitespace(tag("at ")),
cut(alt((string.map(Target::Text), point.map(Target::Point)))),
)
.parse(input)
alt((string.map(Target::Text), point.map(Target::Point))).parse(input)
}
fn mouse_button(input: &str) -> IResult<&str, mouse::Button> {

View file

@ -502,7 +502,7 @@ impl<P: Program + 'static> Tester<P> {
let instruction::Interaction::Mouse(
instruction::Mouse::Click {
button: mouse::Button::Left,
at: Some(instruction::Target::Text(text)),
target: Some(instruction::Target::Text(text)),
},
) = interaction
else {

View file

@ -415,17 +415,26 @@ fn record<Message>(
};
let Interaction::Mouse(
Mouse::Move(at)
| Mouse::Press { at: Some(at), .. }
| Mouse::Release { at: Some(at), .. }
| Mouse::Click { at: Some(at), .. },
Mouse::Move(target)
| Mouse::Press {
target: Some(target),
..
}
| Mouse::Release {
target: Some(target),
..
}
| Mouse::Click {
target: Some(target),
..
},
) = &mut interaction
else {
shell.publish(on_record(interaction));
return;
};
let Target::Point(position) = *at else {
let Target::Point(position) = *target else {
shell.publish(on_record(interaction));
return;
};
@ -433,7 +442,7 @@ fn record<Message>(
if let Some((content, visible_bounds)) =
find_text(position + (bounds.position() - Point::ORIGIN), operate)
{
*at = Target::Text(content);
*target = Target::Text(content);
*last_hovered = visible_bounds;
} else {
*last_hovered = None;