aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorbors[bot] <26634292+bors[bot]@users.noreply.github.com>2020-03-12 16:02:55 +0000
committerGitHub <[email protected]>2020-03-12 16:02:55 +0000
commitd98a5fab46c5850a484349c50dda7cb823cc179a (patch)
tree754340fc8f170ed6057e6302fef1386ae8fb52d9
parent944bd2cbc3af1a11eb6dbaec96fcc0030f42232a (diff)
parenta153b9087520012b5f815b4df6c3657d490b30c8 (diff)
Merge #3543
3543: Parameter inlay hint separate from variable type inlay? #2876 r=matklad a=slyngbaek Add setting to allow enabling either type inlay hints or parameter inlay hints or both. Group the the max inlay hint length option into the object. - Add a new type for the inlayHint options. - Add tests to ensure the inlays don't happen on the server side Co-authored-by: Steffen Lyngbaek <[email protected]>
-rw-r--r--crates/ra_ide/src/inlay_hints.rs113
-rw-r--r--crates/ra_ide/src/lib.rs6
-rw-r--r--crates/rust-analyzer/src/config.rs7
-rw-r--r--crates/rust-analyzer/src/main_loop.rs2
-rw-r--r--crates/rust-analyzer/src/main_loop/handlers.rs9
-rw-r--r--crates/rust-analyzer/src/req.rs14
-rw-r--r--crates/rust-analyzer/src/world.rs5
-rw-r--r--docs/user/features.md4
-rw-r--r--editors/code/package.json11
-rw-r--r--editors/code/src/client.ts2
-rw-r--r--editors/code/src/config.ts18
-rw-r--r--editors/code/src/inlay_hints.ts2
12 files changed, 150 insertions, 43 deletions
diff --git a/crates/ra_ide/src/inlay_hints.rs b/crates/ra_ide/src/inlay_hints.rs
index cf0cbdbd0..59922e14c 100644
--- a/crates/ra_ide/src/inlay_hints.rs
+++ b/crates/ra_ide/src/inlay_hints.rs
@@ -10,7 +10,20 @@ use ra_syntax::{
10 10
11use crate::{FileId, FunctionSignature}; 11use crate::{FileId, FunctionSignature};
12 12
13#[derive(Debug, PartialEq, Eq)] 13#[derive(Clone, Debug, PartialEq, Eq)]
14pub struct InlayConfig {
15 pub type_hints: bool,
16 pub parameter_hints: bool,
17 pub max_length: Option<usize>,
18}
19
20impl Default for InlayConfig {
21 fn default() -> Self {
22 Self { type_hints: true, parameter_hints: true, max_length: None }
23 }
24}
25
26#[derive(Clone, Debug, PartialEq, Eq)]
14pub enum InlayKind { 27pub enum InlayKind {
15 TypeHint, 28 TypeHint,
16 ParameterHint, 29 ParameterHint,
@@ -26,7 +39,7 @@ pub struct InlayHint {
26pub(crate) fn inlay_hints( 39pub(crate) fn inlay_hints(
27 db: &RootDatabase, 40 db: &RootDatabase,
28 file_id: FileId, 41 file_id: FileId,
29 max_inlay_hint_length: Option<usize>, 42 inlay_hint_opts: &InlayConfig,
30) -> Vec<InlayHint> { 43) -> Vec<InlayHint> {
31 let _p = profile("inlay_hints"); 44 let _p = profile("inlay_hints");
32 let sema = Semantics::new(db); 45 let sema = Semantics::new(db);
@@ -36,9 +49,9 @@ pub(crate) fn inlay_hints(
36 for node in file.syntax().descendants() { 49 for node in file.syntax().descendants() {
37 match_ast! { 50 match_ast! {
38 match node { 51 match node {
39 ast::CallExpr(it) => { get_param_name_hints(&mut res, &sema, ast::Expr::from(it)); }, 52 ast::CallExpr(it) => { get_param_name_hints(&mut res, &sema, inlay_hint_opts, ast::Expr::from(it)); },
40 ast::MethodCallExpr(it) => { get_param_name_hints(&mut res, &sema, ast::Expr::from(it)); }, 53 ast::MethodCallExpr(it) => { get_param_name_hints(&mut res, &sema, inlay_hint_opts, ast::Expr::from(it)); },
41 ast::BindPat(it) => { get_bind_pat_hints(&mut res, &sema, max_inlay_hint_length, it); }, 54 ast::BindPat(it) => { get_bind_pat_hints(&mut res, &sema, inlay_hint_opts, it); },
42 _ => (), 55 _ => (),
43 } 56 }
44 } 57 }
@@ -49,8 +62,13 @@ pub(crate) fn inlay_hints(
49fn get_param_name_hints( 62fn get_param_name_hints(
50 acc: &mut Vec<InlayHint>, 63 acc: &mut Vec<InlayHint>,
51 sema: &Semantics<RootDatabase>, 64 sema: &Semantics<RootDatabase>,
65 inlay_hint_opts: &InlayConfig,
52 expr: ast::Expr, 66 expr: ast::Expr,
53) -> Option<()> { 67) -> Option<()> {
68 if !inlay_hint_opts.parameter_hints {
69 return None;
70 }
71
54 let args = match &expr { 72 let args = match &expr {
55 ast::Expr::CallExpr(expr) => expr.arg_list()?.args(), 73 ast::Expr::CallExpr(expr) => expr.arg_list()?.args(),
56 ast::Expr::MethodCallExpr(expr) => expr.arg_list()?.args(), 74 ast::Expr::MethodCallExpr(expr) => expr.arg_list()?.args(),
@@ -84,9 +102,13 @@ fn get_param_name_hints(
84fn get_bind_pat_hints( 102fn get_bind_pat_hints(
85 acc: &mut Vec<InlayHint>, 103 acc: &mut Vec<InlayHint>,
86 sema: &Semantics<RootDatabase>, 104 sema: &Semantics<RootDatabase>,
87 max_inlay_hint_length: Option<usize>, 105 inlay_hint_opts: &InlayConfig,
88 pat: ast::BindPat, 106 pat: ast::BindPat,
89) -> Option<()> { 107) -> Option<()> {
108 if !inlay_hint_opts.type_hints {
109 return None;
110 }
111
90 let ty = sema.type_of_pat(&pat.clone().into())?; 112 let ty = sema.type_of_pat(&pat.clone().into())?;
91 113
92 if should_not_display_type_hint(sema.db, &pat, &ty) { 114 if should_not_display_type_hint(sema.db, &pat, &ty) {
@@ -96,7 +118,7 @@ fn get_bind_pat_hints(
96 acc.push(InlayHint { 118 acc.push(InlayHint {
97 range: pat.syntax().text_range(), 119 range: pat.syntax().text_range(),
98 kind: InlayKind::TypeHint, 120 kind: InlayKind::TypeHint,
99 label: ty.display_truncated(sema.db, max_inlay_hint_length).to_string().into(), 121 label: ty.display_truncated(sema.db, inlay_hint_opts.max_length).to_string().into(),
100 }); 122 });
101 Some(()) 123 Some(())
102} 124}
@@ -202,11 +224,66 @@ fn get_fn_signature(sema: &Semantics<RootDatabase>, expr: &ast::Expr) -> Option<
202 224
203#[cfg(test)] 225#[cfg(test)]
204mod tests { 226mod tests {
227 use crate::inlay_hints::InlayConfig;
205 use insta::assert_debug_snapshot; 228 use insta::assert_debug_snapshot;
206 229
207 use crate::mock_analysis::single_file; 230 use crate::mock_analysis::single_file;
208 231
209 #[test] 232 #[test]
233 fn param_hints_only() {
234 let (analysis, file_id) = single_file(
235 r#"
236 fn foo(a: i32, b: i32) -> i32 { a + b }
237 fn main() {
238 let _x = foo(4, 4);
239 }"#,
240 );
241 assert_debug_snapshot!(analysis.inlay_hints(file_id, &InlayConfig{ parameter_hints: true, type_hints: false, max_length: None}).unwrap(), @r###"
242 [
243 InlayHint {
244 range: [106; 107),
245 kind: ParameterHint,
246 label: "a",
247 },
248 InlayHint {
249 range: [109; 110),
250 kind: ParameterHint,
251 label: "b",
252 },
253 ]"###);
254 }
255
256 #[test]
257 fn hints_disabled() {
258 let (analysis, file_id) = single_file(
259 r#"
260 fn foo(a: i32, b: i32) -> i32 { a + b }
261 fn main() {
262 let _x = foo(4, 4);
263 }"#,
264 );
265 assert_debug_snapshot!(analysis.inlay_hints(file_id, &InlayConfig{ type_hints: false, parameter_hints: false, max_length: None}).unwrap(), @r###"[]"###);
266 }
267
268 #[test]
269 fn type_hints_only() {
270 let (analysis, file_id) = single_file(
271 r#"
272 fn foo(a: i32, b: i32) -> i32 { a + b }
273 fn main() {
274 let _x = foo(4, 4);
275 }"#,
276 );
277 assert_debug_snapshot!(analysis.inlay_hints(file_id, &InlayConfig{ type_hints: true, parameter_hints: false, max_length: None}).unwrap(), @r###"
278 [
279 InlayHint {
280 range: [97; 99),
281 kind: TypeHint,
282 label: "i32",
283 },
284 ]"###);
285 }
286 #[test]
210 fn default_generic_types_should_not_be_displayed() { 287 fn default_generic_types_should_not_be_displayed() {
211 let (analysis, file_id) = single_file( 288 let (analysis, file_id) = single_file(
212 r#" 289 r#"
@@ -221,7 +298,7 @@ fn main() {
221}"#, 298}"#,
222 ); 299 );
223 300
224 assert_debug_snapshot!(analysis.inlay_hints(file_id, None).unwrap(), @r###" 301 assert_debug_snapshot!(analysis.inlay_hints(file_id, &InlayConfig::default()).unwrap(), @r###"
225 [ 302 [
226 InlayHint { 303 InlayHint {
227 range: [69; 71), 304 range: [69; 71),
@@ -278,7 +355,7 @@ fn main() {
278}"#, 355}"#,
279 ); 356 );
280 357
281 assert_debug_snapshot!(analysis.inlay_hints(file_id, None).unwrap(), @r###" 358 assert_debug_snapshot!(analysis.inlay_hints(file_id, &InlayConfig::default()).unwrap(), @r###"
282 [ 359 [
283 InlayHint { 360 InlayHint {
284 range: [193; 197), 361 range: [193; 197),
@@ -358,7 +435,7 @@ fn main() {
358}"#, 435}"#,
359 ); 436 );
360 437
361 assert_debug_snapshot!(analysis.inlay_hints(file_id, None).unwrap(), @r###" 438 assert_debug_snapshot!(analysis.inlay_hints(file_id, &InlayConfig::default()).unwrap(), @r###"
362 [ 439 [
363 InlayHint { 440 InlayHint {
364 range: [21; 30), 441 range: [21; 30),
@@ -422,7 +499,7 @@ fn main() {
422}"#, 499}"#,
423 ); 500 );
424 501
425 assert_debug_snapshot!(analysis.inlay_hints(file_id, None).unwrap(), @r###" 502 assert_debug_snapshot!(analysis.inlay_hints(file_id, &InlayConfig::default()).unwrap(), @r###"
426 [ 503 [
427 InlayHint { 504 InlayHint {
428 range: [21; 30), 505 range: [21; 30),
@@ -472,7 +549,7 @@ fn main() {
472}"#, 549}"#,
473 ); 550 );
474 551
475 assert_debug_snapshot!(analysis.inlay_hints(file_id, None).unwrap(), @r###" 552 assert_debug_snapshot!(analysis.inlay_hints(file_id, &InlayConfig::default()).unwrap(), @r###"
476 [ 553 [
477 InlayHint { 554 InlayHint {
478 range: [188; 192), 555 range: [188; 192),
@@ -567,7 +644,7 @@ fn main() {
567}"#, 644}"#,
568 ); 645 );
569 646
570 assert_debug_snapshot!(analysis.inlay_hints(file_id, None).unwrap(), @r###" 647 assert_debug_snapshot!(analysis.inlay_hints(file_id, &InlayConfig::default()).unwrap(), @r###"
571 [ 648 [
572 InlayHint { 649 InlayHint {
573 range: [188; 192), 650 range: [188; 192),
@@ -662,7 +739,7 @@ fn main() {
662}"#, 739}"#,
663 ); 740 );
664 741
665 assert_debug_snapshot!(analysis.inlay_hints(file_id, None).unwrap(), @r###" 742 assert_debug_snapshot!(analysis.inlay_hints(file_id, &InlayConfig::default()).unwrap(), @r###"
666 [ 743 [
667 InlayHint { 744 InlayHint {
668 range: [252; 256), 745 range: [252; 256),
@@ -734,7 +811,7 @@ fn main() {
734}"#, 811}"#,
735 ); 812 );
736 813
737 assert_debug_snapshot!(analysis.inlay_hints(file_id, Some(8)).unwrap(), @r###" 814 assert_debug_snapshot!(analysis.inlay_hints(file_id, &InlayConfig { max_length: Some(8), ..Default::default() }).unwrap(), @r###"
738 [ 815 [
739 InlayHint { 816 InlayHint {
740 range: [74; 75), 817 range: [74; 75),
@@ -822,7 +899,7 @@ fn main() {
822}"#, 899}"#,
823 ); 900 );
824 901
825 assert_debug_snapshot!(analysis.inlay_hints(file_id, None).unwrap(), @r###" 902 assert_debug_snapshot!(analysis.inlay_hints(file_id, &InlayConfig::default()).unwrap(), @r###"
826 [ 903 [
827 InlayHint { 904 InlayHint {
828 range: [798; 809), 905 range: [798; 809),
@@ -944,7 +1021,7 @@ fn main() {
944}"#, 1021}"#,
945 ); 1022 );
946 1023
947 assert_debug_snapshot!(analysis.inlay_hints(file_id, Some(8)).unwrap(), @r###" 1024 assert_debug_snapshot!(analysis.inlay_hints(file_id, &InlayConfig { max_length: Some(8), ..Default::default() }).unwrap(), @r###"
948 [] 1025 []
949 "### 1026 "###
950 ); 1027 );
@@ -970,7 +1047,7 @@ fn main() {
970}"#, 1047}"#,
971 ); 1048 );
972 1049
973 assert_debug_snapshot!(analysis.inlay_hints(file_id, Some(8)).unwrap(), @r###" 1050 assert_debug_snapshot!(analysis.inlay_hints(file_id, &InlayConfig { max_length: Some(8), ..Default::default() }).unwrap(), @r###"
974 [] 1051 []
975 "### 1052 "###
976 ); 1053 );
diff --git a/crates/ra_ide/src/lib.rs b/crates/ra_ide/src/lib.rs
index 015fae195..922e4caa8 100644
--- a/crates/ra_ide/src/lib.rs
+++ b/crates/ra_ide/src/lib.rs
@@ -68,7 +68,7 @@ pub use crate::{
68 expand_macro::ExpandedMacro, 68 expand_macro::ExpandedMacro,
69 folding_ranges::{Fold, FoldKind}, 69 folding_ranges::{Fold, FoldKind},
70 hover::HoverResult, 70 hover::HoverResult,
71 inlay_hints::{InlayHint, InlayKind}, 71 inlay_hints::{InlayConfig, InlayHint, InlayKind},
72 references::{Declaration, Reference, ReferenceAccess, ReferenceKind, ReferenceSearchResult}, 72 references::{Declaration, Reference, ReferenceAccess, ReferenceKind, ReferenceSearchResult},
73 runnables::{Runnable, RunnableKind, TestId}, 73 runnables::{Runnable, RunnableKind, TestId},
74 source_change::{FileSystemEdit, SourceChange, SourceFileEdit}, 74 source_change::{FileSystemEdit, SourceChange, SourceFileEdit},
@@ -319,9 +319,9 @@ impl Analysis {
319 pub fn inlay_hints( 319 pub fn inlay_hints(
320 &self, 320 &self,
321 file_id: FileId, 321 file_id: FileId,
322 max_inlay_hint_length: Option<usize>, 322 inlay_hint_opts: &InlayConfig,
323 ) -> Cancelable<Vec<InlayHint>> { 323 ) -> Cancelable<Vec<InlayHint>> {
324 self.with_db(|db| inlay_hints::inlay_hints(db, file_id, max_inlay_hint_length)) 324 self.with_db(|db| inlay_hints::inlay_hints(db, file_id, inlay_hint_opts))
325 } 325 }
326 326
327 /// Returns the set of folding ranges. 327 /// Returns the set of folding ranges.
diff --git a/crates/rust-analyzer/src/config.rs b/crates/rust-analyzer/src/config.rs
index a8bf29ddf..bd5904db0 100644
--- a/crates/rust-analyzer/src/config.rs
+++ b/crates/rust-analyzer/src/config.rs
@@ -7,6 +7,8 @@
7//! configure the server itself, feature flags are passed into analysis, and 7//! configure the server itself, feature flags are passed into analysis, and
8//! tweak things like automatic insertion of `()` in completions. 8//! tweak things like automatic insertion of `()` in completions.
9 9
10use crate::req::InlayConfigDef;
11use ra_ide::InlayConfig;
10use rustc_hash::FxHashMap; 12use rustc_hash::FxHashMap;
11 13
12use ra_project_model::CargoFeatures; 14use ra_project_model::CargoFeatures;
@@ -30,7 +32,8 @@ pub struct ServerConfig {
30 32
31 pub lru_capacity: Option<usize>, 33 pub lru_capacity: Option<usize>,
32 34
33 pub max_inlay_hint_length: Option<usize>, 35 #[serde(with = "InlayConfigDef")]
36 pub inlay_hints: InlayConfig,
34 37
35 pub cargo_watch_enable: bool, 38 pub cargo_watch_enable: bool,
36 pub cargo_watch_args: Vec<String>, 39 pub cargo_watch_args: Vec<String>,
@@ -60,7 +63,7 @@ impl Default for ServerConfig {
60 exclude_globs: Vec::new(), 63 exclude_globs: Vec::new(),
61 use_client_watching: false, 64 use_client_watching: false,
62 lru_capacity: None, 65 lru_capacity: None,
63 max_inlay_hint_length: None, 66 inlay_hints: Default::default(),
64 cargo_watch_enable: true, 67 cargo_watch_enable: true,
65 cargo_watch_args: Vec::new(), 68 cargo_watch_args: Vec::new(),
66 cargo_watch_command: "check".to_string(), 69 cargo_watch_command: "check".to_string(),
diff --git a/crates/rust-analyzer/src/main_loop.rs b/crates/rust-analyzer/src/main_loop.rs
index 4f7aac754..495056da3 100644
--- a/crates/rust-analyzer/src/main_loop.rs
+++ b/crates/rust-analyzer/src/main_loop.rs
@@ -177,7 +177,7 @@ pub fn main_loop(
177 .and_then(|it| it.folding_range.as_ref()) 177 .and_then(|it| it.folding_range.as_ref())
178 .and_then(|it| it.line_folding_only) 178 .and_then(|it| it.line_folding_only)
179 .unwrap_or(false), 179 .unwrap_or(false),
180 max_inlay_hint_length: config.max_inlay_hint_length, 180 inlay_hints: config.inlay_hints,
181 cargo_watch: CheckOptions { 181 cargo_watch: CheckOptions {
182 enable: config.cargo_watch_enable, 182 enable: config.cargo_watch_enable,
183 args: config.cargo_watch_args, 183 args: config.cargo_watch_args,
diff --git a/crates/rust-analyzer/src/main_loop/handlers.rs b/crates/rust-analyzer/src/main_loop/handlers.rs
index fcb40432d..921990da0 100644
--- a/crates/rust-analyzer/src/main_loop/handlers.rs
+++ b/crates/rust-analyzer/src/main_loop/handlers.rs
@@ -37,7 +37,7 @@ use crate::{
37 }, 37 },
38 diagnostics::DiagnosticTask, 38 diagnostics::DiagnosticTask,
39 from_json, 39 from_json,
40 req::{self, Decoration, InlayHint, InlayHintsParams, InlayKind}, 40 req::{self, Decoration, InlayHint, InlayHintsParams},
41 semantic_tokens::SemanticTokensBuilder, 41 semantic_tokens::SemanticTokensBuilder,
42 world::WorldSnapshot, 42 world::WorldSnapshot,
43 LspError, Result, 43 LspError, Result,
@@ -997,15 +997,12 @@ pub fn handle_inlay_hints(
997 let analysis = world.analysis(); 997 let analysis = world.analysis();
998 let line_index = analysis.file_line_index(file_id)?; 998 let line_index = analysis.file_line_index(file_id)?;
999 Ok(analysis 999 Ok(analysis
1000 .inlay_hints(file_id, world.options.max_inlay_hint_length)? 1000 .inlay_hints(file_id, &world.options.inlay_hints)?
1001 .into_iter() 1001 .into_iter()
1002 .map(|api_type| InlayHint { 1002 .map(|api_type| InlayHint {
1003 label: api_type.label.to_string(), 1003 label: api_type.label.to_string(),
1004 range: api_type.range.conv_with(&line_index), 1004 range: api_type.range.conv_with(&line_index),
1005 kind: match api_type.kind { 1005 kind: api_type.kind,
1006 ra_ide::InlayKind::TypeHint => InlayKind::TypeHint,
1007 ra_ide::InlayKind::ParameterHint => InlayKind::ParameterHint,
1008 },
1009 }) 1006 })
1010 .collect()) 1007 .collect())
1011} 1008}
diff --git a/crates/rust-analyzer/src/req.rs b/crates/rust-analyzer/src/req.rs
index a3efe3b9f..1dcab2703 100644
--- a/crates/rust-analyzer/src/req.rs
+++ b/crates/rust-analyzer/src/req.rs
@@ -4,6 +4,8 @@ use lsp_types::{Location, Position, Range, TextDocumentIdentifier, Url};
4use rustc_hash::FxHashMap; 4use rustc_hash::FxHashMap;
5use serde::{Deserialize, Serialize}; 5use serde::{Deserialize, Serialize};
6 6
7use ra_ide::{InlayConfig, InlayKind};
8
7pub use lsp_types::{ 9pub use lsp_types::{
8 notification::*, request::*, ApplyWorkspaceEditParams, CodeActionParams, CodeLens, 10 notification::*, request::*, ApplyWorkspaceEditParams, CodeActionParams, CodeLens,
9 CodeLensParams, CompletionParams, CompletionResponse, DiagnosticTag, 11 CodeLensParams, CompletionParams, CompletionResponse, DiagnosticTag,
@@ -196,14 +198,24 @@ pub struct InlayHintsParams {
196} 198}
197 199
198#[derive(Debug, PartialEq, Eq, Deserialize, Serialize)] 200#[derive(Debug, PartialEq, Eq, Deserialize, Serialize)]
199pub enum InlayKind { 201#[serde(remote = "InlayKind")]
202pub enum InlayKindDef {
200 TypeHint, 203 TypeHint,
201 ParameterHint, 204 ParameterHint,
202} 205}
203 206
207#[derive(Deserialize)]
208#[serde(remote = "InlayConfig", rename_all = "camelCase")]
209pub struct InlayConfigDef {
210 pub type_hints: bool,
211 pub parameter_hints: bool,
212 pub max_length: Option<usize>,
213}
214
204#[derive(Debug, Deserialize, Serialize)] 215#[derive(Debug, Deserialize, Serialize)]
205pub struct InlayHint { 216pub struct InlayHint {
206 pub range: Range, 217 pub range: Range,
218 #[serde(with = "InlayKindDef")]
207 pub kind: InlayKind, 219 pub kind: InlayKind,
208 pub label: String, 220 pub label: String,
209} 221}
diff --git a/crates/rust-analyzer/src/world.rs b/crates/rust-analyzer/src/world.rs
index 9ef368529..d358f6b47 100644
--- a/crates/rust-analyzer/src/world.rs
+++ b/crates/rust-analyzer/src/world.rs
@@ -13,7 +13,8 @@ use lsp_types::Url;
13use parking_lot::RwLock; 13use parking_lot::RwLock;
14use ra_cargo_watch::{url_from_path_with_drive_lowercasing, CheckOptions, CheckWatcher}; 14use ra_cargo_watch::{url_from_path_with_drive_lowercasing, CheckOptions, CheckWatcher};
15use ra_ide::{ 15use ra_ide::{
16 Analysis, AnalysisChange, AnalysisHost, CrateGraph, FileId, LibraryData, SourceRootId, 16 Analysis, AnalysisChange, AnalysisHost, CrateGraph, FileId, InlayConfig, LibraryData,
17 SourceRootId,
17}; 18};
18use ra_project_model::{get_rustc_cfg_options, ProjectWorkspace}; 19use ra_project_model::{get_rustc_cfg_options, ProjectWorkspace};
19use ra_vfs::{LineEndings, RootEntry, Vfs, VfsChange, VfsFile, VfsRoot, VfsTask, Watch}; 20use ra_vfs::{LineEndings, RootEntry, Vfs, VfsChange, VfsFile, VfsRoot, VfsTask, Watch};
@@ -34,7 +35,7 @@ pub struct Options {
34 pub publish_decorations: bool, 35 pub publish_decorations: bool,
35 pub supports_location_link: bool, 36 pub supports_location_link: bool,
36 pub line_folding_only: bool, 37 pub line_folding_only: bool,
37 pub max_inlay_hint_length: Option<usize>, 38 pub inlay_hints: InlayConfig,
38 pub rustfmt_args: Vec<String>, 39 pub rustfmt_args: Vec<String>,
39 pub cargo_watch: CheckOptions, 40 pub cargo_watch: CheckOptions,
40} 41}
diff --git a/docs/user/features.md b/docs/user/features.md
index ba4d50fa8..06bc7ded5 100644
--- a/docs/user/features.md
+++ b/docs/user/features.md
@@ -191,8 +191,8 @@ Two types of inlay hints are displayed currently:
191 191
192In VS Code, the following settings can be used to configure the inlay hints: 192In VS Code, the following settings can be used to configure the inlay hints:
193 193
194* `rust-analyzer.displayInlayHints` — toggles inlay hints display on or off 194* `rust-analyzer.inlayHintOpts.displayType` configure which types of inlay hints are shown.
195* `rust-analyzer.maxInlayHintLength` — shortens the hints if their length exceeds the value specified. If no value is specified (`null`), no shortening is applied. 195* `rust-analyzer.inlayHintOpts.maxLength` — shortens the hints if their length exceeds the value specified. If no value is specified (`null`), no shortening is applied.
196 196
197**Note:** VS Code does not have native support for inlay hints [yet](https://github.com/microsoft/vscode/issues/16221) and the hints are implemented using decorations. 197**Note:** VS Code does not have native support for inlay hints [yet](https://github.com/microsoft/vscode/issues/16221) and the hints are implemented using decorations.
198This approach has limitations, the caret movement and bracket highlighting near the edges of the hint may be weird: 198This approach has limitations, the caret movement and bracket highlighting near the edges of the hint may be weird:
diff --git a/editors/code/package.json b/editors/code/package.json
index 09dfc404d..3aaae357a 100644
--- a/editors/code/package.json
+++ b/editors/code/package.json
@@ -312,12 +312,17 @@
312 "exclusiveMinimum": true, 312 "exclusiveMinimum": true,
313 "description": "Number of syntax trees rust-analyzer keeps in memory" 313 "description": "Number of syntax trees rust-analyzer keeps in memory"
314 }, 314 },
315 "rust-analyzer.displayInlayHints": { 315 "rust-analyzer.inlayHints.typeHints": {
316 "type": "boolean", 316 "type": "boolean",
317 "default": true, 317 "default": true,
318 "description": "Display additional type and parameter information in the editor" 318 "description": "Whether to show inlay type hints"
319 }, 319 },
320 "rust-analyzer.maxInlayHintLength": { 320 "rust-analyzer.inlayHints.parameterHints": {
321 "type": "boolean",
322 "default": true,
323 "description": "Whether to show function parameter name inlay hints at the call site"
324 },
325 "rust-analyzer.inlayHints.maxLength": {
321 "type": [ 326 "type": [
322 "null", 327 "null",
323 "integer" 328 "integer"
diff --git a/editors/code/src/client.ts b/editors/code/src/client.ts
index 6ce3b9235..e9f261c24 100644
--- a/editors/code/src/client.ts
+++ b/editors/code/src/client.ts
@@ -29,7 +29,7 @@ export async function createClient(config: Config, serverPath: string): Promise<
29 initializationOptions: { 29 initializationOptions: {
30 publishDecorations: !config.highlightingSemanticTokens, 30 publishDecorations: !config.highlightingSemanticTokens,
31 lruCapacity: config.lruCapacity, 31 lruCapacity: config.lruCapacity,
32 maxInlayHintLength: config.maxInlayHintLength, 32 inlayHints: config.inlayHints,
33 cargoWatchEnable: cargoWatchOpts.enable, 33 cargoWatchEnable: cargoWatchOpts.enable,
34 cargoWatchArgs: cargoWatchOpts.arguments, 34 cargoWatchArgs: cargoWatchOpts.arguments,
35 cargoWatchCommand: cargoWatchOpts.command, 35 cargoWatchCommand: cargoWatchOpts.command,
diff --git a/editors/code/src/config.ts b/editors/code/src/config.ts
index 3ade7e900..6db073bec 100644
--- a/editors/code/src/config.ts
+++ b/editors/code/src/config.ts
@@ -5,6 +5,12 @@ import { log } from "./util";
5 5
6const RA_LSP_DEBUG = process.env.__RA_LSP_SERVER_DEBUG; 6const RA_LSP_DEBUG = process.env.__RA_LSP_SERVER_DEBUG;
7 7
8export interface InlayHintOptions {
9 typeHints: boolean;
10 parameterHints: boolean;
11 maxLength: number | null;
12}
13
8export interface CargoWatchOptions { 14export interface CargoWatchOptions {
9 enable: boolean; 15 enable: boolean;
10 arguments: string[]; 16 arguments: string[];
@@ -22,7 +28,8 @@ export class Config {
22 private static readonly requiresReloadOpts = [ 28 private static readonly requiresReloadOpts = [
23 "cargoFeatures", 29 "cargoFeatures",
24 "cargo-watch", 30 "cargo-watch",
25 "highlighting.semanticTokens" 31 "highlighting.semanticTokens",
32 "inlayHints",
26 ] 33 ]
27 .map(opt => `${Config.rootSection}.${opt}`); 34 .map(opt => `${Config.rootSection}.${opt}`);
28 35
@@ -149,8 +156,13 @@ export class Config {
149 get highlightingOn() { return this.cfg.get("highlightingOn") as boolean; } 156 get highlightingOn() { return this.cfg.get("highlightingOn") as boolean; }
150 get rainbowHighlightingOn() { return this.cfg.get("rainbowHighlightingOn") as boolean; } 157 get rainbowHighlightingOn() { return this.cfg.get("rainbowHighlightingOn") as boolean; }
151 get lruCapacity() { return this.cfg.get("lruCapacity") as null | number; } 158 get lruCapacity() { return this.cfg.get("lruCapacity") as null | number; }
152 get displayInlayHints() { return this.cfg.get("displayInlayHints") as boolean; } 159 get inlayHints(): InlayHintOptions {
153 get maxInlayHintLength() { return this.cfg.get("maxInlayHintLength") as number; } 160 return {
161 typeHints: this.cfg.get("inlayHints.typeHints") as boolean,
162 parameterHints: this.cfg.get("inlayHints.parameterHints") as boolean,
163 maxLength: this.cfg.get("inlayHints.maxLength") as null | number,
164 };
165 }
154 get excludeGlobs() { return this.cfg.get("excludeGlobs") as string[]; } 166 get excludeGlobs() { return this.cfg.get("excludeGlobs") as string[]; }
155 get useClientWatching() { return this.cfg.get("useClientWatching") as boolean; } 167 get useClientWatching() { return this.cfg.get("useClientWatching") as boolean; }
156 get featureFlags() { return this.cfg.get("featureFlags") as Record<string, boolean>; } 168 get featureFlags() { return this.cfg.get("featureFlags") as Record<string, boolean>; }
diff --git a/editors/code/src/inlay_hints.ts b/editors/code/src/inlay_hints.ts
index e1a82e03e..b19b09ad5 100644
--- a/editors/code/src/inlay_hints.ts
+++ b/editors/code/src/inlay_hints.ts
@@ -10,7 +10,7 @@ export function activateInlayHints(ctx: Ctx) {
10 const maybeUpdater = { 10 const maybeUpdater = {
11 updater: null as null | HintsUpdater, 11 updater: null as null | HintsUpdater,
12 onConfigChange() { 12 onConfigChange() {
13 if (!ctx.config.displayInlayHints) { 13 if (!ctx.config.inlayHints.typeHints && !ctx.config.inlayHints.parameterHints) {
14 return this.dispose(); 14 return this.dispose();
15 } 15 }
16 if (!this.updater) this.updater = new HintsUpdater(ctx); 16 if (!this.updater) this.updater = new HintsUpdater(ctx);