use gpui::{
App, Bounds, Context, HapticFeedbackStyle, QuitMode, Window, WindowBounds, WindowOptions,
colors::Colors, div, prelude::*, px, size,
};
const STYLES: [(&str, HapticFeedbackStyle); 3] = [
("Generic", HapticFeedbackStyle::Generic),
("Alignment", HapticFeedbackStyle::Alignment),
("Level change", HapticFeedbackStyle::LevelChange),
];
struct Haptics {
supported: bool,
level: usize,
}
impl Render for Haptics {
fn render(&mut self, window: &mut Window, cx: &mut Context<Self>) -> impl IntoElement {
let colors = Colors::for_appearance(window);
let buttons = STYLES.into_iter().map(|(label, style)| {
div()
.id(label)
.px_4()
.py_3()
.rounded_md()
.bg(colors.selected)
.text_color(colors.selected_text)
.hover(|button| button.opacity(0.85))
.child(label)
.on_hover(move |hovered, _window, cx| {
if *hovered {
cx.play_haptic_feedback(style);
}
})
});
let steps = (0..=10).map(|level| {
div()
.id(("level", level))
.flex_1()
.h_6()
.rounded_sm()
.bg(if level <= self.level {
colors.selected
} else {
colors.container
})
.on_hover(cx.listener(move |this, hovered: &bool, _window, cx| {
if *hovered && this.level != level {
this.level = level;
cx.play_haptic_feedback(HapticFeedbackStyle::LevelChange);
cx.notify();
}
}))
});
let hint = |text: String| div().text_sm().text_color(colors.disabled).child(text);
div()
.size_full()
.flex()
.flex_col()
.gap_4()
.p_8()
.bg(colors.background)
.text_color(colors.text)
.child(if self.supported {
"This machine supports haptic feedback."
} else {
"This machine doesn't support haptic feedback, so the calls do nothing."
})
.child(hint(
"Move the pointer onto a button to feel its pattern.".into(),
))
.child(div().flex().gap_3().children(buttons))
.child(hint(format!(
"Move the pointer along the scale. Level {}",
self.level
)))
.child(div().flex().gap_1().children(steps))
}
}
fn main() {
gpui_platform::application()
.with_quit_mode(QuitMode::LastWindowClosed)
.run(run);
}
pub fn run(cx: &mut App) {
let bounds = Bounds::centered(None, size(px(520.), px(320.)), cx);
cx.open_window(
WindowOptions::default().window_bounds(WindowBounds::Windowed(bounds)),
|_window, cx| {
cx.new(|cx| Haptics {
supported: cx.supports_haptic_feedback(),
level: 0,
})
},
)
.unwrap();
cx.activate(true);
}