diff --git a/kodeview/build.gradle.kts b/kodeview/build.gradle.kts index 2e20552..ed03a71 100644 --- a/kodeview/build.gradle.kts +++ b/kodeview/build.gradle.kts @@ -1,3 +1,5 @@ +import org.jetbrains.kotlin.gradle.ExperimentalWasmDsl + @Suppress("DSL_SCOPE_VIOLATION") plugins { alias(libs.plugins.multiplatform) @@ -26,6 +28,12 @@ dependencies { kotlin { jvm() + @OptIn(ExperimentalWasmDsl::class) + wasmJs { + browser() + binaries.executable() + } + js(IR) { browser() } diff --git a/webExample/build.gradle.kts b/webExample/build.gradle.kts index 7606433..92193d7 100644 --- a/webExample/build.gradle.kts +++ b/webExample/build.gradle.kts @@ -1,3 +1,5 @@ +import org.jetbrains.kotlin.gradle.ExperimentalWasmDsl + @Suppress("DSL_SCOPE_VIOLATION") plugins { alias(libs.plugins.multiplatform) @@ -11,8 +13,15 @@ kotlin { binaries.executable() } + @OptIn(ExperimentalWasmDsl::class) + wasmJs { + browser() + binaries.executable() + } + sourceSets { - val jsMain by getting { + + val commonMain by getting { dependencies { implementation(compose.ui) implementation(compose.foundation) diff --git a/webExample/src/jsMain/kotlin/Dropdown.kt b/webExample/src/commonMain/kotlin/Dropdown.kt similarity index 100% rename from webExample/src/jsMain/kotlin/Dropdown.kt rename to webExample/src/commonMain/kotlin/Dropdown.kt diff --git a/webExample/src/jsMain/kotlin/ThemeSwitcher.kt b/webExample/src/commonMain/kotlin/ThemeSwitcher.kt similarity index 100% rename from webExample/src/jsMain/kotlin/ThemeSwitcher.kt rename to webExample/src/commonMain/kotlin/ThemeSwitcher.kt diff --git a/webExample/src/wasmJsMain/kotlin/main.js.kt b/webExample/src/wasmJsMain/kotlin/main.js.kt new file mode 100644 index 0000000..c1d121f --- /dev/null +++ b/webExample/src/wasmJsMain/kotlin/main.js.kt @@ -0,0 +1,154 @@ +import androidx.compose.foundation.layout.Arrangement +import androidx.compose.foundation.layout.Column +import androidx.compose.foundation.layout.Spacer +import androidx.compose.foundation.layout.fillMaxSize +import androidx.compose.foundation.layout.fillMaxWidth +import androidx.compose.foundation.layout.height +import androidx.compose.foundation.layout.padding +import androidx.compose.foundation.layout.size +import androidx.compose.material3.Divider +import androidx.compose.material3.MaterialTheme +import androidx.compose.material3.Surface +import androidx.compose.material3.Text +import androidx.compose.material3.TextFieldDefaults +import androidx.compose.material3.darkColorScheme +import androidx.compose.material3.lightColorScheme +import androidx.compose.runtime.mutableStateOf +import androidx.compose.runtime.remember +import androidx.compose.ui.Alignment +import androidx.compose.ui.ExperimentalComposeUiApi +import androidx.compose.ui.Modifier +import androidx.compose.ui.graphics.Color +import androidx.compose.ui.text.style.TextAlign +import androidx.compose.ui.unit.dp +import androidx.compose.ui.unit.sp +import androidx.compose.ui.window.CanvasBasedWindow +import dev.snipme.highlights.Highlights +import dev.snipme.highlights.model.SyntaxLanguage +import dev.snipme.highlights.model.SyntaxTheme +import dev.snipme.highlights.model.SyntaxThemes +import dev.snipme.highlights.model.SyntaxThemes.useDark +import dev.snipme.kodeview.view.material3.CodeEditText +import dev.snipme.kodeview.view.CodeTextView + +private val sampleCode = + """ + class Main { + public static void main(String[] args) { + int abcd = 100; + } + } + """.trimIndent() + +@ExperimentalComposeUiApi +fun main() { + CanvasBasedWindow( + title = "KodeView example", + canvasElementId = "ComposeTarget", + applyDefaultStyles = true, + ) { + val isDarkModeState = remember { mutableStateOf(false) } + val isDarkMode = isDarkModeState.value + + val highlightsState = remember { + mutableStateOf( + Highlights.Builder(code = sampleCode).build() + ) + } + val highlights = highlightsState.value + + fun updateSyntaxTheme(theme: SyntaxTheme) { + highlightsState.value = highlights.getBuilder() + .theme(theme) + .build() + } + + fun updateSyntaxLanguage(language: SyntaxLanguage) { + highlightsState.value = highlights.getBuilder() + .language(language) + .build() + } + + MaterialTheme(colorScheme = if (isDarkMode) darkColorScheme() else lightColorScheme()) { + Surface { + Column( + modifier = Modifier + .fillMaxSize() + .padding(16.dp), + horizontalAlignment = Alignment.Start, + verticalArrangement = Arrangement.SpaceBetween + ) { + Spacer(Modifier.height(8.dp)) + + ThemeSwitcher( + isDarkMode, + modifier = Modifier.fillMaxWidth(), + ) { setToDarkMode -> + isDarkModeState.value = setToDarkMode + updateSyntaxTheme(highlights.getTheme().useDark(setToDarkMode)!!) + } + + Spacer(Modifier.height(16.dp)) + + Text( + modifier = Modifier.fillMaxWidth(), + text = "KodeView", + fontSize = 18.sp, + textAlign = TextAlign.Center, + ) + + Spacer(modifier = Modifier.size(16.dp)) + + CodeTextView(highlights = highlights) + + Spacer(modifier = Modifier.size(16.dp)) + + Divider() + + Spacer(modifier = Modifier.size(16.dp)) + + Text("Edit this...") + CodeEditText( + highlights = highlights, + onValueChange = { textValue -> + highlightsState.value = highlights.getBuilder() + .code(textValue) + .build() + }, + colors = TextFieldDefaults.colors( + unfocusedContainerColor = Color.Transparent, + focusedContainerColor = Color.Transparent, + focusedIndicatorColor = Color.Transparent, + unfocusedIndicatorColor = Color.Transparent, + disabledIndicatorColor = Color.Transparent, + errorIndicatorColor = Color.Transparent, + ), + ) + + Spacer(modifier = Modifier.size(16.dp)) + + Spacer(modifier = Modifier.weight(1f)) + + Dropdown( + options = SyntaxThemes.getNames(), + selected = SyntaxThemes.themes().keys.indexOf(highlights.getTheme().key), + ) { selectedThemeName -> + updateSyntaxTheme( + SyntaxThemes.themes(isDarkMode)[selectedThemeName.lowercase()]!! + ) + } + + Spacer(modifier = Modifier.size(16.dp)) + + Dropdown( + options = SyntaxLanguage.getNames(), + selected = SyntaxLanguage.getNames().indexOfFirst { + it.equals(highlights.getLanguage().name, ignoreCase = true) + }) { selectedLanguage -> + updateSyntaxLanguage(SyntaxLanguage.getByName(selectedLanguage)!!) + } + } + } + } + } + } \ No newline at end of file diff --git a/webExample/src/wasmJsMain/resources/index.html b/webExample/src/wasmJsMain/resources/index.html new file mode 100644 index 0000000..446a5fc --- /dev/null +++ b/webExample/src/wasmJsMain/resources/index.html @@ -0,0 +1,15 @@ + + +
+ +