Skip to content

Commit

Permalink
[JEWEL-TBD] Load markdown images using Coil3
Browse files Browse the repository at this point in the history
It supports every image as an inline node
  • Loading branch information
Oleg Baskakov committed Jan 23, 2025
1 parent c64d343 commit 7fdb5ac
Show file tree
Hide file tree
Showing 10 changed files with 259 additions and 32 deletions.
2 changes: 1 addition & 1 deletion .idea/runConfigurations/IDEA.xml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

7 changes: 7 additions & 0 deletions platform/jewel/gradle/libs.versions.toml
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
[versions]
coil = "3.0.4"
commonmark = "0.24.0"
composeDesktop = "1.7.1"
detekt = "1.23.6"
Expand All @@ -17,6 +18,11 @@ ktfmtGradlePlugin = "0.20.1"
poko = "0.17.1"

[libraries]
coil-compose = { module = "io.coil-kt.coil3:coil-compose", version.ref = "coil" }
# network is only needed in a standalone non-ide version
coil-network-ktor2 = { module = "io.coil-kt.coil3:coil-network-ktor2", version.ref = "coil" }
coil-svg = { module = "io.coil-kt.coil3:coil-svg", version.ref = "coil" }

commonmark-core = { module = "org.commonmark:commonmark", version.ref = "commonmark" }
commonmark-ext-autolink = { module = "org.commonmark:commonmark-ext-autolink", version.ref = "commonmark" }

Expand All @@ -25,6 +31,7 @@ filePicker = { module = "com.darkrockstudios:mpfilepicker", version = "3.1.0" }
kotlinSarif = { module = "io.github.detekt.sarif4k:sarif4k", version.ref = "kotlinSarif" }
kotlin-reflect = { module = "org.jetbrains.kotlin:kotlin-reflect", version.ref = "kotlin" }
kotlinx-serialization-json = { module = "org.jetbrains.kotlinx:kotlinx-serialization-json", version.ref = "kotlinxSerialization" }
ktor-client-java = { module = "io.ktor:ktor-client-java", version = "2.3.12" }

jna-core = { module = "net.java.dev.jna:jna", version.ref = "jna" }

