Show More
@@ -363,6 +363,30 b' class Latex(DisplayObject):' | |||
|
363 | 363 | |
|
364 | 364 | class SVG(DisplayObject): |
|
365 | 365 | |
|
366 | def __init__(self, data=None, url=None, filename=None, scoped=False): | |
|
367 | """Create a SVG display object given raw data. | |
|
368 | ||
|
369 | When this object is returned by an expression or passed to the | |
|
370 | display function, it will result in the data being displayed | |
|
371 | in the frontend. If the data is a URL, the data will first be | |
|
372 | downloaded and then displayed. | |
|
373 | ||
|
374 | Parameters | |
|
375 | ---------- | |
|
376 | data : unicode, str or bytes | |
|
377 | The Javascript source code or a URL to download it from. | |
|
378 | url : unicode | |
|
379 | A URL to download the data from. | |
|
380 | filename : unicode | |
|
381 | Path to a local file to load the data from. | |
|
382 | scoped : bool | |
|
383 | Should the SVG declarations be scoped. | |
|
384 | """ | |
|
385 | if not isinstance(scoped, (bool)): | |
|
386 | raise TypeError('expected bool, got: %r' % scoped) | |
|
387 | self.scoped = scoped | |
|
388 | super(SVG, self).__init__(data=data, url=url, filename=filename) | |
|
389 | ||
|
366 | 390 | # wrap data in a property, which extracts the <svg> tag, discarding |
|
367 | 391 | # document headers |
|
368 | 392 | _data = None |
@@ -371,6 +395,8 b' class SVG(DisplayObject):' | |||
|
371 | 395 | def data(self): |
|
372 | 396 | return self._data |
|
373 | 397 | |
|
398 | _scoped_class = "ipython-scoped" | |
|
399 | ||
|
374 | 400 | @data.setter |
|
375 | 401 | def data(self, svg): |
|
376 | 402 | if svg is None: |
@@ -383,6 +409,12 b' class SVG(DisplayObject):' | |||
|
383 | 409 | # get svg tag (should be 1) |
|
384 | 410 | found_svg = x.getElementsByTagName('svg') |
|
385 | 411 | if found_svg: |
|
412 | # If the user request scoping, tag the svg with the | |
|
413 | # ipython-scoped class | |
|
414 | if self.scoped: | |
|
415 | classes = (found_svg[0].getAttribute('class') + | |
|
416 | " " + self._scoped_class) | |
|
417 | found_svg[0].setAttribute('class', classes) | |
|
386 | 418 | svg = found_svg[0].toxml() |
|
387 | 419 | else: |
|
388 | 420 | # fallback on the input, trust the user |
@@ -494,36 +494,40 b' var IPython = (function (IPython) {' | |||
|
494 | 494 | |
|
495 | 495 | |
|
496 | 496 | OutputArea.prototype.append_svg = function (svg, md, element) { |
|
497 | // To avoid style or use collisions between multiple svg figures, | |
|
498 | // svg figures are wrapped inside an iframe. | |
|
499 | ||
|
500 | var iframe = $('<iframe/>') | |
|
501 | iframe.attr('frameborder', 0); | |
|
502 | iframe.attr('scrolling', 'no'); | |
|
503 | ||
|
504 | var wrapper = $("<div/>").addClass("output_subarea output_svg"); | |
|
497 | var wrapper = $('<div/>').addClass('output_subarea output_svg'); | |
|
505 | 498 | wrapper.append(svg); |
|
499 | var svg_element = wrapper.children()[0]; | |
|
500 | ||
|
501 | if (svg_element.classList.contains('ipython-scoped')) { | |
|
502 | // To avoid style or use collisions between multiple svg figures, | |
|
503 | // svg figures are wrapped inside an iframe. | |
|
504 | var iframe = $('<iframe/>') | |
|
505 | iframe.attr('frameborder', 0); | |
|
506 | iframe.attr('scrolling', 'no'); | |
|
507 | ||
|
508 | // Once the iframe is loaded, the svg is dynamically inserted | |
|
509 | iframe.on('load', function() { | |
|
510 | // Set the iframe height and width to fit the svg | |
|
511 | // (the +10 pixel offset handles the default body margins | |
|
512 | // in Chrome) | |
|
513 | iframe.width(svg_element.width.baseVal.value + 10); | |
|
514 | iframe.height(svg_element.height.baseVal.value + 10); | |
|
515 | ||
|
516 | // Workaround needed by Firefox, to properly render svg inside | |
|
517 | // iframes, see http://stackoverflow.com/questions/10177190/ | |
|
518 | // svg-dynamically-added-to-iframe-does-not-render-correctly | |
|
519 | iframe.contents()[0].open(); | |
|
520 | iframe.contents()[0].close(); | |
|
521 | ||
|
522 | // Insert the svg inside the iframe | |
|
523 | var body = iframe.contents().find('body'); | |
|
524 | body.html(wrapper.html()); | |
|
525 | }); | |
|
506 | 526 | |
|
507 | // Once the iframe is loaded, the svg is dynamically inserted | |
|
508 | iframe.on('load', function() { | |
|
509 | // Set the iframe height and width to fit the svg | |
|
510 | // (the +10 pixel offset handles the default body margins | |
|
511 | // in Chrome) | |
|
512 | var svg = wrapper.children()[0]; | |
|
513 | iframe.width(svg.width.baseVal.value + 10); | |
|
514 | iframe.height(svg.height.baseVal.value + 10); | |
|
515 | ||
|
516 | // Workaround needed by Firefox, to properly render svg inside iframes, | |
|
517 | // see http://stackoverflow.com/questions/10177190/svg-dynamically-added-to-iframe-does-not-render-correctly | |
|
518 | iframe.contents()[0].open(); | |
|
519 | iframe.contents()[0].close(); | |
|
520 | ||
|
521 | // Insert the svg inside the iframe | |
|
522 | var body = iframe.contents().find('body'); | |
|
523 | body.html(wrapper.html()); | |
|
524 | }); | |
|
525 | ||
|
526 | element.append(iframe); | |
|
527 | element.append(iframe); | |
|
528 | } else { | |
|
529 | element.append(wrapper); | |
|
530 | } | |
|
527 | 531 | }; |
|
528 | 532 | |
|
529 | 533 |
General Comments 0
You need to be logged in to leave comments.
Login now