Add option to overwrite and redeclaration warning option

This commit is contained in:
2020-09-08 09:39:15 +02:00
parent f23d54d8c8
commit dedbce0fa0
12 changed files with 259 additions and 482 deletions

1
.gitignore vendored
View File

@@ -1,3 +1,4 @@
.gradle .gradle
build build
.idea .idea
local.properties

View File

@@ -1,66 +1,70 @@
import org.jetbrains.kotlin.fir.declarations.builder.buildResolvedImport
plugins { plugins {
kotlin("multiplatform") version "1.4-M1" kotlin("multiplatform") version "1.4.0-rc"
`maven-publish`
} }
group = "nl.astraeus" group = "nl.astraeus"
version = "0.1.0-SNAPSHOT" version = "0.3.6-SNAPSHOT"
repositories { repositories {
maven { setUrl("https://dl.bintray.com/kotlin/kotlin-eap") } maven { setUrl("https://dl.bintray.com/kotlin/kotlin-eap") }
mavenLocal()
mavenCentral() mavenCentral()
} }
//apply(plugin = "kotlin-dce-js")
kotlin { kotlin {
/* Targets configuration omitted.
* To find out how to configure the targets, please follow the link:
* https://kotlinlang.org/docs/reference/building-mpp-with-gradle.html#setting-up-targets */
jvm() jvm()
js { js(BOTH) {
produceExecutable() browser()
browser {
distribution { //produceKotlinLibrary()
directory = File("$projectDir/web/")
}
} }
val hostOs = System.getProperty("os.name")
val isMingwX64 = hostOs.startsWith("Windows")
val nativeTarget = when {
hostOs == "Mac OS X" -> macosX64("native")
hostOs == "Linux" -> linuxX64("native")
isMingwX64 -> mingwX64("native")
else -> throw GradleException("Host OS is not supported in Kotlin/Native.")
} }
sourceSets { sourceSets {
val commonMain by getting { val commonMain by getting {}
dependencies { }
implementation(kotlin("stdlib-common")) }
implementation("io.github.microutils:kotlin-logging-common:1.7.8") publishing {
} repositories {
} maven {
val commonTest by getting { name = "releases"
dependencies { // change to point to your repo, e.g. http://my.org/repo
implementation(kotlin("test-common")) url = uri("http://nexus.astraeus.nl/nexus/content/repositories/releases")
//implementation(kotlin("test-annotations-common")) credentials {
} val nexusUsername: String by project
} val nexusPassword: String by project
val jsMain by getting {
dependencies {
implementation(kotlin("stdlib-js"))
implementation("io.github.microutils:kotlin-logging-js:1.7.8") username = nexusUsername
password = nexusPassword
} }
} }
val jsTest by getting { maven {
dependencies { name = "snapshots"
implementation(kotlin("test-js")) // change to point to your repo, e.g. http://my.org/repo
//implementation(kotlin("test-annotations-js")) url = uri("http://nexus.astraeus.nl/nexus/content/repositories/snapshots")
} credentials {
} val nexusUsername: String by project
val jvmMain by getting { val nexusPassword: String by project
dependencies {
implementation(kotlin("stdlib-jdk8"))
implementation("org.slf4j:slf4j-api:1.7.29") username = nexusUsername
implementation("org.slf4j:slf4j-simple:1.7.29") password = nexusPassword
implementation("io.github.microutils:kotlin-logging:1.7.8")
} }
} }
} }
publications {
val kotlinMultiplatform by getting {
//artifactId = "kotlin-css-generator"
}
}
} }

6
gradle.properties Normal file
View File

@@ -0,0 +1,6 @@
kotlin.code.style=official
kotlin.js.compiler=both
nexusUsername=
nexusPassword=

View File

