@@ -14,13 +14,15 @@ import { loadScriptAsync, replaceScriptChildren } from './utils';
1414
1515declare global {
1616 interface Window {
17+ Plotly : any ;
1718 _ojs : {
1819 ojsConnector : any ;
1920 }
2021 }
2122}
2223
2324let stateElement : HTMLScriptElement | undefined ;
25+ let plotly : boolean = false ;
2426
2527export class PyodideEvaluator implements ExerciseEvaluator {
2628 container : OJSEvaluateElement ;
@@ -186,7 +188,7 @@ export class PyodideEvaluator implements ExerciseEvaluator {
186188
187189 const resultObject = await this . pyodide . runPythonAsync (
188190 atob ( require ( './scripts/Python/capture.py' ) )
189- , { locals } ) ;
191+ , { locals } ) ;
190192 locals . destroy ( ) ;
191193
192194 const value = await resultObject . get ( "value" ) ;
@@ -294,6 +296,24 @@ export class PyodideEvaluator implements ExerciseEvaluator {
294296 dispatchEvent ( new Event ( 'load' ) ) ;
295297 }
296298
299+ const appendPlotlyFigure = async ( figure : PyProxy ) => {
300+ const locals = await this . pyodide . toPy ( { figure } ) ;
301+ const figureJson = await this . pyodide . runPythonAsync ( `
302+ import json
303+ json.dumps(figure)
304+ ` , { locals } ) ;
305+
306+ if ( ! plotly ) {
307+ await loadScriptAsync ( "https://cdn.plot.ly/plotly-2.35.2.min.js" ) ;
308+ plotly = true ;
309+ }
310+ var figureObj = JSON . parse ( figureJson ) ;
311+
312+ const figureDiv = document . createElement ( 'div' ) ;
313+ window . Plotly . newPlot ( figureDiv , figureObj . data , figureObj . layout ) ;
314+ container . appendChild ( figureDiv ) ;
315+ }
316+
297317 const appendHtml = async ( html : string ) => {
298318 if ( options . output ) {
299319 const outputDiv = document . createElement ( "div" ) ;
@@ -342,11 +362,12 @@ export class PyodideEvaluator implements ExerciseEvaluator {
342362 container . appendChild ( errorDiv ) ;
343363 }
344364
345- for ( let i = 0 ; i < await result . outputs . length ; i ++ ) {
365+ for ( let i = 0 ; i < await result . outputs . length ; i ++ ) {
346366 const item = await result . outputs . get ( i ) ;
347367 const imagebitmap = await item . _repr_mime_ ( "application/html-imagebitmap" ) ;
348368 const html = await item . _repr_mime_ ( "text/html" ) ;
349369 const widget = await item . _repr_mime_ ( "application/vnd.jupyter.widget-view+json" ) ;
370+ const plotly = await item . _repr_mime_ ( "application/vnd.plotly.v1+json" ) ;
350371 const plain = await item . _repr_mime_ ( "text/plain" ) ;
351372 const png = await item . _repr_mime_ ( "image/png" ) ;
352373 const jpeg = await item . _repr_mime_ ( "image/jpeg" ) ;
@@ -358,6 +379,8 @@ export class PyodideEvaluator implements ExerciseEvaluator {
358379 appendHtml ( html ) ;
359380 } else if ( widget ) {
360381 appendJupyterWidget ( widget ) ;
382+ } else if ( plotly ) {
383+ appendPlotlyFigure ( plotly ) ;
361384 } else if ( png ) {
362385 appendDataUrlImage ( "image/png" , png ) ;
363386 } else if ( jpeg ) {
0 commit comments