@@ -21,6 +21,7 @@ import org.jetbrains.kotlinx.dataframe.columns.ColumnWithPath
21
21
import org.jetbrains.kotlinx.dataframe.columns.FrameColumn
22
22
import org.jetbrains.kotlinx.dataframe.impl.DataFrameSize
23
23
import org.jetbrains.kotlinx.dataframe.impl.columns.addPath
24
+ import org.jetbrains.kotlinx.dataframe.impl.io.resizeKeepingAspectRatio
24
25
import org.jetbrains.kotlinx.dataframe.impl.renderType
25
26
import org.jetbrains.kotlinx.dataframe.impl.scale
26
27
import org.jetbrains.kotlinx.dataframe.impl.truncate
@@ -31,6 +32,7 @@ import org.jetbrains.kotlinx.dataframe.name
31
32
import org.jetbrains.kotlinx.dataframe.nrow
32
33
import org.jetbrains.kotlinx.dataframe.size
33
34
import java.awt.Desktop
35
+ import java.awt.image.BufferedImage
34
36
import java.io.File
35
37
import java.io.InputStreamReader
36
38
import java.net.URL
@@ -152,7 +154,8 @@ internal fun AnyFrame.toHtmlData(
152
154
DataFrameReference (id, value.size)
153
155
}
154
156
} else {
155
- val html = formatter.format(value, cellRenderer, renderConfig)
157
+ val html =
158
+ formatter.format(downsizeBufferedImageIfNeeded(value, renderConfig), cellRenderer, renderConfig)
156
159
val style = renderConfig.cellFormatter?.invoke(FormattingDSL , it, col)?.attributes()?.ifEmpty { null }
157
160
?.joinToString(" ;" ) { " ${it.first} :${it.second} " }
158
161
HtmlContent (html, style)
@@ -180,6 +183,26 @@ internal fun AnyFrame.toHtmlData(
180
183
return DataFrameHtmlData (style = " " , body = body, script = script)
181
184
}
182
185
186
+ private const val DEFAULT_HTML_IMG_SIZE = 100
187
+
188
+ /* *
189
+ * This method resizes a BufferedImage if necessary, according to the provided DisplayConfiguration.
190
+ * It is essential to prevent potential memory problems when serializing HTML data for display in the Kotlin Notebook plugin.
191
+ *
192
+ * @param value The input value to be checked and possibly downsized.
193
+ * @param renderConfig The DisplayConfiguration to determine if downsizing is needed.
194
+ * @return The downsized BufferedImage if value is a BufferedImage and downsizing is enabled in the DisplayConfiguration,
195
+ * otherwise returns the input value unchanged.
196
+ */
197
+ private fun downsizeBufferedImageIfNeeded (value : Any? , renderConfig : DisplayConfiguration ): Any? =
198
+ when {
199
+ value is BufferedImage && renderConfig.downsizeBufferedImage -> {
200
+ value.resizeKeepingAspectRatio(DEFAULT_HTML_IMG_SIZE )
201
+ }
202
+
203
+ else -> value
204
+ }
205
+
183
206
/* *
184
207
* Renders [this] [DataFrame] as static HTML (meaning no JS is used).
185
208
* CSS rendering is enabled by default but can be turned off using [includeCss]
@@ -568,6 +591,7 @@ public data class DisplayConfiguration(
568
591
internal val localTesting : Boolean = flagFromEnv("KOTLIN_DATAFRAME_LOCAL_TESTING "),
569
592
var useDarkColorScheme : Boolean = false ,
570
593
var enableFallbackStaticTables : Boolean = true ,
594
+ var downsizeBufferedImage : Boolean = true
571
595
) {
572
596
public companion object {
573
597
public val DEFAULT : DisplayConfiguration = DisplayConfiguration ()
0 commit comments