feat(jbm): ast inspector
Signed-off-by: Infi <infi@infi.sh>
This commit is contained in:
parent
c8cb3c4aff
commit
420fba2c45
|
|
@ -20,7 +20,8 @@ fun SheetButton(
|
|||
modifier: Modifier = Modifier,
|
||||
supportingContent: @Composable (() -> Unit)? = null,
|
||||
trailingContent: @Composable (() -> Unit)? = null,
|
||||
dangerous: Boolean = false
|
||||
dangerous: Boolean = false,
|
||||
special: Boolean = false
|
||||
) {
|
||||
Box(
|
||||
modifier = modifier
|
||||
|
|
@ -33,6 +34,8 @@ fun SheetButton(
|
|||
CompositionLocalProvider(
|
||||
value = if (dangerous) {
|
||||
LocalContentColor provides MaterialTheme.colorScheme.error
|
||||
} else if (special) {
|
||||
LocalContentColor provides MaterialTheme.colorScheme.primary
|
||||
} else {
|
||||
LocalContentColor provides MaterialTheme.colorScheme.onSurface
|
||||
}
|
||||
|
|
@ -44,6 +47,8 @@ fun SheetButton(
|
|||
CompositionLocalProvider(
|
||||
value = if (dangerous) {
|
||||
LocalContentColor provides MaterialTheme.colorScheme.error
|
||||
} else if (special) {
|
||||
LocalContentColor provides MaterialTheme.colorScheme.primary
|
||||
} else {
|
||||
LocalContentColor provides MaterialTheme.colorScheme.onSurface
|
||||
}
|
||||
|
|
@ -56,6 +61,8 @@ fun SheetButton(
|
|||
CompositionLocalProvider(
|
||||
value = if (dangerous) {
|
||||
LocalContentColor provides MaterialTheme.colorScheme.error
|
||||
} else if (special) {
|
||||
LocalContentColor provides MaterialTheme.colorScheme.primary
|
||||
} else {
|
||||
LocalContentColor provides MaterialTheme.colorScheme.onSurface
|
||||
}
|
||||
|
|
@ -69,6 +76,8 @@ fun SheetButton(
|
|||
CompositionLocalProvider(
|
||||
value = if (dangerous) {
|
||||
LocalContentColor provides MaterialTheme.colorScheme.error
|
||||
} else if (special) {
|
||||
LocalContentColor provides MaterialTheme.colorScheme.primary
|
||||
} else {
|
||||
LocalContentColor provides MaterialTheme.colorScheme.onSurface
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,103 @@
|
|||
package chat.revolt.sheets
|
||||
|
||||
import androidx.compose.foundation.clickable
|
||||
import androidx.compose.foundation.layout.Column
|
||||
import androidx.compose.foundation.layout.ExperimentalLayoutApi
|
||||
import androidx.compose.foundation.layout.FlowRow
|
||||
import androidx.compose.foundation.layout.fillMaxWidth
|
||||
import androidx.compose.foundation.layout.padding
|
||||
import androidx.compose.foundation.rememberScrollState
|
||||
import androidx.compose.foundation.verticalScroll
|
||||
import androidx.compose.material3.HorizontalDivider
|
||||
import androidx.compose.material3.LocalContentColor
|
||||
import androidx.compose.material3.MaterialTheme
|
||||
import androidx.compose.material3.Text
|
||||
import androidx.compose.runtime.Composable
|
||||
import androidx.compose.runtime.getValue
|
||||
import androidx.compose.runtime.mutableStateOf
|
||||
import androidx.compose.runtime.remember
|
||||
import androidx.compose.runtime.setValue
|
||||
import androidx.compose.ui.Modifier
|
||||
import androidx.compose.ui.draw.drawBehind
|
||||
import androidx.compose.ui.geometry.Offset
|
||||
import androidx.compose.ui.unit.dp
|
||||
import chat.revolt.components.generic.SheetHeaderPadding
|
||||
import chat.revolt.markdown.jbm.JBM
|
||||
import chat.revolt.markdown.jbm.JBMApi
|
||||
import org.intellij.markdown.ast.ASTNode
|
||||
import org.intellij.markdown.ast.getTextInNode
|
||||
|
||||
@OptIn(JBM::class)
|
||||
@Composable
|
||||
fun JBMDebuggerSheet(content: String, modifier: Modifier = Modifier) {
|
||||
val rendered = remember(content) { JBMApi.parse(content) }
|
||||
Column {
|
||||
SheetHeaderPadding {
|
||||
Text(
|
||||
text = "Inspect AST",
|
||||
style = MaterialTheme.typography.headlineSmall
|
||||
)
|
||||
}
|
||||
Column(modifier.verticalScroll(rememberScrollState())) {
|
||||
JBMDebugTree(rendered, content)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Composable
|
||||
fun JBMDebugTree(node: ASTNode, source: String, modifier: Modifier = Modifier) {
|
||||
var showChildren by remember { mutableStateOf(false) }
|
||||
val scheme = MaterialTheme.colorScheme
|
||||
|
||||
Column(
|
||||
modifier
|
||||
.padding(start = 16.dp)
|
||||
.clickable { showChildren = !showChildren }) {
|
||||
JBMDebugNode(node, source, showChildren)
|
||||
if (showChildren && node.children.isNotEmpty()) {
|
||||
Column(Modifier.drawBehind {
|
||||
drawLine(
|
||||
color = scheme.primary,
|
||||
start = Offset(0f, 0f),
|
||||
end = Offset(0f, size.height),
|
||||
strokeWidth = 2.dp.toPx()
|
||||
)
|
||||
}) {
|
||||
node.children.forEach { JBMDebugTree(it, source) }
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@OptIn(ExperimentalLayoutApi::class)
|
||||
@Composable
|
||||
fun JBMDebugNode(node: ASTNode, source: String, showingChildren: Boolean) {
|
||||
Column {
|
||||
FlowRow {
|
||||
if (node.children.isNotEmpty()) {
|
||||
Text(if (showingChildren) "▼ " else "▶ ")
|
||||
}
|
||||
Text(node.type.toString())
|
||||
Text(" - ")
|
||||
if (node.children.isNotEmpty()) {
|
||||
Text("${node.children.size} " + if (node.children.size == 1) "child" else "children")
|
||||
} else {
|
||||
Text("No children")
|
||||
}
|
||||
}
|
||||
|
||||
val text = try {
|
||||
node.getTextInNode(source)
|
||||
} catch (e: Exception) {
|
||||
"<exception>"
|
||||
}
|
||||
Text(
|
||||
text.take(50).toString() + if (text.length > 50) "…" else "",
|
||||
color = if (text == "<exception>") MaterialTheme.colorScheme.error else LocalContentColor.current,
|
||||
modifier = Modifier.padding(4.dp)
|
||||
)
|
||||
HorizontalDivider(
|
||||
Modifier.fillMaxWidth()
|
||||
)
|
||||
}
|
||||
}
|
||||
|
|
@ -36,6 +36,7 @@ import androidx.compose.ui.res.painterResource
|
|||
import androidx.compose.ui.res.stringResource
|
||||
import androidx.compose.ui.text.AnnotatedString
|
||||
import androidx.compose.ui.unit.dp
|
||||
import chat.revolt.BuildConfig
|
||||
import chat.revolt.R
|
||||
import chat.revolt.api.REVOLT_APP
|
||||
import chat.revolt.api.RevoltAPI
|
||||
|
|
@ -44,6 +45,7 @@ import chat.revolt.api.internals.Roles
|
|||
import chat.revolt.api.internals.has
|
||||
import chat.revolt.api.routes.channel.deleteMessage
|
||||
import chat.revolt.api.routes.channel.react
|
||||
import chat.revolt.api.settings.Experiments
|
||||
import chat.revolt.callbacks.UiCallbacks
|
||||
import chat.revolt.components.chat.Message
|
||||
import chat.revolt.components.generic.SheetButton
|
||||
|
|
@ -76,6 +78,9 @@ fun MessageContextSheet(
|
|||
var showShareSheet by remember { mutableStateOf(false) }
|
||||
var showReactSheet by remember { mutableStateOf(false) }
|
||||
var showDeleteMessageConfirmation by remember { mutableStateOf(false) }
|
||||
var showInspectASTSheet by remember { mutableStateOf(false) }
|
||||
val showInspectASTSheetButton =
|
||||
BuildConfig.DEBUG || (message.content != null && Experiments.useKotlinBasedMarkdownRenderer.isEnabled)
|
||||
|
||||
if (showShareSheet) {
|
||||
val shareSheetState = rememberModalBottomSheetState(skipPartiallyExpanded = true)
|
||||
|
|
@ -305,6 +310,19 @@ fun MessageContextSheet(
|
|||
)
|
||||
}
|
||||
|
||||
if (showInspectASTSheet) {
|
||||
val inspectASTSheetState = rememberModalBottomSheetState(skipPartiallyExpanded = true)
|
||||
|
||||
ModalBottomSheet(
|
||||
sheetState = inspectASTSheetState,
|
||||
onDismissRequest = {
|
||||
showInspectASTSheet = false
|
||||
}
|
||||
) {
|
||||
JBMDebuggerSheet(message.content ?: "")
|
||||
}
|
||||
}
|
||||
|
||||
Column(
|
||||
modifier = Modifier
|
||||
.verticalScroll(rememberScrollState())
|
||||
|
|
@ -407,6 +425,26 @@ fun MessageContextSheet(
|
|||
}
|
||||
)
|
||||
|
||||
if (showInspectASTSheetButton) {
|
||||
SheetButton(
|
||||
leadingContent = {
|
||||
Icon(
|
||||
painter = painterResource(id = R.drawable.ic_file_tree_24dp),
|
||||
contentDescription = null
|
||||
)
|
||||
},
|
||||
headlineContent = {
|
||||
Text(
|
||||
text = "Inspect AST"
|
||||
)
|
||||
},
|
||||
onClick = {
|
||||
showInspectASTSheet = true
|
||||
},
|
||||
special = true
|
||||
)
|
||||
}
|
||||
|
||||
SheetButton(
|
||||
leadingContent = {
|
||||
Icon(
|
||||
|
|
|
|||
|
|
@ -0,0 +1,9 @@
|
|||
<vector xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:height="24dp"
|
||||
android:width="24dp"
|
||||
android:viewportWidth="24"
|
||||
android:viewportHeight="24">
|
||||
<path
|
||||
android:fillColor="#ffffff"
|
||||
android:pathData="M3,3H9V7H3V3M15,10H21V14H15V10M15,17H21V21H15V17M13,13H7V18H13V20H7L5,20V9H7V11H13V13Z" />
|
||||
</vector>
|
||||
Loading…
Reference in New Issue