zng_wgt_text_input/
selectable.rs
1use zng_ext_clipboard::COPY_CMD;
4use zng_wgt::prelude::*;
5use zng_wgt_button::Button;
6use zng_wgt_input::focus::FocusableMix;
7use zng_wgt_menu::{
8 self as menu,
9 context::{ContextMenu, context_menu_fn},
10};
11use zng_wgt_style::{Style, StyleMix, impl_style_fn, style_fn};
12use zng_wgt_text::{self as text, *};
13
14#[doc(hidden)]
15pub use zng_wgt::prelude::formatx as __formatx;
16
17#[widget($crate::selectable::SelectableText {
23 ($txt:literal) => {
24 txt = $crate::selectable::__formatx!($txt);
25 };
26 ($txt:expr) => {
27 txt = $txt;
28 };
29 ($txt:tt, $($format:tt)*) => {
30 txt = $crate::selectable::__formatx!($txt, $($format)*);
31 };
32})]
33pub struct SelectableText(FocusableMix<StyleMix<zng_wgt_text::Text>>);
34impl SelectableText {
35 fn widget_intrinsic(&mut self) {
36 self.style_intrinsic(STYLE_FN_VAR, property_id!(self::style_fn));
37 widget_set! {
38 self;
39 txt_selectable = true;
40 style_base_fn = style_fn!(|_| DefaultStyle!());
41 }
42 }
43}
44impl_style_fn!(SelectableText);
45
46#[widget($crate::selectable::DefaultStyle)]
48pub struct DefaultStyle(Style);
49impl DefaultStyle {
50 fn widget_intrinsic(&mut self) {
51 use zng_wgt_input::*;
52 use zng_wgt_layer::*;
53
54 widget_set! {
55 self;
56 replace = true;
57 cursor = CursorIcon::Text;
58
59 popup::context_capture = crate::default_popup_context_capture();
60 context_menu_fn = WidgetFn::new(default_context_menu);
61 selection_toolbar_fn = WidgetFn::new(default_selection_toolbar);
62 selection_color = colors::ACCENT_COLOR_VAR.rgba_map(|c| c.with_alpha(30.pct()));
63 }
64 }
65}
66
67pub fn default_context_menu(args: menu::context::ContextMenuArgs) -> impl UiNode {
71 let id = args.anchor_id;
72 ContextMenu!(ui_vec![Button!(COPY_CMD.scoped(id)), Button!(text::cmd::SELECT_ALL_CMD.scoped(id)),])
73}
74
75pub fn default_selection_toolbar(args: text::SelectionToolbarArgs) -> impl UiNode {
79 if args.is_touch {
80 let id = args.anchor_id;
81 ContextMenu! {
82 style_fn = menu::context::TouchStyle!();
83 children = ui_vec![Button!(COPY_CMD.scoped(id)), Button!(text::cmd::SELECT_ALL_CMD.scoped(id)),]
84 }
85 .boxed()
86 } else {
87 NilUiNode.boxed()
88 }
89}