@@ -7,4 +7,7 @@ pluginManagement {
maven { setUrl("https://plugins.gradle.org/m2/") } maven { setUrl("https://plugins.gradle.org/m2/") }
} }
} }
rootProject.name = "kotlin-css-generator" rootProject.name = "kotlin-css-generator"
enableFeaturePreview("GRADLE_METADATA")

View File

@@ -1,8 +1,45 @@
package nl.astraeus.css.properties package nl.astraeus.css.properties
class Color( class Color(
value: String value: String,
val readOnly: Boolean = true
) : CssProperty(value) { ) : CssProperty(value) {
/* val hue: Int? = null
val saturation: Int? = null
val lightness: Int? = null
val alpha: Double? = null
init {
}
override fun css(): String {
return super.css()
}
fun adjust(
red: Int? = null,
green: Int? = null,
blue: Int? = null,
hue: Int? = null,
saturation: Int? = null,
lightness: Int? = null,
alpha: Double? = null
): Color {
return this
}
fun darken(): Color {
if (readOnly) {
return this
} else {
return this
}
}
fun lighten(): Color {
return this
}*/
companion object { companion object {
val auto = Color("auto") val auto = Color("auto")
@@ -25,12 +62,21 @@ class Color(
hue: Int, hue: Int,
saturation: Int, saturation: Int,
lightness: Int lightness: Int
) = Color("hsl($hue, $saturation, $lightness)") ) = Color("hsl($hue, $saturation%, $lightness%)")
fun hsla( fun hsla(
hue: Int, hue: Int,
saturation: Int, saturation: Int,
lightness: Int, lightness: Int,
alpha: Double alpha: Double
) = Color("hsla($hue, $saturation, $lightness, $alpha)") ) = Color("hsla($hue, $saturation%, $lightness%, $alpha)")
private fun fromHex(
red: Int,
green: Int,
blue: Int
) {
} }
}
} }

View File

@@ -0,0 +1,11 @@
package nl.astraeus.css.style
import nl.astraeus.css.properties.Color
object CssFunctions {
fun darken(color: Color, percentage: Int): Color {
return color
}
}

View File

