summaryrefslogtreecommitdiff
path: root/support/texlab/src/rename/latex_environment.rs
diff options
context:
space:
mode:
authorNorbert Preining <norbert@preining.info>2019-12-03 03:01:24 +0000
committerNorbert Preining <norbert@preining.info>2019-12-03 03:01:24 +0000
commitb8d4bb76703bcb15578e2b23c5d256532180b894 (patch)
treebedd1df7a00521a2bd986b3c0289d6556a59e39b /support/texlab/src/rename/latex_environment.rs
parent02e4625a78a5029e8b5dc2a4ec70193b232f497e (diff)
CTAN sync 201912030301
Diffstat (limited to 'support/texlab/src/rename/latex_environment.rs')
-rw-r--r--support/texlab/src/rename/latex_environment.rs137
1 files changed, 137 insertions, 0 deletions
diff --git a/support/texlab/src/rename/latex_environment.rs b/support/texlab/src/rename/latex_environment.rs
new file mode 100644
index 0000000000..28d6450356
--- /dev/null
+++ b/support/texlab/src/rename/latex_environment.rs
@@ -0,0 +1,137 @@
+use crate::range::RangeExt;
+use crate::syntax::*;
+use crate::workspace::*;
+use futures_boxed::boxed;
+use lsp_types::*;
+use std::collections::HashMap;
+
+#[derive(Debug, PartialEq, Eq, Clone, Copy)]
+pub struct LatexEnvironmentPrepareRenameProvider;
+
+impl FeatureProvider for LatexEnvironmentPrepareRenameProvider {
+ type Params = TextDocumentPositionParams;
+ type Output = Option<Range>;
+
+ #[boxed]
+ async fn execute<'a>(
+ &'a self,
+ request: &'a FeatureRequest<TextDocumentPositionParams>,
+ ) -> Option<Range> {
+ let position = request.params.position;
+ let environment = find_environment(&request.document().tree, position)?;
+ let left_range = environment.left.name().unwrap().range();
+ let right_range = environment.right.name().unwrap().range();
+ if left_range.contains(position) {
+ Some(left_range)
+ } else {
+ Some(right_range)
+ }
+ }
+}
+
+#[derive(Debug, PartialEq, Eq, Clone, Copy)]
+pub struct LatexEnvironmentRenameProvider;
+
+impl FeatureProvider for LatexEnvironmentRenameProvider {
+ type Params = RenameParams;
+ type Output = Option<WorkspaceEdit>;
+
+ #[boxed]
+ async fn execute<'a>(
+ &'a self,
+ request: &'a FeatureRequest<RenameParams>,
+ ) -> Option<WorkspaceEdit> {
+ let environment = find_environment(
+ &request.document().tree,
+ request.params.text_document_position.position,
+ )?;
+ let edits = vec![
+ TextEdit::new(
+ environment.left.name().unwrap().range(),
+ request.params.new_name.clone(),
+ ),
+ TextEdit::new(
+ environment.right.name().unwrap().range(),
+ request.params.new_name.clone(),
+ ),
+ ];
+ let mut changes = HashMap::new();
+ changes.insert(request.document().uri.clone().into(), edits);
+ Some(WorkspaceEdit::new(changes))
+ }
+}
+
+fn find_environment(tree: &SyntaxTree, position: Position) -> Option<&LatexEnvironment> {
+ if let SyntaxTree::Latex(tree) = &tree {
+ for environment in &tree.env.environments {
+ if let Some(left_name) = environment.left.name() {
+ if let Some(right_name) = environment.right.name() {
+ if left_name.range().contains(position) || right_name.range().contains(position)
+ {
+ return Some(environment);
+ }
+ }
+ }
+ }
+ }
+ None
+}
+
+#[cfg(test)]
+mod tests {
+ use super::*;
+ use lsp_types::{Position, Range};
+
+ #[test]
+ fn test_environment() {
+ let edit = test_feature(
+ LatexEnvironmentRenameProvider,
+ FeatureSpec {
+ files: vec![FeatureSpec::file("foo.tex", "\\begin{foo}\n\\end{bar}")],
+ main_file: "foo.tex",
+ position: Position::new(0, 8),
+ new_name: "baz",
+ ..FeatureSpec::default()
+ },
+ );
+ let mut changes = HashMap::new();
+ changes.insert(
+ FeatureSpec::uri("foo.tex"),
+ vec![
+ TextEdit::new(Range::new_simple(0, 7, 0, 10), "baz".into()),
+ TextEdit::new(Range::new_simple(1, 5, 1, 8), "baz".into()),
+ ],
+ );
+ assert_eq!(edit, Some(WorkspaceEdit::new(changes)));
+ }
+
+ #[test]
+ fn test_command() {
+ let edit = test_feature(
+ LatexEnvironmentRenameProvider,
+ FeatureSpec {
+ files: vec![FeatureSpec::file("foo.tex", "\\begin{foo}\n\\end{bar}")],
+ main_file: "foo.tex",
+ position: Position::new(0, 5),
+ new_name: "baz",
+ ..FeatureSpec::default()
+ },
+ );
+ assert_eq!(edit, None);
+ }
+
+ #[test]
+ fn test_bibtex() {
+ let edit = test_feature(
+ LatexEnvironmentRenameProvider,
+ FeatureSpec {
+ files: vec![FeatureSpec::file("foo.bib", "")],
+ main_file: "foo.bib",
+ position: Position::new(0, 0),
+ new_name: "baz",
+ ..FeatureSpec::default()
+ },
+ );
+ assert_eq!(edit, None);
+ }
+}