Skip to content

Commit 9e8f91d

Browse files
committed
Add scaladoc support for interleaved clauses
1 parent 2126c46 commit 9e8f91d

File tree

3 files changed

+55
-26
lines changed

3 files changed

+55
-26
lines changed

scaladoc-testcases/src/tests/extensionParams.scala

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -52,3 +52,8 @@ extension [A <: List[Char]](using String)(using Unit)(a: A)(using Int)(using Num
5252
extension (using String)(using Unit)(a: Animal)(using Int)(using Number)
5353
def f11(b: Any)(c: Any): Any
5454
= ???
55+
def f13(b: Any)[T](c: T): T
56+
= ???
57+
def f14[D](b: D)[T](c: T): T
58+
= ???
59+

scaladoc-testcases/src/tests/methodsAndConstructors.scala

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,3 +60,6 @@ class Methods:
6060
def withImplicitParam2(v: String)(implicit ab: Double, a: Int, b: String): String
6161
= ???
6262

63+
def clauseInterleaving[T](x: T)[U](y: U)(using (T, U)): (T, U)
64+
= ???
65+

scaladoc/src/dotty/tools/scaladoc/tasty/ClassLikeSupport.scala

Lines changed: 47 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -339,45 +339,66 @@ trait ClassLikeSupport:
339339
def parseMethod(
340340
c: ClassDef,
341341
methodSymbol: Symbol,
342-
emptyParamsList: Boolean = false,
343342
paramPrefix: Symbol => String = _ => "",
344343
specificKind: (Kind.Def => Kind) = identity
345344
): Member =
346345
val method = methodSymbol.tree.asInstanceOf[DefDef]
347-
val paramLists: List[TermParamClause] = methodSymbol.nonExtensionTermParamLists
348-
val genericTypes: List[TypeDef] = if (methodSymbol.isClassConstructor) Nil else methodSymbol.nonExtensionLeadingTypeParams
346+
val paramLists = methodSymbol.nonExtensionParamLists
349347

350348
val memberInfo = unwrapMemberInfo(c, methodSymbol)
351349

352-
val basicKind: Kind.Def = Kind.Def(
353-
Right(genericTypes.map(mkTypeArgument(_, memberInfo.genericTypes, memberInfo.contextBounds))) +:
354-
paramLists.zipWithIndex.flatMap { (pList, index) =>
355-
memberInfo.paramLists(index) match
356-
case MemberInfo.EvidenceOnlyParameterList => None
357-
case MemberInfo.RegularParameterList(info) =>
358-
Some(Left(TermParameterList(pList.params.map(
350+
val unshuffledMemberInfoParamLists =
351+
if methodSymbol.isExtensionMethod && methodSymbol.isRightAssoc then
352+
// Taken from RefinedPrinter.scala
353+
val (leadingTyParamss, rest1) = memberInfo.paramLists.span(_.isType)
354+
val (leadingUsing, rest2) = rest1.span(_.isUsing)
355+
val (rightTyParamss, rest3) = rest2.span(_.isType)
356+
val (rightParamss, rest4) = rest3.splitAt(1)
357+
val (leftParamss, rest5) = rest4.splitAt(1)
358+
val (trailingUsing, rest6) = rest5.span(_.isUsing)
359+
if leftParamss.nonEmpty then
360+
// leadingTyParamss ::: leadingUsing ::: leftParamss ::: trailingUsing ::: rightTyParamss ::: rightParamss ::: rest6
361+
// because of takeRight after, this is equivalent to the following:
362+
rightTyParamss ::: rightParamss ::: rest6
363+
else
364+
memberInfo.paramLists // it wasn't a binary operator, after all.
365+
else
366+
memberInfo.paramLists
367+
368+
val croppedUnshuffledMemberInfoParamLists = unshuffledMemberInfoParamLists.takeRight(paramLists.length)
369+
370+
val basicDefKind: Kind.Def = Kind.Def(
371+
paramLists.zip(croppedUnshuffledMemberInfoParamLists).flatMap{
372+
case (_: TermParamClause, MemberInfo.EvidenceOnlyParameterList) => Nil
373+
case (pList: TermParamClause, MemberInfo.RegularParameterList(info)) =>
374+
Some(Left(api.TermParameterList(pList.params.map(
359375
mkParameter(_, paramPrefix, memberInfo = info)), paramListModifier(pList.params)
360376
)))
361-
case _ => assert(false, "memberInfo.termParamLists contains a type parameter list !")
377+
case (TypeParamClause(genericTypeList), MemberInfo.TypeParameterList(memInfoTypes)) =>
378+
Some(Right(genericTypeList.map(mkTypeArgument(_, memInfoTypes, memberInfo.contextBounds))))
379+
case (_,_) =>
380+
assert(false, s"croppedUnshuffledMemberInfoParamLists and SymOps.nonExtensionParamLists disagree on whether this clause is a type or term one")
362381
}
363382
)
364383

365384
val methodKind =
366-
if methodSymbol.isClassConstructor then Kind.Constructor(basicKind)
367-
else if methodSymbol.flags.is(Flags.Implicit) then extractImplicitConversion(method.returnTpt.tpe) match
368-
case Some(conversion) if paramLists.size == 0 || (paramLists.size == 1 && paramLists.head.params.size == 0) =>
369-
Kind.Implicit(basicKind, Some(conversion))
370-
case None if paramLists.size == 1 && paramLists(0).params.size == 1 =>
371-
Kind.Implicit(basicKind, Some(
372-
ImplicitConversion(
373-
paramLists(0).params(0).tpt.tpe.typeSymbol.dri,
374-
method.returnTpt.tpe.typeSymbol.dri
375-
)
376-
))
377-
case _ =>
378-
Kind.Implicit(basicKind, None)
379-
else if methodSymbol.flags.is(Flags.Given) then Kind.Given(basicKind, Some(method.returnTpt.tpe.asSignature), extractImplicitConversion(method.returnTpt.tpe))
380-
else specificKind(basicKind)
385+
if methodSymbol.isClassConstructor then Kind.Constructor(basicDefKind)
386+
else if methodSymbol.flags.is(Flags.Implicit) then
387+
val termParamLists: List[TermParamClause] = methodSymbol.nonExtensionTermParamLists
388+
extractImplicitConversion(method.returnTpt.tpe) match
389+
case Some(conversion) if termParamLists.size == 0 || (termParamLists.size == 1 && termParamLists.head.params.size == 0) =>
390+
Kind.Implicit(basicDefKind, Some(conversion))
391+
case None if termParamLists.size == 1 && termParamLists(0).params.size == 1 =>
392+
Kind.Implicit(basicDefKind, Some(
393+
ImplicitConversion(
394+
termParamLists(0).params(0).tpt.tpe.typeSymbol.dri,
395+
method.returnTpt.tpe.typeSymbol.dri
396+
)
397+
))
398+
case _ =>
399+
Kind.Implicit(basicDefKind, None)
400+
else if methodSymbol.flags.is(Flags.Given) then Kind.Given(basicDefKind, Some(method.returnTpt.tpe.asSignature), extractImplicitConversion(method.returnTpt.tpe))
401+
else specificKind(basicDefKind)
381402

382403
val origin = if !methodSymbol.isOverridden then Origin.RegularlyDefined else
383404
val overriddenSyms = methodSymbol.allOverriddenSymbols.map(_.owner)

0 commit comments

Comments
 (0)