@@ -1,7 +1,6 @@
package nl.astraeus.css.style package nl.astraeus.css.style
import nl.astraeus.css.properties.* import nl.astraeus.css.properties.*
import nl.astraeus.logging.log
typealias Css = Style.() -> Unit typealias Css = Style.() -> Unit
@@ -31,29 +30,27 @@ private fun prp(vararg css: String): List<CssProperty> {
} }
abstract class CssGenerator { abstract class CssGenerator {
val definitions: MutableMap<String, Css> = mutableMapOf() val definitions: MutableMap<String, MutableList<Css>> = mutableMapOf()
val props: MutableMap<String, List<CssProperty>> = mutableMapOf() val props: MutableMap<String, List<CssProperty>> = mutableMapOf()
abstract fun getValidator(name: String): List<Validator>? abstract fun getValidator(name: String): List<Validator>?
private fun propertyCss(indent: String, name: String, props: List<CssProperty>, minified: Boolean): String { private fun propertyCss(indent: String, name: String, props: List<CssProperty>): String {
val builder = StringBuilder() val builder = StringBuilder()
getValidator(name)?.forEach { getValidator(name)?.forEach {
if (!it.validate(props)) { if (!it.validate(props)) {
log.warn { "Validate error '$name' - ${it.getMessage(name)}" } println( "Validate error '$name' - ${it.getMessage(name)}")
} }
} }
for (prop in props) { for (prop in props) {
if (builder.isNotEmpty()) { if (builder.isNotEmpty()) {
builder.append(",") builder.append(" ")
indent(minified, builder, " ")
} }
builder.append(prop.css()) builder.append(prop.css())
} }
return if (!minified) {
val paddedName = StringBuilder() val paddedName = StringBuilder()
paddedName.append(indent) paddedName.append(indent)
paddedName.append(name) paddedName.append(name)
@@ -61,23 +58,25 @@ abstract class CssGenerator {
while (paddedName.length < 32) { while (paddedName.length < 32) {
paddedName.append(' ') paddedName.append(' ')
} }
"$paddedName$builder;\n" return "$paddedName$builder;\n"
} else {
"$name:$builder;"
}
} }
fun generatePropertyCss(indent: String, minified: Boolean): String { fun generatePropertyCss(indent: String): String {
val builder = StringBuilder() val builder = StringBuilder()
for ((name, prop) in props) { for ((name, prop) in props) {
builder.append(propertyCss(indent, name, prop, minified)) builder.append(propertyCss(indent, name, prop))
} }
return builder.toString() return builder.toString()
} }
open fun generateCss(namespace: String = "", indent: String = "", minified: Boolean = false): String { open fun generateCss(
namespace: String = "",
indent: String = "",
minified: Boolean = false,
warnOnRedeclaration: Boolean = true
): String {
val builder = StringBuilder() val builder = StringBuilder()
if (this is ConditionalStyle) { if (this is ConditionalStyle) {
@@ -85,22 +84,20 @@ abstract class CssGenerator {
mq.keys.sorted().forEach { mediaName -> mq.keys.sorted().forEach { mediaName ->
val css = mq[mediaName] val css = mq[mediaName]
indent(minified, builder, indent) builder.append(indent)
builder.append("@media ") builder.append("@media ")
builder.append(mediaName) builder.append(mediaName)
builder.append(" {") builder.append(" {\n")
indent(minified, builder, "\n")
css?.let { css -> css?.let { css ->
val mediaStyle = ConditionalStyle() val mediaStyle = ConditionalStyle()
css(mediaStyle) css(mediaStyle)
builder.append(mediaStyle.generateCss("", " $indent", minified)) builder.append(mediaStyle.generateCss("", " $indent"))
} }
indent(minified, builder, indent) builder.append(indent)
builder.append("}") builder.append("}\n")
indent(minified, builder, "\n")
} }
} }
@@ -108,102 +105,107 @@ abstract class CssGenerator {
mq.keys.sorted().forEach { mediaName -> mq.keys.sorted().forEach { mediaName ->
val css = mq[mediaName] val css = mq[mediaName]
indent(minified, builder, indent) builder.append(indent)
builder.append("@supports ") builder.append("@supports ")
builder.append(mediaName) builder.append(mediaName)
builder.append(" {") builder.append(" {\n")
indent(minified, builder, "\n")
css?.let { css -> css?.let { css ->
val mediaStyle = ConditionalStyle() val mediaStyle = ConditionalStyle()
css(mediaStyle) css(mediaStyle)
builder.append(mediaStyle.generateCss(""," $indent", minified)) builder.append(mediaStyle.generateCss(""," $indent"))
} }
indent(minified, builder, indent) builder.append(indent)
builder.append("}") builder.append("}\n")
indent(minified, builder, "\n")
} }
} }
} }
for ((name, prop) in definitions) { for (name in definitions.keys.sorted()) {
val props = definitions[name]!!
val css = StringBuilder() val css = StringBuilder()
if (warnOnRedeclaration && props.size > 1) {
css.append("/* style '$name' is defined ${props.size} times! */\n")
}
val finalStyle = Style() val finalStyle = Style()
for (prop in props) {
prop(finalStyle) prop(finalStyle)
}
css.append(finalStyle.generatePropertyCss(" $indent", minified)) css.append(finalStyle.generatePropertyCss(" $indent"))
if (css.isNotBlank()) { if (css.isNotBlank()) {
if (name.startsWith(":")) {
builder.append("\n$namespace$name".trim())
} else {
builder.append("\n$namespace $name".trim()) builder.append("\n$namespace $name".trim())
indent(minified, builder, " $indent") }
builder.append("{")
indent(minified, builder, "\n") builder.append(" $indent")
builder.append("{\n")
finalStyle.fontFace?.let { ff -> finalStyle.fontFace?.let { ff ->
indent(minified, builder, " $indent")
builder.append("@font-face {")
indent(minified, builder, "\n")
builder.append(ff.generatePropertyCss( " $indent", minified))
builder.append(" $indent") builder.append(" $indent")
builder.append("}") builder.append("@font-face {\n")
indent(minified, builder, "\n") builder.append(ff.generatePropertyCss( " $indent"))
builder.append(" $indent")
builder.append("}\n")
} }
finalStyle.keyFrames.let { kf -> finalStyle.keyFrames.let { kf ->
kf.keys.sorted().forEach { frameName -> kf.keys.sorted().forEach { frameName ->
val css = kf[frameName] val css = kf[frameName]
indent(minified, builder, " $indent") builder.append(" $indent")
builder.append("@keyframes ") builder.append("@keyframes ")
builder.append(frameName) builder.append(frameName)
builder.append(" {") builder.append(" {\n")
indent(minified, builder, "\n")
css?.let { css -> css?.let { css ->
for ((nr, style) in css.frames) { for ((nr, style) in css.frames) {
indent(minified, builder, " $indent") builder.append(" $indent")
builder.append("${nr}% ") builder.append("${nr}% ")
indent(minified, builder, " $indent") builder.append(" $indent")
builder.append("{") builder.append("{\n")
indent(minified, builder, "\n")
val finalStyle = Style() val finalStyle = Style()
style(finalStyle) style(finalStyle)
builder.append(finalStyle.generatePropertyCss(" $indent", minified)) builder.append(finalStyle.generatePropertyCss(" $indent"))
indent(minified, builder, " $indent") builder.append(" $indent")
builder.append("}") builder.append("}\n")
indent(minified, builder, "\n")
} }
indent(minified, builder, " $indent") builder.append(" $indent")
builder.append("}") builder.append("}\n")
indent(minified, builder, "\n")
} }
} }
} }
builder.append(css) builder.append(css)
builder.append("}") builder.append("}\n\n")
indent(minified, builder, "\n\n")
} }
builder.append(finalStyle.generateCss( "$namespace $name".trim(), indent, minified)) builder.append(finalStyle.generateCss("$namespace $name".trim(), indent))
} }
return builder.toString() return if (minified) {
val stripped = StringBuilder()
val skip = arrayOf(' ', '\t', '\n', '\r')
for (char in builder) {
if (!skip.contains(char)) {
stripped.append(char)
} }
}
private fun indent(minified: Boolean, builder: StringBuilder, indent: String) { stripped.toString();
if (!minified) { } else {
builder.append(indent) builder.toString()
} }
} }
} }
@@ -220,6 +222,8 @@ open class Style : CssGenerator() {
MaxCountValidator(4), MaxCountValidator(4),
InitialInheritSingleValue() InitialInheritSingleValue()
), ),
"animation-iteration-mode" to listOf(MaxCountValidator(4)),
"animation-timing-function" to listOf(MaxCountValidator(4)), "animation-timing-function" to listOf(MaxCountValidator(4)),
"border-image-repeat" to listOf(MaxCountValidator(2)), "border-image-repeat" to listOf(MaxCountValidator(2)),
"border-image-slice" to listOf(MaxCountValidator(4)), "border-image-slice" to listOf(MaxCountValidator(4)),
@@ -229,8 +233,49 @@ open class Style : CssGenerator() {
override fun getValidator(name: String) = validators[name] override fun getValidator(name: String) = validators[name]
private fun addStyle(selector: String, style: Css) {
definitions[selector] = definitions[selector] ?: mutableListOf()
definitions[selector]?.add(style)
}
fun select(selector: String, style: Css) { fun select(selector: String, style: Css) {
definitions[selector] = style addStyle(selector, style)
}
fun descendant(descName: String, style: Css) {
addStyle(descName, style)
}
fun cls(className: String, style: Css) {
addStyle(".$className", style)
}
fun child(childName: String, style: Css) {
addStyle("> $childName", style)
}
fun active(style: Css) {
addStyle(":active", style)
}
fun focus(style: Css) {
addStyle(":focus", style)
}
fun focusWithin(style: Css) {
addStyle(":focus-within", style)
}
fun hover(style: Css) {
addStyle(":hover", style)
}
fun visited(style: Css) {
addStyle(":visited", style)
}
fun plain(name: String, value: String) {
props[name] = prp(value)
} }
fun alignContent(value: AlignContent) { props["align-content"] = prp(value) } fun alignContent(value: AlignContent) { props["align-content"] = prp(value) }
@@ -390,7 +435,7 @@ open class Style : CssGenerator() {
fun gridAutoFlow(flow: GridFlow) { props["grid-auto-flow"] = prp(flow) } fun gridAutoFlow(flow: GridFlow) { props["grid-auto-flow"] = prp(flow) }
fun gridAutoRows(autoRows: GridAuto) { props["grid-auto-rows"] = prp(autoRows) } fun gridAutoRows(autoRows: GridAuto) { props["grid-auto-rows"] = prp(autoRows) }
fun gridAutoRows(size: Measurement) { props["grid-auto-rows"] = prp(size) } fun gridAutoRows(size: Measurement) { props["grid-auto-rows"] = prp(size) }
fun gridColumn(start: GridRowColumn, end: GridRowColumn) { props["grid-column"] = prp(start, end) } fun gridColumn(start: GridRowColumn, end: GridRowColumn) { props["grid-column"] = prp(CssProperty("${start.css()}/${end.css()}")) }
fun gridColumnEnd(end: GridRowColumn) { props["grid-column-end"] = prp(end) } fun gridColumnEnd(end: GridRowColumn) { props["grid-column-end"] = prp(end) }
fun gridColumnGap(gap: GridRowColumn) { props["grid-column-gap"] = prp(gap) } fun gridColumnGap(gap: GridRowColumn) { props["grid-column-gap"] = prp(gap) }
fun gridColumnStart(start: GridRowColumn) { props["grid-column-start"] = prp(start) } fun gridColumnStart(start: GridRowColumn) { props["grid-column-start"] = prp(start) }
@@ -398,13 +443,18 @@ open class Style : CssGenerator() {
rowGap: Measurement = Measurement.px(0), rowGap: Measurement = Measurement.px(0),
columnGap: Measurement = Measurement.px(0) columnGap: Measurement = Measurement.px(0)
) { props["grid-gap"] = prp(rowGap, columnGap) } ) { props["grid-gap"] = prp(rowGap, columnGap) }
fun gridRow(start: GridRowColumn, end: GridRowColumn) { props["grid-row"] = prp(start, end) } fun gridRow(start: GridRowColumn, end: GridRowColumn) { props["grid-row"] = prp(CssProperty("${start.css()}/${end.css()}")) }
fun gridRowEnd(end: GridRowColumn) { props["grid-row-end"] = prp(end) } fun gridRowEnd(end: GridRowColumn) { props["grid-row-end"] = prp(end) }
fun gridRowGap(gap: GridRowColumn) { props["grid-row-end"] = prp(gap) } fun gridRowGap(gap: GridRowColumn) { props["grid-row-end"] = prp(gap) }
fun gridRowStart(start: GridRowColumn) { props["grid-row-start"] = prp(start) } fun gridRowStart(start: GridRowColumn) { props["grid-row-start"] = prp(start) }
fun gridTemplate(template: String) { props["grid-template"] = prp(template) } fun gridTemplate(template: String) { props["grid-template"] = prp(template) }
fun gridTemplateAreas(template: String) { props["grid-template-areas"] = prp(template) } fun gridTemplateAreas(template: String) { props["grid-template-areas"] = prp(template) }
@Deprecated(
"Fixed type, use gridTemplateColumns instead",
ReplaceWith("gridTemplateColumns(columns)")
)
fun gridTemplateColumn(vararg columns: TemplateRowColumn) { props["grid-template-columns"] = prp(*columns) } fun gridTemplateColumn(vararg columns: TemplateRowColumn) { props["grid-template-columns"] = prp(*columns) }
fun gridTemplateColumns(vararg columns: TemplateRowColumn) { props["grid-template-columns"] = prp(*columns) }
fun gridTemplateRows(vararg rows: TemplateRowColumn) { props["grid-template-rows"] = prp(*rows) } fun gridTemplateRows(vararg rows: TemplateRowColumn) { props["grid-template-rows"] = prp(*rows) }
fun hangingPunctuation(punctuation: Isolation) { props["hanging-punctuation"] = prp(punctuation) } fun hangingPunctuation(punctuation: Isolation) { props["hanging-punctuation"] = prp(punctuation) }
fun height(height: Measurement) { props["height"] = prp(height) } fun height(height: Measurement) { props["height"] = prp(height) }
@@ -462,6 +512,12 @@ open class Style : CssGenerator() {
fun overflowX(overflow: Overflow) { props["overflow-x"] = prp(overflow) } fun overflowX(overflow: Overflow) { props["overflow-x"] = prp(overflow) }
fun overflowY(overflow: Overflow) { props["overflow-y"] = prp(overflow) } fun overflowY(overflow: Overflow) { props["overflow-y"] = prp(overflow) }
fun padding(padding: Measurement) { props["padding"] = prp(padding) } fun padding(padding: Measurement) { props["padding"] = prp(padding) }
fun padding(topLeft: Measurement, bottomRight: Measurement) {
props["padding"] = prp(topLeft, bottomRight)
}
fun padding(top: Measurement, right: Measurement, bottom: Measurement, left: Measurement) {
props["padding"] = prp(top, right, bottom, left)
}
fun padding(padding: InitialInherit) { props["padding"] = prp(padding) } fun padding(padding: InitialInherit) { props["padding"] = prp(padding) }
fun paddingBottom(padding: Measurement) { props["padding-bottom"] = prp(padding) } fun paddingBottom(padding: Measurement) { props["padding-bottom"] = prp(padding) }
fun paddingBottom(padding: InitialInherit) { props["padding-bottom"] = prp(padding) } fun paddingBottom(padding: InitialInherit) { props["padding-bottom"] = prp(padding) }

View File

@@ -1,5 +0,0 @@
package nl.astraeus.logging
import mu.KotlinLogging
val log = KotlinLogging.logger {}

View File

@@ -1,17 +1,8 @@
package nl.astraeus.css package nl.astraeus.css
import nl.astraeus.css.properties.Color.Companion.hsl
import nl.astraeus.css.properties.Color.Companion.rgba
import nl.astraeus.css.properties.Measurement.Companion.em
import nl.astraeus.css.properties.Measurement.Companion.px
import nl.astraeus.css.properties.em
import nl.astraeus.css.properties.px
//import kotlin.test.Test
object TestCssBuilder { object TestCssBuilder {
/*
//@Test @Test
fun testBuilder() { fun testBuilder() {
val css = CssBuilder() val css = CssBuilder()
@@ -21,14 +12,22 @@ object TestCssBuilder {
top(10.px()) top(10.px())
left(4.em()) left(4.em())
backgroundColor(rgba(255, 255, 255, 0.75)) backgroundColor(rgba(255, 255, 255, 0.75))
animationIterationMode(
Count.auto,
Count.auto,
Count.auto,
Count.auto,
Count.auto
)
select("> a") { select("> a") {
//color = hsl(200, 50, 50) color(hsl(200, 50, 50))
} }
} }
} }
println(css) println(css)
} }*/
} }

View File

@@ -1,105 +0,0 @@
package nl.astraeus.css
import nl.astraeus.css.properties.*
import nl.astraeus.css.properties.Color.Companion.hex
import nl.astraeus.css.style.Style
class StyleBase(
val mainColor: Color = Color.hsl(128, 50, 50),
val mainBackgroundColor: Color = Color.hsl(64, 50, 50),
val mainFont: TextProperty = text("Arial")
)
private fun Style.sizePX(
left: Int,
top: Int,
width: Int,
height: Int
) {
this@sizePX.top(top.px())
this@sizePX.left(left.px())
this@sizePX.width(width.px())
this@sizePX.height(height.px())
}
private fun generateCss(
base: StyleBase
): String {
val css = CssBuilder()
css.style {
select("body") {
// fontFamily = base.mainFont
// color = base.mainColor
backgroundColor(base.mainBackgroundColor)
// alignContent = AlignContent.initial()
}
select(".test") {
// top = px(10)
// left = em(5)
backgroundColor(Color.rgba(255, 255, 255, 0.75))
//
// select("> a") {
// color = Color.hsl(200, 50, 50)
// }
}
select("nav") {
select("ul") {
color(Color.hsl(0, 100, 25))
backgroundColor(base.mainBackgroundColor)
}
select("li") {
sizePX(25, 25, 200, 200)
animationPlayState(AnimationPlayState.paused, AnimationPlayState.running)
select("a") {
// width = px(725)
// background = text("")
// backgroundColor = base.mainBackgroundColor
}
}
}
}
return css.getCss()
}
fun main() {
val css1 = generateCss(StyleBase())
val css2 = generateCss(StyleBase(
Color.hsl(32, 40, 50),
Color.hsl(64, 60, 35),
text("Courier")
))
println(css1)
println(css2)
val sd = style {
select("#pipo") {
backgroundColor(hex("ffeedd"))
fontFamily("Arial, Courier")
// backgroundColor = Color.hex("eeeeee")
// fontFamily = text("Arial, Courier")
// animationDelay = listOf(DelayDuration.initial())
select("div") {
tableLayout(TableLayout.auto)
tabSize(14.px())
// color = Color.hex("1b1b1b1")
// alignContent = AlignContent.flexStart()
// animationName = listOf(text("foo"), text("bar"))
// animationIterationCount = listOf(
// Count.count(3), Count.infinite())
// animationTimingFunction = listOf(AnimationTimingFunction.cubicBezier(0.1, 0.2, 0.3, 0.4), AnimationTimingFunction.easeInOut())
}
}
}
println("======")
println(sd.generateCss())
}

View File

@@ -1,10 +0,0 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>kotlin-css-generator</title>
</head>
<body>
<script type="text/javascript" src="kotlin-css-generator.js"></script>
</body>
</html>

View File

@@ -1,229 +0,0 @@
package nl.astraeus.css
import nl.astraeus.css.properties.*
import nl.astraeus.css.properties.Color.Companion.hex
import nl.astraeus.css.style.Css
import nl.astraeus.css.style.Style
class StyleBase(
val mainColor: Color = Color.hsl(128, 50, 50),
val mainBackgroundColor: Color = Color.hsl(64, 50, 50),
val mainFont: TextProperty = text("Arial")
)
private fun Style.sizePX(
left: Int,
top: Int,
width: Int,
height: Int
) {
// this@sizePX.top = Measurement.px(top)
// this@sizePX.left = Measurement.px(left)
// this@sizePX.width = Measurement.px(width)
// this@sizePX.height = Measurement.px(height)
}
private fun generateCss(
base: StyleBase
): String {
val css = CssBuilder()
css.style {
select("body") {
// fontFamily = base.mainFont
// color = base.mainColor
// backgroundColor = base.mainBackgroundColor
}
select(".test") {
// top = Measurement.px(10)
// left = Measurement.em(5)
// backgroundColor = Color.rgba(255, 255, 255, 0.75)
select("> a") {
// color = Color.hsl(200, 50, 50)
}
}
select("nav") {
select("ul") {
// color = Color.hsl(0, 100, 25)
// backgroundColor = base.mainBackgroundColor
}
select("li") {
sizePX(25, 25, 200, 200)
select("a") {
// width = Measurement.px(725)
// background = text("red initial")
// backgroundColor = base.mainBackgroundColor
// all = All.initial()
}
}
}
}
return css.getCss()
}
fun main() {
val css1 = generateCss(StyleBase())
val css2 = generateCss(StyleBase(
Color.hsl(32, 40, 50),
Color.hsl(64, 60, 35),
text("Courier")
))
println(css1)
println(css2)
val border = css {
// borderRadius = BorderRadius(1, 2, 3, 4)
// borderColor = listOf(Color.hsl(22,66,55))
select("a") {
// width = Measurement.px(10)
}
}
val border2: Css = {
// borderRadius = BorderRadius(1, 2, 3, 4)
// borderColor = listOf(Color.hsl(20,60,50))
}
val font: Css = {
// fontFamily = text("Arial, Courier")
// fontSize = FontSize.larger()
}
val sd = style {
media("screen and (max-width: 600px)") {
fontSize(12.px())
fontWeight(FontWeight.normal)
supports("bla") {
media("bloe") {
fontSize(14.px())
}
}
}
select("#pipo") {
backgroundColor(hex("eeeeee"))
fontFamily("Arial, Courier")
// animationDelay = listOf(DelayDuration.initial())
select("div") {
fontFace {
fontFamily("SanSation")
fontSize(FontSize.larger)
src("font/sansation_bold.woff")
// fontStretch = FontStretch.condensed()
// fontStyle = FontStyle.italic()
// fontWeight = FontWeight._600()
}
fontFamily("SanSation")
// fontFamily = text("SanSation")
// color = Color.hex("1b1b1b1")
// alignContent = flexStart()
// animationName = listOf(
// text("foo"),
// text("bar")
// )
select("span") {
alignItems(AlignItems.baseline)
alignSelf(AlignSelf.flexStart)
// animationIterationCount = listOf(
// Count.count(3),
// Count.infinite()
// )
// animationTimingFunction = listOf(
// AnimationTimingFunction.cubicBezier(0.1, 0.2, 0.3, 0.4),
// AnimationTimingFunction.easeInOut()
// )
}
select("border-0") {
import(border)
// borderRadius = BorderRadius(4, 5, 6, 7)
}
select("border-1") {
import(border2)
// borderRadius = BorderRadius(4, 5, 6, 7)
}
select("border-2") {
// borderRadius = BorderRadius(4, 5, 6, 7)
import(border2)
borderStyle(BorderStyle.dashed, BorderStyle.dotted)
animationPlayState(AnimationPlayState.paused, AnimationPlayState.running)
keyFrames("mymove") {
percentage(0) {
top(0.px())
}
percentage(50) {
top(60.px())
}
percentage(100) {
top(90.px())
}
}
keyFrames("yourmove") {
percentage(0) {
top(10.px())
}
percentage(40) {
top(20.px())
}
percentage(60) {
top(30.px())
}
percentage(80) {
top(50.px())
color(Color.hex("0000ff"))
}
}
objectFit(ObjectFit.initial)
pageBreakAfter(PageBreak.auto)
tableLayout(TableLayout.auto)
tabSize(12.px())
// display = Display.none()
// borderBottomWidth = BorderWidth.perc(13)
}
}
}
}
val borderStyle = style {
select(".border") {
import(border)
import(font)
select("> p") {
// fontSize = FontSize.smaller()
}
}
}
val test = style {
select("nav") {
alignContent(AlignContent.stretch)
margin(0.px(), 2.em(), 0.5.px(), Measurement.auto)
}
}
println("======")
println(sd.generateCss())
println("======")
println(sd.generateCss(minified = true))
println("======")
println(borderStyle.generateCss())
println("======")
println(test.generateCss())
}