@@ -40,13 +40,13 @@ trait TypesSupport:
40
40
41
41
private def keyword (str : String ): SignaturePart = Keyword (str)
42
42
43
- private def tpe (str : String , dri : DRI )(using inCC : Option [Unit ]): SignaturePart =
43
+ private def tpe (str : String , dri : DRI )(using inCC : Option [Any ]): SignaturePart =
44
44
if inCC.isDefined then
45
45
dotty.tools.scaladoc.Plain (str)
46
46
else
47
47
dotty.tools.scaladoc.Type (str, Some (dri))
48
48
49
- private def tpe (str : String )(using inCC : Option [Unit ]): SignaturePart =
49
+ private def tpe (str : String )(using inCC : Option [Any ]): SignaturePart =
50
50
if inCC.isDefined then
51
51
dotty.tools.scaladoc.Plain (str)
52
52
else
@@ -57,7 +57,7 @@ trait TypesSupport:
57
57
58
58
extension (on : SignaturePart ) def l : List [SignaturePart ] = List (on)
59
59
60
- private def tpe (using Quotes )(symbol : reflect.Symbol )(using inCC : Option [Unit ]): SSignature =
60
+ private def tpe (using Quotes )(symbol : reflect.Symbol )(using inCC : Option [Any ]): SSignature =
61
61
import SymOps ._
62
62
val dri : Option [DRI ] = Option (symbol).filterNot(_.isHiddenByVisibility).map(_.dri)
63
63
if inCC.isDefined then
@@ -105,9 +105,8 @@ trait TypesSupport:
105
105
originalOwner : reflect.Symbol ,
106
106
indent : Int = 0 ,
107
107
skipTypeSuffix : Boolean = false ,
108
- // inCC means in capture-checking context.
109
- // Somewhat hacky, because it should be a Boolean, but then it'd clash with skipTypeSuffix
110
- inCC : Option [Unit ] = None ,
108
+ // inCC means in capture-checking context. If defined, it carries the current capture-set contents.
109
+ inCC : Option [List [reflect.TypeRepr ]] = None ,
111
110
): SSignature =
112
111
import reflect ._
113
112
def noSupported (name : String ): SSignature =
@@ -122,15 +121,8 @@ trait TypesSupport:
122
121
inParens(inner(left, skipThisTypePrefix), shouldWrapInParens(left, tp, true ))
123
122
++ keyword(" & " ).l
124
123
++ inParens(inner(right, skipThisTypePrefix), shouldWrapInParens(right, tp, false ))
125
- case CapturingType (base, refs) =>
126
- inner(base, skipThisTypePrefix) ++ renderCapturing(refs)
127
124
case ByNameType (CapturingType (tpe, refs)) =>
128
- refs match
129
- case Nil => keyword(" -> " ) :: inner(tpe, skipThisTypePrefix)
130
- case List (ref) if ref.isCaptureRoot =>
131
- keyword(" => " ) :: inner(tpe, skipThisTypePrefix)
132
- case refs =>
133
- keyword(" ->" ) :: (renderCaptureSet(refs) ++ (plain(" " ) :: inner(tpe, skipThisTypePrefix)))
125
+ renderCaptureArrow(refs, skipThisTypePrefix) ++ (plain(" " ) :: inner(tpe, skipThisTypePrefix))
134
126
case ByNameType (tpe) => keyword(" =>!! " ) :: inner(tpe, skipThisTypePrefix) // FIXME: does it need change for CC?
135
127
case ConstantType (constant) =>
136
128
plain(constant.show).l
@@ -142,6 +134,10 @@ trait TypesSupport:
142
134
inner(tpe, skipThisTypePrefix) :+ plain(" *" )
143
135
case AppliedType (repeatedClass, Seq (tpe)) if isRepeated(repeatedClass) =>
144
136
inner(tpe, skipThisTypePrefix) :+ plain(" *" )
137
+ case CapturingType (base, refs) => base match
138
+ case t @ AppliedType (base, args) if t.isFunctionType =>
139
+ functionType(t, base, args, skipThisTypePrefix)(using inCC = Some (refs))
140
+ case _ => inner(base, skipThisTypePrefix) ++ renderCapturing(refs, skipThisTypePrefix)
145
141
case AnnotatedType (tpe, _) =>
146
142
inner(tpe, skipThisTypePrefix)
147
143
case tl @ TypeLambda (params, paramBounds, AppliedType (tpe, args))
@@ -258,19 +254,7 @@ trait TypesSupport:
258
254
++ plain(" " ).l
259
255
++ inParens(inner(rhs, skipThisTypePrefix), shouldWrapInParens(rhs, t, false ))
260
256
261
- case t @ AppliedType (tpe, args) if t.isFunctionType =>
262
- val arrow = if t.isContextFunctionType then " ?=> " else " => "
263
- args match
264
- case Nil => Nil
265
- case List (rtpe) => plain(" ()" ).l ++ keyword(arrow).l ++ inner(rtpe, skipThisTypePrefix)
266
- case List (arg, rtpe) =>
267
- val wrapInParens = stripAnnotated(arg) match
268
- case _ : TermRef | _ : TypeRef | _ : ConstantType | _ : ParamRef => false
269
- case at : AppliedType if ! isInfix(at) && ! at.isFunctionType && ! at.isTupleN => false
270
- case _ => true
271
- inParens(inner(arg, skipThisTypePrefix), wrapInParens) ++ keyword(arrow).l ++ inner(rtpe, skipThisTypePrefix)
272
- case _ =>
273
- plain(" (" ).l ++ commas(args.init.map(inner(_, skipThisTypePrefix))) ++ plain(" )" ).l ++ keyword(arrow).l ++ inner(args.last, skipThisTypePrefix)
257
+ case t @ AppliedType (tpe, args) if t.isFunctionType => functionType(t, tpe, args, skipThisTypePrefix)
274
258
275
259
case t @ AppliedType (tpe, typeList) =>
276
260
inner(tpe, skipThisTypePrefix) ++ plain(" [" ).l ++ commas(typeList.map { t => t match
@@ -358,6 +342,27 @@ trait TypesSupport:
358
342
s " ${tpe.show(using Printer .TypeReprStructure )}"
359
343
throw MatchError (msg)
360
344
345
+ private def functionType (using Quotes )(t : reflect.TypeRepr , tpe : reflect.TypeRepr , args : List [reflect.TypeRepr ], skipThisTypePrefix : Boolean )(using
346
+ elideThis : reflect.ClassDef ,
347
+ indent : Int ,
348
+ originalOwner : reflect.Symbol ,
349
+ inCC : Option [List [reflect.TypeRepr ]],
350
+ ): SSignature =
351
+ import reflect ._
352
+ val arrow = if t.isContextFunctionType then keyword(" ?=> " ).l // FIXME: can we have contextual functions with capture sets?
353
+ else plain(" " ) :: (renderCaptureArrow(inCC, skipThisTypePrefix) ++ plain(" " ).l)
354
+ args match
355
+ case Nil => Nil
356
+ case List (rtpe) => plain(" ()" ).l ++ arrow ++ inner(rtpe, skipThisTypePrefix)
357
+ case List (arg, rtpe) =>
358
+ val wrapInParens = stripAnnotated(arg) match
359
+ case _ : TermRef | _ : TypeRef | _ : ConstantType | _ : ParamRef => false
360
+ case at : AppliedType if ! isInfix(at) && ! at.isFunctionType && ! at.isTupleN => false
361
+ case _ => true
362
+ inParens(inner(arg, skipThisTypePrefix), wrapInParens) ++ arrow ++ inner(rtpe, skipThisTypePrefix)
363
+ case _ =>
364
+ plain(" (" ).l ++ commas(args.init.map(inner(_, skipThisTypePrefix))) ++ plain(" )" ).l ++ arrow ++ inner(args.last, skipThisTypePrefix)
365
+
361
366
private def typeBound (using Quotes )(t : reflect.TypeRepr , low : Boolean , skipThisTypePrefix : Boolean )(using elideThis : reflect.ClassDef , originalOwner : reflect.Symbol ) =
362
367
import reflect ._
363
368
val ignore = if (low) t.typeSymbol == defn.NothingClass else t.typeSymbol == defn.AnyClass
@@ -370,7 +375,7 @@ trait TypesSupport:
370
375
}
371
376
372
377
private def typeBoundsTreeOfHigherKindedType (using Quotes )(low : reflect.TypeRepr , high : reflect.TypeRepr , skipThisTypePrefix : Boolean )(
373
- using elideThis : reflect.ClassDef , originalOwner : reflect.Symbol , inCC : Option [Unit ]
378
+ using elideThis : reflect.ClassDef , originalOwner : reflect.Symbol , inCC : Option [List [reflect. TypeRepr ] ]
374
379
) =
375
380
import reflect ._
376
381
def regularTypeBounds (low : TypeRepr , high : TypeRepr ) =
@@ -464,25 +469,48 @@ trait TypesSupport:
464
469
case AnnotatedType (tr, _) => stripAnnotated(tr)
465
470
case other => other
466
471
467
- private def renderCapability (using Quotes )(ref : reflect.TypeRepr )(using elideThis : reflect.ClassDef ): List [SignaturePart ] =
472
+ private def renderCapability (using Quotes )(ref : reflect.TypeRepr , skipThisTypePrefix : Boolean )(
473
+ using elideThis : reflect.ClassDef , originalOwner : reflect.Symbol
474
+ ): SSignature =
468
475
import reflect ._
469
476
ref match
470
- case ReachCapability (c) => renderCapability(c) :+ Keyword (" *" )
477
+ case ReachCapability (c) => renderCapability(c, skipThisTypePrefix ) :+ Keyword (" *" )
471
478
case ThisType (_) => List (Keyword (" this" ))
472
- case t => inner(t)(using skipTypeSuffix = true , inCC = Some (() ))
479
+ case t => inner(t, skipThisTypePrefix )(using skipTypeSuffix = true , inCC = Some (Nil ))
473
480
474
- private def renderCaptureSet (using Quotes )(refs : List [reflect.TypeRepr ])(using elideThis : reflect.ClassDef ): List [SignaturePart ] =
481
+ private def renderCaptureSet (using Quotes )(refs : List [reflect.TypeRepr ], skipThisTypePrefix : Boolean )(
482
+ using elideThis : reflect.ClassDef , originalOwner : reflect.Symbol
483
+ ): SSignature =
475
484
import dotty .tools .scaladoc .tasty .NameNormalizer ._
476
485
import reflect ._
477
486
refs match
478
487
case List (ref) if ref.isCaptureRoot => Nil
479
488
case refs =>
480
- val res0 = refs.map(renderCapability)
489
+ val res0 = refs.map(renderCapability(_, skipThisTypePrefix) )
481
490
val res1 = res0 match
482
491
case Nil => Nil
483
492
case other => other.reduce((r, e) => r ++ (List (Plain (" , " )) ++ e))
484
493
Plain (" {" ) :: (res1 ++ List (Plain (" }" )))
485
494
486
- private def renderCapturing (using Quotes )(refs : List [reflect.TypeRepr ])(using elideThis : reflect.ClassDef ): List [SignaturePart ] =
495
+ private def renderCapturing (using Quotes )(refs : List [reflect.TypeRepr ], skipThisTypePrefix : Boolean )(
496
+ using elideThis : reflect.ClassDef , originalOwner : reflect.Symbol
497
+ ): SSignature =
487
498
import reflect ._
488
- Keyword (" ^" ) :: renderCaptureSet(refs)
499
+ Keyword (" ^" ) :: renderCaptureSet(refs, skipThisTypePrefix)
500
+
501
+ private def renderCaptureArrow (using Quotes )(refs : List [reflect.TypeRepr ], skipThisTypePrefix : Boolean )(
502
+ using elideThis : reflect.ClassDef , originalOwner : reflect.Symbol
503
+ ): SSignature =
504
+ import reflect ._
505
+ refs match
506
+ case Nil => List (Keyword (" ->" ))
507
+ case List (ref) if ref.isCaptureRoot => List (Keyword (" =>" ))
508
+ case refs => Keyword (" ->" ) :: renderCaptureSet(refs, skipThisTypePrefix)
509
+
510
+ private def renderCaptureArrow (using Quotes )(refs : Option [List [reflect.TypeRepr ]], skipThisTypePrefix : Boolean )(
511
+ using elideThis : reflect.ClassDef , originalOwner : reflect.Symbol
512
+ ): SSignature =
513
+ import reflect ._
514
+ refs match
515
+ case None => List (Keyword (" =>" )) // FIXME: is this correct? or should it be `->` by default?
516
+ case Some (refs) => renderCaptureArrow(refs, skipThisTypePrefix)
0 commit comments