Unnamed repository; edit this file 'description' to name the repository.
Diffstat (limited to 'crates/ide/src/inlay_hints/closure_ret.rs')
| -rw-r--r-- | crates/ide/src/inlay_hints/closure_ret.rs | 56 |
1 files changed, 47 insertions, 9 deletions
diff --git a/crates/ide/src/inlay_hints/closure_ret.rs b/crates/ide/src/inlay_hints/closure_ret.rs index 6214e9c8e7..3b41db0f13 100644 --- a/crates/ide/src/inlay_hints/closure_ret.rs +++ b/crates/ide/src/inlay_hints/closure_ret.rs @@ -6,7 +6,7 @@ use syntax::ast::{self, AstNode}; use crate::{ inlay_hints::{closure_has_block_body, label_of_ty, ty_to_text_edit}, - ClosureReturnTypeHints, InlayHint, InlayHintsConfig, InlayKind, + ClosureReturnTypeHints, InlayHint, InlayHintPosition, InlayHintsConfig, InlayKind, }; pub(super) fn hints( @@ -20,9 +20,12 @@ pub(super) fn hints( return None; } - if closure.ret_type().is_some() { - return None; - } + let ret_type = closure.ret_type().map(|rt| (rt.thin_arrow_token(), rt.ty().is_some())); + let arrow = match ret_type { + Some((_, true)) => return None, + Some((arrow, _)) => arrow, + None => None, + }; let has_block_body = closure_has_block_body(&closure); if !has_block_body && config.closure_return_type_hints == ClosureReturnTypeHints::WithBlock { @@ -35,18 +38,26 @@ pub(super) fn hints( let ty = sema.type_of_expr(&ast::Expr::ClosureExpr(closure.clone()))?.adjusted(); let callable = ty.as_callable(sema.db)?; let ty = callable.return_type(); - if ty.is_unit() { + if arrow.is_none() && ty.is_unit() { return None; } + let mut label = label_of_ty(famous_defs, config, &ty)?; + + if arrow.is_none() { + label.prepend_str(" -> "); + } // FIXME?: We could provide text edit to insert braces for closures with non-block body. let text_edit = if has_block_body { ty_to_text_edit( sema, closure.syntax(), &ty, - param_list.syntax().text_range().end(), - String::from(" -> "), + arrow + .as_ref() + .map_or_else(|| param_list.syntax().text_range(), |t| t.text_range()) + .end(), + if arrow.is_none() { String::from(" -> ") } else { String::new() }, ) } else { None @@ -54,9 +65,36 @@ pub(super) fn hints( acc.push(InlayHint { range: param_list.syntax().text_range(), - kind: InlayKind::ClosureReturnType, - label: label_of_ty(famous_defs, config, ty)?, + kind: InlayKind::Type, + label, text_edit, + position: InlayHintPosition::After, + pad_left: false, + pad_right: false, }); Some(()) } + +#[cfg(test)] +mod tests { + use crate::inlay_hints::tests::{check_with_config, DISABLED_CONFIG}; + + use super::*; + + #[test] + fn return_type_hints_for_closure_without_block() { + check_with_config( + InlayHintsConfig { + closure_return_type_hints: ClosureReturnTypeHints::Always, + ..DISABLED_CONFIG + }, + r#" +fn main() { + let a = || { 0 }; + //^^ -> i32 + let b = || 0; + //^^ -> i32 +}"#, + ); + } +} |