From 461e93fc565c46349ee3528c09036dd84d3b87e0 Mon Sep 17 00:00:00 2001 From: Spencer Lyon Date: Wed, 28 Feb 2018 17:26:53 -0500 Subject: [PATCH] ENH: provide "application/vnd.plotly.v1+json" for Plotly and PlotlyJS backends For use in jupyterlab and nteract closes #1418 closes #1386 --- src/Plots.jl | 1 + src/backends/plotly.jl | 10 +++++----- src/output.jl | 30 +++++++++++++++++++++++++++--- 3 files changed, 33 insertions(+), 8 deletions(-) diff --git a/src/Plots.jl b/src/Plots.jl index 51d70256..222270cb 100644 --- a/src/Plots.jl +++ b/src/Plots.jl @@ -14,6 +14,7 @@ using Base.Meta @reexport using PlotThemes import Showoff import StatsBase +import JSON using Requires diff --git a/src/backends/plotly.jl b/src/backends/plotly.jl index 8f21f565..5c2c58e7 100644 --- a/src/backends/plotly.jl +++ b/src/backends/plotly.jl @@ -86,8 +86,6 @@ const _plotly_js_path_remote = "https://cdn.plot.ly/plotly-latest.min.js" function _initialize_backend(::PlotlyBackend; kw...) @eval begin - import JSON - _js_code = open(readstring, _plotly_js_path, "r") # borrowed from https://github.com/plotly/plotly.py/blob/2594076e29584ede2d09f2aa40a8a195b3f3fc66/plotly/offline/offline.py#L64-L71 c/o @spencerlyon2 @@ -740,15 +738,17 @@ function plotly_hover!(d_out::KW, hover) end # get a list of dictionaries, each representing the series params -function plotly_series_json(plt::Plot) +function plotly_series(plt::Plot) slist = [] for series in plt.series_list append!(slist, plotly_series(plt, series)) end - JSON.json(slist) - # JSON.json(map(series -> plotly_series(plt, series), plt.series_list)) + slist end +# get json string for a list of dictionaries, each representing the series params +plotly_series_json(plt::Plot) = JSON.json(plotly_series(plt)) + # ---------------------------------------------------------------- const _use_remote = Ref(false) diff --git a/src/output.jl b/src/output.jl index 99a55d50..3932d94b 100644 --- a/src/output.jl +++ b/src/output.jl @@ -261,23 +261,47 @@ end @require IJulia begin if IJulia.inited + """ + Add extra jupyter mimetypes to display_dict based on the plot backed. + + The default is nothing, except for plotly based backends, where it + adds data for `application/vnd.plotly.v1+json` that is used in + frontends like jupyterlab and nteract. + """ + _extra_mime_info!(plt::Plot, out::Dict) = out + function _extra_mime_info!(plt::Plot{PlotlyJSBackend}, out::Dict) + out["application/vnd.plotly.v1+json"] = JSON.lower(plt.o) + out + end + + function _extra_mime_info!(plt::Plot{PlotlyBackend}, out::Dict) + out["application/vnd.plotly.v1+json"] = Dict( + :data => plotly_series(plt), + :layout => plotly_layout(plt) + ) + out + end + function IJulia.display_dict(plt::Plot) output_type = Symbol(plt.attr[:html_output_format]) if output_type == :auto output_type = get(_best_html_output_type, backend_name(plt.backend), :svg) end + out = Dict() if output_type == :png mime = "image/png" - Dict{String,String}(mime => base64encode(show, MIME(mime), plt)) + out[mime] = base64encode(show, MIME(mime), plt) elseif output_type == :svg mime = "image/svg+xml" - Dict{String,String}(mime => sprint(show, MIME(mime), plt)) + out[mime] = sprint(show, MIME(mime), plt) elseif output_type == :html mime = "text/html" - Dict{String,String}(mime => sprint(show, MIME(mime), plt)) + out[mime] = sprint(show, MIME(mime), plt) else error("Unsupported output type $output_type") end + _extra_mime_info!(plt, out) + out end # default text/plain passes to html... handles Interact issues