Skip to content

Commit cc0ad13

Browse files
committed
chore: cmp ui crash window
1 parent 4e924db commit cc0ad13

File tree

3 files changed

+72
-14
lines changed

3 files changed

+72
-14
lines changed
Lines changed: 18 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,13 @@
1+
@file:OptIn(ExperimentalComposeUiApi::class)
2+
3+
import androidx.compose.runtime.CompositionLocalProvider
14
import androidx.compose.ui.Alignment
5+
import androidx.compose.ui.ExperimentalComposeUiApi
26
import androidx.compose.ui.unit.dp
3-
import androidx.compose.ui.window.Window
4-
import androidx.compose.ui.window.WindowPosition
5-
import androidx.compose.ui.window.application
6-
import androidx.compose.ui.window.rememberWindowState
7+
import androidx.compose.ui.window.*
78
import java.awt.Dimension
89
import java.io.File
10+
import ui.crash.windowExceptionHandlerFactory
911

1012
val resource by lazy {
1113
val file =
@@ -14,13 +16,16 @@ val resource by lazy {
1416
}
1517

1618
fun main() = application {
17-
Window(
18-
title = resource,
19-
state =
20-
rememberWindowState(
21-
width = 800.dp, height = 600.dp, position = WindowPosition(Alignment.Center)),
22-
onCloseRequest = ::exitApplication) {
23-
window.minimumSize = Dimension(350, 600)
24-
App()
25-
}
19+
CompositionLocalProvider(
20+
LocalWindowExceptionHandlerFactory provides windowExceptionHandlerFactory,
21+
) {
22+
val windowState =
23+
rememberWindowState(
24+
width = 800.dp, height = 600.dp, position = WindowPosition(Alignment.Center))
25+
26+
Window(title = resource, state = windowState, onCloseRequest = ::exitApplication) {
27+
window.minimumSize = Dimension(350, 600)
28+
App()
29+
}
30+
}
2631
}
Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
@file:OptIn(ExperimentalComposeUiApi::class)
2+
3+
package ui.crash
4+
5+
import androidx.compose.ui.ExperimentalComposeUiApi
6+
import androidx.compose.ui.window.WindowExceptionHandler
7+
import androidx.compose.ui.window.WindowExceptionHandlerFactory
8+
import dev.suresh.log
9+
import java.awt.Dimension
10+
import java.awt.Font
11+
import java.io.File
12+
import javax.swing.JOptionPane
13+
import javax.swing.JScrollPane
14+
import javax.swing.JTextArea
15+
import kotlin.system.exitProcess
16+
17+
private const val FONT_SIZE = 10
18+
private const val MSG_WIDTH = 640
19+
private const val MSG_HEIGHT = 480
20+
21+
fun showCrashDialog(logDirectory: File, exception: Throwable) {
22+
val title = "App failed unexpectedly"
23+
val text = buildString {
24+
appendLine("Log directory:")
25+
appendLine(logDirectory)
26+
appendLine()
27+
appendLine("Stack trace:")
28+
appendLine(exception.stackTraceToString())
29+
}
30+
JOptionPane.showMessageDialog(
31+
null,
32+
JScrollPane(
33+
JTextArea(text).apply {
34+
font = Font(Font.MONOSPACED, Font.PLAIN, FONT_SIZE)
35+
lineWrap = false
36+
},
37+
JScrollPane.VERTICAL_SCROLLBAR_ALWAYS,
38+
JScrollPane.HORIZONTAL_SCROLLBAR_ALWAYS,
39+
)
40+
.apply { preferredSize = Dimension(MSG_WIDTH, MSG_HEIGHT) },
41+
title,
42+
JOptionPane.ERROR_MESSAGE,
43+
)
44+
}
45+
46+
val windowExceptionHandlerFactory = WindowExceptionHandlerFactory { window ->
47+
WindowExceptionHandler { ex ->
48+
window.dispose()
49+
log.error(ex) { "Application UI crash" }
50+
showCrashDialog(File("."), ex)
51+
exitProcess(1)
52+
}
53+
}

gradle/libs.versions.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -194,7 +194,7 @@ jetbrains-compose-nav = "2.8.0-alpha08"
194194
jetbrains-compose-viewmodel = "2.8.0"
195195
kobweb = "0.18.2"
196196
detekt = "1.23.6"
197-
detekt-compose-rules = "0.4.5"
197+
detekt-compose-rules = "0.4.9"
198198
mappie = "0.6.0"
199199

200200
[libraries]

0 commit comments

Comments
 (0)