moving files around

This commit is contained in:
Dongdong Zhou 2020-10-15 18:03:20 +01:00
parent 6cd5af264f
commit c07afe9264
25 changed files with 240 additions and 51 deletions

34
Cargo.lock generated
View File

@ -35,9 +35,9 @@ dependencies = [
[[package]]
name = "anyhow"
version = "1.0.32"
version = "1.0.33"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "6b602bfe940d21c130f3895acd65221e8a61270debe89d628b9cb4e3ccb8569b"
checksum = "a1fd36ffbb1fb7c834eac128ea8d0e310c5aeb635548f9d58861e1308d46e71c"
[[package]]
name = "anymap"
@ -1491,6 +1491,28 @@ dependencies = [
"xi-rpc",
]
[[package]]
name = "lapce-core"
version = "0.0.1"
dependencies = [
"anyhow",
"serde",
"serde_json",
"toml",
"xi-rpc",
]
[[package]]
name = "lapce-lsp"
version = "0.0.1"
dependencies = [
"anyhow",
"lapce-core",
"serde",
"serde_json",
"xi-rpc",
]
[[package]]
name = "lazy_static"
version = "0.2.11"
@ -2523,9 +2545,9 @@ dependencies = [
[[package]]
name = "serde_json"
version = "1.0.57"
version = "1.0.59"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "164eacbdb13512ec2745fb09d51fd5b22b0d65ed294a1dcf7285a360c80a675c"
checksum = "dcac07dbffa1c65e7f816ab9eba78eb142c6d44410f4eeba1e26e4f5dfa56b95"
dependencies = [
"itoa",
"ryu",
@ -2908,9 +2930,9 @@ checksum = "238ce071d267c5710f9d31451efec16c5ee22de34df17cc05e56cbc92e967117"
[[package]]
name = "toml"
version = "0.5.6"
version = "0.5.7"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "ffc92d160b1eef40665be3a05630d003936a3bc7da7421277846c2613e92c71a"
checksum = "75cf45bb0bef80604d001caaec0d09da99611b3c0fd39d3080468875cdb65645"
dependencies = [
"serde",
]

View File

@ -14,7 +14,6 @@ anyhow = "1.0.32"
strum = "0.19"
strum_macros = "0.19"
lazy_static = "1.4.0"
# piet-cairo = "0.0.6"
serde = "1.0"
serde_json = "1.0"
syntect = "3.2"
@ -28,3 +27,6 @@ druid = { git = "https://github.com/linebender/druid", features = ["svg"] }
[build-dependencies]
cc = "*"
[workspace]
members = ["lsp", "core"]

12
core/Cargo.toml Normal file
View File

@ -0,0 +1,12 @@
[package]
name = "lapce-core"
version = "0.0.1"
authors = ["Dongdong Zhou <dzhou121@gmail.com>"]
edition = "2018"
[dependencies]
anyhow = "1.0.33"
serde = { version = "1.0", features = ["derive"] }
toml = "0.5.7"
xi-rpc = { path = "../../xi-editor/rust/rpc/" }
serde_json = "1.0.59"

View File

@ -43,8 +43,8 @@ pub struct LapceContainer {
}
impl LapceContainer {
pub fn new(state: LapceState) -> Self {
let palette = Palette::new(state.palette.lock().scroll_widget_id)
pub fn new() -> Self {
let palette = Palette::new(LAPCE_STATE.palette.lock().scroll_widget_id)
.border(theme::BORDER_LIGHT, 1.0)
.background(LapceTheme::PALETTE_BACKGROUND);
let palette_id = WidgetId::next();

View File

@ -63,6 +63,7 @@ pub enum EditorOperator {
#[derive(Clone)]
pub struct EditorUIState {
pub cursor: (usize, usize),
pub mode: Mode,
pub visual_mode: VisualMode,
pub selection: Selection,
pub selection_start_line: usize,
@ -122,6 +123,7 @@ pub fn update(
if editor.selection != old_editor.selection
|| editor.visual_mode != old_editor.visual_mode
|| editor.mode != old_editor.mode
{
let rect = Rect::ZERO
.with_origin(Point::new(
@ -681,6 +683,7 @@ impl EditorUIState {
pub fn new() -> EditorUIState {
EditorUIState {
cursor: (0, 0),
mode: Mode::Normal,
visual_mode: VisualMode::Normal,
selection: Selection::new(),
selection_start_line: 0,
@ -1356,6 +1359,7 @@ pub fn run_command(
editor_ui_state.cursor =
buffer.offset_to_line_col(editor.selection.get_cursor_offset());
editor_ui_state.visual_mode = self.visual_mode.clone();
editor_ui_state.mode = self.mode.clone();
self.notify_fill_text_layouts(ctx, &buffer_id);
None
}
@ -1505,15 +1509,6 @@ fn event(
LapceUICommand::RequestPaint => {
ctx.request_paint();
}
LapceUICommand::EditorViewSize(size) => {
LAPCE_STATE
.editor_split
.lock()
.editors
.get_mut(&self.view_id)
.unwrap()
.view_size = *size;
}
LapceUICommand::FillTextLayouts => {
LAPCE_STATE.editor_split.lock().fill_text_layouts(
ctx,
@ -1631,11 +1626,13 @@ fn lifecycle(
) {
match event {
LifeCycle::Size(size) => {
ctx.submit_command(Command::new(
LAPCE_UI_COMMAND,
LapceUICommand::EditorViewSize(*size),
Target::Widget(self.view_id.clone()),
));
LAPCE_STATE
.editor_split
.lock()
.editors
.get_mut(&self.view_id)
.unwrap()
.view_size = *size;
ctx.submit_command(Command::new(
LAPCE_UI_COMMAND,
LapceUICommand::FillTextLayouts,

5
core/src/lib.rs Normal file
View File

@ -0,0 +1,5 @@
pub mod buffer;
pub mod command;
pub mod editor;
pub mod plugin;
pub mod state;

View File

@ -1,4 +1,4 @@
use anyhow::Result;
use anyhow::{anyhow, Result};
use serde::{Deserialize, Deserializer, Serialize};
use std::{
collections::HashMap,
@ -12,9 +12,9 @@
thread,
};
use toml;
use xi_rpc::{self, RpcLoop, RpcPeer};
use xi_rpc::{self, Handler, RpcLoop, RpcPeer};
use crate::{editor::Counter, state::LapceState};
use crate::{editor::Counter, state::LAPCE_STATE};
pub type PluginName = String;
@ -25,13 +25,17 @@ pub struct PluginCatalog {
items: HashMap<PluginName, Arc<PluginDescription>>,
locations: HashMap<PathBuf, Arc<PluginDescription>>,
id_counter: Counter,
running: Vec<Plugin>,
}
pub struct PluginHandler {}
#[derive(Deserialize)]
pub struct PluginDescription {
pub name: String,
pub version: String,
pub exec_path: PathBuf,
dir: Option<PathBuf>,
}
pub struct Plugin {
@ -47,6 +51,7 @@ pub fn new() -> PluginCatalog {
items: HashMap::new(),
locations: HashMap::new(),
id_counter: Counter::default(),
running: Vec::new(),
}
}
@ -73,6 +78,12 @@ pub fn load_from_paths(&mut self, paths: &[PathBuf]) {
}
}
}
pub fn start_all(&mut self) {
for (_, manifest) in self.items.clone().iter() {
start_plugin_process(manifest.clone(), self.next_plugin_id());
}
}
}
fn find_all_manifests(paths: &[PathBuf]) -> Vec<PathBuf> {
@ -91,6 +102,7 @@ fn find_all_manifests(paths: &[PathBuf]) -> Vec<PathBuf> {
.for_each(|f| manifest_paths.push(f))
});
}
println!("mainfiest paths {:?}", manifest_paths);
manifest_paths
}
@ -100,6 +112,7 @@ fn load_manifest(path: &Path) -> Result<PluginDescription> {
file.read_to_string(&mut contents)?;
let mut manifest: PluginDescription = toml::from_str(&contents)?;
// normalize relative paths
manifest.dir = Some(path.parent().unwrap().canonicalize()?);
if manifest.exec_path.starts_with("./") {
manifest.exec_path = path
.parent()
@ -110,17 +123,26 @@ fn load_manifest(path: &Path) -> Result<PluginDescription> {
Ok(manifest)
}
fn start_plugin_process(
plugin_desc: Arc<PluginDescription>,
id: PluginId,
state: LapceState,
) {
fn start_plugin_process(plugin_desc: Arc<PluginDescription>, id: PluginId) {
thread::spawn(move || {
let child = Command::new(&plugin_desc.exec_path)
.stdin(Stdio::piped())
.stdout(Stdio::piped())
.spawn();
child.map(|mut child| {
println!(
"start plugin {:?} {:?}",
plugin_desc.exec_path, plugin_desc.dir
);
let parts: Vec<&str> = plugin_desc
.exec_path
.to_str()
.unwrap()
.split(" ")
.into_iter()
.collect();
let mut child = Command::new(parts[0]);
for part in &parts[1..] {
child.arg(part);
}
child.current_dir(plugin_desc.dir.as_ref().unwrap());
let child = child.stdin(Stdio::piped()).stdout(Stdio::piped()).spawn();
if let Err(e) = child.map(|mut child| {
let child_stdin = child.stdin.take().unwrap();
let child_stdout = child.stdout.take().unwrap();
let mut looper = RpcLoop::new(child_stdin);
@ -133,7 +155,55 @@ fn start_plugin_process(
id,
};
// looper.mainloop(|| BufReader::new(child_stdout), handler);
});
LAPCE_STATE.plugins.lock().running.push(plugin);
let mut handler = PluginHandler {};
if let Err(e) =
looper.mainloop(|| BufReader::new(child_stdout), &mut handler)
{
println!("plugin main loop failed {} {:?}", e, plugin_desc.dir);
}
}) {
println!(
"can't start plugin sub process {} {:?}",
e, plugin_desc.exec_path
);
}
});
}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "snake_case")]
/// RPC Notifications sent from the host
pub enum HostNotification {}
#[derive(Debug, Clone, Serialize, Deserialize)]
#[serde(rename_all = "snake_case")]
/// RPC Request sent from the host
pub enum HostRequest {}
#[derive(Serialize, Deserialize, Debug, PartialEq)]
pub enum PluginNotification {}
#[derive(Serialize, Deserialize, Debug, PartialEq)]
pub enum PluginRequest {}
impl Handler for PluginHandler {
type Notification = PluginNotification;
type Request = PluginRequest;
fn handle_notification(
&mut self,
ctx: &xi_rpc::RpcCtx,
rpc: Self::Notification,
) {
}
fn handle_request(
&mut self,
ctx: &xi_rpc::RpcCtx,
rpc: Self::Request,
) -> Result<serde_json::Value, xi_rpc::RemoteError> {
Err(xi_rpc::RemoteError::InvalidRequest(None))
}
}

View File

@ -214,6 +214,23 @@ fn event(
selection.clone(),
);
data.new_editor(&new_editor.view_id);
let editor_ui = data.get_editor(&active);
let selection = editor_ui.selection.clone();
let visual_mode = editor_ui.visual_mode.clone();
let mode = editor_ui.mode.clone();
let selection_start_line =
editor_ui.selection_start_line;
let selection_end_line =
editor_ui.selection_end_line;
let new_editor_ui =
data.get_editor_mut(&new_editor.view_id);
new_editor_ui.selection = selection;
new_editor_ui.visual_mode = visual_mode;
new_editor_ui.mode = mode;
new_editor_ui.selection_start_line =
selection_start_line;
new_editor_ui.selection_end_line =
selection_end_line;
let new_editor_view = EditorView::new(
new_editor.split_id,

View File

@ -12,6 +12,7 @@
keypress::KeyPressState,
language::TreeSitter,
palette::PaletteState,
plugin::PluginCatalog,
};
use anyhow::{anyhow, Result};
use druid::{
@ -21,7 +22,8 @@
use lazy_static::lazy_static;
use parking_lot::Mutex;
use std::{
collections::HashMap, fs::File, io::Read, str::FromStr, sync::Arc, thread,
collections::HashMap, fs::File, io::Read, path::PathBuf, str::FromStr,
sync::Arc, thread,
};
use toml;
@ -135,6 +137,7 @@ pub struct LapceState {
pub editor_split: Arc<Mutex<EditorSplitState>>,
pub container: Option<WidgetId>,
pub file_explorer: Arc<Mutex<FileExplorerState>>,
pub plugins: Arc<Mutex<PluginCatalog>>,
}
impl Data for LapceState {
@ -147,6 +150,9 @@ fn same(&self, other: &Self) -> bool {
impl LapceState {
pub fn new() -> LapceState {
let mut plugins = PluginCatalog::new();
plugins.reload_from_paths(&[PathBuf::from_str("./lsp").unwrap()]);
plugins.start_all();
LapceState {
theme: Self::get_theme().unwrap_or(HashMap::new()),
focus: Arc::new(Mutex::new(LapceFocus::Editor)),
@ -155,6 +161,7 @@ pub fn new() -> LapceState {
file_explorer: Arc::new(Mutex::new(FileExplorerState::new())),
container: None,
keypress: Arc::new(Mutex::new(KeyPressState::new())),
plugins: Arc::new(Mutex::new(plugins)),
}
}
@ -166,7 +173,6 @@ fn get_theme() -> Result<HashMap<String, Color>> {
let mut theme = HashMap::new();
for (name, hex) in toml_theme.iter() {
println!("{}", name);
if let Ok(color) = hex_to_color(hex) {
theme.insert(name.to_string(), color);
}
@ -355,12 +361,6 @@ pub fn hex_to_color(hex: &str) -> Result<Color> {
),
_ => return Err(anyhow!("invalid hex color")),
};
println!(
"{} {} {}",
u8::from_str_radix(&r, 16)?,
u8::from_str_radix(&g, 16)?,
u8::from_str_radix(&b, 16)?
);
Ok(Color::rgb8(
u8::from_str_radix(&r, 16)?,
u8::from_str_radix(&g, 16)?,

12
lsp/Cargo.toml Normal file
View File

@ -0,0 +1,12 @@
[package]
name = "lapce-lsp"
version = "0.0.1"
authors = ["Dongdong Zhou <dzhou121@gmail.com>"]
edition = "2018"
[dependencies]
serde = { version = "1.0", features = ["derive"] }
serde_json = "1.0.59"
xi-rpc = { path = "../../xi-editor/rust/rpc/" }
lapce-core = { path = "../core" }
anyhow = "1.0.32"

3
lsp/manifest.toml Normal file
View File

@ -0,0 +1,3 @@
name = "lapce-lsp-plugin"
version = "0.1"
exec_path = "cargo run --bin lapce-lsp-plugin"

View File

@ -0,0 +1,5 @@
use lapce_lsp::mainloop;
fn main() {
mainloop();
}

32
lsp/src/dispatch.rs Normal file
View File

@ -0,0 +1,32 @@
use lapce::plugin::{HostNotfication, HostRequest};
use serde::{Deserialize, Deserializer, Serialize};
use serde_json::Value;
use xi_rpc::Handler;
pub struct Dispatcher {}
impl Dispatcher {
pub fn new() -> Dispatcher {
Dispatcher {}
}
}
impl Handler for Dispatcher {
type Notification = HostNotification;
type Request = HostRequest;
fn handle_notification(
&mut self,
ctx: &xi_rpc::RpcCtx,
rpc: Self::Notification,
) {
}
fn handle_request(
&mut self,
ctx: &xi_rpc::RpcCtx,
rpc: Self::Request,
) -> Result<Value, xi_rpc::RemoteError> {
Err(xi_rpc::RemoteError::InvalidRequest(None))
}
}

14
lsp/src/lib.rs Normal file
View File

@ -0,0 +1,14 @@
mod dispatch;
use dispatch::Dispatcher;
use std::io;
use xi_rpc::RpcLoop;
pub fn mainloop() {
let stdin = io::stdin();
let stdout = io::stdout();
let mut rpc_looper = RpcLoop::new(stdout);
let mut dispatcher = Dispatcher::new();
rpc_looper.mainloop(|| stdin.lock(), &mut dispatcher);
}

View File

@ -40,10 +40,10 @@
fn tree_sitter_rust() -> Language;
}
fn build_app(state: LapceState) -> impl Widget<LapceUIState> {
fn build_app() -> impl Widget<LapceUIState> {
let container_id = WidgetId::next();
let container =
IdentityWrapper::wrap(LapceContainer::new(state), container_id.clone());
IdentityWrapper::wrap(LapceContainer::new(), container_id.clone());
// LAPCE_STATE.set_container(container_id);
let main_split = LapceSplit::new(true)
.with_child(FileExplorer::new(), 300.0)
@ -127,9 +127,7 @@ pub fn main() {
});
}
// WindowDesc::new(|| LapceContainer::new());
let state = LapceState::new();
let init_state = state.clone();
let window = WindowDesc::new(move || build_app(init_state))
let window = WindowDesc::new(build_app)
.title(
LocalizedString::new("split-demo-window-title")
.with_placeholder("Split Demo"),