input: Update Input selection behavior to like OS input. (#247)
Revert old implementation - https://github.com/huacnlee/gpui-component/pull/26 - https://github.com/zed-industries/zed/pull/14340 ## Before https://github.com/user-attachments/assets/52ce2e3a-3e1d-4ba2-af42-76b1df987404 ## After https://github.com/user-attachments/assets/9aa8cfe1-5928-4d20-b534-806140c7ee59 ## The Input in the Browser https://github.com/user-attachments/assets/c913248e-b1dc-46d6-a517-e1231e606171
This commit is contained in:
parent
0e16d742bb
commit
f77993082d
1 changed files with 61 additions and 8 deletions
|
|
@ -410,12 +410,6 @@ impl TextInput {
|
||||||
self.is_selecting = false;
|
self.is_selecting = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
fn on_mouse_move(&mut self, event: &MouseMoveEvent, cx: &mut ViewContext<Self>) {
|
|
||||||
if self.is_selecting {
|
|
||||||
self.select_to(self.index_for_mouse_position(event.position), cx);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
fn show_character_palette(&mut self, _: &ShowCharacterPalette, cx: &mut ViewContext<Self>) {
|
fn show_character_palette(&mut self, _: &ShowCharacterPalette, cx: &mut ViewContext<Self>) {
|
||||||
cx.show_character_palette();
|
cx.show_character_palette();
|
||||||
}
|
}
|
||||||
|
|
@ -657,6 +651,48 @@ impl TextInput {
|
||||||
self.pause_blink_cursor(cx)
|
self.pause_blink_cursor(cx)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn on_drag_move(&mut self, event: &MouseMoveEvent, cx: &mut ViewContext<Self>) {
|
||||||
|
if self.text.is_empty() {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if self.last_layout.is_none() {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if !self.focus_handle.is_focused(cx) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
if !self.is_selecting {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
let offset = self.offset_of_position(event.position);
|
||||||
|
self.select_to(offset, cx);
|
||||||
|
}
|
||||||
|
|
||||||
|
fn offset_of_position(&self, position: Point<Pixels>) -> usize {
|
||||||
|
let bounds = self.last_bounds.unwrap_or_default();
|
||||||
|
let position = position - bounds.origin;
|
||||||
|
self.last_layout
|
||||||
|
.as_ref()
|
||||||
|
.map(|line| match line.index_for_x(position.x) {
|
||||||
|
Some(ix) => ix,
|
||||||
|
None => {
|
||||||
|
let last_index = line.len();
|
||||||
|
// If the mouse is on the right side of the last character, move to the end
|
||||||
|
// Otherwise, move to the start of the line
|
||||||
|
if position.x > line.x_for_index(last_index) {
|
||||||
|
last_index
|
||||||
|
} else {
|
||||||
|
0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.unwrap_or(0)
|
||||||
|
}
|
||||||
|
|
||||||
fn is_valid_input(&self, new_text: &str) -> bool {
|
fn is_valid_input(&self, new_text: &str) -> bool {
|
||||||
if new_text.is_empty() {
|
if new_text.is_empty() {
|
||||||
return true;
|
return true;
|
||||||
|
|
@ -807,6 +843,21 @@ impl FocusableView for TextInput {
|
||||||
struct TextElement {
|
struct TextElement {
|
||||||
input: View<TextInput>,
|
input: View<TextInput>,
|
||||||
}
|
}
|
||||||
|
impl TextElement {
|
||||||
|
fn paint_mouse_listeners(&mut self, cx: &mut WindowContext) {
|
||||||
|
cx.on_mouse_event({
|
||||||
|
let input = self.input.clone();
|
||||||
|
|
||||||
|
move |event: &MouseMoveEvent, _, cx| {
|
||||||
|
if event.pressed_button == Some(MouseButton::Left) {
|
||||||
|
input.update(cx, |input, cx| {
|
||||||
|
input.on_drag_move(event, cx);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
struct PrepaintState {
|
struct PrepaintState {
|
||||||
scroll_offset: Point<Pixels>,
|
scroll_offset: Point<Pixels>,
|
||||||
line: Option<ShapedLine>,
|
line: Option<ShapedLine>,
|
||||||
|
|
@ -1015,6 +1066,8 @@ impl Element for TextElement {
|
||||||
input.last_layout = Some(line);
|
input.last_layout = Some(line);
|
||||||
input.last_bounds = Some(bounds);
|
input.last_bounds = Some(bounds);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
self.paint_mouse_listeners(cx);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
@ -1057,8 +1110,8 @@ impl Render for TextInput {
|
||||||
.on_key_down(cx.listener(Self::on_key_down_for_blink_cursor))
|
.on_key_down(cx.listener(Self::on_key_down_for_blink_cursor))
|
||||||
.on_mouse_down(MouseButton::Left, cx.listener(Self::on_mouse_down))
|
.on_mouse_down(MouseButton::Left, cx.listener(Self::on_mouse_down))
|
||||||
.on_mouse_up(MouseButton::Left, cx.listener(Self::on_mouse_up))
|
.on_mouse_up(MouseButton::Left, cx.listener(Self::on_mouse_up))
|
||||||
.on_mouse_up_out(MouseButton::Left, cx.listener(Self::on_mouse_up))
|
// .on_mouse_up_out(MouseButton::Left, cx.listener(Self::on_mouse_up))
|
||||||
.on_mouse_move(cx.listener(Self::on_mouse_move))
|
// .on_mouse_move(cx.listener(Self::on_mouse_move))
|
||||||
.size_full()
|
.size_full()
|
||||||
.line_height(rems(1.25))
|
.line_height(rems(1.25))
|
||||||
.text_size(rems(0.875))
|
.text_size(rems(0.875))
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue