@@ -198,28 +198,69 @@ fn get_bind_pat_hints(
198
198
199
199
let descended = sema. descend_node_into_attributes ( pat. clone ( ) ) . pop ( ) ;
200
200
let desc_pat = descended. as_ref ( ) . unwrap_or ( pat) ;
201
- let krate = sema. scope ( desc_pat. syntax ( ) ) . module ( ) . map ( |it| it. krate ( ) ) ;
202
- let famous_defs = FamousDefs ( sema, krate) ;
203
-
204
201
let ty = sema. type_of_pat ( & desc_pat. clone ( ) . into ( ) ) ?. original ;
205
202
206
203
if should_not_display_type_hint ( sema, & pat, & ty) {
207
204
return None ;
208
205
}
209
206
207
+ let krate = sema. scope ( desc_pat. syntax ( ) ) . module ( ) . map ( |it| it. krate ( ) ) ;
208
+ let famous_defs = FamousDefs ( sema, krate) ;
209
+ let label = hint_iterator ( sema, & famous_defs, config, & ty) ;
210
+
211
+ let label = match label {
212
+ Some ( label) => label,
213
+ None => {
214
+ let ty = ty. display_truncated ( sema. db , config. max_length ) . to_string ( ) ;
215
+ if Some ( & * ty) == get_constructor_name ( sema, pat) . as_deref ( ) {
216
+ return None ;
217
+ }
218
+ ty. into ( )
219
+ }
220
+ } ;
221
+
210
222
acc. push ( InlayHint {
211
223
range : match pat. name ( ) {
212
224
Some ( name) => name. syntax ( ) . text_range ( ) ,
213
225
None => pat. syntax ( ) . text_range ( ) ,
214
226
} ,
215
227
kind : InlayKind :: TypeHint ,
216
- label : hint_iterator ( sema, & famous_defs, config, & ty)
217
- . unwrap_or_else ( || ty. display_truncated ( sema. db , config. max_length ) . to_string ( ) . into ( ) ) ,
228
+ label,
218
229
} ) ;
219
230
220
231
Some ( ( ) )
221
232
}
222
233
234
+ fn get_constructor_name ( sema : & Semantics < RootDatabase > , pat : & ast:: IdentPat ) -> Option < String > {
235
+ let it = pat. syntax ( ) . parent ( ) ?;
236
+ let expr = match_ast ! {
237
+ match it {
238
+ ast:: LetStmt ( it) => it. initializer( ) ,
239
+ ast:: Condition ( it) => it. expr( ) ,
240
+ _ => None ,
241
+ }
242
+ } ;
243
+
244
+ if let Some ( expr) = expr {
245
+ let expr = sema. descend_node_into_attributes ( expr. clone ( ) ) . pop ( ) . unwrap_or ( expr) ;
246
+ let expr = match expr {
247
+ ast:: Expr :: TryExpr ( it) => it. expr ( ) ,
248
+ ast:: Expr :: AwaitExpr ( it) => it. expr ( ) ,
249
+ expr => Some ( expr) ,
250
+ } ?;
251
+ let path = match expr {
252
+ ast:: Expr :: CallExpr ( call) => match call. expr ( ) ? {
253
+ ast:: Expr :: PathExpr ( p) => p. path ( ) ,
254
+ _ => None ,
255
+ } ,
256
+ _ => None ,
257
+ } ?;
258
+ let seg = path. qualifier ( ) ?. segment ( ) ?;
259
+ return Some ( seg. to_string ( ) ) ;
260
+ }
261
+ None
262
+ }
263
+
223
264
/// Checks if the type is an Iterator from std::iter and replaces its hint with an `impl Iterator<Item = Ty>`.
224
265
fn hint_iterator (
225
266
sema : & Semantics < RootDatabase > ,
@@ -1234,6 +1275,51 @@ fn main() {
1234
1275
) ;
1235
1276
}
1236
1277
1278
+ #[ test]
1279
+ fn skip_constructor_type_hints ( ) {
1280
+ check_types (
1281
+ r#"
1282
+ //- minicore: try
1283
+ use core::ops::ControlFlow;
1284
+
1285
+ struct Struct;
1286
+ struct TupleStruct();
1287
+
1288
+ impl Struct {
1289
+ fn new() -> Self {
1290
+ Struct
1291
+ }
1292
+ fn try_new() -> ControlFlow<(), Self> {
1293
+ ControlFlow::Continue(Struct)
1294
+ }
1295
+ }
1296
+
1297
+ struct Generic<T>(T);
1298
+ impl Generic<i32> {
1299
+ fn new() -> Self {
1300
+ Generic(0)
1301
+ }
1302
+ }
1303
+
1304
+ fn main() {
1305
+ let strukt = Struct::new();
1306
+ let tuple_struct = TupleStruct();
1307
+ // ^^^^^^^^^^^^ TupleStruct
1308
+ let generic0 = Generic::new();
1309
+ // ^^^^^^^^ Generic<i32>
1310
+ let generic1 = Generic::<i32>::new();
1311
+ // ^^^^^^^^ Generic<i32>
1312
+ let generic2 = <Generic<i32>>::new();
1313
+ // ^^^^^^^^ Generic<i32>
1314
+ }
1315
+
1316
+ fn fallible() -> ControlFlow<()> {
1317
+ let strukt = Struct::try_new()?;
1318
+ }
1319
+ "# ,
1320
+ ) ;
1321
+ }
1322
+
1237
1323
#[ test]
1238
1324
fn closures ( ) {
1239
1325
check (
0 commit comments