Trigger columnar selection behavior on middle mouse down (#12005)
fixes https://github.com/zed-industries/zed/issues/11990 Release Notes: - Changed middle mouse down to trigger a columnar selection, creating a rectangle of multi cursors over a dragged region. ([#11990](https://github.com/zed-industries/zed/issues/11990))
This commit is contained in:
parent
1f611a9c90
commit
410c46a551
2 changed files with 66 additions and 26 deletions
|
@ -302,6 +302,7 @@ pub enum SelectPhase {
|
||||||
},
|
},
|
||||||
BeginColumnar {
|
BeginColumnar {
|
||||||
position: DisplayPoint,
|
position: DisplayPoint,
|
||||||
|
reset: bool,
|
||||||
goal_column: u32,
|
goal_column: u32,
|
||||||
},
|
},
|
||||||
Extend {
|
Extend {
|
||||||
|
@ -2277,7 +2278,8 @@ impl Editor {
|
||||||
SelectPhase::BeginColumnar {
|
SelectPhase::BeginColumnar {
|
||||||
position,
|
position,
|
||||||
goal_column,
|
goal_column,
|
||||||
} => self.begin_columnar_selection(position, goal_column, cx),
|
reset,
|
||||||
|
} => self.begin_columnar_selection(position, goal_column, reset, cx),
|
||||||
SelectPhase::Extend {
|
SelectPhase::Extend {
|
||||||
position,
|
position,
|
||||||
click_count,
|
click_count,
|
||||||
|
@ -2397,6 +2399,7 @@ impl Editor {
|
||||||
&mut self,
|
&mut self,
|
||||||
position: DisplayPoint,
|
position: DisplayPoint,
|
||||||
goal_column: u32,
|
goal_column: u32,
|
||||||
|
reset: bool,
|
||||||
cx: &mut ViewContext<Self>,
|
cx: &mut ViewContext<Self>,
|
||||||
) {
|
) {
|
||||||
if !self.focus_handle.is_focused(cx) {
|
if !self.focus_handle.is_focused(cx) {
|
||||||
|
@ -2404,16 +2407,33 @@ impl Editor {
|
||||||
}
|
}
|
||||||
|
|
||||||
let display_map = self.display_map.update(cx, |map, cx| map.snapshot(cx));
|
let display_map = self.display_map.update(cx, |map, cx| map.snapshot(cx));
|
||||||
|
|
||||||
|
if reset {
|
||||||
|
let pointer_position = display_map
|
||||||
|
.buffer_snapshot
|
||||||
|
.anchor_before(position.to_point(&display_map));
|
||||||
|
|
||||||
|
self.change_selections(Some(Autoscroll::newest()), cx, |s| {
|
||||||
|
s.clear_disjoint();
|
||||||
|
s.set_pending_anchor_range(
|
||||||
|
pointer_position..pointer_position,
|
||||||
|
SelectMode::Character,
|
||||||
|
);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
let tail = self.selections.newest::<Point>(cx).tail();
|
let tail = self.selections.newest::<Point>(cx).tail();
|
||||||
self.columnar_selection_tail = Some(display_map.buffer_snapshot.anchor_before(tail));
|
self.columnar_selection_tail = Some(display_map.buffer_snapshot.anchor_before(tail));
|
||||||
|
|
||||||
self.select_columns(
|
if !reset {
|
||||||
tail.to_display_point(&display_map),
|
self.select_columns(
|
||||||
position,
|
tail.to_display_point(&display_map),
|
||||||
goal_column,
|
position,
|
||||||
&display_map,
|
goal_column,
|
||||||
cx,
|
&display_map,
|
||||||
);
|
cx,
|
||||||
|
);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
fn update_selection(
|
fn update_selection(
|
||||||
|
|
|
@ -477,6 +477,7 @@ impl EditorElement {
|
||||||
editor.select(
|
editor.select(
|
||||||
SelectPhase::BeginColumnar {
|
SelectPhase::BeginColumnar {
|
||||||
position,
|
position,
|
||||||
|
reset: false,
|
||||||
goal_column: point_for_position.exact_unclipped.column(),
|
goal_column: point_for_position.exact_unclipped.column(),
|
||||||
},
|
},
|
||||||
cx,
|
cx,
|
||||||
|
@ -530,7 +531,6 @@ impl EditorElement {
|
||||||
cx.stop_propagation();
|
cx.stop_propagation();
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(target_os = "linux")]
|
|
||||||
fn mouse_middle_down(
|
fn mouse_middle_down(
|
||||||
editor: &mut Editor,
|
editor: &mut Editor,
|
||||||
event: &MouseDownEvent,
|
event: &MouseDownEvent,
|
||||||
|
@ -538,25 +538,22 @@ impl EditorElement {
|
||||||
text_hitbox: &Hitbox,
|
text_hitbox: &Hitbox,
|
||||||
cx: &mut ViewContext<Editor>,
|
cx: &mut ViewContext<Editor>,
|
||||||
) {
|
) {
|
||||||
if !text_hitbox.is_hovered(cx) || editor.read_only(cx) {
|
if cx.default_prevented() {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if let Some(item) = cx.read_from_primary() {
|
let point_for_position =
|
||||||
let point_for_position =
|
position_map.point_for_position(text_hitbox.bounds, event.position);
|
||||||
position_map.point_for_position(text_hitbox.bounds, event.position);
|
let position = point_for_position.previous_valid;
|
||||||
let position = point_for_position.previous_valid;
|
|
||||||
|
|
||||||
editor.select(
|
editor.select(
|
||||||
SelectPhase::Begin {
|
SelectPhase::BeginColumnar {
|
||||||
position,
|
position,
|
||||||
add: false,
|
reset: true,
|
||||||
click_count: 1,
|
goal_column: point_for_position.exact_unclipped.column(),
|
||||||
},
|
},
|
||||||
cx,
|
cx,
|
||||||
);
|
);
|
||||||
editor.insert(item.text(), cx);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fn mouse_up(
|
fn mouse_up(
|
||||||
|
@ -586,6 +583,28 @@ impl EditorElement {
|
||||||
cx.stop_propagation();
|
cx.stop_propagation();
|
||||||
} else if end_selection {
|
} else if end_selection {
|
||||||
cx.stop_propagation();
|
cx.stop_propagation();
|
||||||
|
} else if cfg!(target_os = "linux") && event.button == MouseButton::Middle {
|
||||||
|
if !text_hitbox.is_hovered(cx) || editor.read_only(cx) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
#[cfg(target_os = "linux")]
|
||||||
|
if let Some(item) = cx.read_from_clipboard() {
|
||||||
|
let point_for_position =
|
||||||
|
position_map.point_for_position(text_hitbox.bounds, event.position);
|
||||||
|
let position = point_for_position.previous_valid;
|
||||||
|
|
||||||
|
editor.select(
|
||||||
|
SelectPhase::Begin {
|
||||||
|
position,
|
||||||
|
add: false,
|
||||||
|
click_count: 1,
|
||||||
|
},
|
||||||
|
cx,
|
||||||
|
);
|
||||||
|
editor.insert(item.text(), cx);
|
||||||
|
}
|
||||||
|
cx.stop_propagation()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -3241,7 +3260,6 @@ impl EditorElement {
|
||||||
MouseButton::Right => editor.update(cx, |editor, cx| {
|
MouseButton::Right => editor.update(cx, |editor, cx| {
|
||||||
Self::mouse_right_down(editor, event, &position_map, &text_hitbox, cx);
|
Self::mouse_right_down(editor, event, &position_map, &text_hitbox, cx);
|
||||||
}),
|
}),
|
||||||
#[cfg(target_os = "linux")]
|
|
||||||
MouseButton::Middle => editor.update(cx, |editor, cx| {
|
MouseButton::Middle => editor.update(cx, |editor, cx| {
|
||||||
Self::mouse_middle_down(editor, event, &position_map, &text_hitbox, cx);
|
Self::mouse_middle_down(editor, event, &position_map, &text_hitbox, cx);
|
||||||
}),
|
}),
|
||||||
|
@ -3273,7 +3291,9 @@ impl EditorElement {
|
||||||
move |event: &MouseMoveEvent, phase, cx| {
|
move |event: &MouseMoveEvent, phase, cx| {
|
||||||
if phase == DispatchPhase::Bubble {
|
if phase == DispatchPhase::Bubble {
|
||||||
editor.update(cx, |editor, cx| {
|
editor.update(cx, |editor, cx| {
|
||||||
if event.pressed_button == Some(MouseButton::Left) {
|
if event.pressed_button == Some(MouseButton::Left)
|
||||||
|
|| event.pressed_button == Some(MouseButton::Middle)
|
||||||
|
{
|
||||||
Self::mouse_dragged(
|
Self::mouse_dragged(
|
||||||
editor,
|
editor,
|
||||||
event,
|
event,
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue