def components(self, obj, fmt=None, comm=True, **kwargs): """ Returns data and metadata dictionaries containing HTML and JS components to include render in app, notebook, or standalone document. """ if isinstance(obj, Plot): plot = obj else: plot, fmt = self._validate(obj, fmt) data, metadata = {}, {} if isinstance(plot, Viewable): from bokeh.document import Document dynamic = bool(plot.object.traverse(lambda x: x, [DynamicMap])) embed = (not (dynamic or self.widget_mode == 'live') or config.embed) comm = self.comm_manager.get_server_comm() if comm else None doc = Document() with config.set(embed=embed): model = plot.layout._render_model(doc, comm) return render_model(model, comm) if embed else render_mimebundle(model, doc, comm) else: html = self._figure_data(plot, fmt, as_script=True, **kwargs) data['text/html'] = html return (data, {MIME_TYPES['jlab-hv-exec']: metadata})
def test_render_mimebundle(document, comm): div = Div() data, metadata = render_mimebundle(div, document, comm) assert metadata == { 'application/vnd.holoviews_exec.v0+json': { 'id': div.ref['id'] } } assert 'application/vnd.holoviews_exec.v0+json' in data assert 'text/html' in data assert data['application/vnd.holoviews_exec.v0+json'] == ''
def components(self, obj, fmt=None, comm=True, **kwargs): """ Returns data and metadata dictionaries containing HTML and JS components to include render in app, notebook, or standalone document. """ if isinstance(obj, Plot): plot = obj else: plot, fmt = self._validate(obj, fmt) data, metadata = {}, {} if isinstance(plot, Viewable): registry = list(Stream.registry.items()) objects = plot.object.traverse(lambda x: x) dynamic, streams = False, False for source in objects: dynamic |= isinstance(source, DynamicMap) streams |= any( src is source or (src._plot_id is not None and src._plot_id == source._plot_id) for src, streams in registry for s in streams) embed = (not (dynamic or streams or self.widget_mode == 'live') or config.embed) comm = self.comm_manager.get_server_comm() if comm else None doc = Document() with config.set(embed=embed): model = plot.layout._render_model(doc, comm) if embed: return render_model(model, comm) else: args = (model, doc, comm) if panel_version > '0.9.3': from panel.models.comm_manager import CommManager ref = model.ref['id'] manager = CommManager(comm_id=comm.id, plot_id=ref) client_comm = self.comm_manager.get_client_comm( on_msg=partial(plot._on_msg, ref, manager), on_error=partial(plot._on_error, ref), on_stdout=partial(plot._on_stdout, ref)) manager.client_comm_id = client_comm.id args = args + (manager, ) return render_mimebundle(*args) else: html = self._figure_data(plot, fmt, as_script=True, **kwargs) data['text/html'] = html return (data, {MIME_TYPES['jlab-hv-exec']: metadata})
def _render_panel(self, plot, embed=False, comm=True): comm = self.comm_manager.get_server_comm() if comm else None doc = Document() with config.set(embed=embed): model = plot.layout._render_model(doc, comm) if embed: return render_model(model, comm) ref = model.ref['id'] manager = PnCommManager(comm_id=comm.id, plot_id=ref) client_comm = self.comm_manager.get_client_comm( on_msg=partial(plot._on_msg, ref, manager), on_error=partial(plot._on_error, ref), on_stdout=partial(plot._on_stdout, ref) ) manager.client_comm_id = client_comm.id return render_mimebundle(model, doc, comm, manager)
def _figure_data(self, plot, fmt, doc=None, as_script=False, **kwargs): """ Given a plot instance, an output format and an optional bokeh document, return the corresponding data. If as_script is True, the content will be split in an HTML and a JS component. """ model = plot.state if doc is None: doc = plot.document else: plot.document = doc for m in model.references(): m._document = None doc.theme = self.theme doc.add_root(model) # Bokeh raises warnings about duplicate tools and empty subplots # but at the holoviews level these are not issues logger = logging.getLogger(bokeh.core.validation.check.__file__) logger.disabled = True if fmt == 'png': from bokeh.io.export import get_screenshot_as_png img = get_screenshot_as_png(plot.state, None) imgByteArr = BytesIO() img.save(imgByteArr, format='PNG') data = imgByteArr.getvalue() if as_script: b64 = base64.b64encode(data).decode("utf-8") (mime_type, tag) = MIME_TYPES[fmt], HTML_TAGS[fmt] src = HTML_TAGS['base64'].format(mime_type=mime_type, b64=b64) div = tag.format(src=src, mime_type=mime_type, css='') else: div = render_mimebundle(plot.state, doc, plot.comm)[0]['text/html'] plot.document = doc if as_script: return div else: return data
def _figure_data(self, plot, fmt, doc=None, as_script=False, **kwargs): """ Given a plot instance, an output format and an optional bokeh document, return the corresponding data. If as_script is True, the content will be split in an HTML and a JS component. """ model = plot.state if doc is None: doc = plot.document else: plot.document = doc for m in model.references(): m._document = None doc.theme = self.theme doc.add_root(model) # Bokeh raises warnings about duplicate tools and empty subplots # but at the holoviews level these are not issues logger = logging.getLogger(bokeh.core.validation.check.__file__) logger.disabled = True if fmt == 'gif': from bokeh.io.export import get_screenshot_as_png, create_webdriver webdriver = create_webdriver() nframes = len(plot) frames = [] for i in range(nframes): plot.update(i) img = get_screenshot_as_png(plot.state, webdriver) frames.append(img) webdriver.close() bio = BytesIO() duration = (1. / self.fps) * 1000 frames[0].save(bio, format='GIF', append_images=frames[1:], save_all=True, duration=duration, loop=0) bio.seek(0) data = bio.read() elif fmt == 'png': from bokeh.io.export import get_screenshot_as_png img = get_screenshot_as_png(plot.state, None) imgByteArr = BytesIO() img.save(imgByteArr, format='PNG') data = imgByteArr.getvalue() else: div = render_mimebundle(plot.state, doc, plot.comm)[0]['text/html'] if as_script and fmt in ['png', 'gif']: b64 = base64.b64encode(data).decode("utf-8") (mime_type, tag) = MIME_TYPES[fmt], HTML_TAGS[fmt] src = HTML_TAGS['base64'].format(mime_type=mime_type, b64=b64) div = tag.format(src=src, mime_type=mime_type, css='') plot.document = doc if as_script: return div else: return data
def components(self, obj, fmt=None, comm=True, **kwargs): """ Returns data and metadata dictionaries containing HTML and JS components to include render in app, notebook, or standalone document. """ if isinstance(obj, Plot): plot = obj else: plot, fmt = self._validate(obj, fmt) data, metadata = {}, {} if isinstance(plot, Viewable): registry = list(Stream.registry.items()) objects = plot.object.traverse(lambda x: x) dynamic, streams = False, False for source in objects: dynamic |= isinstance(source, DynamicMap) streams |= any( src is source or (src._plot_id is not None and src._plot_id == source._plot_id) for src, streams in registry for s in streams ) embed = (not (dynamic or streams or self.widget_mode == 'live') or config.embed) # This part should be factored out in Panel and then imported # here for HoloViews 2.0, which will be able to require a # recent Panel version. if embed or config.comms == 'default': comm = self.comm_manager.get_server_comm() if comm else None doc = Document() with config.set(embed=embed): model = plot.layout._render_model(doc, comm) if embed: return render_model(model, comm) args = (model, doc, comm) if panel_version > '0.9.3': from panel.models.comm_manager import CommManager ref = model.ref['id'] manager = CommManager(comm_id=comm.id, plot_id=ref) client_comm = self.comm_manager.get_client_comm( on_msg=partial(plot._on_msg, ref, manager), on_error=partial(plot._on_error, ref), on_stdout=partial(plot._on_stdout, ref) ) manager.client_comm_id = client_comm.id args = args + (manager,) return render_mimebundle(*args) # Handle rendering object as ipywidget widget = ipywidget(plot, combine_events=True) if hasattr(widget, '_repr_mimebundle_'): return widget._repr_mimebundle() plaintext = repr(widget) if len(plaintext) > 110: plaintext = plaintext[:110] + '…' data = { 'text/plain': plaintext, } if widget._view_name is not None: data['application/vnd.jupyter.widget-view+json'] = { 'version_major': 2, 'version_minor': 0, 'model_id': widget._model_id } if config.comms == 'vscode': # Unfortunately VSCode does not yet handle _repr_mimebundle_ from IPython.display import display display(data, raw=True) return {'text/html': '<div style="display: none"></div>'}, {} return data, {} else: html = self._figure_data(plot, fmt, as_script=True, **kwargs) data['text/html'] = html return (data, {MIME_TYPES['jlab-hv-exec']: metadata})