diff options
-rw-r--r-- | crates/assists/src/handlers/fill_match_arms.rs | 2 | ||||
-rw-r--r-- | crates/assists/src/handlers/generate_from_impl_for_enum.rs | 2 | ||||
-rw-r--r-- | crates/assists/src/utils.rs | 25 | ||||
-rw-r--r-- | crates/ide/src/inlay_hints.rs | 19 |
4 files changed, 29 insertions, 19 deletions
diff --git a/crates/assists/src/handlers/fill_match_arms.rs b/crates/assists/src/handlers/fill_match_arms.rs index 676f5ad92..eda45f5b3 100644 --- a/crates/assists/src/handlers/fill_match_arms.rs +++ b/crates/assists/src/handlers/fill_match_arms.rs | |||
@@ -59,7 +59,7 @@ pub(crate) fn fill_match_arms(acc: &mut Assists, ctx: &AssistContext) -> Option< | |||
59 | .filter(|variant_pat| is_variant_missing(&mut arms, variant_pat)) | 59 | .filter(|variant_pat| is_variant_missing(&mut arms, variant_pat)) |
60 | .map(|pat| make::match_arm(iter::once(pat), make::expr_empty_block())) | 60 | .map(|pat| make::match_arm(iter::once(pat), make::expr_empty_block())) |
61 | .collect::<Vec<_>>(); | 61 | .collect::<Vec<_>>(); |
62 | if Some(enum_def) == FamousDefs(&ctx.sema, module.krate()).core_option_Option() { | 62 | if Some(enum_def) == FamousDefs(&ctx.sema, Some(module.krate())).core_option_Option() { |
63 | // Match `Some` variant first. | 63 | // Match `Some` variant first. |
64 | mark::hit!(option_order); | 64 | mark::hit!(option_order); |
65 | variants.reverse() | 65 | variants.reverse() |
diff --git a/crates/assists/src/handlers/generate_from_impl_for_enum.rs b/crates/assists/src/handlers/generate_from_impl_for_enum.rs index 7f04b9572..674e5a175 100644 --- a/crates/assists/src/handlers/generate_from_impl_for_enum.rs +++ b/crates/assists/src/handlers/generate_from_impl_for_enum.rs | |||
@@ -75,7 +75,7 @@ fn existing_from_impl( | |||
75 | let enum_ = variant.parent_enum(sema.db); | 75 | let enum_ = variant.parent_enum(sema.db); |
76 | let krate = enum_.module(sema.db).krate(); | 76 | let krate = enum_.module(sema.db).krate(); |
77 | 77 | ||
78 | let from_trait = FamousDefs(sema, krate).core_convert_From()?; | 78 | let from_trait = FamousDefs(sema, Some(krate)).core_convert_From()?; |
79 | 79 | ||
80 | let enum_type = enum_.ty(sema.db); | 80 | let enum_type = enum_.ty(sema.db); |
81 | 81 | ||
diff --git a/crates/assists/src/utils.rs b/crates/assists/src/utils.rs index 4e89a7aed..1a6b48b45 100644 --- a/crates/assists/src/utils.rs +++ b/crates/assists/src/utils.rs | |||
@@ -275,7 +275,7 @@ impl TryEnum { | |||
275 | /// somewhat similar to the known paths infra inside hir, but it different; We | 275 | /// somewhat similar to the known paths infra inside hir, but it different; We |
276 | /// want to make sure that IDE specific paths don't become interesting inside | 276 | /// want to make sure that IDE specific paths don't become interesting inside |
277 | /// the compiler itself as well. | 277 | /// the compiler itself as well. |
278 | pub struct FamousDefs<'a, 'b>(pub &'a Semantics<'b, RootDatabase>, pub Crate); | 278 | pub struct FamousDefs<'a, 'b>(pub &'a Semantics<'b, RootDatabase>, pub Option<Crate>); |
279 | 279 | ||
280 | #[allow(non_snake_case)] | 280 | #[allow(non_snake_case)] |
281 | impl FamousDefs<'_, '_> { | 281 | impl FamousDefs<'_, '_> { |
@@ -362,6 +362,10 @@ pub mod prelude { | |||
362 | pub use prelude::*; | 362 | pub use prelude::*; |
363 | "#; | 363 | "#; |
364 | 364 | ||
365 | pub fn core(&self) -> Option<Crate> { | ||
366 | self.find_crate("core") | ||
367 | } | ||
368 | |||
365 | pub(crate) fn core_convert_From(&self) -> Option<Trait> { | 369 | pub(crate) fn core_convert_From(&self) -> Option<Trait> { |
366 | self.find_trait("core:convert:From") | 370 | self.find_trait("core:convert:From") |
367 | } | 371 | } |
@@ -399,21 +403,20 @@ pub use prelude::*; | |||
399 | } | 403 | } |
400 | } | 404 | } |
401 | 405 | ||
406 | fn find_crate(&self, name: &str) -> Option<Crate> { | ||
407 | let krate = self.1?; | ||
408 | let db = self.0.db; | ||
409 | let res = | ||
410 | krate.dependencies(db).into_iter().find(|dep| dep.name.to_string() == name)?.krate; | ||
411 | Some(res) | ||
412 | } | ||
413 | |||
402 | fn find_def(&self, path: &str) -> Option<ScopeDef> { | 414 | fn find_def(&self, path: &str) -> Option<ScopeDef> { |
403 | let db = self.0.db; | 415 | let db = self.0.db; |
404 | let mut path = path.split(':'); | 416 | let mut path = path.split(':'); |
405 | let trait_ = path.next_back()?; | 417 | let trait_ = path.next_back()?; |
406 | let std_crate = path.next()?; | 418 | let std_crate = path.next()?; |
407 | let std_crate = if self | 419 | let std_crate = self.find_crate(std_crate)?; |
408 | .1 | ||
409 | .display_name(db) | ||
410 | .map(|name| name.to_string() == std_crate) | ||
411 | .unwrap_or(false) | ||
412 | { | ||
413 | self.1 | ||
414 | } else { | ||
415 | self.1.dependencies(db).into_iter().find(|dep| dep.name.to_string() == std_crate)?.krate | ||
416 | }; | ||
417 | let mut module = std_crate.root_module(db); | 420 | let mut module = std_crate.root_module(db); |
418 | for segment in path { | 421 | for segment in path { |
419 | module = module.children(db).find_map(|child| { | 422 | module = module.children(db).find_map(|child| { |
diff --git a/crates/ide/src/inlay_hints.rs b/crates/ide/src/inlay_hints.rs index 56b985e80..cccea129a 100644 --- a/crates/ide/src/inlay_hints.rs +++ b/crates/ide/src/inlay_hints.rs | |||
@@ -99,6 +99,9 @@ fn get_chaining_hints( | |||
99 | return None; | 99 | return None; |
100 | } | 100 | } |
101 | 101 | ||
102 | let krate = sema.scope(expr.syntax()).module().map(|it| it.krate()); | ||
103 | let famous_defs = FamousDefs(&sema, krate); | ||
104 | |||
102 | let mut tokens = expr | 105 | let mut tokens = expr |
103 | .syntax() | 106 | .syntax() |
104 | .siblings_with_tokens(Direction::Next) | 107 | .siblings_with_tokens(Direction::Next) |
@@ -128,7 +131,7 @@ fn get_chaining_hints( | |||
128 | acc.push(InlayHint { | 131 | acc.push(InlayHint { |
129 | range: expr.syntax().text_range(), | 132 | range: expr.syntax().text_range(), |
130 | kind: InlayKind::ChainingHint, | 133 | kind: InlayKind::ChainingHint, |
131 | label: hint_iterator(sema, config, &ty).unwrap_or_else(|| { | 134 | label: hint_iterator(sema, &famous_defs, config, &ty).unwrap_or_else(|| { |
132 | ty.display_truncated(sema.db, config.max_length).to_string().into() | 135 | ty.display_truncated(sema.db, config.max_length).to_string().into() |
133 | }), | 136 | }), |
134 | }); | 137 | }); |
@@ -188,6 +191,9 @@ fn get_bind_pat_hints( | |||
188 | return None; | 191 | return None; |
189 | } | 192 | } |
190 | 193 | ||
194 | let krate = sema.scope(pat.syntax()).module().map(|it| it.krate()); | ||
195 | let famous_defs = FamousDefs(&sema, krate); | ||
196 | |||
191 | let ty = sema.type_of_pat(&pat.clone().into())?; | 197 | let ty = sema.type_of_pat(&pat.clone().into())?; |
192 | 198 | ||
193 | if should_not_display_type_hint(sema, &pat, &ty) { | 199 | if should_not_display_type_hint(sema, &pat, &ty) { |
@@ -196,7 +202,7 @@ fn get_bind_pat_hints( | |||
196 | acc.push(InlayHint { | 202 | acc.push(InlayHint { |
197 | range: pat.syntax().text_range(), | 203 | range: pat.syntax().text_range(), |
198 | kind: InlayKind::TypeHint, | 204 | kind: InlayKind::TypeHint, |
199 | label: hint_iterator(sema, config, &ty) | 205 | label: hint_iterator(sema, &famous_defs, config, &ty) |
200 | .unwrap_or_else(|| ty.display_truncated(sema.db, config.max_length).to_string().into()), | 206 | .unwrap_or_else(|| ty.display_truncated(sema.db, config.max_length).to_string().into()), |
201 | }); | 207 | }); |
202 | 208 | ||
@@ -206,6 +212,7 @@ fn get_bind_pat_hints( | |||
206 | /// Checks if the type is an Iterator from std::iter and replaces its hint with an `impl Iterator<Item = Ty>`. | 212 | /// Checks if the type is an Iterator from std::iter and replaces its hint with an `impl Iterator<Item = Ty>`. |
207 | fn hint_iterator( | 213 | fn hint_iterator( |
208 | sema: &Semantics<RootDatabase>, | 214 | sema: &Semantics<RootDatabase>, |
215 | famous_defs: &FamousDefs, | ||
209 | config: &InlayHintsConfig, | 216 | config: &InlayHintsConfig, |
210 | ty: &hir::Type, | 217 | ty: &hir::Type, |
211 | ) -> Option<SmolStr> { | 218 | ) -> Option<SmolStr> { |
@@ -214,11 +221,11 @@ fn hint_iterator( | |||
214 | .last() | 221 | .last() |
215 | .and_then(|strukt| strukt.as_adt())?; | 222 | .and_then(|strukt| strukt.as_adt())?; |
216 | let krate = strukt.krate(db)?; | 223 | let krate = strukt.krate(db)?; |
217 | if krate.display_name(db).as_deref() != Some("core") { | 224 | if krate != famous_defs.core()? { |
218 | return None; | 225 | return None; |
219 | } | 226 | } |
220 | let iter_trait = FamousDefs(sema, krate).core_iter_Iterator()?; | 227 | let iter_trait = famous_defs.core_iter_Iterator()?; |
221 | let iter_mod = FamousDefs(sema, krate).core_iter()?; | 228 | let iter_mod = famous_defs.core_iter()?; |
222 | // assert this struct comes from `core::iter` | 229 | // assert this struct comes from `core::iter` |
223 | iter_mod.visibility_of(db, &strukt.into()).filter(|&vis| vis == hir::Visibility::Public)?; | 230 | iter_mod.visibility_of(db, &strukt.into()).filter(|&vis| vis == hir::Visibility::Public)?; |
224 | if ty.impls_trait(db, iter_trait, &[]) { | 231 | if ty.impls_trait(db, iter_trait, &[]) { |
@@ -230,7 +237,7 @@ fn hint_iterator( | |||
230 | const LABEL_START: &str = "impl Iterator<Item = "; | 237 | const LABEL_START: &str = "impl Iterator<Item = "; |
231 | const LABEL_END: &str = ">"; | 238 | const LABEL_END: &str = ">"; |
232 | 239 | ||
233 | let ty_display = hint_iterator(sema, config, &ty) | 240 | let ty_display = hint_iterator(sema, famous_defs, config, &ty) |
234 | .map(|assoc_type_impl| assoc_type_impl.to_string()) | 241 | .map(|assoc_type_impl| assoc_type_impl.to_string()) |
235 | .unwrap_or_else(|| { | 242 | .unwrap_or_else(|| { |
236 | ty.display_truncated( | 243 | ty.display_truncated( |