From 67ee0bc320f7ef637149fe67ffddc813dface24c Mon Sep 17 00:00:00 2001 From: IceMimosa Date: Mon, 19 Jul 2021 23:35:49 +0800 Subject: [PATCH] IDEA plugin - `@apply` support generic & currying (#68) --- .gitignore | 2 +- .../plugin/processor/AbsProcessor.scala | 30 ++++++++++++++++--- .../processor/clazz/ApplyProcessor.scala | 9 +++--- 3 files changed, 32 insertions(+), 9 deletions(-) diff --git a/.gitignore b/.gitignore index 070f70f..a674188 100644 --- a/.gitignore +++ b/.gitignore @@ -18,4 +18,4 @@ examples2-13/target/ intellij-plugin/target/ intellij-plugin/project/project/ intellij-plugin/project/target/ -/.idea/ +.run/ \ No newline at end of file diff --git a/intellij-plugin/src/main/scala/io/github/dreamylost/plugin/processor/AbsProcessor.scala b/intellij-plugin/src/main/scala/io/github/dreamylost/plugin/processor/AbsProcessor.scala index 60e29af..5249a95 100644 --- a/intellij-plugin/src/main/scala/io/github/dreamylost/plugin/processor/AbsProcessor.scala +++ b/intellij-plugin/src/main/scala/io/github/dreamylost/plugin/processor/AbsProcessor.scala @@ -19,15 +19,37 @@ abstract class AbsProcessor extends Processor { * @return name and type */ protected def getConstructorParameters(clazz: ScClass, withSecond: Boolean = true): Seq[(String, String)] = { + this.getConstructorCurryingParameters(clazz, withSecond, withCurrying = false).head + } + + /** + * get constructor parameters with currying + * + * @return + * if `withCurrying` = true, return (name: type, name: type)(name: type)... + * else return (name: type, name: type, name: type, ...) + */ + protected def getConstructorCurryingParameters(clazz: ScClass, withSecond: Boolean = true, withCurrying: Boolean = true): Seq[Seq[(String, String)]] = { val constructors = if (withSecond) { clazz.constructors.map(Some(_)) } else { Seq(clazz.constructor.map(_.asInstanceOf[ScMethodLike])) } - constructors.flatten.flatMap(_.getParameterList.getParameters) - .collect { - case p: ScClassParameter => - p.name -> p.`type`().toOption.map(_.toString).getOrElse("Unit") + if (withCurrying) { + constructors.flatten.flatMap { c => + c.effectiveParameterClauses.map(_.effectiveParameters.collect { + case p: ScClassParameter => + p.name -> p.`type`().toOption.map(_.toString).getOrElse("Unit") + }) } + } else { + Seq( + constructors.flatten.flatMap(_.getParameterList.getParameters) + .collect { + case p: ScClassParameter => + p.name -> p.`type`().toOption.map(_.toString).getOrElse("Unit") + } + ) + } } } diff --git a/intellij-plugin/src/main/scala/io/github/dreamylost/plugin/processor/clazz/ApplyProcessor.scala b/intellij-plugin/src/main/scala/io/github/dreamylost/plugin/processor/clazz/ApplyProcessor.scala index c3e9cfd..ba51f5f 100644 --- a/intellij-plugin/src/main/scala/io/github/dreamylost/plugin/processor/clazz/ApplyProcessor.scala +++ b/intellij-plugin/src/main/scala/io/github/dreamylost/plugin/processor/clazz/ApplyProcessor.scala @@ -21,10 +21,11 @@ class ApplyProcessor extends AbsProcessor { source match { case obj: ScObject => val clazz = obj.fakeCompanionClassOrCompanionClass.asInstanceOf[ScClass] - val nameAndTypes = getConstructorParameters(clazz, withSecond = false) - .map(o => s"${o._1}: ${o._2}") - .mkString(", ") - Seq(s"def apply($nameAndTypes): ${clazz.getName} = ???") + val nameAndTypes = getConstructorCurryingParameters(clazz, withSecond = false) + .map(_.map(o => s"${o._1}: ${o._2}").mkString("(", ", ", ")")) + .mkString + val genericTypes = clazz.typeParamString + Seq(s"def apply$genericTypes$nameAndTypes: ${clazz.getName}$genericTypes = ???") case _ => Nil } case _ => Nil -- GitLab