Browse Source

Examples. Notepad. Move to 1.0.0-beta1

pull/1312/head
Igor Demin 3 years ago
parent
commit
ade07cb465
  1. 2
      examples/notepad/build.gradle.kts
  2. 2
      examples/notepad/src/main/kotlin/NotepadApplication.kt
  3. 3
      examples/notepad/src/main/kotlin/common/AppResources.kt
  4. 2
      examples/notepad/src/main/kotlin/main.kt
  5. 77
      examples/notepad/src/main/kotlin/util/AwtIcons.kt
  6. 3
      examples/notepad/src/main/kotlin/util/Dialogs.kt
  7. 1
      examples/notepad/src/main/kotlin/window/NotepadWindow.kt
  8. 12
      examples/notepad/src/main/kotlin/window/NotepadWindowState.kt

2
examples/notepad/build.gradle.kts

@ -5,7 +5,7 @@ plugins {
// __KOTLIN_COMPOSE_VERSION__
kotlin("jvm") version "1.5.31"
// __LATEST_COMPOSE_RELEASE_VERSION__
id("org.jetbrains.compose") version ("1.0.0-alpha4-build411")
id("org.jetbrains.compose") version ("1.0.0-beta1")
}
repositories {

2
examples/notepad/src/main/kotlin/NotepadApplication.kt

@ -1,7 +1,6 @@
import androidx.compose.runtime.Composable
import androidx.compose.runtime.key
import androidx.compose.runtime.rememberCoroutineScope
import androidx.compose.ui.ExperimentalComposeUiApi
import androidx.compose.ui.window.ApplicationScope
import androidx.compose.ui.window.MenuScope
import androidx.compose.ui.window.Tray
@ -22,7 +21,6 @@ fun ApplicationScope.NotepadApplication(state: NotepadApplicationState) {
}
}
@OptIn(ExperimentalComposeUiApi::class)
@Composable
private fun ApplicationScope.ApplicationTray(state: NotepadApplicationState) {
Tray(

3
examples/notepad/src/main/kotlin/common/AppResources.kt

@ -18,13 +18,12 @@ val LocalAppResources = staticCompositionLocalOf<AppResources> {
@Composable
fun rememberAppResources(): AppResources {
val icon = rememberVectorPainter(Icons.Default.Description, Color(0xFF2CA4E1))
val icon = rememberVectorPainter(Icons.Default.Description, tintColor = Color(0xFF2CA4E1))
return remember { AppResources(icon) }
}
class AppResources(val icon: VectorPainter)
@OptIn(ExperimentalComposeUiApi::class)
@Composable
fun rememberVectorPainter(image: ImageVector, tintColor: Color) =
rememberVectorPainter(

2
examples/notepad/src/main/kotlin/main.kt

@ -1,10 +1,8 @@
import androidx.compose.runtime.CompositionLocalProvider
import androidx.compose.ui.ExperimentalComposeUiApi
import androidx.compose.ui.window.application
import common.LocalAppResources
import common.rememberAppResources
@OptIn(ExperimentalComposeUiApi::class)
fun main() = application {
CompositionLocalProvider(LocalAppResources provides rememberAppResources()) {
NotepadApplication(rememberApplicationState())

77
examples/notepad/src/main/kotlin/util/AwtIcons.kt

@ -1,77 +0,0 @@
package util
import androidx.compose.runtime.CompositionLocalProvider
import androidx.compose.ui.geometry.isSpecified
import androidx.compose.ui.graphics.Canvas
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.ColorFilter
import androidx.compose.ui.graphics.ImageBitmap
import androidx.compose.ui.graphics.drawscope.CanvasDrawScope
import androidx.compose.ui.graphics.painter.Painter
import androidx.compose.ui.graphics.vector.ImageVector
import androidx.compose.ui.graphics.vector.rememberVectorPainter
import androidx.compose.ui.platform.LocalDensity
import androidx.compose.ui.platform.LocalLayoutDirection
import androidx.compose.ui.unit.Density
import androidx.compose.ui.unit.LayoutDirection
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.withContext
import java.awt.Point
import java.awt.image.BufferedImage
import java.awt.image.ColorModel
import java.awt.image.DataBuffer
import java.awt.image.DataBufferInt
import java.awt.image.Raster
import java.awt.image.SinglePixelPackedSampleModel
import kotlin.math.roundToInt
suspend fun ImageVector.toAwtImage(tintColor: Color): BufferedImage {
return withContext(Dispatchers.Default) {
compose {
val density = Density(1f)
val layoutDirection = LayoutDirection.Ltr
lateinit var result: BufferedImage
CompositionLocalProvider(
LocalDensity provides density,
LocalLayoutDirection provides layoutDirection,
) {
result = rememberVectorPainter(this@toAwtImage)
.toAwtImage(density, layoutDirection, ColorFilter.tint(tintColor))
}
result
}
}
}
private fun Painter.toAwtImage(
density: Density,
layoutDirection: LayoutDirection,
colorFilter: ColorFilter
): BufferedImage {
require(intrinsicSize.isSpecified) {
"Icon should support intrinsicSize"
}
val width = intrinsicSize.width.roundToInt()
val height = intrinsicSize.height.roundToInt()
val bitmap = ImageBitmap(width, height)
val canvas = Canvas(bitmap)
CanvasDrawScope().draw(
density, layoutDirection, canvas, intrinsicSize
) {
draw(intrinsicSize, colorFilter = colorFilter)
}
val pixels = IntArray(width * height)
bitmap.readPixels(pixels)
val bitMasks = intArrayOf(0xFF0000, 0xFF00, 0xFF, -0x1000000)
val sm = SinglePixelPackedSampleModel(DataBuffer.TYPE_INT, width, height, bitMasks)
val db = DataBufferInt(pixels, pixels.size)
val wr = Raster.createWritableRaster(sm, db, Point())
return BufferedImage(ColorModel.getRGBdefault(), wr, false, null)
}

3
examples/notepad/src/main/kotlin/util/Dialogs.kt

@ -6,6 +6,7 @@ import androidx.compose.ui.ExperimentalComposeUiApi
import androidx.compose.ui.window.AwtWindow
import androidx.compose.ui.window.FrameWindowScope
import androidx.compose.ui.window.WindowScope
import kotlinx.coroutines.DelicateCoroutinesApi
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.GlobalScope
import kotlinx.coroutines.launch
@ -15,7 +16,6 @@ import java.io.File
import java.nio.file.Path
import javax.swing.JOptionPane
@OptIn(ExperimentalComposeUiApi::class)
@Composable
fun FrameWindowScope.FileDialog(
title: String,
@ -41,6 +41,7 @@ fun FrameWindowScope.FileDialog(
dispose = FileDialog::dispose
)
@OptIn(DelicateCoroutinesApi::class)
@Composable
fun WindowScope.YesNoCancelDialog(
title: String,

1
examples/notepad/src/main/kotlin/window/NotepadWindow.kt

@ -14,7 +14,6 @@ import kotlinx.coroutines.launch
import util.FileDialog
import util.YesNoCancelDialog
@OptIn(ExperimentalComposeUiApi::class)
@Composable
fun NotepadWindow(state: NotepadWindowState) {
val scope = rememberCoroutineScope()

12
examples/notepad/src/main/kotlin/window/NotepadWindowState.kt

@ -8,15 +8,10 @@ import androidx.compose.ui.window.Notification
import androidx.compose.ui.window.WindowPlacement
import androidx.compose.ui.window.WindowState
import common.Settings
import kotlinx.coroutines.CompletableDeferred
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.GlobalScope
import kotlinx.coroutines.Job
import kotlinx.coroutines.*
import kotlinx.coroutines.channels.Channel
import kotlinx.coroutines.flow.Flow
import kotlinx.coroutines.flow.receiveAsFlow
import kotlinx.coroutines.launch
import kotlinx.coroutines.withContext
import util.AlertDialogResult
import java.nio.file.Path
@ -129,11 +124,11 @@ class NotepadWindowState(
try {
saveJob?.join()
_notifications.offer(NotepadWindowNotification.SaveSuccess(path))
_notifications.trySend(NotepadWindowNotification.SaveSuccess(path))
} catch (e: Exception) {
isChanged = true
e.printStackTrace()
_notifications.offer(NotepadWindowNotification.SaveError(path))
_notifications.trySend(NotepadWindowNotification.SaveError(path))
}
}
@ -171,6 +166,7 @@ class NotepadWindowState(
}
}
@OptIn(DelicateCoroutinesApi::class)
private fun Path.launchSaving(text: String) = GlobalScope.launch {
writeTextAsync(text)
}

Loading…
Cancel
Save