Skip to content

Commit

Permalink
Fix formatting for gradient path with several params
Browse files Browse the repository at this point in the history
  • Loading branch information
egorikftp committed Jul 24, 2024
1 parent 4dd6120 commit 8bc7afc
Show file tree
Hide file tree
Showing 4 changed files with 234 additions and 45 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,35 @@ package io.github.composegears.valkyrie.generator.ext

import com.squareup.kotlinpoet.CodeBlock

fun CodeBlock.Builder.argumentBlock(
argumentFlow: String,
vararg args: Any?,
block: CodeBlock.Builder.() -> Unit,
) {
add("$argumentFlow\n", *args)
indention(block)
newLine()
add(")")
}

fun CodeBlock.Builder.nestedArgumentBlock(
argumentFlow: String,
vararg args: Any?,
block: CodeBlock.Builder.() -> Unit,
) {
add("$argumentFlow\n", *args)
indention(block)
newLine()
add("),")
newLine()
}

fun CodeBlock.Builder.indention(block: CodeBlock.Builder.() -> Unit) {
indent()
block()
unindent()
}

fun CodeBlock.Builder.newLine() {
add("\n")
}
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,11 @@ import androidx.compose.material.icons.generator.vector.StrokeJoin
import androidx.compose.material.icons.generator.vector.VectorNode
import com.squareup.kotlinpoet.CodeBlock
import com.squareup.kotlinpoet.buildCodeBlock
import io.github.composegears.valkyrie.generator.ext.argumentBlock
import io.github.composegears.valkyrie.generator.ext.formatFloat
import io.github.composegears.valkyrie.generator.ext.indention
import io.github.composegears.valkyrie.generator.ext.nestedArgumentBlock
import io.github.composegears.valkyrie.generator.ext.newLine
import io.github.composegears.valkyrie.generator.ext.toColorHex
import io.github.composegears.valkyrie.generator.imagevector.util.PathParams.FillAlphaParam
import io.github.composegears.valkyrie.generator.imagevector.util.PathParams.FillParam
Expand Down Expand Up @@ -38,7 +41,7 @@ internal fun CodeBlock.Builder.addPath(
add(
codeBlock = buildCodeBlock {
add("%M(", MemberNames.Path)
fillPathArgs(pathParams.first())
fillPathArgs(param = pathParams.first(), handleMultiline = true)
beginControlFlow(")")
pathBody()
endControlFlow()
Expand Down Expand Up @@ -69,10 +72,13 @@ internal fun CodeBlock.Builder.addPath(
}
}

private fun CodeBlock.Builder.fillPathArgs(param: PathParams) {
private fun CodeBlock.Builder.fillPathArgs(
param: PathParams,
handleMultiline: Boolean = false,
) {
// TODO: arg "name" missing
when (param) {
is FillParam -> fillArg(param)
is FillParam -> fillArg(param, handleMultiline)
is FillAlphaParam -> fillAlphaArg(param)
is FillTypeParam -> pathFillTypeArg(param)
is StrokeAlphaParam -> strokeAlphaArg(param)
Expand All @@ -84,65 +90,80 @@ private fun CodeBlock.Builder.fillPathArgs(param: PathParams) {
}
}

private fun CodeBlock.Builder.fillArg(path: FillParam) {
private fun CodeBlock.Builder.fillArg(
path: FillParam,
handleMultiline: Boolean,
) {
when (val fill = path.fill) {
is Fill.Color -> {
add("fill = %M(%M(${fill.colorHex.toColorHex()}))", MemberNames.SolidColor, MemberNames.Color)
}
is Fill.LinearGradient -> {
add("\n")
indention {
add("fill = %T.linearGradient(\n", ClassNames.Brush)
if (handleMultiline) {
newLine()
indention {
add("colorStops = arrayOf(\n")
indention {
add(
fill.colorStops.joinToString(separator = ",\n") { stop ->
"${stop.first.formatFloat()} to %M(${stop.second.toColorHex()})"
},
*Array(fill.colorStops.size) { MemberNames.Color },
)
}
add("\n),\n")
add(
"start = %M(${fill.startX.formatFloat()}, ${fill.startY.formatFloat()}),\n",
MemberNames.Offset,
)
add(
"end = %M(${fill.endX.formatFloat()}, ${fill.endY.formatFloat()})\n",
MemberNames.Offset,
)
addLinearGradient(fill)
}
add(")\n")
newLine()
} else {
addLinearGradient(fill)
}
}
is Fill.RadialGradient -> {
add("\n")
indention {
add("fill = %T.radialGradient(\n", ClassNames.Brush)
if (handleMultiline) {
newLine()
indention {
add("colorStops = arrayOf(\n")
indention {
add(
fill.colorStops.joinToString(separator = ",\n") { stop ->
"${stop.first.formatFloat()} to %M(${stop.second.toColorHex()})"
},
*Array(fill.colorStops.size) { MemberNames.Color },
)
}
add("\n),\n")
add(
"center = %M(${fill.centerX.formatFloat()}, ${fill.centerY.formatFloat()}),\n",
MemberNames.Offset,
)
add("radius = ${fill.gradientRadius.formatFloat()}\n")
addRadialGradient(fill)
}
add(")\n")
newLine()
} else {
addRadialGradient(fill)
}
}
}
}

private fun CodeBlock.Builder.addLinearGradient(fill: Fill.LinearGradient) {
argumentBlock("fill = %T.linearGradient(", ClassNames.Brush) {
nestedArgumentBlock("colorStops = arrayOf(") {
add(
fill.colorStops.joinToString(separator = ",\n") { stop ->
"${stop.first.formatFloat()} to %M(${stop.second.toColorHex()})"
},
*Array(fill.colorStops.size) { MemberNames.Color },
)
}
add(
"start = %M(${fill.startX.formatFloat()}, ${fill.startY.formatFloat()}),",
MemberNames.Offset,
)
newLine()
add(
"end = %M(${fill.endX.formatFloat()}, ${fill.endY.formatFloat()})",
MemberNames.Offset,
)
}
}

private fun CodeBlock.Builder.addRadialGradient(fill: Fill.RadialGradient) {
argumentBlock("fill = %T.radialGradient(", ClassNames.Brush) {
nestedArgumentBlock("colorStops = arrayOf(") {
add(
fill.colorStops.joinToString(separator = ",\n") { stop ->
"${stop.first.formatFloat()} to %M(${stop.second.toColorHex()})"
},
*Array(fill.colorStops.size) { MemberNames.Color },
)
}
add(
"center = %M(${fill.centerX.formatFloat()}, ${fill.centerY.formatFloat()}),",
MemberNames.Offset,
)
newLine()
add("radius = ${fill.gradientRadius.formatFloat()}")
}
}

private fun CodeBlock.Builder.fillAlphaArg(param: FillAlphaParam) {
add("fillAlpha = ${param.fillAlpha.formatFloat()}")
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -270,4 +270,114 @@ class SvgGradientParserTest {
""".trimIndent()
assertEquals(expectedOutput, output)
}

@Test
fun `svg linear gradient with stroke parsing`() {
val icon = loadIcon("ic_linear_gradient_with_stroke.svg")
val parserOutput = IconParser.toVector(icon)
val output = ImageVectorGenerator.convert(
vector = parserOutput.vector,
kotlinName = parserOutput.kotlinName,
config = ImageVectorGeneratorConfig(
packageName = "io.github.composegears.valkyrie.icons",
packName = "",
nestedPackName = "",
generatePreview = false,
),
).content

val expectedOutput = """
package io.github.composegears.valkyrie.icons
import androidx.compose.ui.geometry.Offset
import androidx.compose.ui.graphics.Brush
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.SolidColor
import androidx.compose.ui.graphics.vector.ImageVector
import androidx.compose.ui.graphics.vector.path
import androidx.compose.ui.unit.dp
val LinearGradientWithStroke: ImageVector
get() {
if (_LinearGradientWithStroke != null) {
return _LinearGradientWithStroke!!
}
_LinearGradientWithStroke = ImageVector.Builder(
name = "LinearGradientWithStroke",
defaultWidth = 24.dp,
defaultHeight = 24.dp,
viewportWidth = 24f,
viewportHeight = 24f
).apply {
path(
fill = Brush.linearGradient(
colorStops = arrayOf(
0.097f to Color(0xFF0095D5),
0.301f to Color(0xFF238AD9),
0.621f to Color(0xFF557BDE),
0.864f to Color(0xFF7472E2),
1f to Color(0xFF806EE3)
),
start = Offset(6.384f, 29.605f),
end = Offset(17.723f, 18.267f)
),
stroke = SolidColor(Color(0x00000000))
) {
moveTo(0f, 24f)
lineTo(12.039f, 11.961f)
lineTo(24f, 24f)
close()
moveTo(0f, 24f)
}
path(
fill = Brush.linearGradient(
colorStops = arrayOf(
0.118f to Color(0xFF0095D5),
0.418f to Color(0xFF3C83DC),
0.696f to Color(0xFF6D74E1),
0.833f to Color(0xFF806EE3)
),
start = Offset(1.684f, 4.824f),
end = Offset(8.269f, -1.762f)
),
stroke = SolidColor(Color(0x00000000))
) {
moveTo(0f, 0f)
lineTo(12.039f, 0f)
lineTo(0f, 13f)
close()
moveTo(0f, 0f)
}
path(
fill = Brush.linearGradient(
colorStops = arrayOf(
0.107f to Color(0xFFC757BC),
0.214f to Color(0xFFD0609A),
0.425f to Color(0xFFE1725C),
0.605f to Color(0xFFEE7E2F),
0.743f to Color(0xFFF58613),
0.823f to Color(0xFFF88909)
),
start = Offset(-4.041f, 22.066f),
end = Offset(18.293f, -0.268f)
),
stroke = SolidColor(Color(0x00000000))
) {
moveTo(12.039f, 0f)
lineTo(0f, 12.68f)
lineTo(0f, 24f)
lineTo(24f, 0f)
close()
moveTo(12.039f, 0f)
}
}.build()
return _LinearGradientWithStroke!!
}
private var _LinearGradientWithStroke: ImageVector? = null
""".trimIndent()
assertEquals(expectedOutput, output)
}
}
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.

0 comments on commit 8bc7afc

Please sign in to comment.