Expand Down
4 changes: 4 additions & 0 deletions platform/jewel/markdown/core/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,10 @@ plugins {
dependencies {
api(projects.ui)
api(libs.commonmark.core)
runtimeOnly(libs.ktor.client.java)
implementation(libs.coil.compose)
implementation(libs.coil.network.ktor2)
implementation(libs.coil.svg)

testImplementation(compose.desktop.uiTestJUnit4)
testImplementation(projects.ui)
Expand Down
126 changes: 126 additions & 0 deletions platform/jewel/markdown/core/intellij.platform.jewel.markdown.core.iml
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,132 @@
</SOURCES>
</library>
</orderEntry>
<orderEntry type="module-library">
<library name="io.coil.kt.coil3.core.jvm" type="repository">
<properties include-transitive-deps="false" maven-id="io.coil-kt.coil3:coil-core-jvm:3.0.4">
<verification>
<artifact url="file://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-core-jvm/3.0.4/coil-core-jvm-3.0.4.jar">
<sha256sum>635860bca98d3709b5714e3356100cb20af825a28d2f930bfcb448d7f78cfbdf</sha256sum>
</artifact>
</verification>
</properties>
<CLASSES>
<root url="jar://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-core-jvm/3.0.4/coil-core-jvm-3.0.4.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES>
<root url="jar://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-core-jvm/3.0.4/coil-core-jvm-3.0.4-sources.jar!/" />
</SOURCES>
</library>
</orderEntry>
<orderEntry type="module-library">
<library name="io.coil.kt.coil3.jvm" type="repository">
<properties include-transitive-deps="false" maven-id="io.coil-kt.coil3:coil-jvm:3.0.4">
<verification>
<artifact url="file://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-jvm/3.0.4/coil-jvm-3.0.4.jar">
<sha256sum>cca25e168e69956d01c5581a6523582f1809805d74c478e91802a15e321906e4</sha256sum>
</artifact>
</verification>
</properties>
<CLASSES>
<root url="jar://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-jvm/3.0.4/coil-jvm-3.0.4.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES>
<root url="jar://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-jvm/3.0.4/coil-jvm-3.0.4-sources.jar!/" />
</SOURCES>
</library>
</orderEntry>
<orderEntry type="module-library" exported="">
<library name="io.coil.kt.coil3.compose.core.jvm" type="repository">
<properties include-transitive-deps="false" maven-id="io.coil-kt.coil3:coil-compose-core-jvm:3.0.4">
<verification>
<artifact url="file://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-compose-core-jvm/3.0.4/coil-compose-core-jvm-3.0.4.jar">
<sha256sum>a0c8585e76bf426025d509e57fa09a7f9cc030327d641b93555714646b28721b</sha256sum>
</artifact>
</verification>
</properties>
<CLASSES>
<root url="jar://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-compose-core-jvm/3.0.4/coil-compose-core-jvm-3.0.4.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES>
<root url="jar://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-compose-core-jvm/3.0.4/coil-compose-core-jvm-3.0.4-sources.jar!/" />
</SOURCES>
</library>
</orderEntry>
<orderEntry type="module-library" exported="">
<library name="io.coil.kt.coil3.compose.jvm" type="repository">
<properties include-transitive-deps="false" maven-id="io.coil-kt.coil3:coil-compose-jvm:3.0.4">
<verification>
<artifact url="file://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-compose-jvm/3.0.4/coil-compose-jvm-3.0.4.jar">
<sha256sum>fdff25fb0065a29130ef4fc2276c91c11fd69ea8df8b1c241f648ce1b161b5a3</sha256sum>
</artifact>
</verification>
</properties>
<CLASSES>
<root url="jar://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-compose-jvm/3.0.4/coil-compose-jvm-3.0.4.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES>
<root url="jar://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-compose-jvm/3.0.4/coil-compose-jvm-3.0.4-sources.jar!/" />
</SOURCES>
</library>
</orderEntry>
<orderEntry type="module-library">
<library name="io.coil.kt.coil3.network.core.jvm" type="repository">
<properties include-transitive-deps="false" maven-id="io.coil-kt.coil3:coil-network-core-jvm:3.0.4">
<verification>
<artifact url="file://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-network-core-jvm/3.0.4/coil-network-core-jvm-3.0.4.jar">
<sha256sum>3268b588b18708b91bd9db300579d3fec9970570aeda8a34a5ee5b8a94fb43f8</sha256sum>
</artifact>
</verification>
</properties>
<CLASSES>
<root url="jar://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-network-core-jvm/3.0.4/coil-network-core-jvm-3.0.4.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES>
<root url="jar://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-network-core-jvm/3.0.4/coil-network-core-jvm-3.0.4-sources.jar!/" />
</SOURCES>
</library>
</orderEntry>
<orderEntry type="module-library">
<library name="io.coil.kt.coil3.network.ktor2.jvm" type="repository">
<properties include-transitive-deps="false" maven-id="io.coil-kt.coil3:coil-network-ktor2-jvm:3.0.4">
<verification>
<artifact url="file://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-network-ktor2-jvm/3.0.4/coil-network-ktor2-jvm-3.0.4.jar">
<sha256sum>1b5b67d6cc0ae0272e285cabe37e270637780f2465eeef0fbb883b6f89311124</sha256sum>
</artifact>
</verification>
</properties>
<CLASSES>
<root url="jar://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-network-ktor2-jvm/3.0.4/coil-network-ktor2-jvm-3.0.4.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES>
<root url="jar://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-network-ktor2-jvm/3.0.4/coil-network-ktor2-jvm-3.0.4-sources.jar!/" />
</SOURCES>
</library>
</orderEntry>
<orderEntry type="module-library" exported="">
<library name="io.coil.kt.coil3.svg.jvm" type="repository">
<properties include-transitive-deps="false" maven-id="io.coil-kt.coil3:coil-svg-jvm:3.0.4">
<verification>
<artifact url="file://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-svg-jvm/3.0.4/coil-svg-jvm-3.0.4.jar">
<sha256sum>ce0c4898911033bc28eb1483ce48b6f87ec76d01fc04574b79a8e9dfd56aa311</sha256sum>
</artifact>
</verification>
</properties>
<CLASSES>
<root url="jar://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-svg-jvm/3.0.4/coil-svg-jvm-3.0.4.jar!/" />
</CLASSES>
<JAVADOC />
<SOURCES>
<root url="jar://$MAVEN_REPOSITORY$/io/coil-kt/coil3/coil-svg-jvm/3.0.4/coil-svg-jvm-3.0.4-sources.jar!/" />
</SOURCES>
</library>
</orderEntry>
<orderEntry type="module-library" scope="TEST">
<library name="org.jetbrains.compose.ui.ui.test.junit4" type="repository">
<properties include-transitive-deps="false" maven-id="org.jetbrains.compose.ui:ui-test-junit4:1.7.1">
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,10 @@ import androidx.compose.runtime.setValue
import androidx.compose.ui.Modifier
import androidx.compose.ui.semantics.semantics
import androidx.compose.ui.unit.dp
import coil3.ImageLoader
import coil3.PlatformContext
import coil3.compose.setSingletonImageLoaderFactory
import coil3.memory.MemoryCache
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.withContext
Expand Down Expand Up @@ -76,6 +80,7 @@ public fun Markdown(
markdownStyling: MarkdownStyling = JewelTheme.markdownStyling,
blockRenderer: MarkdownBlockRenderer = DefaultMarkdownBlockRenderer(markdownStyling),
) {
setSingletonImageLoaderFactory(::createImageLoader)
if (selectable) {
SelectionContainer(modifier.semantics { rawMarkdown = markdown }) {
Column(verticalArrangement = Arrangement.spacedBy(markdownStyling.blockVerticalSpacing)) {
Expand Down Expand Up @@ -110,6 +115,7 @@ public fun LazyMarkdown(
markdownStyling: MarkdownStyling = JewelTheme.markdownStyling,
blockRenderer: MarkdownBlockRenderer = JewelTheme.markdownBlockRenderer,
) {
setSingletonImageLoaderFactory(::createImageLoader)
if (selectable) {
SelectionContainer(modifier) {
LazyColumn(
Expand All @@ -131,3 +137,17 @@ public fun LazyMarkdown(
}
}
}

private const val IMAGES_MEMORY_CACHE_SIZE = 24L * 1024 * 1024 // 24mb

/**
* This method sets up an image loader with a memory cache but disables the disk cache. Disabling the disk cache is
* necessary because Coil crashes when attempting to use the file system cache with IDEA platform.
*
* Otherwise, Coil3 will throw java.lang.NoSuchMethodError: kotlinx.coroutines.CoroutineDispatcher.limitedParallelism
*/
private fun createImageLoader(context: PlatformContext) =
ImageLoader.Builder(context)
.memoryCache { MemoryCache.Builder().maxSizeBytes(IMAGES_MEMORY_CACHE_SIZE).build() }
.diskCache(null)
.build()
Original file line number Diff line number Diff line change
Expand Up @@ -236,7 +236,7 @@ public class MarkdownProcessor(
}

private fun Node.tryProcessMarkdownBlock(): MarkdownBlock? =
// Non-Block children are ignored
// Nodes that are not blocks or unsupported types are ignored
when (this) {
is Paragraph -> toMarkdownParagraph()
is Heading -> toMarkdownHeadingOrNull()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -77,17 +77,7 @@ public open class DefaultInlineMarkdownRenderer(private val rendererExtensions:
}

is InlineMarkdown.Image -> {
appendInlineContent(
INLINE_IMAGE,
buildString {
appendLine(child.source)
append(child.alt)
if (!child.title.isNullOrBlank()) {
appendLine()
append(child.title)
}
},
)
appendInlineContent(child.source, "![${child.title}](...)")
}

is InlineMarkdown.CustomNode ->
Expand Down
Loading

0 comments on commit 7fdb5ac

Please sign in to comment.