mirror of
https://github.com/niri-wm/niri.git
synced 2026-06-21 02:01:55 +07:00
Make DnD edge view scroll configurable
This commit is contained in:
@@ -59,6 +59,8 @@ pub struct Config {
|
||||
#[knuffel(child, default)]
|
||||
pub animations: Animations,
|
||||
#[knuffel(child, default)]
|
||||
pub gestures: Gestures,
|
||||
#[knuffel(child, default)]
|
||||
pub environment: Environment,
|
||||
#[knuffel(children(name = "window-rule"))]
|
||||
pub window_rules: Vec<WindowRule>,
|
||||
@@ -1115,6 +1117,32 @@ pub struct SpringParams {
|
||||
pub epsilon: f64,
|
||||
}
|
||||
|
||||
#[derive(knuffel::Decode, Debug, Default, Clone, Copy, PartialEq)]
|
||||
pub struct Gestures {
|
||||
#[knuffel(child, default)]
|
||||
pub dnd_edge_view_scroll: DndEdgeViewScroll,
|
||||
}
|
||||
|
||||
#[derive(knuffel::Decode, Debug, Clone, Copy, PartialEq)]
|
||||
pub struct DndEdgeViewScroll {
|
||||
#[knuffel(child, unwrap(argument), default = Self::default().trigger_width)]
|
||||
pub trigger_width: FloatOrInt<0, 65535>,
|
||||
#[knuffel(child, unwrap(argument), default = Self::default().delay_ms)]
|
||||
pub delay_ms: u16,
|
||||
#[knuffel(child, unwrap(argument), default = Self::default().max_speed)]
|
||||
pub max_speed: FloatOrInt<0, 1_000_000>,
|
||||
}
|
||||
|
||||
impl Default for DndEdgeViewScroll {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
trigger_width: FloatOrInt(30.), // Taken from GTK 4.
|
||||
delay_ms: 50,
|
||||
max_speed: FloatOrInt(1500.),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(knuffel::Decode, Debug, Default, Clone, PartialEq, Eq)]
|
||||
pub struct Environment(#[knuffel(children)] pub Vec<EnvironmentVariable>);
|
||||
|
||||
@@ -3679,6 +3707,13 @@ mod tests {
|
||||
window-open { off; }
|
||||
}
|
||||
|
||||
gestures {
|
||||
dnd-edge-view-scroll {
|
||||
trigger-width 10
|
||||
max-speed 50
|
||||
}
|
||||
}
|
||||
|
||||
environment {
|
||||
QT_QPA_PLATFORM "wayland"
|
||||
DISPLAY null
|
||||
@@ -4252,6 +4287,17 @@ mod tests {
|
||||
},
|
||||
),
|
||||
},
|
||||
gestures: Gestures {
|
||||
dnd_edge_view_scroll: DndEdgeViewScroll {
|
||||
trigger_width: FloatOrInt(
|
||||
10.0,
|
||||
),
|
||||
delay_ms: 50,
|
||||
max_speed: FloatOrInt(
|
||||
50.0,
|
||||
),
|
||||
},
|
||||
},
|
||||
environment: Environment(
|
||||
[
|
||||
EnvironmentVariable {
|
||||
|
||||
@@ -328,6 +328,7 @@ pub struct Options {
|
||||
/// Window height that `toggle_window_height()` switches between.
|
||||
pub preset_window_heights: Vec<PresetSize>,
|
||||
pub animations: niri_config::Animations,
|
||||
pub gestures: niri_config::Gestures,
|
||||
// Debug flags.
|
||||
pub disable_resize_throttling: bool,
|
||||
pub disable_transactions: bool,
|
||||
@@ -354,6 +355,7 @@ impl Default for Options {
|
||||
],
|
||||
default_column_width: None,
|
||||
animations: Default::default(),
|
||||
gestures: Default::default(),
|
||||
disable_resize_throttling: false,
|
||||
disable_transactions: false,
|
||||
preset_window_heights: vec![
|
||||
@@ -582,6 +584,7 @@ impl Options {
|
||||
preset_column_widths,
|
||||
default_column_width,
|
||||
animations: config.animations.clone(),
|
||||
gestures: config.gestures,
|
||||
disable_resize_throttling: config.debug.disable_resize_throttling,
|
||||
disable_transactions: config.debug.disable_transactions,
|
||||
preset_window_heights,
|
||||
|
||||
@@ -2806,6 +2806,8 @@ impl<W: LayoutElement> ScrollingSpace<W> {
|
||||
return;
|
||||
};
|
||||
|
||||
let config = &self.options.gestures.dnd_edge_view_scroll;
|
||||
|
||||
let now = self.clock.now_unadjusted();
|
||||
gesture.dnd_last_event_time = Some(now);
|
||||
|
||||
@@ -2819,13 +2821,14 @@ impl<W: LayoutElement> ScrollingSpace<W> {
|
||||
|
||||
// Delay starting the gesture a bit to avoid unwanted movement when dragging across
|
||||
// monitors.
|
||||
if now.saturating_sub(nonzero_start) < Duration::from_millis(50) {
|
||||
let delay = Duration::from_millis(u64::from(config.delay_ms));
|
||||
if now.saturating_sub(nonzero_start) < delay {
|
||||
return;
|
||||
}
|
||||
|
||||
let time_delta = now.saturating_sub(last_time).as_secs_f64();
|
||||
|
||||
let delta = delta * time_delta * 50.;
|
||||
let delta = delta * time_delta * config.max_speed.0;
|
||||
|
||||
gesture.tracker.push(delta, now);
|
||||
|
||||
|
||||
+17
-7
@@ -1614,22 +1614,32 @@ impl<W: LayoutElement> Workspace<W> {
|
||||
}
|
||||
|
||||
pub fn dnd_scroll_gesture_scroll(&mut self, pos: Point<f64, Logical>) {
|
||||
// Taken from GTK 4.
|
||||
const SCROLL_EDGE_SIZE: f64 = 30.;
|
||||
let config = &self.options.gestures.dnd_edge_view_scroll;
|
||||
let trigger_width = config.trigger_width.0;
|
||||
|
||||
// This working area intentionally does not include extra struts from Options.
|
||||
let x = pos.x - self.working_area.loc.x;
|
||||
let width = self.working_area.size.w;
|
||||
let x = x.clamp(0., width);
|
||||
|
||||
let delta = if x < SCROLL_EDGE_SIZE {
|
||||
-(SCROLL_EDGE_SIZE - x)
|
||||
} else if width - x < SCROLL_EDGE_SIZE {
|
||||
SCROLL_EDGE_SIZE - (width - x)
|
||||
let x = x.clamp(0., width);
|
||||
let trigger_width = trigger_width.clamp(0., width / 2.);
|
||||
|
||||
let delta = if x < trigger_width {
|
||||
-(trigger_width - x)
|
||||
} else if width - x < trigger_width {
|
||||
trigger_width - (width - x)
|
||||
} else {
|
||||
0.
|
||||
};
|
||||
|
||||
let delta = if trigger_width < 0.01 {
|
||||
// Sanity check for trigger-width 0 or small window sizes.
|
||||
0.
|
||||
} else {
|
||||
// Normalize to [0, 1].
|
||||
delta / trigger_width
|
||||
};
|
||||
|
||||
self.scrolling.dnd_scroll_gesture_scroll(delta);
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user