new way to handle command

This commit is contained in:
Dongdong Zhou 2021-10-04 12:14:35 +01:00
parent 9395635221
commit 0fdda202f8
10 changed files with 156 additions and 150 deletions

1
Cargo.lock generated
View File

@ -2159,6 +2159,7 @@ dependencies = [
"git2",
"im",
"include_dir",
"indexmap",
"itertools 0.10.1",
"jsonrpc-lite",
"lapce-proxy",

View File

@ -5,6 +5,7 @@ authors = ["Dongdong Zhou <dzhou121@gmail.com>"]
edition = "2018"
[dependencies]
indexmap = "1.7.0"
directories = "4.0.1"
tinyfiledialogs = "3.8.3"
itertools = "0.10.1"

View File

@ -206,13 +206,7 @@ fn event(
main_split: data.main_split.clone(),
proxy: data.proxy.clone(),
};
mut_keypress.key_down(
ctx,
key_event,
data,
&mut code_action_data,
env,
);
mut_keypress.key_down(ctx, key_event, &mut code_action_data, env);
data.keypress = keypress;
data.main_split = code_action_data.main_split.clone();
ctx.set_handled();

View File

@ -2,6 +2,7 @@
use anyhow::Result;
use druid::{Point, Rect, Selector, Size, WidgetId};
use indexmap::IndexMap;
use lsp_types::{
CodeActionResponse, CompletionItem, CompletionResponse, Location, Position,
PublishDiagnosticsParams, Range, TextEdit,
@ -47,8 +48,8 @@ pub enum CommandTarget {
Plugin(String),
}
pub fn lapce_internal_commands() -> HashMap<String, LapceCommandNew> {
let mut commands = HashMap::new();
pub fn lapce_internal_commands() -> IndexMap<String, LapceCommandNew> {
let mut commands = IndexMap::new();
for c in LapceWorkbenchCommand::iter() {
let command = LapceCommandNew {
@ -272,18 +273,6 @@ pub enum LapceCommand {
NextUnmatchedRightCurlyBracket,
#[strum(serialize = "previous_unmatched_left_curly_bracket")]
PreviousUnmatchedLeftCurlyBracket,
#[strum(serialize = "open_folder")]
#[strum(message = "Open Folder")]
OpenFolder,
#[strum(serialize = "change_theme")]
#[strum(message = "Change Theme")]
ChangeTheme,
#[strum(serialize = "open_settings")]
#[strum(message = "Open Settings")]
OpenSettings,
#[strum(serialize = "open_keyboard_shortcuts")]
#[strum(message = "Open Keyboard Shortcuts")]
OpenKeyboardShortcuts,
#[strum(serialize = "join_lines")]
JoinLines,
#[strum(serialize = "search_whole_word_forward")]

View File

@ -504,8 +504,30 @@ pub fn run_workbench_command(
env: &Env,
) {
match command {
LapceWorkbenchCommand::OpenFolder => {}
LapceWorkbenchCommand::ChangeTheme => {}
LapceWorkbenchCommand::OpenFolder => {
let event_sink = ctx.get_external_handle();
thread::spawn(move || {
if let Some(folder) =
tinyfiledialogs::select_folder_dialog("Open folder", "./")
{
event_sink.submit_command(
LAPCE_UI_COMMAND,
LapceUICommand::SetWorkspace(LapceWorkspace {
kind: LapceWorkspaceType::Local,
path: PathBuf::from(folder),
}),
Target::Auto,
);
}
});
}
LapceWorkbenchCommand::ChangeTheme => {
ctx.submit_command(Command::new(
LAPCE_UI_COMMAND,
LapceUICommand::RunPalette(Some(PaletteType::Theme)),
Target::Widget(self.palette.widget_id),
));
}
LapceWorkbenchCommand::OpenSettings => {
if let Some(proj_dirs) = ProjectDirs::from("", "", "Lapce") {
std::fs::create_dir_all(proj_dirs.config_dir());
@ -530,7 +552,30 @@ pub fn run_workbench_command(
);
}
}
LapceWorkbenchCommand::OpenKeyboardShortcuts => {}
LapceWorkbenchCommand::OpenKeyboardShortcuts => {
if let Some(proj_dirs) = ProjectDirs::from("", "", "Lapce") {
std::fs::create_dir_all(proj_dirs.config_dir());
let path = proj_dirs.config_dir().join("keymaps.toml");
{
std::fs::OpenOptions::new()
.create_new(true)
.write(true)
.open(&path);
}
let editor_view_id = self.main_split.active.clone();
self.main_split.jump_to_location(
ctx,
*editor_view_id,
EditorLocationNew {
path: path.clone(),
position: None,
scroll_offset: None,
},
&self.config,
);
}
}
LapceWorkbenchCommand::Palette => {
ctx.submit_command(Command::new(
LAPCE_UI_COMMAND,

View File

@ -42,6 +42,7 @@
use anyhow::{anyhow, Result};
use bit_vec::BitVec;
use crossbeam_channel::{self, bounded};
use druid::kurbo::BezPath;
use druid::widget::{LensWrap, WidgetWrapper};
use druid::{
kurbo::Line, piet::PietText, theme, widget::Flex, widget::IdentityWrapper,
@ -213,7 +214,18 @@ fn buffer_mut(&mut self) -> &mut BufferNew {
Arc::make_mut(&mut self.buffer)
}
fn get_code_actions(&mut self, ctx: &mut EventCtx) {
fn sync_buffer_position(&mut self, scroll_offset: Vec2) {
let cursor_offset = self.editor.cursor.offset();
if self.buffer.cursor_offset != cursor_offset
|| self.buffer.scroll_offset != scroll_offset
{
let buffer = self.buffer_mut();
buffer.cursor_offset = cursor_offset;
buffer.scroll_offset = scroll_offset;
}
}
fn get_code_actions(&self, ctx: &mut EventCtx) {
if !self.buffer.loaded {
return;
}
@ -1644,7 +1656,8 @@ fn paint_diagnostics(&self, ctx: &mut PaintCtx) {
let x1 = if line == end.line as usize {
end.character as f64 * width
} else {
self.buffer.line_len(line) as f64 * width
(self.buffer.line_end_col(line, false) + 1) as f64
* width
};
let y1 = (line + 1) as f64 * line_height;
let y0 = (line + 1) as f64 * line_height - 2.0;
@ -1665,7 +1678,7 @@ fn paint_diagnostics(&self, ctx: &mut PaintCtx) {
.config
.get_color_unchecked(LapceTheme::LAPCE_WARN),
};
ctx.fill(Rect::new(x0, y0, x1, y1), color);
paint_wave_line(ctx, Point::new(x0, y0), x1 - x0, &color);
}
}
}
@ -2962,24 +2975,19 @@ fn event(
match event {
Event::KeyDown(key_event) => {
ctx.set_handled();
let mut keypress = data.keypress.clone();
if Arc::make_mut(&mut keypress).key_down(
ctx,
key_event,
data,
&mut editor_data,
env,
) {
self.ensure_cursor_visible(
ctx,
&mut editor_data,
None,
env,
);
self.ensure_cursor_visible(ctx, &editor_data, None, env);
}
// editor_data.sync_buffer_position(
// self.editor.widget().inner().offset(),
// );
editor_data.sync_buffer_position(
self.editor.widget().editor.widget().inner().offset(),
);
editor_data.get_code_actions(ctx);
data.keypress = keypress.clone();
@ -3014,7 +3022,6 @@ fn event(
Arc::make_mut(&mut keypress).key_down(
ctx,
key_event,
data,
&mut LapceEditorEmptyContent {},
env,
);
@ -4125,3 +4132,26 @@ fn process_get_references(
);
Ok(())
}
fn paint_wave_line(
ctx: &mut PaintCtx,
origin: Point,
max_width: f64,
color: &Color,
) {
let mut path = BezPath::new();
let mut x = 0.0;
let width = 3.5;
let height = 4.0;
path.move_to(origin + (0.0, height / 2.0));
let mut direction = 1.0;
while x < max_width {
let point = origin + (x, height / 2.0);
let p1 = point + (width / 2.0, -height / 2.0 * direction);
let p2 = point + (width, 0.0);
path.quad_to(p1, p2);
x += width;
direction *= -1.0;
}
ctx.stroke(path, color, 1.2);
}

View File

@ -4,14 +4,17 @@
use anyhow::{anyhow, Result};
use directories::ProjectDirs;
use druid::KbKey;
use druid::{
Color, Data, Env, EventCtx, ExtEventSink, KeyEvent, Modifiers, Target, WidgetId,
WindowId,
};
use druid::{Command, KbKey};
use indexmap::IndexMap;
use toml;
use crate::command::{lapce_internal_commands, CommandTarget, LapceCommandNew};
use crate::command::{
lapce_internal_commands, CommandTarget, LapceCommandNew, LAPCE_NEW_COMMAND,
};
use crate::data::LapceTabData;
use crate::{
command::LapceCommand,
@ -65,7 +68,7 @@ fn run_command(
pub struct KeyPressData {
pending_keypress: Vec<KeyPress>,
keymaps: im::HashMap<Vec<(Modifiers, druid::keyboard_types::Code)>, Vec<KeyMap>>,
commands: Arc<HashMap<String, LapceCommandNew>>,
pub commands: Arc<IndexMap<String, LapceCommandNew>>,
count: Option<usize>,
}
@ -90,7 +93,6 @@ fn run_command<T: KeyPressFocus>(
ctx: &mut EventCtx,
command: &str,
count: Option<usize>,
data: &mut LapceTabData,
focus: &mut T,
env: &Env,
) -> Result<()> {
@ -99,7 +101,11 @@ fn run_command<T: KeyPressFocus>(
let cmd = LapceCommand::from_str(command)?;
focus.run_command(ctx, &cmd, count, env);
} else {
data.run_command(ctx, cmd, count, env);
ctx.submit_command(Command::new(
LAPCE_NEW_COMMAND,
cmd.clone(),
Target::Auto,
));
}
}
Ok(())
@ -129,7 +135,6 @@ pub fn key_down<T: KeyPressFocus>(
&mut self,
ctx: &mut EventCtx,
key_event: &KeyEvent,
data: &mut LapceTabData,
focus: &mut T,
env: &Env,
) -> bool {
@ -183,14 +188,14 @@ pub fn key_down<T: KeyPressFocus>(
match keymatch {
KeymapMatch::Full(command) => {
let count = self.count.take();
self.run_command(ctx, &command, count, data, focus, env);
self.run_command(ctx, &command, count, focus, env);
self.pending_keypress = Vec::new();
return true;
}
KeymapMatch::Multiple(commands) => {
let count = self.count.take();
for command in commands {
self.run_command(ctx, &command, count, data, focus, env);
self.run_command(ctx, &command, count, focus, env);
}
self.pending_keypress = Vec::new();
return true;

View File

@ -34,10 +34,10 @@
use uuid::Uuid;
use crate::{
command::LapceUICommand,
command::LAPCE_COMMAND,
command::LAPCE_UI_COMMAND,
command::{CommandTarget, LapceCommand},
command::{CommandTarget, LapceCommand, LAPCE_NEW_COMMAND},
command::{LapceCommandNew, LapceUICommand},
config::{Config, LapceTheme},
data::{
EditorContent, EditorKind, LapceEditorData, LapceEditorViewData,
@ -82,10 +82,10 @@ fn string(&self) -> String {
fn has_preview(&self) -> bool {
match &self {
PaletteType::File | PaletteType::Workspace | PaletteType::Command => {
false
}
_ => true,
PaletteType::Line
| PaletteType::DocumentSymbol
| PaletteType::Reference => true,
_ => false,
}
}
}
@ -116,7 +116,7 @@ pub enum PaletteItemContent {
},
ReferenceLocation(PathBuf, EditorLocationNew),
Workspace(LapceWorkspace),
Command(LapceCommand),
Command(LapceCommandNew),
Theme(String),
}
@ -189,44 +189,29 @@ fn select(&self, ctx: &mut EventCtx, preview: bool) -> Option<PaletteType> {
Target::Auto,
));
}
PaletteItemContent::Command(command) => match command {
LapceCommand::ChangeTheme => {
if !preview {
return Some(PaletteType::Theme);
}
PaletteItemContent::Command(command) => {
if !preview {
ctx.submit_command(Command::new(
LAPCE_NEW_COMMAND,
command.clone(),
Target::Auto,
));
}
LapceCommand::OpenFolder => {
if !preview {
let event_sink = ctx.get_external_handle();
thread::spawn(move || {
if let Some(folder) =
tinyfiledialogs::select_folder_dialog(
"Open folder",
"./",
)
{
event_sink.submit_command(
LAPCE_UI_COMMAND,
LapceUICommand::SetWorkspace(LapceWorkspace {
kind: LapceWorkspaceType::Local,
path: PathBuf::from(folder),
}),
Target::Auto,
);
}
});
}
}
_ => {
if !preview {
ctx.submit_command(Command::new(
LAPCE_COMMAND,
command.clone(),
Target::Auto,
));
}
}
},
// LapceCommand::ChangeTheme => {
// if !preview {
// return Some(PaletteType::Theme);
// }
// }
// _ => {
// if !preview {
// ctx.submit_command(Command::new(
// LAPCE_NEW_COMMAND,
// command.clone(),
// Target::Auto,
// ));
// }
// }
}
}
None
}
@ -292,7 +277,8 @@ fn paint(
PaletteItemContent::Command(command) => (
None,
command
.get_message()
.palette_desc
.as_ref()
.map(|m| m.to_string())
.unwrap_or("".to_string()),
indices.to_vec(),
@ -871,9 +857,12 @@ fn get_themes(&mut self, ctx: &mut EventCtx, config: &Config) {
fn get_commands(&mut self, ctx: &mut EventCtx) {
let palette = Arc::make_mut(&mut self.palette);
palette.items = LapceCommand::iter()
.filter_map(|c| {
c.get_message().map(|m| NewPaletteItem {
palette.items = self
.keypress
.commands
.iter()
.filter_map(|(_, c)| {
c.palette_desc.as_ref().map(|m| NewPaletteItem {
content: PaletteItemContent::Command(c.clone()),
filter_text: m.to_string(),
score: 0,
@ -1123,7 +1112,7 @@ fn event(
let mut keypress = data.keypress.clone();
let mut_keypress = Arc::make_mut(&mut keypress);
let mut palette_data = data.palette_view_data();
mut_keypress.key_down(ctx, key_event, data, &mut palette_data, env);
mut_keypress.key_down(ctx, key_event, &mut palette_data, env);
data.palette = palette_data.palette.clone();
data.keypress = keypress;
data.workspace = palette_data.workspace.clone();

View File

@ -350,7 +350,6 @@ fn event(
Arc::make_mut(&mut keypress).key_down(
ctx,
key_event,
data,
Arc::make_mut(&mut source_control),
env,
);

View File

@ -11,7 +11,10 @@
use crate::{
buffer::{BufferId, BufferNew, BufferState, BufferUpdate, UpdateEvent},
code_action::CodeAction,
command::{LapceCommand, LapceUICommand, LAPCE_COMMAND, LAPCE_UI_COMMAND},
command::{
LapceCommand, LapceUICommand, LAPCE_COMMAND, LAPCE_NEW_COMMAND,
LAPCE_UI_COMMAND,
},
completion::{CompletionContainer, CompletionNew, CompletionStatus},
config::Config,
data::{EditorDiagnostic, EditorKind, LapceMainSplitData, LapceTabData},
@ -156,59 +159,9 @@ fn event(
}
}
}
Event::Command(cmd) if cmd.is(LAPCE_COMMAND) => {
let command = cmd.get_unchecked(LAPCE_COMMAND);
match command {
LapceCommand::OpenSettings => {
if let Some(proj_dirs) = ProjectDirs::from("", "", "Lapce") {
std::fs::create_dir_all(proj_dirs.config_dir());
let path = proj_dirs.config_dir().join("settings.toml");
{
std::fs::OpenOptions::new()
.create_new(true)
.write(true)
.open(&path);
}
let editor_view_id = data.main_split.active.clone();
data.main_split.jump_to_location(
ctx,
*editor_view_id,
EditorLocationNew {
path: path.clone(),
position: None,
scroll_offset: None,
},
&data.config,
);
}
}
LapceCommand::OpenKeyboardShortcuts => {
if let Some(proj_dirs) = ProjectDirs::from("", "", "Lapce") {
std::fs::create_dir_all(proj_dirs.config_dir());
let path = proj_dirs.config_dir().join("keymaps.toml");
{
std::fs::OpenOptions::new()
.create_new(true)
.write(true)
.open(&path);
}
let editor_view_id = data.main_split.active.clone();
data.main_split.jump_to_location(
ctx,
*editor_view_id,
EditorLocationNew {
path: path.clone(),
position: None,
scroll_offset: None,
},
&data.config,
);
}
}
_ => (),
}
Event::Command(cmd) if cmd.is(LAPCE_NEW_COMMAND) => {
let command = cmd.get_unchecked(LAPCE_NEW_COMMAND);
data.run_command(ctx, command, None, env);
ctx.set_handled();
}
Event::Command(cmd) if cmd.is(LAPCE_UI_COMMAND) => {