Kira Resari
Kira Resari

Reputation: 2420

How to add Desktop Support to Kotlin Multiplatform Mobile Project

Using Android Studio with the Kotlin Multiplatform Mobile plugin, I have created a KMM project, which provides support for Android and iOS.

However, I would also like to be able to use the same code base and UI to deploy to create a desktop app. Is that possible? And if yes, how?

Upvotes: 7

Views: 5564

Answers (2)

FieryCat
FieryCat

Reputation: 1889

By now it can be used https://kmp.jetbrains.com/ to generate project for all needed platforms.

Upvotes: 3

Kira Resari
Kira Resari

Reputation: 2420

Yes, it is possible. In fact, this tutorial details how to do it, albeit in a quite roundabout way that took me several days to complete:

https://www.kodeco.com/books/kotlin-multiplatform-by-tutorials/v1.0/chapters/1-introduction

Because of that, I have taken the liberty to creating a short summary for how you can create a basic project setup for a Desktop/Android/iOS app:

  1. Install the Kotlin Multiplatform Mobile and Compose Multiplatform IDE Support plugins in Android Studio

  2. Create a new Kotlin Multiplatform App project (under Phone and Tablet)

    • For the following points, I am going to assume the project name is "My Project" and the package name is com.domain.project
  3. In the shared/build.gradle.kts, in the kotlin block, after android(), add:

    • jvm("desktop"){
          compilations.all {
              kotlinOptions.jvmTarget = "11"
          }
      }
      
  4. Add a new desktop folder at the top level of the app

  5. Add a new file build.gradle.kts into the desktop folder, and fill it with this content:

    • import org.jetbrains.compose.compose
      import org.jetbrains.compose.desktop.application.dsl.TargetFormat
      
      plugins {
          kotlin("multiplatform")
          id("org.jetbrains.compose") version "1.2.2"
      }
      
      group = "com.domain.project"
      version = "1.0.0"
      
      kotlin {
          jvm {
              withJava()
              compilations.all {
                  kotlinOptions.jvmTarget = "11"
              }
          }
          sourceSets {
              val jvmMain by getting {
                  kotlin.srcDirs("src/jvmMain/kotlin")
                  dependencies {
                      implementation(compose.desktop.currentOs)
                      api(compose.runtime)
                      api(compose.foundation)
                      api(compose.material)
                      api(compose.ui)
                      api(compose.materialIconsExtended)
      
                      implementation(project(":shared"))
                  }
              }
          }
      }
      
      compose.desktop {
          application {
              mainClass = "MainKt"
              nativeDistributions {
                  targetFormats(TargetFormat.Dmg, TargetFormat.Msi, TargetFormat.Deb)
                  packageName = "MyProject"
                  macOS {
                      bundleID = "com.domain.project"
                  }
              }
          }
      }
      
  6. On the top level, in the settings.gradle.kts add include(":desktop") at the very end

  7. Click on "sync now" (Or File > Sync project with gradle files)

    • After the sync, the desktop folder should now be recognized as a module, indicated by a little square at the bottom right of the folder icon
  8. In the desktop module, create the folder chain src/jvmMain/kotlin

  9. In the just created kotlin folder create the Kotlin file Main, and fill it as follows:

    • import androidx.compose.foundation.layout.fillMaxSize
      import androidx.compose.material.Surface
      import androidx.compose.ui.Modifier
      import androidx.compose.ui.window.Window
      import androidx.compose.ui.window.application
      import androidx.compose.ui.window.rememberWindowState
      import androidx.compose.material.*
      
      fun main() {
          application {
              val windowState = rememberWindowState()
      
              Window(
                  onCloseRequest = ::exitApplication,
                  state = windowState,
                  title = "My Project"
              ) {
                  Surface(modifier = Modifier.fillMaxSize()) {
                      Text(text = "Welcome to my Project")
                  }
              }
          }
      }
      
  10. Add a run configuration of type Gradle with the following settings:

    • Name: "Desktop"
    • Run: "run"
    • Gradle Project: "project:desktop"
  11. Create the file shared/src/desktopMain/kotiln/com.domain.project/Platform.kt, and fill it with this:

    • package com.domain.project
      
      class DesktopPlatform : Platform {
          override val name: String = "Desktop"
      }
      
      actual fun getPlatform(): Platform = DesktopPlatform()
      
  12. You should now be able to run the desktop app

After that, you can then create shared Compose views that will work on both android and desktop. Chapter 5 of aforementioned tutorial covers that:

https://www.kodeco.com/books/kotlin-multiplatform-by-tutorials/v1.0/chapters/5-developing-ui-compose-multiplatform

In addition, here's a bare-bones version of a project that I created using the above steps:

https://github.com/KiraResari/ceal-chronicler/releases/tag/basic-android-and-desktop-app

Upvotes: 17

Related Questions