How Jetpack Compose for Web Enables Cross‑Platform UI with Kotlin
Jetpack Compose for Web, JetBrains' new Kotlin‑based framework, lets developers write responsive web interfaces that share code with desktop and Android, offering composable DOM APIs, multi‑platform widgets, and practical code examples to accelerate UI development.
Introduction
I discovered a multi‑platform UI debugging tool that lets a single codebase run on many platforms, which is impressive, so I’m sharing it here.
What is Jetpack Compose for Web?
The tool is JetBrains' newly released Jetpack Compose for Web . According to the official description, the project is built on Google’s modern UI toolkit Jetpack Compose and allows developers to write responsive Web UI using Kotlin.
Jetpack Compose itself is a new Android UI toolkit that simplifies and speeds up native interface development with less code, powerful tools, and an intuitive Kotlin API.
UI code and preview:
Jetpack Compose for Web aims to simplify and accelerate Web UI development, enabling UI code sharing across Web, desktop, and Android apps. It is currently in a technical preview stage.
Composable DOM API
Express design and layout through DOM elements and HTML tags.
Build UI representations using a type‑safe HTML DSL.
Create stylesheets with a type‑safe CSS DSL for full visual control.
Integrate with other JavaScript libraries via DOM sub‑trees.
Multi‑platform widgets with Web support
Leverage Kotlin’s expect‑actual mechanism to provide platform‑specific implementations, allowing Compose widgets to run on Android, desktop, and Web.
Experimental layout primitives and APIs similar to those in Compose for Desktop/Android.
Sample Code
Greeting example:
fun greet() = listOf("Hello", "Hallo", "Hola", "Servus").random()
renderComposable("greetingContainer") {
var greeting by remember { mutableStateOf(greet()) }
Button(attrs = { onClick { greeting = greet() } }) {
Text(greeting)
}
}
// Result: ServusBuilding a UI with Compose for Web:
fun main() {
renderComposable("root") {
var platform by remember { mutableStateOf("a platform") }
P { Text("Welcome to Compose for $platform! ") }
Button(attrs = { onClick { platform = "Web" } }) { Text("...for what?") }
A("https://www.jetbrains.com/lp/compose-web") { Text("Learn more!") }
}
}Simple counter using composable DOM:
fun main() {
val count = mutableStateOf(0)
renderComposable(rootElementId = "root") {
Button(attrs = { onClick { count.value-- } }) { Text("-") }
Span(style = { padding(15.px) }) { Text("${count.value}") }
Button(attrs = { onClick { count.value++ } }) { Text("+") }
}
}Defining and using a stylesheet:
object MyStyleSheet : StyleSheet() {
val container by style {
border(1.px, LineStyle.Solid, Color.RGB(255, 0, 0))
}
}
@Composable
fun MyComponent() {
Div(attrs = { classes(MyStyleSheet.container) }) {
Text("Hello world!")
}
}
fun main() {
renderComposable(rootElementId = "root") {
Style(MyStyleSheet)
MyComponent()
}
}Declaring and using CSS variables:
object MyVariables : CSSVariables {
val contentBackgroundColor by variable<Color>()
}
object MyStyleSheet : StyleSheet() {
val container by style { MyVariables.contentBackgroundColor(Color("blue")) }
val content by style { backgroundColor(MyVariables.contentBackgroundColor.value()) }
}
@Composable
fun MyComponent() {
Div(attrs = { classes(MyStyleSheet.container) }) {
Span(attrs = { classes(MyStyleSheet.content) }) { Text("Hello world!") }
}
}Additional preview image:
Signed-in readers can open the original source through BestHub's protected redirect.
This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactand we will review it promptly.
Java Backend Technology
Focus on Java-related technologies: SSM, Spring ecosystem, microservices, MySQL, MyCat, clustering, distributed systems, middleware, Linux, networking, multithreading. Occasionally cover DevOps tools like Jenkins, Nexus, Docker, and ELK. Also share technical insights from time to time, committed to Java full-stack development!
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.
