fix: clippy issues
This commit is contained in:
@@ -16,7 +16,7 @@ chrono.workspace = true
|
|||||||
|
|
||||||
paste = "1"
|
paste = "1"
|
||||||
regex = "1"
|
regex = "1"
|
||||||
unicode-segmentation = "1.11.0"
|
unicode-segmentation = "1.12.0"
|
||||||
uuid = "1.10"
|
uuid = "1.10"
|
||||||
once_cell = "1.19.0"
|
once_cell = "1.19.0"
|
||||||
image = "0.25.1"
|
image = "0.25.1"
|
||||||
|
|||||||
@@ -1,18 +1,22 @@
|
|||||||
use crate::{
|
|
||||||
button::{Button, ButtonVariants as _},
|
|
||||||
h_flex, IconName, Sizable as _,
|
|
||||||
};
|
|
||||||
use gpui::{
|
use gpui::{
|
||||||
prelude::FluentBuilder, AnyElement, App, ClipboardItem, Element, ElementId, GlobalElementId,
|
prelude::FluentBuilder, AnyElement, App, ClipboardItem, Element, ElementId, GlobalElementId,
|
||||||
IntoElement, LayoutId, ParentElement, SharedString, Styled, Window,
|
IntoElement, LayoutId, ParentElement, SharedString, Styled, Window,
|
||||||
};
|
};
|
||||||
use std::{cell::RefCell, rc::Rc, time::Duration};
|
use std::{cell::RefCell, rc::Rc, time::Duration};
|
||||||
|
|
||||||
|
use crate::{
|
||||||
|
button::{Button, ButtonVariants as _},
|
||||||
|
h_flex, IconName, Sizable as _,
|
||||||
|
};
|
||||||
|
|
||||||
|
type ContentBuilder = Option<Box<dyn Fn(&mut Window, &mut App) -> AnyElement>>;
|
||||||
|
type CopiedCallback = Option<Rc<dyn Fn(SharedString, &mut Window, &mut App)>>;
|
||||||
|
|
||||||
pub struct Clipboard {
|
pub struct Clipboard {
|
||||||
id: ElementId,
|
id: ElementId,
|
||||||
value: SharedString,
|
value: SharedString,
|
||||||
content_builder: Option<Box<dyn Fn(&mut Window, &mut App) -> AnyElement>>,
|
content_builder: ContentBuilder,
|
||||||
copied_callback: Option<Rc<dyn Fn(SharedString, &mut Window, &mut App)>>,
|
copied_callback: CopiedCallback,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Clipboard {
|
impl Clipboard {
|
||||||
|
|||||||
@@ -19,11 +19,13 @@ pub trait ContextMenuExt: ParentElement + Sized {
|
|||||||
impl<E> ContextMenuExt for Stateful<E> where E: ParentElement {}
|
impl<E> ContextMenuExt for Stateful<E> where E: ParentElement {}
|
||||||
impl<E> ContextMenuExt for FocusableWrapper<E> where E: ParentElement {}
|
impl<E> ContextMenuExt for FocusableWrapper<E> where E: ParentElement {}
|
||||||
|
|
||||||
|
type Menu =
|
||||||
|
Option<Box<dyn Fn(PopupMenu, &mut Window, &mut Context<PopupMenu>) -> PopupMenu + 'static>>;
|
||||||
|
|
||||||
/// A context menu that can be shown on right-click.
|
/// A context menu that can be shown on right-click.
|
||||||
pub struct ContextMenu {
|
pub struct ContextMenu {
|
||||||
id: ElementId,
|
id: ElementId,
|
||||||
menu:
|
menu: Menu,
|
||||||
Option<Box<dyn Fn(PopupMenu, &mut Window, &mut Context<PopupMenu>) -> PopupMenu + 'static>>,
|
|
||||||
anchor: Corner,
|
anchor: Corner,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,9 +1,3 @@
|
|||||||
use crate::{
|
|
||||||
h_flex,
|
|
||||||
list::{self, List, ListDelegate, ListItem},
|
|
||||||
theme::{scale::ColorScaleStep, ActiveTheme},
|
|
||||||
v_flex, Icon, IconName, Sizable, Size, StyleSized, StyledExt,
|
|
||||||
};
|
|
||||||
use gpui::{
|
use gpui::{
|
||||||
actions, anchored, canvas, deferred, div, prelude::FluentBuilder, px, rems, AnyElement, App,
|
actions, anchored, canvas, deferred, div, prelude::FluentBuilder, px, rems, AnyElement, App,
|
||||||
AppContext, Bounds, ClickEvent, Context, DismissEvent, ElementId, Entity, EventEmitter,
|
AppContext, Bounds, ClickEvent, Context, DismissEvent, ElementId, Entity, EventEmitter,
|
||||||
@@ -11,6 +5,13 @@ use gpui::{
|
|||||||
Pixels, Render, SharedString, StatefulInteractiveElement, Styled, Task, WeakEntity, Window,
|
Pixels, Render, SharedString, StatefulInteractiveElement, Styled, Task, WeakEntity, Window,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
use crate::{
|
||||||
|
h_flex,
|
||||||
|
list::{self, List, ListDelegate, ListItem},
|
||||||
|
theme::{scale::ColorScaleStep, ActiveTheme},
|
||||||
|
v_flex, Icon, IconName, Sizable, Size, StyleSized, StyledExt,
|
||||||
|
};
|
||||||
|
|
||||||
actions!(dropdown, [Up, Down, Enter, Escape]);
|
actions!(dropdown, [Up, Down, Enter, Escape]);
|
||||||
|
|
||||||
const CONTEXT: &str = "Dropdown";
|
const CONTEXT: &str = "Dropdown";
|
||||||
@@ -524,11 +525,6 @@ where
|
|||||||
cx.notify();
|
cx.notify();
|
||||||
}
|
}
|
||||||
|
|
||||||
fn clean(&mut self, _: &ClickEvent, window: &mut Window, cx: &mut Context<Self>) {
|
|
||||||
self.set_selected_index(None, window, cx);
|
|
||||||
cx.emit(DropdownEvent::Confirm(None));
|
|
||||||
}
|
|
||||||
|
|
||||||
fn display_title(&self, window: &Window, cx: &App) -> impl IntoElement {
|
fn display_title(&self, window: &Window, cx: &App) -> impl IntoElement {
|
||||||
let title = if let Some(selected_index) = &self.selected_index(window, cx) {
|
let title = if let Some(selected_index) = &self.selected_index(window, cx) {
|
||||||
let title = self
|
let title = self
|
||||||
|
|||||||
@@ -271,7 +271,7 @@ impl TextElement {
|
|||||||
|
|
||||||
// print_points_as_svg_path(&line_corners, &points);
|
// print_points_as_svg_path(&line_corners, &points);
|
||||||
|
|
||||||
let first_p = *points.get(0).unwrap();
|
let first_p = *points.first().unwrap();
|
||||||
let mut builder = gpui::PathBuilder::fill();
|
let mut builder = gpui::PathBuilder::fill();
|
||||||
builder.move_to(bounds.origin + first_p);
|
builder.move_to(bounds.origin + first_p);
|
||||||
for p in points.iter().skip(1) {
|
for p in points.iter().skip(1) {
|
||||||
@@ -503,6 +503,16 @@ impl Element for TextElement {
|
|||||||
let origin = bounds.origin;
|
let origin = bounds.origin;
|
||||||
|
|
||||||
let mut offset_y = px(0.);
|
let mut offset_y = px(0.);
|
||||||
|
|
||||||
|
if self.input.read(cx).masked {
|
||||||
|
// Move down offset for vertical centering the *****
|
||||||
|
if cfg!(target_os = "macos") {
|
||||||
|
offset_y = px(3.);
|
||||||
|
} else {
|
||||||
|
offset_y = px(2.5);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
for line in prepaint.lines.iter() {
|
for line in prepaint.lines.iter() {
|
||||||
let p = point(origin.x, origin.y + offset_y);
|
let p = point(origin.x, origin.y + offset_y);
|
||||||
_ = line.paint(p, line_height, window, cx);
|
_ = line.paint(p, line_height, window, cx);
|
||||||
|
|||||||
@@ -1,7 +1,13 @@
|
|||||||
//! A text input field that allows the user to enter text.
|
use gpui::{
|
||||||
//!
|
actions, div, point, prelude::FluentBuilder as _, px, AnyElement, App, AppContext, Bounds,
|
||||||
//! Based on the `Input` example from the `gpui` crate.
|
ClipboardItem, Context, Entity, EntityInputHandler, EventEmitter, FocusHandle, Focusable, Half,
|
||||||
//! https://github.com/zed-industries/zed/blob/main/crates/gpui/examples/input.rs
|
InteractiveElement as _, IntoElement, KeyBinding, KeyDownEvent, MouseButton, MouseDownEvent,
|
||||||
|
MouseMoveEvent, MouseUpEvent, ParentElement as _, Pixels, Point, Rems, Render, ScrollHandle,
|
||||||
|
ScrollWheelEvent, SharedString, Styled as _, UTF16Selection, Window, WrappedLine,
|
||||||
|
};
|
||||||
|
use smallvec::SmallVec;
|
||||||
|
use std::{cell::Cell, ops::Range, rc::Rc};
|
||||||
|
use unicode_segmentation::*;
|
||||||
|
|
||||||
use super::{blink_cursor::BlinkCursor, change::Change, element::TextElement};
|
use super::{blink_cursor::BlinkCursor, change::Change, element::TextElement};
|
||||||
use crate::{
|
use crate::{
|
||||||
@@ -11,16 +17,6 @@ use crate::{
|
|||||||
theme::{scale::ColorScaleStep, ActiveTheme},
|
theme::{scale::ColorScaleStep, ActiveTheme},
|
||||||
Sizable, Size, StyleSized, StyledExt,
|
Sizable, Size, StyleSized, StyledExt,
|
||||||
};
|
};
|
||||||
use gpui::{
|
|
||||||
actions, div, point, prelude::FluentBuilder as _, px, AnyElement, App, AppContext, Bounds,
|
|
||||||
ClickEvent, ClipboardItem, Context, Entity, EntityInputHandler, EventEmitter, FocusHandle,
|
|
||||||
Focusable, Half, InteractiveElement as _, IntoElement, KeyBinding, KeyDownEvent, MouseButton,
|
|
||||||
MouseDownEvent, MouseMoveEvent, MouseUpEvent, ParentElement as _, Pixels, Point, Rems, Render,
|
|
||||||
ScrollHandle, ScrollWheelEvent, SharedString, Styled as _, UTF16Selection, Window, WrappedLine,
|
|
||||||
};
|
|
||||||
use smallvec::SmallVec;
|
|
||||||
use std::{cell::Cell, ops::Range, rc::Rc};
|
|
||||||
use unicode_segmentation::*;
|
|
||||||
|
|
||||||
actions!(
|
actions!(
|
||||||
input,
|
input,
|
||||||
@@ -29,6 +25,8 @@ actions!(
|
|||||||
Delete,
|
Delete,
|
||||||
DeleteToBeginningOfLine,
|
DeleteToBeginningOfLine,
|
||||||
DeleteToEndOfLine,
|
DeleteToEndOfLine,
|
||||||
|
DeleteToPreviousWordStart,
|
||||||
|
DeleteToNextWordEnd,
|
||||||
Enter,
|
Enter,
|
||||||
Up,
|
Up,
|
||||||
Down,
|
Down,
|
||||||
@@ -45,6 +43,8 @@ actions!(
|
|||||||
SelectToEndOfLine,
|
SelectToEndOfLine,
|
||||||
SelectToStart,
|
SelectToStart,
|
||||||
SelectToEnd,
|
SelectToEnd,
|
||||||
|
SelectToPreviousWordStart,
|
||||||
|
SelectToNextWordEnd,
|
||||||
ShowCharacterPalette,
|
ShowCharacterPalette,
|
||||||
Copy,
|
Copy,
|
||||||
Cut,
|
Cut,
|
||||||
@@ -55,6 +55,8 @@ actions!(
|
|||||||
MoveToEndOfLine,
|
MoveToEndOfLine,
|
||||||
MoveToStart,
|
MoveToStart,
|
||||||
MoveToEnd,
|
MoveToEnd,
|
||||||
|
MoveToPreviousWord,
|
||||||
|
MoveToNextWord,
|
||||||
TextChanged,
|
TextChanged,
|
||||||
]
|
]
|
||||||
);
|
);
|
||||||
@@ -77,6 +79,14 @@ pub fn init(cx: &mut App) {
|
|||||||
KeyBinding::new("cmd-backspace", DeleteToBeginningOfLine, Some(CONTEXT)),
|
KeyBinding::new("cmd-backspace", DeleteToBeginningOfLine, Some(CONTEXT)),
|
||||||
#[cfg(target_os = "macos")]
|
#[cfg(target_os = "macos")]
|
||||||
KeyBinding::new("cmd-delete", DeleteToEndOfLine, Some(CONTEXT)),
|
KeyBinding::new("cmd-delete", DeleteToEndOfLine, Some(CONTEXT)),
|
||||||
|
#[cfg(target_os = "macos")]
|
||||||
|
KeyBinding::new("alt-backspace", DeleteToPreviousWordStart, Some(CONTEXT)),
|
||||||
|
#[cfg(not(target_os = "macos"))]
|
||||||
|
KeyBinding::new("ctrl-backspace", DeleteToPreviousWordStart, Some(CONTEXT)),
|
||||||
|
#[cfg(target_os = "macos")]
|
||||||
|
KeyBinding::new("alt-delete", DeleteToNextWordEnd, Some(CONTEXT)),
|
||||||
|
#[cfg(not(target_os = "macos"))]
|
||||||
|
KeyBinding::new("ctrl-delete", DeleteToNextWordEnd, Some(CONTEXT)),
|
||||||
KeyBinding::new("enter", Enter, Some(CONTEXT)),
|
KeyBinding::new("enter", Enter, Some(CONTEXT)),
|
||||||
KeyBinding::new("up", Up, Some(CONTEXT)),
|
KeyBinding::new("up", Up, Some(CONTEXT)),
|
||||||
KeyBinding::new("down", Down, Some(CONTEXT)),
|
KeyBinding::new("down", Down, Some(CONTEXT)),
|
||||||
@@ -99,6 +109,14 @@ pub fn init(cx: &mut App) {
|
|||||||
#[cfg(target_os = "macos")]
|
#[cfg(target_os = "macos")]
|
||||||
KeyBinding::new("shift-cmd-right", SelectToEndOfLine, Some(CONTEXT)),
|
KeyBinding::new("shift-cmd-right", SelectToEndOfLine, Some(CONTEXT)),
|
||||||
#[cfg(target_os = "macos")]
|
#[cfg(target_os = "macos")]
|
||||||
|
KeyBinding::new("alt-shift-left", SelectToPreviousWordStart, Some(CONTEXT)),
|
||||||
|
#[cfg(not(target_os = "macos"))]
|
||||||
|
KeyBinding::new("ctrl-shift-left", SelectToPreviousWordStart, Some(CONTEXT)),
|
||||||
|
#[cfg(target_os = "macos")]
|
||||||
|
KeyBinding::new("alt-shift-right", SelectToNextWordEnd, Some(CONTEXT)),
|
||||||
|
#[cfg(not(target_os = "macos"))]
|
||||||
|
KeyBinding::new("ctrl-shift-right", SelectToNextWordEnd, Some(CONTEXT)),
|
||||||
|
#[cfg(target_os = "macos")]
|
||||||
KeyBinding::new("ctrl-cmd-space", ShowCharacterPalette, Some(CONTEXT)),
|
KeyBinding::new("ctrl-cmd-space", ShowCharacterPalette, Some(CONTEXT)),
|
||||||
#[cfg(target_os = "macos")]
|
#[cfg(target_os = "macos")]
|
||||||
KeyBinding::new("cmd-a", SelectAll, Some(CONTEXT)),
|
KeyBinding::new("cmd-a", SelectAll, Some(CONTEXT)),
|
||||||
@@ -133,6 +151,14 @@ pub fn init(cx: &mut App) {
|
|||||||
#[cfg(target_os = "macos")]
|
#[cfg(target_os = "macos")]
|
||||||
KeyBinding::new("cmd-down", MoveToEnd, Some(CONTEXT)),
|
KeyBinding::new("cmd-down", MoveToEnd, Some(CONTEXT)),
|
||||||
#[cfg(target_os = "macos")]
|
#[cfg(target_os = "macos")]
|
||||||
|
KeyBinding::new("alt-left", MoveToPreviousWord, Some(CONTEXT)),
|
||||||
|
#[cfg(target_os = "macos")]
|
||||||
|
KeyBinding::new("alt-right", MoveToNextWord, Some(CONTEXT)),
|
||||||
|
#[cfg(not(target_os = "macos"))]
|
||||||
|
KeyBinding::new("ctrl-left", MoveToPreviousWord, Some(CONTEXT)),
|
||||||
|
#[cfg(not(target_os = "macos"))]
|
||||||
|
KeyBinding::new("ctrl-right", MoveToNextWord, Some(CONTEXT)),
|
||||||
|
#[cfg(target_os = "macos")]
|
||||||
KeyBinding::new("cmd-shift-up", SelectToStart, Some(CONTEXT)),
|
KeyBinding::new("cmd-shift-up", SelectToStart, Some(CONTEXT)),
|
||||||
#[cfg(target_os = "macos")]
|
#[cfg(target_os = "macos")]
|
||||||
KeyBinding::new("cmd-shift-down", SelectToEnd, Some(CONTEXT)),
|
KeyBinding::new("cmd-shift-down", SelectToEnd, Some(CONTEXT)),
|
||||||
@@ -438,13 +464,13 @@ impl TextInput {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Set the disabled state of the input field.
|
/// Set the disabled state of the input field.
|
||||||
pub fn set_disabled(&mut self, disabled: bool, window: &mut Window, cx: &mut Context<Self>) {
|
pub fn set_disabled(&mut self, disabled: bool, _window: &mut Window, cx: &mut Context<Self>) {
|
||||||
self.disabled = disabled;
|
self.disabled = disabled;
|
||||||
cx.notify();
|
cx.notify();
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Set the masked state of the input field.
|
/// Set the masked state of the input field.
|
||||||
pub fn set_masked(&mut self, masked: bool, window: &mut Window, cx: &mut Context<Self>) {
|
pub fn set_masked(&mut self, masked: bool, _window: &mut Window, cx: &mut Context<Self>) {
|
||||||
self.masked = masked;
|
self.masked = masked;
|
||||||
cx.notify();
|
cx.notify();
|
||||||
}
|
}
|
||||||
@@ -474,7 +500,7 @@ impl TextInput {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Set the Input size
|
/// Set the Input size
|
||||||
pub fn set_size(&mut self, size: Size, window: &mut Window, cx: &mut Context<Self>) {
|
pub fn set_size(&mut self, size: Size, _window: &mut Window, cx: &mut Context<Self>) {
|
||||||
self.size = size;
|
self.size = size;
|
||||||
cx.notify();
|
cx.notify();
|
||||||
}
|
}
|
||||||
@@ -550,7 +576,7 @@ impl TextInput {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Set true to show indicator at the input right.
|
/// Set true to show indicator at the input right.
|
||||||
pub fn set_loading(&mut self, loading: bool, window: &mut Window, cx: &mut Context<Self>) {
|
pub fn set_loading(&mut self, loading: bool, _window: &mut Window, cx: &mut Context<Self>) {
|
||||||
self.loading = loading;
|
self.loading = loading;
|
||||||
cx.notify();
|
cx.notify();
|
||||||
}
|
}
|
||||||
@@ -565,7 +591,7 @@ impl TextInput {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/// Focus the input field.
|
/// Focus the input field.
|
||||||
pub fn focus(&self, window: &mut Window, cx: &mut Context<Self>) {
|
pub fn focus(&self, window: &mut Window, _cx: &mut Context<Self>) {
|
||||||
self.focus_handle.focus(window);
|
self.focus_handle.focus(window);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -653,6 +679,25 @@ impl TextInput {
|
|||||||
self.move_to(end, window, cx);
|
self.move_to(end, window, cx);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn move_to_previous_word(
|
||||||
|
&mut self,
|
||||||
|
_: &MoveToPreviousWord,
|
||||||
|
window: &mut Window,
|
||||||
|
cx: &mut Context<Self>,
|
||||||
|
) {
|
||||||
|
let offset = self.previous_start_of_word();
|
||||||
|
self.move_to(offset, window, cx);
|
||||||
|
}
|
||||||
|
fn move_to_next_word(
|
||||||
|
&mut self,
|
||||||
|
_: &MoveToNextWord,
|
||||||
|
window: &mut Window,
|
||||||
|
cx: &mut Context<Self>,
|
||||||
|
) {
|
||||||
|
let offset = self.next_end_of_word();
|
||||||
|
self.move_to(offset, window, cx);
|
||||||
|
}
|
||||||
|
|
||||||
fn select_to_start(&mut self, _: &SelectToStart, window: &mut Window, cx: &mut Context<Self>) {
|
fn select_to_start(&mut self, _: &SelectToStart, window: &mut Window, cx: &mut Context<Self>) {
|
||||||
self.select_to(0, window, cx);
|
self.select_to(0, window, cx);
|
||||||
}
|
}
|
||||||
@@ -682,6 +727,47 @@ impl TextInput {
|
|||||||
self.select_to(self.next_boundary(offset), window, cx);
|
self.select_to(self.next_boundary(offset), window, cx);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn select_to_previous_word(
|
||||||
|
&mut self,
|
||||||
|
_: &SelectToPreviousWordStart,
|
||||||
|
window: &mut Window,
|
||||||
|
cx: &mut Context<Self>,
|
||||||
|
) {
|
||||||
|
let offset = self.previous_start_of_word();
|
||||||
|
self.select_to(offset, window, cx);
|
||||||
|
}
|
||||||
|
|
||||||
|
fn select_to_next_word(
|
||||||
|
&mut self,
|
||||||
|
_: &SelectToNextWordEnd,
|
||||||
|
window: &mut Window,
|
||||||
|
cx: &mut Context<Self>,
|
||||||
|
) {
|
||||||
|
let offset = self.next_end_of_word();
|
||||||
|
self.select_to(offset, window, cx);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Return the start offset of the previous word.
|
||||||
|
fn previous_start_of_word(&mut self) -> usize {
|
||||||
|
let offset = self.selected_range.start;
|
||||||
|
let prev_str = &self.text[..offset].to_string();
|
||||||
|
UnicodeSegmentation::split_word_bound_indices(prev_str as &str)
|
||||||
|
.filter(|(_, s)| !s.trim_start().is_empty())
|
||||||
|
.next_back()
|
||||||
|
.map(|(i, _)| i)
|
||||||
|
.unwrap_or(0)
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Return the next end offset of the next word.
|
||||||
|
fn next_end_of_word(&mut self) -> usize {
|
||||||
|
let offset = self.cursor_offset();
|
||||||
|
let next_str = &self.text[offset..].to_string();
|
||||||
|
UnicodeSegmentation::split_word_bound_indices(next_str as &str)
|
||||||
|
.find(|(_, s)| !s.trim_start().is_empty())
|
||||||
|
.map(|(i, s)| offset + i + s.len())
|
||||||
|
.unwrap_or(self.text.len())
|
||||||
|
}
|
||||||
|
|
||||||
/// Get start of line
|
/// Get start of line
|
||||||
fn start_of_line(&mut self, window: &mut Window, cx: &mut Context<Self>) -> usize {
|
fn start_of_line(&mut self, window: &mut Window, cx: &mut Context<Self>) -> usize {
|
||||||
if self.is_single_line() {
|
if self.is_single_line() {
|
||||||
@@ -689,13 +775,12 @@ impl TextInput {
|
|||||||
}
|
}
|
||||||
|
|
||||||
let offset = self.previous_boundary(self.cursor_offset());
|
let offset = self.previous_boundary(self.cursor_offset());
|
||||||
let line = self
|
|
||||||
.text_for_range(self.range_to_utf16(&(0..offset + 1)), &mut None, window, cx)
|
self.text_for_range(self.range_to_utf16(&(0..offset + 1)), &mut None, window, cx)
|
||||||
.unwrap_or_default()
|
.unwrap_or_default()
|
||||||
.rfind('\n')
|
.rfind('\n')
|
||||||
.map(|i| i + 1)
|
.map(|i| i + 1)
|
||||||
.unwrap_or(0);
|
.unwrap_or(0)
|
||||||
line
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Get end of line
|
/// Get end of line
|
||||||
@@ -779,6 +864,38 @@ impl TextInput {
|
|||||||
self.pause_blink_cursor(cx);
|
self.pause_blink_cursor(cx);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fn delete_previous_word(
|
||||||
|
&mut self,
|
||||||
|
_: &DeleteToPreviousWordStart,
|
||||||
|
window: &mut Window,
|
||||||
|
cx: &mut Context<Self>,
|
||||||
|
) {
|
||||||
|
let offset = self.previous_start_of_word();
|
||||||
|
self.replace_text_in_range(
|
||||||
|
Some(self.range_to_utf16(&(offset..self.cursor_offset()))),
|
||||||
|
"",
|
||||||
|
window,
|
||||||
|
cx,
|
||||||
|
);
|
||||||
|
self.pause_blink_cursor(cx);
|
||||||
|
}
|
||||||
|
|
||||||
|
fn delete_next_word(
|
||||||
|
&mut self,
|
||||||
|
_: &DeleteToNextWordEnd,
|
||||||
|
window: &mut Window,
|
||||||
|
cx: &mut Context<Self>,
|
||||||
|
) {
|
||||||
|
let offset = self.next_end_of_word();
|
||||||
|
self.replace_text_in_range(
|
||||||
|
Some(self.range_to_utf16(&(self.cursor_offset()..offset))),
|
||||||
|
"",
|
||||||
|
window,
|
||||||
|
cx,
|
||||||
|
);
|
||||||
|
self.pause_blink_cursor(cx);
|
||||||
|
}
|
||||||
|
|
||||||
fn enter(&mut self, _: &Enter, window: &mut Window, cx: &mut Context<Self>) {
|
fn enter(&mut self, _: &Enter, window: &mut Window, cx: &mut Context<Self>) {
|
||||||
if self.is_multi_line() {
|
if self.is_multi_line() {
|
||||||
let is_eof = self.selected_range.end == self.text.len();
|
let is_eof = self.selected_range.end == self.text.len();
|
||||||
@@ -795,10 +912,6 @@ impl TextInput {
|
|||||||
cx.emit(InputEvent::PressEnter);
|
cx.emit(InputEvent::PressEnter);
|
||||||
}
|
}
|
||||||
|
|
||||||
fn clean(&mut self, _: &ClickEvent, window: &mut Window, cx: &mut Context<Self>) {
|
|
||||||
self.replace_text("", window, cx);
|
|
||||||
}
|
|
||||||
|
|
||||||
fn on_mouse_down(
|
fn on_mouse_down(
|
||||||
&mut self,
|
&mut self,
|
||||||
event: &MouseDownEvent,
|
event: &MouseDownEvent,
|
||||||
@@ -1122,7 +1235,7 @@ impl TextInput {
|
|||||||
cx.notify()
|
cx.notify()
|
||||||
}
|
}
|
||||||
|
|
||||||
fn unselect(&mut self, window: &mut Window, cx: &mut Context<Self>) {
|
fn unselect(&mut self, _window: &mut Window, cx: &mut Context<Self>) {
|
||||||
self.selected_range = self.cursor_offset()..self.cursor_offset();
|
self.selected_range = self.cursor_offset()..self.cursor_offset();
|
||||||
cx.notify()
|
cx.notify()
|
||||||
}
|
}
|
||||||
@@ -1209,7 +1322,7 @@ impl TextInput {
|
|||||||
fn on_key_down_for_blink_cursor(
|
fn on_key_down_for_blink_cursor(
|
||||||
&mut self,
|
&mut self,
|
||||||
_: &KeyDownEvent,
|
_: &KeyDownEvent,
|
||||||
window: &mut Window,
|
_window: &mut Window,
|
||||||
cx: &mut Context<Self>,
|
cx: &mut Context<Self>,
|
||||||
) {
|
) {
|
||||||
self.pause_blink_cursor(cx)
|
self.pause_blink_cursor(cx)
|
||||||
@@ -1272,7 +1385,7 @@ impl EntityInputHandler for TextInput {
|
|||||||
range_utf16: Range<usize>,
|
range_utf16: Range<usize>,
|
||||||
adjusted_range: &mut Option<Range<usize>>,
|
adjusted_range: &mut Option<Range<usize>>,
|
||||||
_window: &mut Window,
|
_window: &mut Window,
|
||||||
cx: &mut Context<Self>,
|
_cx: &mut Context<Self>,
|
||||||
) -> Option<String> {
|
) -> Option<String> {
|
||||||
let range = self.range_from_utf16(&range_utf16);
|
let range = self.range_from_utf16(&range_utf16);
|
||||||
adjusted_range.replace(self.range_to_utf16(&range));
|
adjusted_range.replace(self.range_to_utf16(&range));
|
||||||
@@ -1283,7 +1396,7 @@ impl EntityInputHandler for TextInput {
|
|||||||
&mut self,
|
&mut self,
|
||||||
_ignore_disabled_input: bool,
|
_ignore_disabled_input: bool,
|
||||||
_window: &mut Window,
|
_window: &mut Window,
|
||||||
cx: &mut Context<Self>,
|
_cx: &mut Context<Self>,
|
||||||
) -> Option<UTF16Selection> {
|
) -> Option<UTF16Selection> {
|
||||||
Some(UTF16Selection {
|
Some(UTF16Selection {
|
||||||
range: self.range_to_utf16(&self.selected_range),
|
range: self.range_to_utf16(&self.selected_range),
|
||||||
@@ -1294,14 +1407,14 @@ impl EntityInputHandler for TextInput {
|
|||||||
fn marked_text_range(
|
fn marked_text_range(
|
||||||
&self,
|
&self,
|
||||||
_window: &mut Window,
|
_window: &mut Window,
|
||||||
cx: &mut Context<Self>,
|
_cx: &mut Context<Self>,
|
||||||
) -> Option<Range<usize>> {
|
) -> Option<Range<usize>> {
|
||||||
self.marked_range
|
self.marked_range
|
||||||
.as_ref()
|
.as_ref()
|
||||||
.map(|range| self.range_to_utf16(range))
|
.map(|range| self.range_to_utf16(range))
|
||||||
}
|
}
|
||||||
|
|
||||||
fn unmark_text(&mut self, _window: &mut Window, cx: &mut Context<Self>) {
|
fn unmark_text(&mut self, _window: &mut Window, _cx: &mut Context<Self>) {
|
||||||
self.marked_range = None;
|
self.marked_range = None;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1437,6 +1550,8 @@ impl Render for TextInput {
|
|||||||
.on_action(cx.listener(Self::delete))
|
.on_action(cx.listener(Self::delete))
|
||||||
.on_action(cx.listener(Self::delete_to_beginning_of_line))
|
.on_action(cx.listener(Self::delete_to_beginning_of_line))
|
||||||
.on_action(cx.listener(Self::delete_to_end_of_line))
|
.on_action(cx.listener(Self::delete_to_end_of_line))
|
||||||
|
.on_action(cx.listener(Self::delete_previous_word))
|
||||||
|
.on_action(cx.listener(Self::delete_next_word))
|
||||||
.on_action(cx.listener(Self::enter))
|
.on_action(cx.listener(Self::enter))
|
||||||
})
|
})
|
||||||
.on_action(cx.listener(Self::left))
|
.on_action(cx.listener(Self::left))
|
||||||
@@ -1452,10 +1567,14 @@ impl Render for TextInput {
|
|||||||
.on_action(cx.listener(Self::select_all))
|
.on_action(cx.listener(Self::select_all))
|
||||||
.on_action(cx.listener(Self::select_to_start_of_line))
|
.on_action(cx.listener(Self::select_to_start_of_line))
|
||||||
.on_action(cx.listener(Self::select_to_end_of_line))
|
.on_action(cx.listener(Self::select_to_end_of_line))
|
||||||
|
.on_action(cx.listener(Self::select_to_previous_word))
|
||||||
|
.on_action(cx.listener(Self::select_to_next_word))
|
||||||
.on_action(cx.listener(Self::home))
|
.on_action(cx.listener(Self::home))
|
||||||
.on_action(cx.listener(Self::end))
|
.on_action(cx.listener(Self::end))
|
||||||
.on_action(cx.listener(Self::move_to_start))
|
.on_action(cx.listener(Self::move_to_start))
|
||||||
.on_action(cx.listener(Self::move_to_end))
|
.on_action(cx.listener(Self::move_to_end))
|
||||||
|
.on_action(cx.listener(Self::move_to_previous_word))
|
||||||
|
.on_action(cx.listener(Self::move_to_next_word))
|
||||||
.on_action(cx.listener(Self::select_to_start))
|
.on_action(cx.listener(Self::select_to_start))
|
||||||
.on_action(cx.listener(Self::select_to_end))
|
.on_action(cx.listener(Self::select_to_end))
|
||||||
.on_action(cx.listener(Self::show_character_palette))
|
.on_action(cx.listener(Self::show_character_palette))
|
||||||
|
|||||||
@@ -20,6 +20,8 @@ pub fn init(cx: &mut App) {
|
|||||||
cx.bind_keys([KeyBinding::new("escape", Escape, Some(CONTEXT))])
|
cx.bind_keys([KeyBinding::new("escape", Escape, Some(CONTEXT))])
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type OnClose = Rc<dyn Fn(&ClickEvent, &mut Window, &mut App) + 'static>;
|
||||||
|
|
||||||
#[derive(IntoElement)]
|
#[derive(IntoElement)]
|
||||||
pub struct Modal {
|
pub struct Modal {
|
||||||
base: Div,
|
base: Div,
|
||||||
@@ -29,7 +31,7 @@ pub struct Modal {
|
|||||||
width: Pixels,
|
width: Pixels,
|
||||||
max_width: Option<Pixels>,
|
max_width: Option<Pixels>,
|
||||||
margin_top: Option<Pixels>,
|
margin_top: Option<Pixels>,
|
||||||
on_close: Rc<dyn Fn(&ClickEvent, &mut Window, &mut App) + 'static>,
|
on_close: OnClose,
|
||||||
show_close: bool,
|
show_close: bool,
|
||||||
keyboard: bool,
|
keyboard: bool,
|
||||||
/// This will be change when open the modal, the focus handle is create when open the modal.
|
/// This will be change when open the modal, the focus handle is create when open the modal.
|
||||||
|
|||||||
@@ -16,10 +16,12 @@ pub fn init(cx: &mut App) {
|
|||||||
cx.bind_keys([KeyBinding::new("escape", Escape, Some(CONTEXT))])
|
cx.bind_keys([KeyBinding::new("escape", Escape, Some(CONTEXT))])
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type PopoverChild<T> = Rc<dyn Fn(&mut Window, &mut Context<T>) -> AnyElement>;
|
||||||
|
|
||||||
pub struct PopoverContent {
|
pub struct PopoverContent {
|
||||||
focus_handle: FocusHandle,
|
focus_handle: FocusHandle,
|
||||||
content: Rc<dyn Fn(&mut Window, &mut Context<Self>) -> AnyElement>,
|
|
||||||
max_width: Option<Pixels>,
|
max_width: Option<Pixels>,
|
||||||
|
child: PopoverChild<Self>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl PopoverContent {
|
impl PopoverContent {
|
||||||
@@ -31,7 +33,7 @@ impl PopoverContent {
|
|||||||
|
|
||||||
Self {
|
Self {
|
||||||
focus_handle,
|
focus_handle,
|
||||||
content: Rc::new(content),
|
child: Rc::new(content),
|
||||||
max_width: None,
|
max_width: None,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -58,15 +60,18 @@ impl Render for PopoverContent {
|
|||||||
.on_action(cx.listener(|_, _: &Escape, _, cx| cx.emit(DismissEvent)))
|
.on_action(cx.listener(|_, _: &Escape, _, cx| cx.emit(DismissEvent)))
|
||||||
.p_2()
|
.p_2()
|
||||||
.when_some(self.max_width, |this, v| this.max_w(v))
|
.when_some(self.max_width, |this, v| this.max_w(v))
|
||||||
.child(self.content.clone()(window, cx))
|
.child(self.child.clone()(window, cx))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type Trigger = Option<Box<dyn FnOnce(bool, &Window, &App) -> AnyElement + 'static>>;
|
||||||
|
type Content<M> = Option<Rc<dyn Fn(&mut Window, &mut App) -> Entity<M> + 'static>>;
|
||||||
|
|
||||||
pub struct Popover<M: ManagedView> {
|
pub struct Popover<M: ManagedView> {
|
||||||
id: ElementId,
|
id: ElementId,
|
||||||
anchor: Corner,
|
anchor: Corner,
|
||||||
trigger: Option<Box<dyn FnOnce(bool, &Window, &App) -> AnyElement + 'static>>,
|
trigger: Trigger,
|
||||||
content: Option<Rc<dyn Fn(&mut Window, &mut App) -> Entity<M> + 'static>>,
|
content: Content<M>,
|
||||||
/// Style for trigger element.
|
/// Style for trigger element.
|
||||||
/// This is used for hotfix the trigger element style to support w_full.
|
/// This is used for hotfix the trigger element style to support w_full.
|
||||||
trigger_style: Option<StyleRefinement>,
|
trigger_style: Option<StyleRefinement>,
|
||||||
|
|||||||
@@ -67,10 +67,13 @@ enum PopupMenuItem {
|
|||||||
icon: Option<Icon>,
|
icon: Option<Icon>,
|
||||||
label: SharedString,
|
label: SharedString,
|
||||||
action: Option<Box<dyn Action>>,
|
action: Option<Box<dyn Action>>,
|
||||||
|
#[allow(clippy::type_complexity)]
|
||||||
handler: Rc<dyn Fn(&mut Window, &mut App)>,
|
handler: Rc<dyn Fn(&mut Window, &mut App)>,
|
||||||
},
|
},
|
||||||
ElementItem {
|
ElementItem {
|
||||||
|
#[allow(clippy::type_complexity)]
|
||||||
render: Box<dyn Fn(&mut Window, &mut App) -> AnyElement + 'static>,
|
render: Box<dyn Fn(&mut Window, &mut App) -> AnyElement + 'static>,
|
||||||
|
#[allow(clippy::type_complexity)]
|
||||||
handler: Rc<dyn Fn(&mut Window, &mut App)>,
|
handler: Rc<dyn Fn(&mut Window, &mut App)>,
|
||||||
},
|
},
|
||||||
Submenu {
|
Submenu {
|
||||||
@@ -249,6 +252,7 @@ impl PopupMenu {
|
|||||||
self
|
self
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[allow(clippy::type_complexity)]
|
||||||
fn wrap_handler(&self, action: Box<dyn Action>) -> Rc<dyn Fn(&mut Window, &mut App)> {
|
fn wrap_handler(&self, action: Box<dyn Action>) -> Rc<dyn Fn(&mut Window, &mut App)> {
|
||||||
let action_focus_handle = self.action_focus_handle.clone();
|
let action_focus_handle = self.action_focus_handle.clone();
|
||||||
|
|
||||||
|
|||||||
@@ -1,5 +1,3 @@
|
|||||||
use super::resize_handle;
|
|
||||||
use crate::{h_flex, v_flex, AxisExt};
|
|
||||||
use gpui::{
|
use gpui::{
|
||||||
canvas, div, prelude::FluentBuilder, px, relative, Along, AnyElement, AnyView, App, AppContext,
|
canvas, div, prelude::FluentBuilder, px, relative, Along, AnyElement, AnyView, App, AppContext,
|
||||||
Axis, Bounds, Context, Element, Entity, EntityId, EventEmitter, IntoElement, IsZero,
|
Axis, Bounds, Context, Element, Entity, EntityId, EventEmitter, IntoElement, IsZero,
|
||||||
@@ -8,6 +6,9 @@ use gpui::{
|
|||||||
};
|
};
|
||||||
use std::rc::Rc;
|
use std::rc::Rc;
|
||||||
|
|
||||||
|
use super::resize_handle;
|
||||||
|
use crate::{h_flex, v_flex, AxisExt};
|
||||||
|
|
||||||
pub(crate) const PANEL_MIN_SIZE: Pixels = px(100.);
|
pub(crate) const PANEL_MIN_SIZE: Pixels = px(100.);
|
||||||
|
|
||||||
pub enum ResizablePanelEvent {
|
pub enum ResizablePanelEvent {
|
||||||
@@ -90,11 +91,6 @@ impl ResizablePanelGroup {
|
|||||||
self
|
self
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Returns the sizes of the resizable panels.
|
|
||||||
pub(crate) fn sizes(&self) -> Vec<Pixels> {
|
|
||||||
self.sizes.clone()
|
|
||||||
}
|
|
||||||
|
|
||||||
/// Calculates the sum of all panel sizes within the group.
|
/// Calculates the sum of all panel sizes within the group.
|
||||||
pub fn total_size(&self) -> Pixels {
|
pub fn total_size(&self) -> Pixels {
|
||||||
self.sizes.iter().fold(px(0.0), |acc, &size| acc + size)
|
self.sizes.iter().fold(px(0.0), |acc, &size| acc + size)
|
||||||
|
|||||||
Reference in New Issue
Block a user