├── .babelrc
├── .gitignore
├── LICENSE
├── README.md
├── dist
├── aframe-html-shader.js
└── aframe-html-shader.min.js
├── example.gif
├── examples
├── basic
│ ├── cheesecake.png
│ └── index.html
├── dynamic
│ ├── index.css
│ └── index.html
└── stress
│ ├── index.css
│ └── index.html
├── index.html
├── index.js
├── lib
└── html2canvas
│ ├── clone.js
│ ├── color.js
│ ├── core.js
│ ├── dummyimagecontainer.js
│ ├── font.js
│ ├── fontmetrics.js
│ ├── framecontainer.js
│ ├── gradientcontainer.js
│ ├── imagecontainer.js
│ ├── imageloader.js
│ ├── lineargradientcontainer.js
│ ├── log.js
│ ├── nodecontainer.js
│ ├── nodeparser.js
│ ├── proxy.js
│ ├── proxyimagecontainer.js
│ ├── pseudoelementcontainer.js
│ ├── renderer.js
│ ├── renderers
│ └── canvas.js
│ ├── stackingcontext.js
│ ├── support.js
│ ├── svgcontainer.js
│ ├── svgnodecontainer.js
│ ├── textcontainer.js
│ ├── utils.js
│ ├── webkitgradientcontainer.js
│ └── xhr.js
├── package.json
└── webpack.config.js
/.babelrc:
--------------------------------------------------------------------------------
1 | { "presets": ["es2015"] }
2 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | .sw[ponm]
2 | examples/build.js
3 | examples/node_modules/
4 | gh-pages
5 | node_modules/
6 | npm-debug.log
7 | .DS_Store
--------------------------------------------------------------------------------
/LICENSE:
--------------------------------------------------------------------------------
1 | The MIT License (MIT)
2 |
3 | Copyright (c) 2015 Mayo Tobita
4 |
5 | Permission is hereby granted, free of charge, to any person obtaining a copy
6 | of this software and associated documentation files (the "Software"), to deal
7 | in the Software without restriction, including without limitation the rights
8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 | copies of the Software, and to permit persons to whom the Software is
10 | furnished to do so, subject to the following conditions:
11 |
12 | The above copyright notice and this permission notice shall be included in all
13 | copies or substantial portions of the Software.
14 |
15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21 | SOFTWARE.
22 |
23 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # A-Frame HTML Shader
2 |
3 | A shader to render 2D HTML and CSS to a texture for [A-Frame](https://aframe.io).
4 |
5 | Inspired by:
6 |
7 | - [@scenevr](https://github.com/scenevr)'s [htmltexture-component](https://github.com/scenevr/htmltexture-component)
8 | - [@niklasvh](https://github.com/niklasvh)'s [html2canvas](https://github.com/niklasvh/html2canvas)
9 |
10 | **[DEMO](https://mayognaise.github.io/aframe-html-shader/basic/index.html)**
11 |
12 | 
13 |
14 | **The screenshot of the HTML element is done via [`html2canvas`](https://html2canvas.hertzen.com/). To learn more about the library, check out [`html2canvas`'s documentation](https://html2canvas.hertzen.com/documentation.html)**
15 |
16 | ## Properties
17 |
18 | - A-Frame's basic material properties still supported (e.g., `side`, `transparent`).
19 | - `width` and `height` are sizes to capture. For example, if the HTML element's dimensions are `640x480` and `width: 200; height: 100`, then the rendered HTML canvas will be cropped to 200px width and 100px height from the left-top position.
20 | - `fps` is the framerate to render per second. If we only need to render once and be static, we can keep the value at `0`.
21 | - `ratio` lets us use the HTML element's natural aspect ratio. If we keep the value as `null`, the generated canvas will scaled for fit to the entity's geometry. If we set `ratio: width`, the geometry's height will be changed to match the HTML element's ratio, and vice-versa for `ratio: height`.
22 |
23 | | Property | Description | Default Value |
24 | | -------- | ----------- | ------------- |
25 | | target | DOM element to render, given by a CSS selector (e.g., `#foo`). | null |
26 | | width | Width to capture. | Target's width |
27 | | height | height to capture. | Target's height |
28 | | fps | FPS to render. For example, providing 10 will refresh the material against the HTML 10 times per second. By default, the material will be static. | 0 |
29 | | ratio | Use target's ratio (i.e., `width`, `height`). | height |
30 | | debug | For debugging purposes, a DOM element which to append a rendered canvas to. Provided via a CSS selector (e.g., `#debug`). debug DOM to append generated canvas from `html2canvas` | null |
31 |
32 | For reference, check out the following links:
33 |
34 | - [Material](https://aframe.io/docs/components/material.html)
35 | - [Textures](https://aframe.io/docs/components/material.html#Textures)
36 | - [Flat Shading Model](https://aframe.io/docs/core/shaders.html#Flat-Shading-Model)
37 |
38 | [Available options](https://html2canvas.hertzen.com/documentation.html#available-options) by `html2canvas` will be ready for properties soon.
39 |
40 | ## Limitations
41 |
42 | We will often see that the rendered looks different from how the source HTML in
43 | 2D. The process takes trial-and-error and can also depend on the device.
44 |
45 | To check what is actually rendered by `html2canvas`, set the `debug` property
46 | to append and view the generated canvas. More for limitations, see
47 | [`html2canvas`'s documentation on
48 | limitations](https://html2canvas.hertzen.com/documentation.html#limitations).
49 |
50 | ## Method
51 |
52 | The following method is coming soon:
53 |
54 | - render() (This is useful when you set `fps` as `0`)
55 |
56 | ## Events
57 |
58 | The following events are coming soon:
59 |
60 | - `html-ready` when `html2canvas` set and ready to render
61 | - `html-draw` each time it renders
62 |
63 | ## Visibility
64 |
65 | For the conversion to canvas to work, we need to make the target HTML element
66 | technically visible and within the viewport, but we also don't want it to get
67 | in the way of our scene. We usually want to give the HTML element a fixed
68 | position and z-index it under everything:
69 |
70 | ```html
71 |
72 | ```
73 |
74 | ## Usage
75 |
76 | ### Browser Installation
77 |
78 | Install and use by directly including the [browser files](dist):
79 |
80 | ```html
81 |
82 | My A-Frame Scene
83 |
84 |
85 |
86 |
87 |
88 |
89 |
90 |
91 |
92 |
95 |
96 | ```
97 |
98 | ### NPM Installation
99 |
100 | Install via NPM:
101 |
102 | ```bash
103 | npm install --save aframe-html-shader
104 | ```
105 |
106 | Then register and use.
107 |
108 | ```js
109 | import 'aframe'
110 | import 'aframe-html-shader'
111 | ```
112 |
--------------------------------------------------------------------------------
/dist/aframe-html-shader.min.js:
--------------------------------------------------------------------------------
1 | !function(t){function e(r){if(n[r])return n[r].exports;var i=n[r]={exports:{},id:r,loaded:!1};return t[r].call(i.exports,i,i.exports,e),i.loaded=!0,i.exports}var n={};return e.m=t,e.c=n,e.p="",e(0)}([function(t,e,n){"use strict";function r(t){return t&&t.__esModule?t:{default:t}}function i(t,e){return{status:"error",target:e,message:t,timestamp:Date.now()}}var o="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},s=n(7),a=r(s);if("undefined"==typeof AFRAME)throw"Component attempted to register before AFRAME was available.";var c=AFRAME.utils.debug;c.enable("shader:html:warn");var h=c("shader:html:warn"),u=c("shader:html:debug");AFRAME.registerShader("html",{schema:{color:{type:"color"},fog:{default:!0},target:{default:null},debug:{default:null},fps:{type:"number",default:0},width:{default:null},height:{default:null},ratio:{default:null}},init:function(t){return u("init",t),this.__cnv=document.createElement("canvas"),this.__cnv.width=2,this.__cnv.height=2,this.__ctx=this.__cnv.getContext("2d"),this.__texture=new THREE.Texture(this.__cnv),this.__reset(),this.material=new THREE.MeshBasicMaterial({map:this.__texture}),this.el.sceneEl.addBehavior(this),this.material},update:function(t){return u("update",t),this.__updateMaterial(t),this.__updateTexture(t),this.material},tick:function(t){if(!this.__paused&&this.__target&&this.__nextTime){var e=Date.now();e>this.__nextTime&&this.__render()}},__updateMaterial:function(t){var e=this.material,n=this.__getMaterialData(t);Object.keys(n).forEach(function(t){e[t]=n[t]})},__getMaterialData:function(t){return{fog:t.fog,color:new THREE.Color(t.color)}},__setTexure:function(t){u("__setTexure",t),"error"===t.status?(h("Error: "+t.message+"\ntarget: "+t.target),this.__reset()):"success"===t.status&&t.target!==this.__textureSrc&&this.__ready(t)},__updateTexture:function(t){var e=this,n=t.target,r=t.fps,i=t.width,o=t.height,s=t.ratio;this.__width=i||this.schema.width.default,this.__height=o||this.schema.height.default;var a=function(){e.__debugEl&&(e.__debugEl.innerHTML="",e.__debugEl=e.schema.debug.default)};if(t.debug){var c=this.__validateAndGetQuerySelector(t.debug);c&&!c.error?this.__debugEl=c:a()}else a();if(s&&"width"===s||"height"===s?this.__ratio=s:this.__ratio=this.schema.ratio.default,r)if(this.__fps>0)this.__fps=r;else if(r===-1){this.__fps=this.schema.fps.default,this.__target&&this.__render();var h=Object.assign({},this.el.getAttribute("material"));delete h.fps,this.el.setAttribute("material",h)}else this.__fps=r,this.__target&&(this.play(),this.__render());else this.__fps>0?this.pause():this.__fps=this.schema.fps.default;if(n){if(n===this.__target)return;this.__target=n,this.__validateSrc(n,this.__setTexure.bind(this))}else this.__reset()},__validateSrc:function(t,e){var n=void 0,r=this.__validateAndGetQuerySelector(t);if(r&&"object"===("undefined"==typeof r?"undefined":o(r))){if(r.error)n=r.error;else{var s=r.tagName.toLowerCase();"img"===s||"video"===s?n="For <"+s+"> element, please use `shader:flat`":e({status:"success",target:t,targetEl:r,timestamp:Date.now()})}if(n){var a=i(n,t);e(a)}}},__validateAndGetQuerySelector:function(t){try{var e=document.querySelector(t);return e?e:{error:"No element was found matching the selector"}}catch(t){return{error:"no valid selector"}}},pause:function(){u("pause"),this.__paused=!0,this.__nextTime=null},play:function(){u("play"),this.__paused=!1},togglePlayback:function(){this.paused()?this.play():this.pause()},paused:function(){return this.__paused},__clearCanvas:function(){this.__ctx&&this.__texture&&(this.__ctx.clearRect(0,0,this.__width,this.__height),this.__texture.needsUpdate=!0)},__draw:function(t){if(u("__draw"),this.__ctx&&this.__texture){var e=t.width/t.height,n=this.__cnv.width=THREE.Math.nearestPowerOfTwo(t.width),r=this.__cnv.height=THREE.Math.nearestPowerOfTwo(t.height);if(this.__ctx.drawImage(t,0,0,n,r),this.__texture.needsUpdate=!0,this.__ratio){var i=this.el.getObject3D("mesh").geometry.metadata.parameters,o=i.width,s=i.height;this.el.setAttribute("geometry",Object.assign({},this.el.getAttribute("geometry"),{width:"width"===this.__ratio?o:s*e,height:"width"===this.__ratio?o/e:s}))}this.__debugEl&&(this.__debugEl.innerHTML="",this.__debugEl.appendChild(t)),this.__setNextTick()}},__render:function(){if(this.__nextTime=null,this.__targetEl){var t=this.__targetEl.getBoundingClientRect(),e=t.width,n=t.height;(0,a.default)(this.__targetEl,{background:void 0,width:this.__width||e,height:this.__height||n,onrendered:this.__draw.bind(this)})}},__setNextTick:function(){this.__fps>0&&(this.__nextTime=Date.now()+1e3/this.__fps)},__ready:function(t){var e=t.target,n=t.targetEl;u("__ready"),this.__target=e,this.__targetEl=n,this.play(),this.__render()},__reset:function(){this.pause(),this.__clearCanvas(),this.__target=null,this.__targetEl=null,this.__debugEl=null}})},function(t,e){"use strict";e.smallImage=function(){return"data:image/gif;base64,R0lGODlhAQABAIAAAAAAAP///yH5BAEAAAAALAAAAAABAAEAAAIBRAA7"},e.bind=function(t,e){return function(){return t.apply(e,arguments)}},e.decode64=function(t){var e,n,r,i,o,s,a,c,h="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/",u=t.length,l="";for(e=0;e>4,a=(15&r)<<4|i>>2,c=(3&i)<<6|o,l+=64===i?String.fromCharCode(s):64===o||o===-1?String.fromCharCode(s,a):String.fromCharCode(s,a,c);return l},e.getBounds=function(t){if(t.getBoundingClientRect){var e=t.getBoundingClientRect(),n=null==t.offsetWidth?e.width:t.offsetWidth;return{top:e.top,bottom:e.bottom||e.top+e.height,right:e.left+n,left:e.left,width:n,height:null==t.offsetHeight?e.height:t.offsetHeight}}return{}},e.offsetBounds=function(t){var n=t.offsetParent?e.offsetBounds(t.offsetParent):{top:0,left:0};return{top:t.offsetTop+n.top,bottom:t.offsetTop+t.offsetHeight+n.top,right:t.offsetLeft+n.left+t.offsetWidth,left:t.offsetLeft+n.left,width:t.offsetWidth,height:t.offsetHeight}},e.parseBackgrounds=function(t){var e,n,r,i,o,s,a,c=" \r\n\t",h=[],u=0,l=0,d=function(){e&&('"'===n.substr(0,1)&&(n=n.substr(1,n.length-2)),n&&a.push(n),"-"===e.substr(0,1)&&(i=e.indexOf("-",1)+1)>0&&(r=e.substr(0,i),e=e.substr(i)),h.push({prefix:r,method:e.toLowerCase(),value:o,args:a,image:null})),a=[],e=r=n=o=""};return a=[],e=r=n=o="",t.split("").forEach(function(t){if(!(0===u&&c.indexOf(t)>-1)){switch(t){case'"':s?s===t&&(s=null):s=t;break;case"(":if(s)break;if(0===u)return u=1,void(o+=t);l++;break;case")":if(s)break;if(1===u){if(0===l)return u=0,o+=t,void d();l--}break;case",":if(s)break;if(0===u)return void d();if(1===u&&0===l&&!e.match(/^url$/i))return a.push(n),n="",void(o+=t)}o+=t,0===u?e+=t:n+=t}}),d(),h}},function(t,e){"use strict";var n=function t(){t.options.logging&&window.console&&window.console.log&&Function.prototype.bind.call(window.console.log,window.console).apply(window.console,[Date.now()-t.options.start+"ms","html2canvas:"].concat([].slice.call(arguments,0)))};n.options={logging:!1},t.exports=n},function(t,e,n){"use strict";function r(t,e){this.node=t,this.parent=e,this.stack=null,this.bounds=null,this.borders=null,this.clip=[],this.backgroundClip=[],this.offsetBounds=null,this.visible=null,this.computedStyles=null,this.colors={},this.styles={},this.backgroundImages=null,this.transformData=null,this.transformMatrix=null,this.isPseudoElement=!1,this.opacity=null}function i(t){var e=t.options[t.selectedIndex||0];return e?e.text||"":""}function o(t){if(t&&"matrix"===t[1])return t[2].split(",").map(function(t){return parseFloat(t.trim())});if(t&&"matrix3d"===t[1]){var e=t[2].split(",").map(function(t){return parseFloat(t.trim())});return[e[0],e[1],e[4],e[5],e[12],e[13]]}}function s(t){return t.toString().indexOf("%")!==-1}function a(t){return t.replace("px","")}function c(t){return parseFloat(t)}var h=n(4),u=n(1),l=u.getBounds,d=u.parseBackgrounds,p=u.offsetBounds;r.prototype.cloneTo=function(t){t.visible=this.visible,t.borders=this.borders,t.bounds=this.bounds,t.clip=this.clip,t.backgroundClip=this.backgroundClip,t.computedStyles=this.computedStyles,t.styles=this.styles,t.backgroundImages=this.backgroundImages,t.opacity=this.opacity},r.prototype.getOpacity=function(){return null===this.opacity?this.opacity=this.cssFloat("opacity"):this.opacity},r.prototype.assignStack=function(t){this.stack=t,t.children.push(this)},r.prototype.isElementVisible=function(){return this.node.nodeType===Node.TEXT_NODE?this.parent.visible:"none"!==this.css("display")&&"hidden"!==this.css("visibility")&&!this.node.hasAttribute("data-html2canvas-ignore")&&("INPUT"!==this.node.nodeName||"hidden"!==this.node.getAttribute("type"))},r.prototype.css=function(t){return this.computedStyles||(this.computedStyles=this.isPseudoElement?this.parent.computedStyle(this.before?":before":":after"):this.computedStyle(null)),this.styles[t]||(this.styles[t]=this.computedStyles[t])},r.prototype.prefixedCss=function(t){var e=["webkit","moz","ms","o"],n=this.css(t);return void 0===n&&e.some(function(e){return n=this.css(e+t.substr(0,1).toUpperCase()+t.substr(1)),void 0!==n},this),void 0===n?null:n},r.prototype.computedStyle=function(t){return this.node.ownerDocument.defaultView.getComputedStyle(this.node,t)},r.prototype.cssInt=function(t){var e=parseInt(this.css(t),10);return isNaN(e)?0:e},r.prototype.color=function(t){return this.colors[t]||(this.colors[t]=new h(this.css(t)))},r.prototype.cssFloat=function(t){var e=parseFloat(this.css(t));return isNaN(e)?0:e},r.prototype.fontWeight=function(){var t=this.css("fontWeight");switch(parseInt(t,10)){case 401:t="bold";break;case 400:t="normal"}return t},r.prototype.parseClip=function(){var t=this.css("clip").match(this.CLIP);return t?{top:parseInt(t[1],10),right:parseInt(t[2],10),bottom:parseInt(t[3],10),left:parseInt(t[4],10)}:null},r.prototype.parseBackgroundImages=function(){return this.backgroundImages||(this.backgroundImages=d(this.css("backgroundImage")))},r.prototype.cssList=function(t,e){var n=(this.css(t)||"").split(",");return n=n[e||0]||n[0]||"auto",n=n.trim().split(" "),1===n.length&&(n=[n[0],s(n[0])?"auto":n[0]]),n},r.prototype.parseBackgroundSize=function(t,e,n){var r,i,o=this.cssList("backgroundSize",n);if(s(o[0]))r=t.width*parseFloat(o[0])/100;else{if(/contain|cover/.test(o[0])){var a=t.width/t.height,c=e.width/e.height;return a3&&(this.a=t[3])),Array.isArray(t)};var r=/^#([a-f0-9]{3})$/i;n.prototype.hex3=function(t){var e=null;return null!==(e=t.match(r))&&(this.r=parseInt(e[1][0]+e[1][0],16),this.g=parseInt(e[1][1]+e[1][1],16),this.b=parseInt(e[1][2]+e[1][2],16)),null!==e};var i=/^#([a-f0-9]{6})$/i;n.prototype.hex6=function(t){var e=null;return null!==(e=t.match(i))&&(this.r=parseInt(e[1].substring(0,2),16),this.g=parseInt(e[1].substring(2,4),16),this.b=parseInt(e[1].substring(4,6),16)),null!==e};var o=/^rgb\(\s*(\d{1,3})\s*,\s*(\d{1,3})\s*,\s*(\d{1,3})\s*\)$/;n.prototype.rgb=function(t){var e=null;return null!==(e=t.match(o))&&(this.r=Number(e[1]),this.g=Number(e[2]),this.b=Number(e[3])),null!==e};var s=/^rgba\(\s*(\d{1,3})\s*,\s*(\d{1,3})\s*,\s*(\d{1,3})\s*,\s*(\d?\.?\d+)\s*\)$/;n.prototype.rgba=function(t){var e=null;return null!==(e=t.match(s))&&(this.r=Number(e[1]),this.g=Number(e[2]),this.b=Number(e[3]),this.a=Number(e[4])),null!==e},n.prototype.toString=function(){return null!==this.a&&1!==this.a?"rgba("+[this.r,this.g,this.b,this.a].join(",")+")":"rgb("+[this.r,this.g,this.b].join(",")+")"},n.prototype.namedColor=function(t){t=t.toLowerCase();var e=a[t];if(e)this.r=e[0],this.g=e[1],this.b=e[2];else if("transparent"===t)return this.r=this.g=this.b=this.a=0,!0;return!!e},n.prototype.isColor=!0;var a={aliceblue:[240,248,255],antiquewhite:[250,235,215],aqua:[0,255,255],aquamarine:[127,255,212],azure:[240,255,255],beige:[245,245,220],bisque:[255,228,196],black:[0,0,0],blanchedalmond:[255,235,205],blue:[0,0,255],blueviolet:[138,43,226],brown:[165,42,42],burlywood:[222,184,135],cadetblue:[95,158,160],chartreuse:[127,255,0],chocolate:[210,105,30],coral:[255,127,80],cornflowerblue:[100,149,237],cornsilk:[255,248,220],crimson:[220,20,60],cyan:[0,255,255],darkblue:[0,0,139],darkcyan:[0,139,139],darkgoldenrod:[184,134,11],darkgray:[169,169,169],darkgreen:[0,100,0],darkgrey:[169,169,169],darkkhaki:[189,183,107],darkmagenta:[139,0,139],darkolivegreen:[85,107,47],darkorange:[255,140,0],darkorchid:[153,50,204],darkred:[139,0,0],darksalmon:[233,150,122],darkseagreen:[143,188,143],darkslateblue:[72,61,139],darkslategray:[47,79,79],darkslategrey:[47,79,79],darkturquoise:[0,206,209],darkviolet:[148,0,211],deeppink:[255,20,147],deepskyblue:[0,191,255],dimgray:[105,105,105],dimgrey:[105,105,105],dodgerblue:[30,144,255],firebrick:[178,34,34],floralwhite:[255,250,240],forestgreen:[34,139,34],fuchsia:[255,0,255],gainsboro:[220,220,220],ghostwhite:[248,248,255],gold:[255,215,0],goldenrod:[218,165,32],gray:[128,128,128],green:[0,128,0],greenyellow:[173,255,47],grey:[128,128,128],honeydew:[240,255,240],hotpink:[255,105,180],indianred:[205,92,92],indigo:[75,0,130],ivory:[255,255,240],khaki:[240,230,140],lavender:[230,230,250],lavenderblush:[255,240,245],lawngreen:[124,252,0],lemonchiffon:[255,250,205],lightblue:[173,216,230],lightcoral:[240,128,128],lightcyan:[224,255,255],lightgoldenrodyellow:[250,250,210],lightgray:[211,211,211],lightgreen:[144,238,144],lightgrey:[211,211,211],lightpink:[255,182,193],lightsalmon:[255,160,122],lightseagreen:[32,178,170],lightskyblue:[135,206,250],lightslategray:[119,136,153],lightslategrey:[119,136,153],lightsteelblue:[176,196,222],lightyellow:[255,255,224],lime:[0,255,0],limegreen:[50,205,50],linen:[250,240,230],magenta:[255,0,255],maroon:[128,0,0],mediumaquamarine:[102,205,170],mediumblue:[0,0,205],mediumorchid:[186,85,211],mediumpurple:[147,112,219],mediumseagreen:[60,179,113],mediumslateblue:[123,104,238],mediumspringgreen:[0,250,154],mediumturquoise:[72,209,204],mediumvioletred:[199,21,133],midnightblue:[25,25,112],mintcream:[245,255,250],mistyrose:[255,228,225],moccasin:[255,228,181],navajowhite:[255,222,173],navy:[0,0,128],oldlace:[253,245,230],olive:[128,128,0],olivedrab:[107,142,35],orange:[255,165,0],orangered:[255,69,0],orchid:[218,112,214],palegoldenrod:[238,232,170],palegreen:[152,251,152],paleturquoise:[175,238,238],palevioletred:[219,112,147],papayawhip:[255,239,213],peachpuff:[255,218,185],peru:[205,133,63],pink:[255,192,203],plum:[221,160,221],powderblue:[176,224,230],purple:[128,0,128],rebeccapurple:[102,51,153],red:[255,0,0],rosybrown:[188,143,143],royalblue:[65,105,225],saddlebrown:[139,69,19],salmon:[250,128,114],sandybrown:[244,164,96],seagreen:[46,139,87],seashell:[255,245,238],sienna:[160,82,45],silver:[192,192,192],skyblue:[135,206,235],slateblue:[106,90,205],slategray:[112,128,144],slategrey:[112,128,144],snow:[255,250,250],springgreen:[0,255,127],steelblue:[70,130,180],tan:[210,180,140],teal:[0,128,128],thistle:[216,191,216],tomato:[255,99,71],turquoise:[64,224,208],violet:[238,130,238],wheat:[245,222,179],white:[255,255,255],whitesmoke:[245,245,245],yellow:[255,255,0],yellowgreen:[154,205,50]};t.exports=n},function(t,e,n){"use strict";function r(t,e,n){var r="withCredentials"in new XMLHttpRequest;if(!e)return Promise.reject("No proxy configured");var i=s(r),c=a(e,t,i);return r?u(c):o(n,c,i).then(function(t){return f(t.content)})}function i(t,e,n){var r="crossOrigin"in new Image,i=s(r),c=a(e,t,i);return r?Promise.resolve(c):o(n,c,i).then(function(t){return"data:"+t.type+";base64,"+t.content})}function o(t,e,n){return new Promise(function(r,i){var o=t.createElement("script"),s=function(){delete window.html2canvas.proxy[n],t.body.removeChild(o)};window.html2canvas.proxy[n]=function(t){s(),r(t)},o.src=e,o.onerror=function(t){s(),i(t)},t.body.appendChild(o)})}function s(t){return t?"":"html2canvas_"+Date.now()+"_"+ ++g+"_"+Math.round(1e5*Math.random())}function a(t,e,n){return t+"?url="+encodeURIComponent(e)+(n.length?"&callback=html2canvas.proxy."+n:"")}function c(t){return function(e){var n,r=new DOMParser;try{n=r.parseFromString(e,"text/html")}catch(t){d("DOMParser not supported, falling back to createHTMLDocument"),n=document.implementation.createHTMLDocument("");try{n.open(),n.write(e),n.close()}catch(t){d("createHTMLDocument write not supported, falling back to document.body.innerHTML"),n.body.innerHTML=e}}var i=n.querySelector("base");if(!i||!i.href.host){var o=n.createElement("base");o.href=t,n.head.insertBefore(o,n.head.firstChild)}return n}}function h(t,e,n,i,o,s){return new r(t,e,window.document).then(c(t)).then(function(t){return p(t,n,i,o,s,0,0)})}var u=n(11),l=n(1),d=n(2),p=n(6),f=l.decode64,g=0;e.Proxy=r,e.ProxyURL=i,e.loadUrlDocument=h},function(t,e,n){"use strict";function r(t,e,n){!t.defaultView||e===t.defaultView.pageXOffset&&n===t.defaultView.pageYOffset||t.defaultView.scrollTo(e,n)}function i(t,e){try{e&&(e.width=t.width,e.height=t.height,e.getContext("2d").putImageData(t.getContext("2d").getImageData(0,0,t.width,t.height),0,0))}catch(e){a("Unable to copy canvas content from",t,e)}}function o(t,e){for(var n=3===t.nodeType?document.createTextNode(t.nodeValue):t.cloneNode(!1),r=t.firstChild;r;)e!==!0&&1===r.nodeType&&"SCRIPT"===r.nodeName||n.appendChild(o(r,e)),r=r.nextSibling;return 1===t.nodeType&&(n._scrollTop=t.scrollTop,n._scrollLeft=t.scrollLeft,"CANVAS"===t.nodeName?i(t,n):"TEXTAREA"!==t.nodeName&&"SELECT"!==t.nodeName||(n.value=t.value)),n}function s(t){if(1===t.nodeType){t.scrollTop=t._scrollTop,t.scrollLeft=t._scrollLeft;for(var e=t.firstChild;e;)s(e),e=e.nextSibling}}var a=n(2);t.exports=function(t,e,n,i,a,c,h){var u=o(t.documentElement,a.javascriptEnabled),l=e.createElement("iframe");return l.className="html2canvas-container",l.style.visibility="hidden",l.style.position="fixed",l.style.left="-10000px",l.style.top="0px",l.style.border="0",l.width=n,l.height=i,l.scrolling="no",e.body.appendChild(l),new Promise(function(e){var n=l.contentWindow.document;l.contentWindow.onload=l.onload=function(){var t=setInterval(function(){n.body.childNodes.length>0&&(s(n.documentElement),clearInterval(t),"view"===a.type&&(l.contentWindow.scrollTo(c,h),!/(iPad|iPhone|iPod)/g.test(navigator.userAgent)||l.contentWindow.scrollY===h&&l.contentWindow.scrollX===c||(n.documentElement.style.top=-h+"px",n.documentElement.style.left=-c+"px",n.documentElement.style.position="absolute")),e(l))},50)},n.open(),n.write(""),r(t,c,h),n.replaceChild(n.adoptNode(u),n.documentElement),n.close()})}},function(t,e,n){function r(t,e){g++;e=e||{},e.logging&&(d.options.logging=!0,d.options.start=Date.now()),e.async="undefined"==typeof e.async||e.async,e.allowTaint="undefined"!=typeof e.allowTaint&&e.allowTaint,e.removeContainer="undefined"==typeof e.removeContainer||e.removeContainer,e.javascriptEnabled="undefined"!=typeof e.javascriptEnabled&&e.javascriptEnabled,e.imageTimeout="undefined"==typeof e.imageTimeout?1e4:e.imageTimeout,e.renderer="function"==typeof e.renderer?e.renderer:c,e.strict=!!e.strict;var n=e.width||512,r=e.height||512;return i(t,n,r).then(function(t){e.onrendered(t)})}function i(t,e,n){var i=new a(t.ownerDocument),o=new h({useCORS:!0},i),s={renderer:r.CanvasRenderer},c=(f(t),new s.renderer(e,n,o,s,document)),l=new u(t,c,i,o,s);return l.ready.then(function(){return c.canvas})}var o,s,a=n(24),c=n(22),h=n(17),u=n(18),l=n(3),d=n(2),p=n(1),f=(n(6),n(5).loadUrlDocument,p.getBounds),g=0;r.CanvasRenderer=c,r.NodeContainer=l,r.log=d,r.utils=p;var m="undefined"==typeof document||"function"!=typeof Object.create||"function"!=typeof document.createElement("canvas").getContext?function(){return Promise.reject("No canvas support")}:r;t.exports=m,o=[],s=function(){return m}.apply(e,o),!(void 0!==s&&(t.exports=s))},function(t,e){"use strict";function n(t){this.src=t.value,this.colorStops=[],this.type=null,this.x0=.5,this.y0=.5,this.x1=.5,this.y1=.5,this.promise=Promise.resolve(!0)}n.TYPES={LINEAR:1,RADIAL:2},n.REGEXP_COLORSTOP=/^\s*(rgba?\(\s*\d{1,3},\s*\d{1,3},\s*\d{1,3}(?:,\s*[0-9\.]+)?\s*\)|[a-z]{3,20}|#[a-f0-9]{3,6})(?:\s+(\d{1,3}(?:\.\d+)?)(%|px)?)?(?:\s|$)/i,t.exports=n},function(t,e,n){"use strict";function r(t){i.apply(this,arguments),this.type=i.TYPES.LINEAR;var e=r.REGEXP_DIRECTION.test(t.args[0])||!i.REGEXP_COLORSTOP.test(t.args[0]);e?t.args[0].split(/\s+/).reverse().forEach(function(t,e){switch(t){case"left":this.x0=0,this.x1=1;break;case"top":this.y0=0,this.y1=1;break;case"right":this.x0=1,this.x1=0;break;case"bottom":this.y0=1,this.y1=0;break;case"to":var n=this.y0,r=this.x0;this.y0=this.y1,this.x0=this.x1,this.x1=r,this.y1=n;break;case"center":break;default:var i=.01*parseFloat(t,10);if(isNaN(i))break;0===e?(this.y0=i,this.y1=1-this.y0):(this.x0=i,this.x1=1-this.x0)}},this):(this.y0=0,this.y1=1),this.colorStops=t.args.slice(e?1:0).map(function(t){var e=t.match(i.REGEXP_COLORSTOP),n=+e[2],r=0===n?"%":e[3];return{color:new o(e[1]),stop:"%"===r?n/100:null}}),null===this.colorStops[0].stop&&(this.colorStops[0].stop=0),null===this.colorStops[this.colorStops.length-1].stop&&(this.colorStops[this.colorStops.length-1].stop=1),this.colorStops.forEach(function(t,e){null===t.stop&&this.colorStops.slice(e).some(function(n,r){return null!==n.stop&&(t.stop=(n.stop-this.colorStops[e-1].stop)/(r+1)+this.colorStops[e-1].stop,!0)},this)},this)}var i=n(8),o=n(4);r.prototype=Object.create(i.prototype),r.REGEXP_DIRECTION=/^\s*(?:to|left|right|top|bottom|center|\d{1,3}(?:\.\d+)?%?)(?:\s|$)/i,t.exports=r},function(t,e,n){"use strict";function r(t){this.src=t,this.image=null;var e=this;this.promise=this.hasFabric().then(function(){return e.isInline(t)?Promise.resolve(e.inlineFormatting(t)):i(t)}).then(function(t){return new Promise(function(n){window.html2canvas.svg.fabric.loadSVGFromString(t,e.createCanvas.call(e,n))})})}var i=n(11),o=n(1).decode64;r.prototype.hasFabric=function(){return window.html2canvas.svg&&window.html2canvas.svg.fabric?Promise.resolve():Promise.reject(new Error("html2canvas.svg.js is not loaded, cannot render svg"))},r.prototype.inlineFormatting=function(t){return/^data:image\/svg\+xml;base64,/.test(t)?this.decode64(this.removeContentType(t)):this.removeContentType(t)},r.prototype.removeContentType=function(t){return t.replace(/^data:image\/svg\+xml(;base64)?,/,"")},r.prototype.isInline=function(t){return/^data:image\/svg\+xml/i.test(t)},r.prototype.createCanvas=function(t){var e=this;return function(n,r){var i=new window.html2canvas.svg.fabric.StaticCanvas("c");e.image=i.lowerCanvasEl,i.setWidth(r.width).setHeight(r.height).add(window.html2canvas.svg.fabric.util.groupSVGElements(n,r)).renderAll(),t(i.lowerCanvasEl)}},r.prototype.decode64=function(t){return"function"==typeof window.atob?window.atob(t):o(t)},t.exports=r},function(t,e){"use strict";function n(t){return new Promise(function(e,n){var r=new XMLHttpRequest;r.open("GET",t),r.onload=function(){200===r.status?e(r.responseText):n(new Error(r.statusText))},r.onerror=function(){n(new Error("Network Error"))},r.send()})}t.exports=n},function(t,e,n){"use strict";function r(t){if(this.src=t,i("DummyImageContainer for",t),!this.promise||!this.image){i("Initiating DummyImageContainer"),r.prototype.image=new Image;var e=this.image;r.prototype.promise=new Promise(function(t,n){e.onload=t,e.onerror=n,e.src=o(),e.complete===!0&&t(e)})}}var i=n(2),o=n(1).smallImage;t.exports=r},function(t,e,n){"use strict";function r(t,e){var n,r,o=document.createElement("div"),s=document.createElement("img"),a=document.createElement("span"),c="Hidden Text";o.style.visibility="hidden",o.style.fontFamily=t,o.style.fontSize=e,o.style.margin=0,o.style.padding=0,document.body.appendChild(o),s.src=i(),s.width=1,s.height=1,s.style.margin=0,s.style.padding=0,s.style.verticalAlign="baseline",a.style.fontFamily=t,a.style.fontSize=e,a.style.margin=0,a.style.padding=0,a.appendChild(document.createTextNode(c)),o.appendChild(a),o.appendChild(s),n=s.offsetTop-a.offsetTop+1,o.removeChild(a),o.appendChild(document.createTextNode(c)),o.style.lineHeight="normal",s.style.verticalAlign="super",r=s.offsetTop-o.offsetTop+1,document.body.removeChild(o),this.baseline=n,this.lineWidth=1,this.middle=r}var i=n(1).smallImage;t.exports=r},function(t,e,n){"use strict";function r(){this.data={}}var i=n(13);r.prototype.getMetrics=function(t,e){return void 0===this.data[t+"-"+e]&&(this.data[t+"-"+e]=new i(t,e)),this.data[t+"-"+e]},t.exports=r},function(t,e,n){"use strict";function r(t,e,r){this.image=null,this.src=t;var i=this,s=o(t);this.promise=(e?new Promise(function(e){"about:blank"===t.contentWindow.document.URL||null==t.contentWindow.document.documentElement?t.contentWindow.onload=t.onload=function(){e(t)}:e(t)}):this.proxyLoad(r.proxy,s,r)).then(function(t){var e=n(7);return e(t.contentWindow.document.documentElement,{type:"view",width:t.width,height:t.height,proxy:r.proxy,javascriptEnabled:r.javascriptEnabled,removeContainer:r.removeContainer,allowTaint:r.allowTaint,imageTimeout:r.imageTimeout/2})}).then(function(t){return i.image=t})}var i=n(1),o=i.getBounds,s=n(5).loadUrlDocument;r.prototype.proxyLoad=function(t,e,n){var r=this.src;return s(r.src,t,r.ownerDocument,e.width,e.height,n)},t.exports=r},function(t,e){"use strict";function n(t,e){this.src=t,this.image=new Image;var n=this;this.tainted=null,this.promise=new Promise(function(r,i){n.image.onload=r,n.image.onerror=i,e&&(n.image.crossOrigin="anonymous"),n.image.src=t,n.image.complete===!0&&r(n.image)})}t.exports=n},function(t,e,n){"use strict";function r(t,e){this.link=null,this.options=t,this.support=e,this.origin=this.getOrigin(window.location.href)}var i=n(2),o=n(16),s=n(12),a=n(19),c=n(15),h=n(10),u=n(25),l=n(9),d=n(27),p=n(1).bind;r.prototype.findImages=function(t){var e=[];return t.reduce(function(t,e){switch(e.node.nodeName){case"IMG":return t.concat([{args:[e.node.src],method:"url"}]);case"svg":case"IFRAME":return t.concat([{args:[e.node],method:e.node.nodeName}])}return t},[]).forEach(this.addImage(e,this.loadImage),this),e},r.prototype.findBackgroundImage=function(t,e){return e.parseBackgroundImages().filter(this.hasImageBackground).forEach(this.addImage(t,this.loadImage),this),t},r.prototype.addImage=function(t,e){return function(n){n.args.forEach(function(r){this.imageExists(t,r)||(t.splice(0,0,e.call(this,n)),i("Added image #"+t.length,"string"==typeof r?r.substring(0,100):r))},this)}},r.prototype.hasImageBackground=function(t){return"none"!==t.method},r.prototype.loadImage=function(t){if("url"===t.method){var e=t.args[0];return!this.isSVG(e)||this.support.svg||this.options.allowTaint?e.match(/data:image\/.*;base64,/i)?new o(e.replace(/url\(['"]{0,}|['"]{0,}\)$/gi,""),!1):this.isSameOrigin(e)||this.options.allowTaint===!0||this.isSVG(e)?new o(e,!1):this.support.cors&&!this.options.allowTaint&&this.options.useCORS?new o(e,!0):this.options.proxy?new a(e,this.options.proxy):new s(e):new h(e)}return"linear-gradient"===t.method?new l(t):"gradient"===t.method?new d(t):"svg"===t.method?new u(t.args[0],this.support.svg):"IFRAME"===t.method?new c(t.args[0],this.isSameOrigin(t.args[0].src),this.options):new s(t)},r.prototype.isSVG=function(t){return"svg"===t.substring(t.length-3).toLowerCase()||h.prototype.isInline(t)},r.prototype.imageExists=function(t,e){return t.some(function(t){return t.src===e})},r.prototype.isSameOrigin=function(t){return this.getOrigin(t)===this.origin},r.prototype.getOrigin=function(t){var e=this.link||(this.link=document.createElement("a"));return e.href=t,e.href=e.href,e.protocol+e.hostname+e.port},r.prototype.getPromise=function(t){return this.timeout(t,this.options.imageTimeout).catch(function(){var e=new s(t.src);return e.promise.then(function(e){t.image=e})})},r.prototype.get=function(t){var e=null;return this.images.some(function(n){return(e=n).src===t})?e:null},r.prototype.fetch=function(t){return this.images=t.reduce(p(this.findBackgroundImage,this),this.findImages(t)),this.images.forEach(function(t,e){t.promise.then(function(){i("Succesfully loaded image #"+(e+1),t)},function(n){i("Failed loading image #"+(e+1),t,n)})}),this.ready=Promise.all(this.images.map(this.getPromise,this)),i("Finished searching images"),this},r.prototype.timeout=function(t,e){var n,r=Promise.race([t.promise,new Promise(function(r,o){n=setTimeout(function(){i("Timed out loading image",t),o(t)},e)})]).then(function(t){return clearTimeout(n),t});return r.catch(function(){clearTimeout(n)}),r},t.exports=r},function(t,e,n){"use strict";function r(t,e,n,r,i){j("Starting NodeParser"),this.renderer=e,this.options=i,this.range=null,this.support=n,this.renderQueue=[],this.stack=new q(!0,1,t.ownerDocument,null);var o=new W(t,null);if(i.background&&e.rectangle(0,0,e.width,e.height,new G(i.background)),t===t.ownerDocument.documentElement){var s=new W(o.color("backgroundColor").isTransparent()?t.ownerDocument.body:t.ownerDocument.documentElement,null);e.rectangle(0,0,e.width,e.height,s.color("backgroundColor"))}o.visibile=o.isElementVisible(),this.createPseudoHideStyles(t.ownerDocument),
2 | this.disableAnimations(t.ownerDocument),this.nodes=B([o].concat(this.getChildren(o)).filter(function(t){return t.visible=t.isElementVisible()}).map(this.getPseudoElements,this)),this.fontMetrics=new X,j("Fetched nodes, total:",this.nodes.length),j("Calculate overflow clips"),this.calculateOverflowClips(),j("Start fetching images"),this.images=r.fetch(this.nodes.filter(S)),this.ready=this.images.ready.then(Q(function(){return j("Images loaded, starting parsing"),j("Creating stacking contexts"),this.createStackingContexts(),j("Sorting stacking contexts"),this.sortStackingContexts(this.stack),this.parse(this.stack),j("Render queue created with "+this.renderQueue.length+" items"),new Promise(Q(function(t){i.async?"function"==typeof i.async?i.async.call(this,this.renderQueue,t):this.renderQueue.length>0?(this.renderIndex=0,this.asyncRenderer(this.renderQueue,t)):t():(this.renderQueue.forEach(this.paint,this),t())},this))},this))}function i(t){return t.parent&&t.parent.clip.length}function o(t){return t.replace(/(\-[a-z])/g,function(t){return t.toUpperCase().replace("-","")})}function s(){}function a(t,e,n,r){return t.map(function(i,o){if(i.width>0){var s=e.left,a=e.top,c=e.width,h=e.height-t[2].width;switch(o){case 0:h=t[0].width,i.args=l({c1:[s,a],c2:[s+c,a],c3:[s+c-t[1].width,a+h],c4:[s+t[3].width,a+h]},r[0],r[1],n.topLeftOuter,n.topLeftInner,n.topRightOuter,n.topRightInner);break;case 1:s=e.left+e.width-t[1].width,c=t[1].width,i.args=l({c1:[s+c,a],c2:[s+c,a+h+t[2].width],c3:[s,a+h],c4:[s,a+t[0].width]},r[1],r[2],n.topRightOuter,n.topRightInner,n.bottomRightOuter,n.bottomRightInner);break;case 2:a=a+e.height-t[2].width,h=t[2].width,i.args=l({c1:[s+c,a+h],c2:[s,a+h],c3:[s+t[3].width,a],c4:[s+c-t[3].width,a]},r[2],r[3],n.bottomRightOuter,n.bottomRightInner,n.bottomLeftOuter,n.bottomLeftInner);break;case 3:c=t[3].width,i.args=l({c1:[s,a+h+t[2].width],c2:[s,a],c3:[s+c,a+t[0].width],c4:[s+c,a+h]},r[3],r[0],n.bottomLeftOuter,n.bottomLeftInner,n.topLeftOuter,n.topLeftInner)}}return i})}function c(t,e,n,r){var i=4*((Math.sqrt(2)-1)/3),o=n*i,s=r*i,a=t+n,c=e+r;return{topLeft:u({x:t,y:c},{x:t,y:c-s},{x:a-o,y:e},{x:a,y:e}),topRight:u({x:t,y:e},{x:t+o,y:e},{x:a,y:c-s},{x:a,y:c}),bottomRight:u({x:a,y:e},{x:a,y:e+s},{x:t+o,y:c},{x:t,y:c}),bottomLeft:u({x:a,y:c},{x:a-o,y:c},{x:t,y:e+s},{x:t,y:e})}}function h(t,e,n){var r=t.left,i=t.top,o=t.width,s=t.height,a=e[0][0]o+n[3].width?0:u-n[3].width,l-n[0].width).topRight.subdivide(.5),bottomRightOuter:c(r+w,i+y,d,p).bottomRight.subdivide(.5),bottomRightInner:c(r+Math.min(w,o-n[3].width),i+Math.min(y,s+n[0].width),Math.max(0,d-n[1].width),p-n[2].width).bottomRight.subdivide(.5),bottomLeftOuter:c(r,i+b,f,g).bottomLeft.subdivide(.5),bottomLeftInner:c(r+n[3].width,i+b,Math.max(0,f-n[3].width),g-n[2].width).bottomLeft.subdivide(.5)}}function u(t,e,n,r){var i=function(t,e,n){return{x:t.x+(e.x-t.x)*n,y:t.y+(e.y-t.y)*n}};return{start:t,startControl:e,endControl:n,end:r,subdivide:function(o){var s=i(t,e,o),a=i(e,n,o),c=i(n,r,o),h=i(s,a,o),l=i(a,c,o),d=i(h,l,o);return[u(t,s,h,d),u(d,l,c,r)]},curveTo:function(t){t.push(["bezierCurve",e.x,e.y,n.x,n.y,r.x,r.y])},curveToReversed:function(r){r.push(["bezierCurve",n.x,n.y,e.x,e.y,t.x,t.y])}}}function l(t,e,n,r,i,o,s){var a=[];return e[0]>0||e[1]>0?(a.push(["line",r[1].start.x,r[1].start.y]),r[1].curveTo(a)):a.push(["line",t.c1[0],t.c1[1]]),n[0]>0||n[1]>0?(a.push(["line",o[0].start.x,o[0].start.y]),o[0].curveTo(a),a.push(["line",s[0].end.x,s[0].end.y]),s[0].curveToReversed(a)):(a.push(["line",t.c2[0],t.c2[1]]),a.push(["line",t.c3[0],t.c3[1]])),e[0]>0||e[1]>0?(a.push(["line",i[1].end.x,i[1].end.y]),i[1].curveToReversed(a)):a.push(["line",t.c4[0],t.c4[1]]),a}function d(t,e,n,r,i,o,s){e[0]>0||e[1]>0?(t.push(["line",r[0].start.x,r[0].start.y]),r[0].curveTo(t),r[1].curveTo(t)):t.push(["line",o,s]),(n[0]>0||n[1]>0)&&t.push(["line",i[0].start.x,i[0].start.y])}function p(t){return t.cssInt("zIndex")<0}function f(t){return t.cssInt("zIndex")>0}function g(t){return 0===t.cssInt("zIndex")}function m(t){return["inline","inline-block","inline-table"].indexOf(t.css("display"))!==-1}function y(t){return t instanceof q}function w(t){return t.node.data.trim().length>0}function b(t){return/^(normal|none|0px)$/.test(t.parent.css("letterSpacing"))}function v(t){return["TopLeft","TopRight","BottomRight","BottomLeft"].map(function(e){var n=t.css("border"+e+"Radius"),r=n.split(" ");return r.length<=1&&(r[1]=r[0]),r.map(P)})}function x(t){return t.nodeType===Node.TEXT_NODE||t.nodeType===Node.ELEMENT_NODE}function _(t){var e=t.css("position"),n=["absolute","relative","fixed"].indexOf(e)!==-1?t.css("zIndex"):"auto";return"auto"!==n}function E(t){return"static"!==t.css("position")}function T(t){return"none"!==t.css("float")}function k(t){return["inline-block","inline-table"].indexOf(t.css("display"))!==-1}function C(t){var e=this;return function(){return!t.apply(e,arguments)}}function S(t){return t.node.nodeType===Node.ELEMENT_NODE}function I(t){return t.isPseudoElement===!0}function R(t){return t.node.nodeType===Node.TEXT_NODE}function O(t){return function(e,n){return e.cssInt("zIndex")+t.indexOf(e)/t.length-(n.cssInt("zIndex")+t.indexOf(n)/t.length)}}function A(t){return t.getOpacity()<1}function P(t){return parseInt(t,10)}function L(t){return t.width}function N(t){return t.node.nodeType!==Node.ELEMENT_NODE||["SCRIPT","HEAD","TITLE","OBJECT","BR","OPTION"].indexOf(t.node.nodeName)===-1}function B(t){return[].concat.apply([],t)}function M(t){var e=t.substr(0,1);return e===t.substr(t.length-1)&&e.match(/'|"/)?t.substr(1,t.length-2):t}function D(t){for(var e,n=[],r=0,i=!1;t.length;)F(t[r])===i?(e=t.splice(0,r),e.length&&n.push(V.ucs2.encode(e)),i=!i,r=0):r++,r>=t.length&&(e=t.splice(0,r),e.length&&n.push(V.ucs2.encode(e)));return n}function F(t){return[32,13,10,9,45].indexOf(t)!==-1}function H(t){return/[^\u0000-\u00ff]/.test(t)}var j=n(2),V=n(28),W=n(3),z=n(26),U=n(20),X=n(14),G=n(4),q=n(23),Y=n(1),Q=Y.bind,$=Y.getBounds,J=Y.parseBackgrounds,K=Y.offsetBounds;r.prototype.calculateOverflowClips=function(){this.nodes.forEach(function(t){if(S(t)){I(t)&&t.appendToDOM(),t.borders=this.parseBorders(t);var e="hidden"===t.css("overflow")?[t.borders.clip]:[],n=t.parseClip();n&&["absolute","fixed"].indexOf(t.css("position"))!==-1&&e.push([["rect",t.bounds.left+n.left,t.bounds.top+n.top,n.right-n.left,n.bottom-n.top]]),t.clip=i(t)?t.parent.clip.concat(e):e,t.backgroundClip="hidden"!==t.css("overflow")?t.clip.concat([t.borders.clip]):t.clip,I(t)&&t.cleanDOM()}else R(t)&&(t.clip=i(t)?t.parent.clip:[]);I(t)||(t.bounds=null)},this)},r.prototype.asyncRenderer=function(t,e,n){n=n||Date.now(),this.paint(t[this.renderIndex++]),t.length===this.renderIndex?e():n+20>Date.now()?this.asyncRenderer(t,e,n):setTimeout(Q(function(){this.asyncRenderer(t,e)},this),0)},r.prototype.createPseudoHideStyles=function(t){this.createStyles(t,"."+U.prototype.PSEUDO_HIDE_ELEMENT_CLASS_BEFORE+':before { content: "" !important; display: none !important; }.'+U.prototype.PSEUDO_HIDE_ELEMENT_CLASS_AFTER+':after { content: "" !important; display: none !important; }')},r.prototype.disableAnimations=function(t){this.createStyles(t,"* { -webkit-animation: none !important; -moz-animation: none !important; -o-animation: none !important; animation: none !important; -webkit-transition: none !important; -moz-transition: none !important; -o-transition: none !important; transition: none !important;}")},r.prototype.createStyles=function(t,e){if(!window.hidePseudoElementsAdded){window.hidePseudoElementsAdded=!0;var n=t.createElement("style");n.innerHTML=e,t.body.appendChild(n)}},r.prototype.getPseudoElements=function(t){var e=[[t]];if(t.node.nodeType===Node.ELEMENT_NODE){var n=this.getPseudoElement(t,":before"),r=this.getPseudoElement(t,":after");n&&e.push(n),r&&e.push(r)}return B(e)},r.prototype.getPseudoElement=function(t,e){var n=t.computedStyle(e);if(!n||!n.content||"none"===n.content||"-moz-alt-content"===n.content||"none"===n.display)return null;for(var r=M(n.content),i="url"===r.substr(0,3),s=document.createElement(i?"img":"html2canvaspseudoelement"),a=new U(s,t,e),c=n.length-1;c>=0;c--){var h=o(n.item(c));s.style[h]=n[h]}if(s.className=U.prototype.PSEUDO_HIDE_ELEMENT_CLASS_BEFORE+" "+U.prototype.PSEUDO_HIDE_ELEMENT_CLASS_AFTER,i)return s.src=J(r)[0].args[0],[a];var u=document.createTextNode(r);return s.appendChild(u),[a,new z(u,a)]},r.prototype.getChildren=function(t){return B([].filter.call(t.node.childNodes,x).map(function(e){var n=[e.nodeType===Node.TEXT_NODE?new z(e,t):new W(e,t)].filter(N);return e.nodeType===Node.ELEMENT_NODE&&n.length&&"TEXTAREA"!==e.tagName?n[0].isElementVisible()?n.concat(this.getChildren(n[0])):[]:n},this))},r.prototype.newStackingContext=function(t,e){var n=new q(e,t.getOpacity(),t.node,t.parent);t.cloneTo(n);var r=e?n.getParentStack(this):n.parent.stack;r.contexts.push(n),t.stack=n},r.prototype.createStackingContexts=function(){this.nodes.forEach(function(t){S(t)&&(this.isRootElement(t)||A(t)||_(t)||this.isBodyWithTransparentRoot(t)||t.hasTransform())?this.newStackingContext(t,!0):S(t)&&(E(t)&&g(t)||k(t)||T(t))?this.newStackingContext(t,!1):t.assignStack(t.parent.stack)},this)},r.prototype.isBodyWithTransparentRoot=function(t){return"BODY"===t.node.nodeName&&t.parent.color("backgroundColor").isTransparent()},r.prototype.isRootElement=function(t){return null===t.parent},r.prototype.sortStackingContexts=function(t){t.contexts.sort(O(t.contexts.slice(0))),t.contexts.forEach(this.sortStackingContexts,this)},r.prototype.parseTextBounds=function(t){return function(e,n,r){if("none"!==t.parent.css("textDecoration").substr(0,4)||0!==e.trim().length){if(this.support.rangeBounds&&!t.parent.hasTransform()){var i=r.slice(0,n).join("").length;return this.getRangeBounds(t.node,i,e.length)}if(t.node&&"string"==typeof t.node.data){var o=t.node.splitText(e.length),s=this.getWrapperBounds(t.node,t.parent.hasTransform());return t.node=o,s}}else this.support.rangeBounds&&!t.parent.hasTransform()||(t.node=t.node.splitText(e.length));return{}}},r.prototype.getWrapperBounds=function(t,e){var n=t.ownerDocument.createElement("html2canvaswrapper"),r=t.parentNode,i=t.cloneNode(!0);n.appendChild(t.cloneNode(!0)),r.replaceChild(n,t);var o=e?K(n):$(n);return r.replaceChild(i,n),o},r.prototype.getRangeBounds=function(t,e,n){var r=this.range||(this.range=t.ownerDocument.createRange());return r.setStart(t,e),r.setEnd(t,e+n),r.getBoundingClientRect()},r.prototype.parse=function(t){var e=t.contexts.filter(p),n=t.children.filter(S),r=n.filter(C(T)),i=r.filter(C(E)).filter(C(m)),o=n.filter(C(E)).filter(T),a=r.filter(C(E)).filter(m),c=t.contexts.concat(r.filter(E)).filter(g),h=t.children.filter(R).filter(w),u=t.contexts.filter(f);e.concat(i).concat(o).concat(a).concat(c).concat(h).concat(u).forEach(function(t){this.renderQueue.push(t),y(t)&&(this.parse(t),this.renderQueue.push(new s))},this)},r.prototype.paint=function(t){try{t instanceof s?this.renderer.ctx.restore():R(t)?(I(t.parent)&&t.parent.appendToDOM(),this.paintText(t),I(t.parent)&&t.parent.cleanDOM()):this.paintNode(t)}catch(t){if(j(t),this.options.strict)throw t}},r.prototype.paintNode=function(t){y(t)&&(this.renderer.setOpacity(t.opacity),this.renderer.ctx.save(),t.hasTransform()&&this.renderer.setTransform(t.parseTransform())),"INPUT"===t.node.nodeName&&"checkbox"===t.node.type?this.paintCheckbox(t):"INPUT"===t.node.nodeName&&"radio"===t.node.type?this.paintRadio(t):this.paintElement(t)},r.prototype.paintElement=function(t){var e=t.parseBounds();this.renderer.clip(t.backgroundClip,function(){this.renderer.renderBackground(t,e,t.borders.borders.map(L))},this),this.renderer.clip(t.clip,function(){this.renderer.renderBorders(t.borders.borders)},this),this.renderer.clip(t.backgroundClip,function(){switch(t.node.nodeName){case"svg":case"IFRAME":var n=this.images.get(t.node);n?this.renderer.renderImage(t,e,t.borders,n):j("Error loading <"+t.node.nodeName+">",t.node);break;case"IMG":var r=this.images.get(t.node.src);r?this.renderer.renderImage(t,e,t.borders,r):j("Error loading ",t.node.src);break;case"CANVAS":this.renderer.renderImage(t,e,t.borders,{image:t.node});break;case"SELECT":case"INPUT":case"TEXTAREA":this.paintFormValue(t)}},this)},r.prototype.paintCheckbox=function(t){var e=t.parseBounds(),n=Math.min(e.width,e.height),r={width:n-1,height:n-1,top:e.top,left:e.left},i=[3,3],o=[i,i,i,i],s=[1,1,1,1].map(function(t){return{color:new G("#A5A5A5"),width:t}}),c=h(r,o,s);this.renderer.clip(t.backgroundClip,function(){this.renderer.rectangle(r.left+1,r.top+1,r.width-2,r.height-2,new G("#DEDEDE")),this.renderer.renderBorders(a(s,r,c,o)),t.node.checked&&(this.renderer.font(new G("#424242"),"normal","normal","bold",n-3+"px","arial"),this.renderer.text("✔",r.left+n/6,r.top+n-1))},this)},r.prototype.paintRadio=function(t){var e=t.parseBounds(),n=Math.min(e.width,e.height)-2;this.renderer.clip(t.backgroundClip,function(){this.renderer.circleStroke(e.left+1,e.top+1,n,new G("#DEDEDE"),1,new G("#A5A5A5")),t.node.checked&&this.renderer.circle(Math.ceil(e.left+n/4)+1,Math.ceil(e.top+n/4)+1,Math.floor(n/2),new G("#424242"))},this)},r.prototype.paintFormValue=function(t){var e=t.getValue();if(e.length>0){var n=t.node.ownerDocument,r=n.createElement("html2canvaswrapper"),i=["lineHeight","textAlign","fontFamily","fontWeight","fontSize","color","paddingLeft","paddingTop","paddingRight","paddingBottom","width","height","borderLeftStyle","borderTopStyle","borderLeftWidth","borderTopWidth","boxSizing","whiteSpace","wordWrap"];i.forEach(function(e){try{r.style[e]=t.css(e)}catch(t){j("html2canvas: Parse: Exception caught in renderFormValue: "+t.message)}});var o=t.parseBounds();r.style.position="fixed",r.style.left=o.left+"px",r.style.top=o.top+"px",r.textContent=e,n.body.appendChild(r),this.paintText(new z(r.firstChild,t)),n.body.removeChild(r)}},r.prototype.paintText=function(t){t.applyTextTransform();var e=V.ucs2.decode(t.node.data),n=this.options.letterRendering&&!b(t)||H(t.node.data)?e.map(function(t){return V.ucs2.encode([t])}):D(e),r=t.parent.fontWeight(),i=t.parent.css("fontSize"),o=t.parent.css("fontFamily"),s=t.parent.parseTextShadows();this.renderer.font(t.parent.color("color"),t.parent.css("fontStyle"),t.parent.css("fontVariant"),r,i,o),s.length?this.renderer.fontShadow(s[0].color,s[0].offsetX,s[0].offsetY,s[0].blur):this.renderer.clearShadow(),this.renderer.clip(t.parent.clip,function(){n.map(this.parseTextBounds(t),this).forEach(function(e,r){e&&(this.renderer.text(n[r],e.left,e.bottom),this.renderTextDecoration(t.parent,e,this.fontMetrics.getMetrics(o,i)))},this)},this)},r.prototype.renderTextDecoration=function(t,e,n){switch(t.css("textDecoration").split(" ")[0]){case"underline":this.renderer.rectangle(e.left,Math.round(e.top+n.baseline+n.lineWidth),e.width,1,t.color("color"));break;case"overline":this.renderer.rectangle(e.left,Math.round(e.top),e.width,1,t.color("color"));break;case"line-through":this.renderer.rectangle(e.left,Math.ceil(e.top+n.middle+n.lineWidth),e.width,1,t.color("color"))}};var Z={inset:[["darken",.6],["darken",.1],["darken",.1],["darken",.6]]};r.prototype.parseBorders=function(t){var e=t.parseBounds(),n=v(t),r=["Top","Right","Bottom","Left"].map(function(e,n){var r=t.css("border"+e+"Style"),i=t.color("border"+e+"Color");"inset"===r&&i.isBlack()&&(i=new G([255,255,255,i.a]));var o=Z[r]?Z[r][n]:null;return{width:t.cssInt("border"+e+"Width"),color:o?i[o[0]](o[1]):i,args:null}}),i=h(e,n,r);return{clip:this.parseBackgroundClip(t,i,r,n,e),borders:a(r,e,i,n)}},r.prototype.parseBackgroundClip=function(t,e,n,r,i){var o=t.css("backgroundClip"),s=[];switch(o){case"content-box":case"padding-box":d(s,r[0],r[1],e.topLeftInner,e.topRightInner,i.left+n[3].width,i.top+n[0].width),d(s,r[1],r[2],e.topRightInner,e.bottomRightInner,i.left+i.width-n[1].width,i.top+n[0].width),d(s,r[2],r[3],e.bottomRightInner,e.bottomLeftInner,i.left+i.width-n[1].width,i.top+i.height-n[2].width),d(s,r[3],r[0],e.bottomLeftInner,e.topLeftInner,i.left+n[3].width,i.top+i.height-n[2].width);break;default:d(s,r[0],r[1],e.topLeftOuter,e.topRightOuter,i.left,i.top),d(s,r[1],r[2],e.topRightOuter,e.bottomRightOuter,i.left+i.width,i.top),d(s,r[2],r[3],e.bottomRightOuter,e.bottomLeftOuter,i.left+i.width,i.top+i.height),d(s,r[3],r[0],e.bottomLeftOuter,e.topLeftOuter,i.left,i.top+i.height)}return s},t.exports=r},function(t,e,n){"use strict";function r(t,e){var n=document.createElement("a");n.href=t,t=n.href,this.src=t,this.image=new Image;var r=this;this.promise=new Promise(function(n,o){r.image.crossOrigin="Anonymous",r.image.onload=n,r.image.onerror=o,new i(t,e,document).then(function(t){r.image.src=t}).catch(o)})}var i=n(5).ProxyURL;t.exports=r},function(t,e,n){"use strict";function r(t,e,n){i.call(this,t,e),this.isPseudoElement=!0,this.before=":before"===n}var i=n(3);r.prototype.cloneTo=function(t){r.prototype.cloneTo.call(this,t),t.isPseudoElement=!0,t.before=this.before},r.prototype=Object.create(i.prototype),r.prototype.appendToDOM=function(){this.before?this.parent.node.insertBefore(this.node,this.parent.node.firstChild):this.parent.node.appendChild(this.node),this.parent.node.className+=" "+this.getHideClass()},r.prototype.cleanDOM=function(){this.node.parentNode.removeChild(this.node),this.parent.node.className=this.parent.node.className.replace(this.getHideClass(),"")},r.prototype.getHideClass=function(){return this["PSEUDO_HIDE_ELEMENT_CLASS_"+(this.before?"BEFORE":"AFTER")]},r.prototype.PSEUDO_HIDE_ELEMENT_CLASS_BEFORE="___html2canvas___pseudoelement_before",r.prototype.PSEUDO_HIDE_ELEMENT_CLASS_AFTER="___html2canvas___pseudoelement_after",t.exports=r},function(t,e,n){"use strict";function r(t,e,n,r,i){this.width=t,this.height=e,this.images=n,this.options=r,this.document=i}var i=n(2);r.prototype.renderImage=function(t,e,n,r){var i=t.cssInt("paddingLeft"),o=t.cssInt("paddingTop"),s=t.cssInt("paddingRight"),a=t.cssInt("paddingBottom"),c=n.borders,h=e.width-(c[1].width+c[3].width+i+s),u=e.height-(c[0].width+c[2].width+o+a);this.drawImage(r,0,0,r.image.width||h,r.image.height||u,e.left+i+c[3].width,e.top+o+c[0].width,h,u)},r.prototype.renderBackground=function(t,e,n){e.height>0&&e.width>0&&(this.renderBackgroundColor(t,e),this.renderBackgroundImage(t,e,n))},r.prototype.renderBackgroundColor=function(t,e){var n=t.color("backgroundColor");n.isTransparent()||this.rectangle(e.left,e.top,e.width,e.height,n)},r.prototype.renderBorders=function(t){t.forEach(this.renderBorder,this)},r.prototype.renderBorder=function(t){t.color.isTransparent()||null===t.args||this.drawShape(t.args,t.color)},r.prototype.renderBackgroundImage=function(t,e,n){var r=t.parseBackgroundImages();r.reverse().forEach(function(r,o,s){switch(r.method){case"url":var a=this.images.get(r.args[0]);a?this.renderBackgroundRepeating(t,e,a,s.length-(o+1),n):i("Error loading background-image",r.args[0]);break;case"linear-gradient":case"gradient":var c=this.images.get(r.value);c?this.renderBackgroundGradient(c,e,n):i("Error loading background-image",r.args[0]);break;case"none":break;default:i("Unknown background-image type",r.args[0])}},this)},r.prototype.renderBackgroundRepeating=function(t,e,n,r,i){var o=t.parseBackgroundSize(e,n.image,r),s=t.parseBackgroundPosition(e,n.image,r,o),a=t.parseBackgroundRepeat(r);switch(a){case"repeat-x":case"repeat no-repeat":this.backgroundRepeatShape(n,s,o,e,e.left+i[3],e.top+s.top+i[0],99999,o.height,i);break;case"repeat-y":case"no-repeat repeat":this.backgroundRepeatShape(n,s,o,e,e.left+s.left+i[3],e.top+i[0],o.width,99999,i);break;case"no-repeat":this.backgroundRepeatShape(n,s,o,e,e.left+s.left+i[3],e.top+s.top+i[0],o.width,o.height,i);break;default:this.renderBackgroundRepeat(n,s,o,{top:e.top,left:e.left},i[3],i[0])}},t.exports=r},function(t,e,n){"use strict";function r(t,e){s.apply(this,arguments),this.canvas=this.options.canvas||this.document.createElement("canvas"),this.options.canvas||(this.canvas.width=t,this.canvas.height=e),this.ctx=this.canvas.getContext("2d"),this.taintCtx=this.document.createElement("canvas").getContext("2d"),this.ctx.textBaseline="bottom",this.variables={},c("Initialized CanvasRenderer with size",t,"x",e)}function i(t){return t.length>0}var o="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},s=n(21),a=n(9),c=n(2);r.prototype=Object.create(s.prototype),r.prototype.setFillStyle=function(t){return this.ctx.fillStyle="object"===("undefined"==typeof t?"undefined":o(t))&&t.isColor?t.toString():t,this.ctx},r.prototype.rectangle=function(t,e,n,r,i){this.setFillStyle(i).fillRect(t,e,n,r)},r.prototype.circle=function(t,e,n,r){this.setFillStyle(r),this.ctx.beginPath(),this.ctx.arc(t+n/2,e+n/2,n/2,0,2*Math.PI,!0),this.ctx.closePath(),this.ctx.fill()},r.prototype.circleStroke=function(t,e,n,r,i,o){this.circle(t,e,n,r),this.ctx.strokeStyle=o.toString(),this.ctx.stroke()},r.prototype.drawShape=function(t,e){this.shape(t),this.setFillStyle(e).fill()},r.prototype.taints=function(t){if(null===t.tainted){this.taintCtx.drawImage(t.image,0,0);try{this.taintCtx.getImageData(0,0,1,1),t.tainted=!1}catch(e){this.taintCtx=document.createElement("canvas").getContext("2d"),t.tainted=!0}}return t.tainted},r.prototype.drawImage=function(t,e,n,r,i,o,s,a,c){this.taints(t)&&!this.options.allowTaint||this.ctx.drawImage(t.image,e,n,r,i,o,s,a,c)},r.prototype.clip=function(t,e,n){this.ctx.save(),t.filter(i).forEach(function(t){this.shape(t).clip()},this),e.call(n),this.ctx.restore()},r.prototype.shape=function(t){return this.ctx.beginPath(),t.forEach(function(t,e){"rect"===t[0]?this.ctx.rect.apply(this.ctx,t.slice(1)):this.ctx[0===e?"moveTo":t[0]+"To"].apply(this.ctx,t.slice(1))},this),this.ctx.closePath(),this.ctx},r.prototype.font=function(t,e,n,r,i,o){this.setFillStyle(t).font=[e,n,r,i,o].join(" ").split(",")[0]},r.prototype.fontShadow=function(t,e,n,r){this.setVariable("shadowColor",t.toString()).setVariable("shadowOffsetY",e).setVariable("shadowOffsetX",n).setVariable("shadowBlur",r)},r.prototype.clearShadow=function(){this.setVariable("shadowColor","rgba(0,0,0,0)")},r.prototype.setOpacity=function(t){this.ctx.globalAlpha=t},r.prototype.setTransform=function(t){this.ctx.translate(t.origin[0],t.origin[1]),this.ctx.transform.apply(this.ctx,t.matrix),this.ctx.translate(-t.origin[0],-t.origin[1])},r.prototype.setVariable=function(t,e){return this.variables[t]!==e&&(this.variables[t]=this.ctx[t]=e),this},r.prototype.text=function(t,e,n){this.ctx.fillText(t,e,n)},r.prototype.backgroundRepeatShape=function(t,e,n,r,i,o,s,a,c){var h=[["line",Math.round(i),Math.round(o)],["line",Math.round(i+s),Math.round(o)],["line",Math.round(i+s),Math.round(a+o)],["line",Math.round(i),Math.round(a+o)]];this.clip([h],function(){this.renderBackgroundRepeat(t,e,n,r,c[3],c[0])},this)},r.prototype.renderBackgroundRepeat=function(t,e,n,r,i,o){var s=Math.round(r.left+e.left+i),a=Math.round(r.top+e.top+o);this.setFillStyle(this.ctx.createPattern(this.resizeImage(t,n),"repeat")),this.ctx.translate(s,a),this.ctx.fill(),this.ctx.translate(-s,-a)},r.prototype.renderBackgroundGradient=function(t,e){if(t instanceof a){var n=this.ctx.createLinearGradient(e.left+e.width*t.x0,e.top+e.height*t.y0,e.left+e.width*t.x1,e.top+e.height*t.y1);t.colorStops.forEach(function(t){n.addColorStop(t.stop,t.color.toString())}),this.rectangle(e.left,e.top,e.width,e.height,n)}},r.prototype.resizeImage=function(t,e){var n=t.image;if(n.width===e.width&&n.height===e.height)return n;var r,i=document.createElement("canvas");return i.width=e.width,i.height=e.height,r=i.getContext("2d"),r.drawImage(n,0,0,n.width,n.height,0,0,e.width,e.height),i},t.exports=r},function(t,e,n){"use strict";function r(t,e,n,r){i.call(this,n,r),this.ownStacking=t,this.contexts=[],this.children=[],this.opacity=(this.parent?this.parent.stack.opacity:1)*e}var i=n(3);r.prototype=Object.create(i.prototype),r.prototype.getParentStack=function(t){var e=this.parent?this.parent.stack:null;return e?e.ownStacking?e:e.getParentStack(t):t.stack},t.exports=r},function(t,e){"use strict";function n(t){this.rangeBounds=this.testRangeBounds(t),this.cors=this.testCORS(),this.svg=this.testSVG()}n.prototype.testRangeBounds=function(t){var e,n,r,i,o=!1;return t.createRange&&(e=t.createRange(),e.getBoundingClientRect&&(n=t.createElement("boundtest"),n.style.height="123px",n.style.display="block",t.body.appendChild(n),e.selectNode(n),r=e.getBoundingClientRect(),i=r.height,123===i&&(o=!0),t.body.removeChild(n))),o},n.prototype.testCORS=function(){return"undefined"!=typeof(new Image).crossOrigin},n.prototype.testSVG=function(){var t=new Image,e=document.createElement("canvas"),n=e.getContext("2d");t.src="data:image/svg+xml, ";try{n.drawImage(t,0,0),e.toDataURL()}catch(t){return!1}return!0},t.exports=n},function(t,e,n){"use strict";function r(t,e){this.src=t,this.image=null;var n=this;this.promise=e?new Promise(function(e,r){n.image=new Image,n.image.onload=e,n.image.onerror=r,n.image.src="data:image/svg+xml,"+(new XMLSerializer).serializeToString(t),n.image.complete===!0&&e(n.image)}):this.hasFabric().then(function(){return new Promise(function(e){window.html2canvas.svg.fabric.parseSVGDocument(t,n.createCanvas.call(n,e))})})}var i=n(10);r.prototype=Object.create(i.prototype),t.exports=r},function(t,e,n){"use strict";function r(t,e){o.call(this,t,e)}function i(t,e,n){if(t.length>0)return e+n.toUpperCase()}var o=n(3);r.prototype=Object.create(o.prototype),r.prototype.applyTextTransform=function(){this.node.data=this.transform(this.parent.css("textTransform"))},r.prototype.transform=function(t){var e=this.node.data;switch(t){case"lowercase":return e.toLowerCase();case"capitalize":return e.replace(/(^|\s|:|-|\(|\))([a-z])/g,i);case"uppercase":return e.toUpperCase();default:return e}},t.exports=r},function(t,e,n){"use strict";function r(t){i.apply(this,arguments),this.type="linear"===t.args[0]?i.TYPES.LINEAR:i.TYPES.RADIAL}var i=n(8);r.prototype=Object.create(i.prototype),t.exports=r},function(t,e,n){var r;(function(t,i){!function(o){function s(t){throw new RangeError(P[t])}function a(t,e){for(var n=t.length,r=[];n--;)r[n]=e(t[n]);return r}function c(t,e){var n=t.split("@"),r="";n.length>1&&(r=n[0]+"@",t=n[1]),t=t.replace(A,".");var i=t.split("."),o=a(i,e).join(".");return r+o}function h(t){for(var e,n,r=[],i=0,o=t.length;i=55296&&e<=56319&&i65535&&(t-=65536,e+=B(t>>>10&1023|55296),t=56320|1023&t),e+=B(t)}).join("")}function l(t){return t-48<10?t-22:t-65<26?t-65:t-97<26?t-97:x}function d(t,e){return t+22+75*(t<26)-((0!=e)<<5)}function p(t,e,n){var r=0;for(t=n?N(t/k):t>>1,t+=N(t/e);t>L*E>>1;r+=x)t=N(t/L);return N(r+(L+1)*t/(t+T))}function f(t){var e,n,r,i,o,a,c,h,d,f,g=[],m=t.length,y=0,w=S,b=C;for(n=t.lastIndexOf(I),n<0&&(n=0),r=0;r=128&&s("not-basic"),g.push(t.charCodeAt(r));for(i=n>0?n+1:0;i=m&&s("invalid-input"),h=l(t.charCodeAt(i++)),(h>=x||h>N((v-y)/a))&&s("overflow"),y+=h*a,d=c<=b?_:c>=b+E?E:c-b,!(hN(v/f)&&s("overflow"),a*=f;e=g.length+1,b=p(y-o,e,0==o),N(y/e)>v-w&&s("overflow"),w+=N(y/e),y%=e,g.splice(y++,0,w)}return u(g)}function g(t){var e,n,r,i,o,a,c,u,l,f,g,m,y,w,b,T=[];for(t=h(t),m=t.length,e=S,n=0,o=C,a=0;a=e&&gN((v-n)/y)&&s("overflow"),n+=(c-e)*y,e=c,a=0;av&&s("overflow"),g==e){for(u=n,l=x;f=l<=o?_:l>=o+E?E:l-o,!(u= 0x80 (not a basic code point)","invalid-input":"Invalid input"},L=x-_,N=Math.floor,B=String.fromCharCode;b={version:"1.4.1",ucs2:{decode:h,encode:u},decode:f,encode:g,toASCII:y,toUnicode:m},r=function(){return b}.call(e,n,e,t),!(void 0!==r&&(t.exports=r))}(this)}).call(e,n(29)(t),function(){return this}())},function(t,e){t.exports=function(t){return t.webpackPolyfill||(t.deprecate=function(){},t.paths=[],t.children=[],t.webpackPolyfill=1),t}}]);
--------------------------------------------------------------------------------
/example.gif:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/mayognaise/aframe-html-shader/a1b86cde13308f13d1bababa8bd9f8bfae75b8b7/example.gif
--------------------------------------------------------------------------------
/examples/basic/cheesecake.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/mayognaise/aframe-html-shader/a1b86cde13308f13d1bababa8bd9f8bfae75b8b7/examples/basic/cheesecake.png
--------------------------------------------------------------------------------
/examples/basic/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | A-Frame HTML Shader - Basic
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
CHEESECAKE FOR YOU
20 |
21 |
22 |
23 |
24 |
ARE YOU HUNGRY?
25 |
26 |
27 |
28 |
29 |
WELCOME
30 |
HA HA HA
31 |
DON'T LOOK DOWN
32 |
33 |
34 |
35 |
36 |
--------------------------------------------------------------------------------
/examples/dynamic/index.css:
--------------------------------------------------------------------------------
1 | html {
2 | position: inherit !important;
3 | }
4 | .buttons {
5 | position: fixed;
6 | z-index: 2;
7 | right: 0;
8 | text-align: right;
9 | top: 0;
10 | height: 0;
11 | }
12 | .buttons a {
13 | display: inline-block;
14 | border: none;
15 | cursor: pointer;
16 | padding: 1em;
17 | margin: 1em 1em 0 0;
18 | background: gray;
19 | color: white;
20 | font: 14px monospace;
21 | text-decoration: none;
22 | }
23 | .buttons a:active {
24 | background: #333;
25 | }
26 | .spacer {
27 | position: relative;
28 | pointer-events: none;
29 | height: 100%;
30 | }
31 | .spacer2 {
32 | position: relative;
33 | pointer-events: none;
34 | height: 1px;
35 | }
36 |
--------------------------------------------------------------------------------
/examples/dynamic/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | A-Frame HTML Shader - Dynamic
6 |
7 |
8 |
9 |
80 |
126 |
127 |
128 |
129 |
130 |
131 |
132 |
133 |
134 |
135 |
136 |
137 |
138 |
139 |
140 |
141 |
〠
142 |
143 |
HELLO★
144 | A
145 |
146 |
147 |
148 |
149 |
153 |
154 |
155 |
156 |
157 |
174 |
175 |
176 |
--------------------------------------------------------------------------------
/examples/stress/index.css:
--------------------------------------------------------------------------------
1 | .tile {
2 | position: absolute;
3 | top: 50%;
4 | left: 50%;
5 | --x: calc((var(--j, 0) - 3)*5em);
6 | --y: calc((var(--i, 0) - 3)*5em);
7 | --x1: calc(1.41421*var(--x));
8 | --y1: calc(1.41421*var(--y));
9 | transform: translate(var(--x), var(--y));
10 | animation: s 1.5s cubic-bezier(0.35, 0, 0.8, 1) infinite alternate;
11 | }
12 | .tile:nth-child(n + 8) {
13 | --i: 1;
14 | }
15 | .tile:nth-child(7n + 2) {
16 | --j: 1;
17 | }
18 | .tile:nth-child(n + 15) {
19 | --i: 2;
20 | }
21 | .tile:nth-child(7n + 3) {
22 | --j: 2;
23 | }
24 | .tile:nth-child(n + 22) {
25 | --i: 3;
26 | }
27 | .tile:nth-child(7n + 4) {
28 | --j: 3;
29 | }
30 | .tile:nth-child(n + 29) {
31 | --i: 4;
32 | }
33 | .tile:nth-child(7n + 5) {
34 | --j: 4;
35 | }
36 | .tile:nth-child(n + 36) {
37 | --i: 5;
38 | }
39 | .tile:nth-child(7n + 6) {
40 | --j: 5;
41 | }
42 | .tile:nth-child(n + 43) {
43 | --i: 6;
44 | }
45 | .tile:nth-child(7n + 7) {
46 | --j: 6;
47 | }
48 | .tile:after {
49 | position: absolute;
50 | margin: -2.5em;
51 | width: 5em;
52 | height: 5em;
53 | box-shadow: inset 0 0 0 1px;
54 | background: dimgray;
55 | animation: r 3s ease-in-out infinite;
56 | content: "";
57 | }
58 | .tile:nth-child(2n):after {
59 | animation-direction: reverse;
60 | }
61 |
62 | @keyframes s {
63 | to {
64 | transform: translate(var(--x1), var(--y1));
65 | }
66 | }
67 | @keyframes r {
68 | to {
69 | transform: rotate(90deg);
70 | }
71 | }
72 |
--------------------------------------------------------------------------------
/examples/stress/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | A-Frame HTML Shader - Stress
6 |
7 |
8 |
9 |
10 |
11 |
12 |
13 |
14 |
15 |
16 |
17 |
18 |
19 |
20 |
30 |
31 |
32 |
--------------------------------------------------------------------------------
/index.html:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 | A-Frame HTML Shader
6 |
7 |
28 |
29 |
30 | A-Frame HTML Shader
31 | Basic
32 |
33 |
38 |
39 |
40 |
--------------------------------------------------------------------------------
/index.js:
--------------------------------------------------------------------------------
1 | /**
2 | * A shader to render HTML DOM Element
3 | * Inspired by @scenevr's `htmltexture-component`
4 | * @see https://github.com/scenevr/htmltexture-component
5 | */
6 |
7 |
8 | import html2canvas from './lib/html2canvas/core'
9 |
10 | if (typeof AFRAME === 'undefined') {
11 | throw 'Component attempted to register before AFRAME was available.'
12 | }
13 |
14 | /* get util from AFRAME */
15 | const { debug } = AFRAME.utils
16 | // debug.enable('shader:html:*')
17 | debug.enable('shader:html:warn')
18 | const warn = debug('shader:html:warn')
19 | const log = debug('shader:html:debug')
20 |
21 | /* create error message */
22 | function createError (err, target) {
23 | return { status: 'error', target: target, message: err, timestamp: Date.now() }
24 | }
25 |
26 |
27 | AFRAME.registerShader('html', {
28 |
29 | /**
30 | * For material component:
31 | * @see https://github.com/aframevr/aframe/blob/60d198ef8e2bfbc57a13511ae5fca7b62e01691b/src/components/material.js
32 | * For example of `registerShader`:
33 | * @see https://github.com/aframevr/aframe/blob/41a50cd5ac65e462120ecc2e5091f5daefe3bd1e/src/shaders/flat.js
34 | * For MeshBasicMaterial
35 | * @see http://threejs.org/docs/#Reference/Materials/MeshBasicMaterial
36 | */
37 |
38 | schema: {
39 |
40 | /* For material */
41 | color: { type: 'color' },
42 | fog: { default: true },
43 |
44 | /* For texuture */
45 | target: { default: null },
46 | debug: { default: null },
47 | fps: { type: 'number', default: 0 },
48 | width: { default: null },
49 | height: { default: null },
50 | ratio: { default: null },
51 |
52 | },
53 |
54 | /**
55 | * Initialize material. Called once.
56 | * @protected
57 | */
58 | init (data) {
59 | log('init', data)
60 | this.__cnv = document.createElement('canvas')
61 | this.__cnv.width = 2
62 | this.__cnv.height = 2
63 | this.__ctx = this.__cnv.getContext('2d')
64 | this.__texture = new THREE.Texture(this.__cnv)
65 | this.__reset()
66 | this.material = new THREE.MeshBasicMaterial({ map: this.__texture })
67 | this.el.sceneEl.addBehavior(this)
68 | return this.material
69 | },
70 |
71 | /**
72 | * Update or create material.
73 | * @param {object|null} oldData
74 | */
75 | update (oldData) {
76 | log('update', oldData)
77 | this.__updateMaterial(oldData)
78 | this.__updateTexture(oldData)
79 | return this.material
80 | },
81 |
82 | /**
83 | * Called on each scene tick.
84 | * @protected
85 | */
86 | tick (t) {
87 |
88 | if (this.__paused || !this.__target || !this.__nextTime) { return }
89 |
90 | const now = Date.now()
91 | if (now > this.__nextTime) {
92 | this.__render()
93 | }
94 |
95 | },
96 |
97 | /*================================
98 | = material =
99 | ================================*/
100 |
101 | /**
102 | * Updating existing material.
103 | * @param {object} data - Material component data.
104 | */
105 | __updateMaterial (data) {
106 | const { material } = this
107 | const newData = this.__getMaterialData(data)
108 | Object.keys(newData).forEach(key => {
109 | material[key] = newData[key]
110 | })
111 | },
112 |
113 |
114 | /**
115 | * Builds and normalize material data, normalizing stuff along the way.
116 | * @param {Object} data - Material data.
117 | * @return {Object} data - Processed material data.
118 | */
119 | __getMaterialData (data) {
120 | return {
121 | fog: data.fog,
122 | color: new THREE.Color(data.color),
123 | }
124 | },
125 |
126 |
127 | /*==============================
128 | = texure =
129 | ==============================*/
130 |
131 | /**
132 | * set texure
133 | * @private
134 | * @param {Object} data
135 | * @property {string} status - success / error
136 | * @property {string} target - target url
137 | * @property {DOM Element} targetEl - target
138 | * @property {Date} timestamp - created at the texure
139 | */
140 |
141 | __setTexure (data) {
142 | log('__setTexure', data)
143 | if (data.status === 'error') {
144 | warn(`Error: ${data.message}\ntarget: ${data.target}`)
145 | this.__reset()
146 | }
147 | else if (data.status === 'success' && data.target !== this.__textureSrc) {
148 | /* Texture added or changed */
149 | this.__ready(data)
150 | }
151 | },
152 |
153 | /**
154 | * Update or create texure.
155 | * @param {Object} data - Material component data.
156 | */
157 | __updateTexture (data) {
158 |
159 | const { target, fps, width, height, ratio } = data
160 | this.__width = width || this.schema.width.default
161 | this.__height = height || this.schema.height.default
162 |
163 | /* debug */
164 | const resetDebug = () => {
165 | if (this.__debugEl) {
166 | this.__debugEl.innerHTML = ''
167 | this.__debugEl = this.schema.debug.default
168 | }
169 | }
170 | if (data.debug) {
171 | const el = this.__validateAndGetQuerySelector(data.debug)
172 | if (el && !el.error) { this.__debugEl = el }
173 | else resetDebug()
174 | }
175 | else resetDebug()
176 |
177 | /* ratio */
178 | if(ratio && ratio === 'width' || ratio === 'height') {
179 | this.__ratio = ratio
180 | }
181 | else {
182 | this.__ratio = this.schema.ratio.default
183 | }
184 |
185 | /* fps */
186 | if (fps) {
187 | if (this.__fps > 0) {
188 | this.__fps = fps
189 | }
190 | else if (fps === -1) {
191 | /* render only once */
192 | this.__fps = this.schema.fps.default
193 | if (this.__target) {
194 | this.__render()
195 | }
196 | /* set attribute */
197 | const material = Object.assign({}, this.el.getAttribute('material'))
198 | delete material.fps
199 | this.el.setAttribute('material', material)
200 | }
201 | else {
202 | this.__fps = fps
203 | if (this.__target) {
204 | this.play()
205 | this.__render()
206 | }
207 | }
208 | }
209 | else {
210 | if (this.__fps > 0) {
211 | this.pause()
212 | }
213 | else {
214 | this.__fps = this.schema.fps.default
215 | }
216 | }
217 |
218 | /* target */
219 | if (target) {
220 | if (target === this.__target) { return }
221 | this.__target = target
222 | // return
223 | this.__validateSrc(target, this.__setTexure.bind(this))
224 | } else {
225 | /* Texture removed */
226 | this.__reset()
227 | }
228 | },
229 |
230 | /*=============================================
231 | = varidation for texure =
232 | =============================================*/
233 |
234 | /**
235 | * varidate src
236 | * @private
237 | * @param {string} target - dom selector
238 | * @param {Function} cb - callback
239 | */
240 | __validateSrc (target, cb) {
241 |
242 | let message
243 |
244 | /* check if target is a query selector */
245 | const el = this.__validateAndGetQuerySelector(target)
246 | if (!el || typeof el !== 'object') { return }
247 | if (el.error) {
248 | message = el.error
249 | }
250 | else {
251 | const tagName = el.tagName.toLowerCase()
252 | if (tagName === 'img' || tagName === 'video') {
253 | message = `For <${tagName}> element, please use \`shader:flat\``
254 | }
255 | else {
256 | cb({ status: 'success', target: target, targetEl: el, timestamp: Date.now() })
257 | }
258 | }
259 |
260 | /* if there is message, create error data */
261 | if (message) {
262 | const err = createError(message, target)
263 | cb(err)
264 | }
265 |
266 | },
267 |
268 | /**
269 | * Query and validate a query selector,
270 | *
271 | * @param {string} selector - DOM selector.
272 | * @return {object} Selected DOM element | error message object.
273 | */
274 | __validateAndGetQuerySelector (selector) {
275 | try {
276 | var el = document.querySelector(selector)
277 | if (!el) {
278 | return { error: 'No element was found matching the selector' }
279 | }
280 | return el
281 | } catch (e) { // Capture exception if it's not a valid selector.
282 | return { error: 'no valid selector' }
283 | }
284 | },
285 |
286 |
287 | /*================================
288 | = playback =
289 | ================================*/
290 |
291 | /**
292 | * Pause video
293 | * @public
294 | */
295 | pause () {
296 | log('pause')
297 | this.__paused = true
298 | this.__nextTime = null
299 | },
300 |
301 | /**
302 | * Play video
303 | * @public
304 | */
305 | play () {
306 | log('play')
307 | this.__paused = false
308 | },
309 |
310 | /**
311 | * Toggle playback. play if paused and pause if played.
312 | * @public
313 | */
314 |
315 | togglePlayback () {
316 | if (this.paused()) { this.play() }
317 | else { this.pause() }
318 |
319 | },
320 |
321 | /**
322 | * Return if the playback is paused.
323 | * @public
324 | * @return {boolean}
325 | */
326 | paused () {
327 | return this.__paused
328 | },
329 |
330 | /*==============================
331 | = canvas =
332 | ==============================*/
333 |
334 | /**
335 | * clear canvas
336 | * @private
337 | */
338 | __clearCanvas () {
339 | if (!this.__ctx || !this.__texture) { return }
340 | this.__ctx.clearRect(0, 0, this.__width, this.__height)
341 | this.__texture.needsUpdate = true
342 | },
343 |
344 | /**
345 | * draw
346 | * @private
347 | */
348 | __draw (canvas) {
349 | log('__draw')
350 | if (!this.__ctx || !this.__texture) { return }
351 | const ratio = canvas.width / canvas.height
352 | const cnvW = this.__cnv.width = THREE.Math.nearestPowerOfTwo(canvas.width)
353 | const cnvH = this.__cnv.height = THREE.Math.nearestPowerOfTwo(canvas.height)
354 | this.__ctx.drawImage(canvas, 0, 0, cnvW, cnvH)
355 | this.__texture.needsUpdate = true
356 | if (this.__ratio) {
357 | /* change size */
358 | const { width, height } = this.el.getObject3D('mesh').geometry.metadata.parameters
359 | this.el.setAttribute('geometry', Object.assign({}, this.el.getAttribute('geometry'), {
360 | width: (this.__ratio === 'width')? width : height * ratio,
361 | height: (this.__ratio === 'width')? width / ratio : height
362 | }))
363 | }
364 |
365 | /* append if debug element exists */
366 | if (this.__debugEl) {
367 | this.__debugEl.innerHTML = ''
368 | this.__debugEl.appendChild(canvas)
369 | }
370 |
371 | /* setup next tick */
372 | this.__setNextTick()
373 |
374 | },
375 |
376 | /**
377 | * render
378 | * @private
379 | */
380 | __render () {
381 | this.__nextTime = null
382 | if (!this.__targetEl) { return }
383 | const { width, height } = this.__targetEl.getBoundingClientRect()
384 | html2canvas(this.__targetEl, {
385 | background: undefined,
386 | width: this.__width || width,
387 | height: this.__height || height,
388 | onrendered: this.__draw.bind(this)
389 | })
390 | },
391 |
392 | /**
393 | * get next time to draw
394 | * @private
395 | */
396 | __setNextTick () {
397 | if (this.__fps > 0) {
398 | this.__nextTime = Date.now() + (1000 / this.__fps)
399 | }
400 | },
401 |
402 |
403 | /*============================
404 | = ready =
405 | ============================*/
406 |
407 | /**
408 | * setup html animation and play if autoplay is true
409 | * @private
410 | * @property {string} target - target url
411 | * @property {DOM Element} targetEl - target
412 | */
413 | __ready ({ target, targetEl }) {
414 | log('__ready')
415 | this.__target = target
416 | this.__targetEl = targetEl
417 | this.play()
418 | this.__render()
419 | },
420 |
421 |
422 |
423 | /*=============================
424 | = reset =
425 | =============================*/
426 |
427 | /**
428 | * @private
429 | */
430 |
431 | __reset () {
432 | this.pause()
433 | this.__clearCanvas()
434 | this.__target = null
435 | this.__targetEl = null
436 | this.__debugEl = null
437 | },
438 |
439 |
440 |
441 | })
442 |
443 |
--------------------------------------------------------------------------------
/lib/html2canvas/clone.js:
--------------------------------------------------------------------------------
1 | var log = require('./log');
2 |
3 | function restoreOwnerScroll(ownerDocument, x, y) {
4 | if (ownerDocument.defaultView && (x !== ownerDocument.defaultView.pageXOffset || y !== ownerDocument.defaultView.pageYOffset)) {
5 | ownerDocument.defaultView.scrollTo(x, y);
6 | }
7 | }
8 |
9 | function cloneCanvasContents(canvas, clonedCanvas) {
10 | try {
11 | if (clonedCanvas) {
12 | clonedCanvas.width = canvas.width;
13 | clonedCanvas.height = canvas.height;
14 | clonedCanvas.getContext("2d").putImageData(canvas.getContext("2d").getImageData(0, 0, canvas.width, canvas.height), 0, 0);
15 | }
16 | } catch(e) {
17 | log("Unable to copy canvas content from", canvas, e);
18 | }
19 | }
20 |
21 | function cloneNode(node, javascriptEnabled) {
22 | var clone = node.nodeType === 3 ? document.createTextNode(node.nodeValue) : node.cloneNode(false);
23 |
24 | var child = node.firstChild;
25 | while(child) {
26 | if (javascriptEnabled === true || child.nodeType !== 1 || child.nodeName !== 'SCRIPT') {
27 | clone.appendChild(cloneNode(child, javascriptEnabled));
28 | }
29 | child = child.nextSibling;
30 | }
31 |
32 | if (node.nodeType === 1) {
33 | clone._scrollTop = node.scrollTop;
34 | clone._scrollLeft = node.scrollLeft;
35 | if (node.nodeName === "CANVAS") {
36 | cloneCanvasContents(node, clone);
37 | } else if (node.nodeName === "TEXTAREA" || node.nodeName === "SELECT") {
38 | clone.value = node.value;
39 | }
40 | }
41 |
42 | return clone;
43 | }
44 |
45 | function initNode(node) {
46 | if (node.nodeType === 1) {
47 | node.scrollTop = node._scrollTop;
48 | node.scrollLeft = node._scrollLeft;
49 |
50 | var child = node.firstChild;
51 | while(child) {
52 | initNode(child);
53 | child = child.nextSibling;
54 | }
55 | }
56 | }
57 |
58 | module.exports = function(ownerDocument, containerDocument, width, height, options, x ,y) {
59 | var documentElement = cloneNode(ownerDocument.documentElement, options.javascriptEnabled);
60 | var container = containerDocument.createElement("iframe");
61 |
62 | container.className = "html2canvas-container";
63 | container.style.visibility = "hidden";
64 | container.style.position = "fixed";
65 | container.style.left = "-10000px";
66 | container.style.top = "0px";
67 | container.style.border = "0";
68 | container.width = width;
69 | container.height = height;
70 | container.scrolling = "no"; // ios won't scroll without it
71 | containerDocument.body.appendChild(container);
72 |
73 | return new Promise(function(resolve) {
74 | var documentClone = container.contentWindow.document;
75 |
76 | /* Chrome doesn't detect relative background-images assigned in inline