paste_tool.rs - icy_draw - icy_draw is the successor to mystic draw. fork / mirror
(HTM) git clone https://git.drkhsh.at/icy_draw.git
(DIR) Log
(DIR) Files
(DIR) Refs
(DIR) README
(DIR) LICENSE
---
paste_tool.rs (6319B)
---
1 use super::{move_layer_imp::get_layer_offset_text, Event, MKey, Position, Tool};
2 use crate::{to_message, AnsiEditor, Message};
3 use eframe::egui::{self, Key};
4 use i18n_embed_fl::fl;
5 use icy_engine_egui::TerminalCalc;
6
7 #[derive(Default)]
8 pub struct PasteTool {
9 start_offset: Position,
10 drag_started: bool,
11 drag_offset: Position,
12 last_tool: usize,
13 closed: bool,
14 }
15
16 impl PasteTool {
17 pub(crate) fn new(selected_tool: usize) -> Self {
18 Self {
19 last_tool: selected_tool,
20 ..Default::default()
21 }
22 }
23 }
24
25 impl Tool for PasteTool {
26 fn get_icon(&self) -> &egui::Image<'static> {
27 &super::icons::MOVE_SVG
28 }
29
30 fn tool_name(&self) -> String {
31 String::new()
32 }
33
34 fn tooltip(&self) -> String {
35 String::new()
36 }
37
38 fn use_caret(&self, _editor: &AnsiEditor) -> bool {
39 false
40 }
41
42 fn is_visible(&self) -> bool {
43 false
44 }
45
46 fn is_exclusive(&self) -> bool {
47 true
48 }
49
50 fn use_selection(&self) -> bool {
51 false
52 }
53
54 fn show_ui(&mut self, ctx: &egui::Context, ui: &mut egui::Ui, editor_opt: Option<&mut AnsiEditor>) -> Option<Message> {
55 let mut result = None;
56 if let Some(editor) = editor_opt {
57 if let Some(layer) = editor.buffer_view.lock().get_edit_state().get_cur_layer() {
58 self.closed = !layer.role.is_paste();
59 }
60 } else {
61 self.closed = true;
62 }
63
64 if self.closed {
65 return Some(Message::SelectTool(self.last_tool));
66 }
67
68 ui.label(fl!(crate::LANGUAGE_LOADER, "paste_mode-description"));
69 ui.add_space(8.0);
70 egui::Grid::new("paste_mode_grid").num_columns(2).spacing([4.0, 4.0]).show(ui, |ui| {
71 ui.with_layout(egui::Layout::right_to_left(egui::Align::Center), |ui| {
72 ui.strong("S -");
73 });
74 if ui.button(fl!(crate::LANGUAGE_LOADER, "paste_mode-stamp")).clicked() || ui.input(|i| i.key_pressed(Key::S)) {
75 result = Some(Message::StampLayerDown);
76 }
77 ui.end_row();
78 ui.with_layout(egui::Layout::right_to_left(egui::Align::Center), |ui| {
79 ui.strong("R -");
80 });
81 if ui.button(fl!(crate::LANGUAGE_LOADER, "paste_mode-rotate")).clicked() || ui.input(|i| i.key_pressed(Key::R)) {
82 result = Some(Message::RotateLayer);
83 }
84 ui.end_row();
85 ui.with_layout(egui::Layout::right_to_left(egui::Align::Center), |ui| {
86 ui.strong("X -");
87 });
88 if ui.button(fl!(crate::LANGUAGE_LOADER, "paste_mode-flipx")).clicked() || ui.input(|i| i.key_pressed(Key::X)) {
89 result = Some(Message::FlipX);
90 }
91 ui.end_row();
92 ui.with_layout(egui::Layout::right_to_left(egui::Align::Center), |ui| {
93 ui.strong("Y -");
94 });
95 if ui.button(fl!(crate::LANGUAGE_LOADER, "paste_mode-flipy")).clicked() || ui.input(|i| i.key_pressed(Key::Y)) {
96 result = Some(Message::FlipY);
97 }
98 ui.end_row();
99 ui.with_layout(egui::Layout::right_to_left(egui::Align::Center), |ui| {
100 ui.strong("T -");
101 });
102 if ui.button(fl!(crate::LANGUAGE_LOADER, "paste_mode-transparent")).clicked() || ui.input(|i| i.key_pressed(Key::T)) {
103 result = Some(Message::MakeLayerTransparent);
104 }
105 ui.end_row();
106 });
107
108 if ctx.input(|i| i.key_pressed(Key::Escape)) {
109 return Some(Message::RemoveFloatingLayer);
110 }
111 result
112 }
113
114 fn handle_drag_begin(&mut self, editor: &mut AnsiEditor, _response: &egui::Response) -> Event {
115 self.drag_started = false;
116
117 if let Some(layer) = editor.buffer_view.lock().get_edit_state_mut().get_cur_layer_mut() {
118 self.start_offset = layer.get_offset();
119 self.drag_offset = self.start_offset;
120 self.drag_started = true;
121 }
122 Event::None
123 }
124
125 fn handle_drag(&mut self, _ui: &egui::Ui, response: egui::Response, editor: &mut AnsiEditor, _calc: &TerminalCalc) -> egui::Response {
126 if !self.drag_started {
127 return response;
128 }
129 if let Some(layer) = editor.buffer_view.lock().get_edit_state_mut().get_cur_layer_mut() {
130 self.drag_offset = self.start_offset + editor.drag_pos.cur_abs - editor.drag_pos.start_abs;
131 layer.set_preview_offset(Some(self.drag_offset));
132 }
133 response.on_hover_cursor(egui::CursorIcon::Grabbing)
134 }
135
136 fn get_toolbar_location_text(&self, editor: &AnsiEditor) -> String {
137 get_layer_offset_text(editor)
138 }
139
140 fn handle_hover(&mut self, _ui: &egui::Ui, response: egui::Response, _editor: &mut AnsiEditor, _cur: Position, _cur_abs: Position) -> egui::Response {
141 response.on_hover_cursor(egui::CursorIcon::Move)
142 }
143
144 fn handle_drag_end(&mut self, editor: &mut AnsiEditor) -> Option<Message> {
145 if !self.drag_started {
146 return None;
147 }
148 to_message(editor.buffer_view.lock().get_edit_state_mut().move_layer(self.drag_offset))
149 }
150
151 fn handle_key(&mut self, editor: &mut AnsiEditor, key: MKey, modifier: super::MModifiers) -> Event {
152 let offset = if let Some(layer) = editor.buffer_view.lock().get_edit_state_mut().get_cur_layer_mut() {
153 layer.get_offset()
154 } else {
155 return Event::None;
156 };
157 let i = if matches!(modifier, super::MModifiers::Shift) { 2 } else { 1 };
158 match key {
159 MKey::Down => {
160 let _ = editor.buffer_view.lock().get_edit_state_mut().move_layer(offset + Position::new(0, i));
161 }
162 MKey::Up => {
163 let _ = editor.buffer_view.lock().get_edit_state_mut().move_layer(offset - Position::new(0, i));
164 }
165 MKey::Left => {
166 let _ = editor.buffer_view.lock().get_edit_state_mut().move_layer(offset - Position::new(i, 0));
167 }
168 MKey::Right => {
169 let _ = editor.buffer_view.lock().get_edit_state_mut().move_layer(offset + Position::new(i, 0));
170 }
171 _ => {}
172 }
173 Event::None
174 }
175 }