| /* eslint-disable */ |
| |
| // gif.js 0.2.0 - https://github.com/jnordberg/gif.js |
| (function(f) { |
| if (typeof exports === "object" && typeof module !== "undefined") { |
| module.exports = f() |
| } else if (typeof define === "function" && define.amd) { |
| define([], f) |
| } else { |
| var g; |
| if (typeof window !== "undefined") { |
| g = window |
| } else if (typeof global !== "undefined") { |
| g = global |
| } else if (typeof self !== "undefined") { |
| g = self |
| } else { |
| g = this |
| } |
| g.GIF = f() |
| } |
| })(function() { |
| var define, module, exports; |
| return function e(t, n, r) { |
| function s(o, u) { |
| if (!n[o]) { |
| if (!t[o]) { |
| var a = typeof require == "function" && require; |
| if (!u && a) return a(o, !0); |
| if (i) return i(o, !0); |
| var f = new Error("Cannot find module '" + o + "'"); |
| throw f.code = "MODULE_NOT_FOUND", f |
| } |
| var l = n[o] = { |
| exports: {} |
| }; |
| t[o][0].call(l.exports, function(e) { |
| var n = t[o][1][e]; |
| return s(n ? n : e) |
| }, l, l.exports, e, t, n, r) |
| } |
| return n[o].exports |
| } |
| var i = typeof require == "function" && require; |
| for (var o = 0; o < r.length; o++) s(r[o]); |
| return s |
| }({ |
| 1: [function(require, module, exports) { |
| function EventEmitter() { |
| this._events = this._events || {}; |
| this._maxListeners = this._maxListeners || undefined |
| } |
| module.exports = EventEmitter; |
| EventEmitter.EventEmitter = EventEmitter; |
| EventEmitter.prototype._events = undefined; |
| EventEmitter.prototype._maxListeners = undefined; |
| EventEmitter.defaultMaxListeners = 10; |
| EventEmitter.prototype.setMaxListeners = function(n) { |
| if (!isNumber(n) || n < 0 || isNaN(n)) throw TypeError("n must be a positive number"); |
| this._maxListeners = n; |
| return this |
| }; |
| EventEmitter.prototype.emit = function(type) { |
| var er, handler, len, args, i, listeners; |
| if (!this._events) this._events = {}; |
| if (type === "error") { |
| if (!this._events.error || isObject(this._events.error) && !this._events.error.length) { |
| er = arguments[1]; |
| if (er instanceof Error) { |
| throw er |
| } else { |
| var err = new Error('Uncaught, unspecified "error" event. (' + er + ")"); |
| err.context = er; |
| throw err |
| } |
| } |
| } |
| handler = this._events[type]; |
| if (isUndefined(handler)) return false; |
| if (isFunction(handler)) { |
| switch (arguments.length) { |
| case 1: |
| handler.call(this); |
| break; |
| case 2: |
| handler.call(this, arguments[1]); |
| break; |
| case 3: |
| handler.call(this, arguments[1], arguments[2]); |
| break; |
| default: |
| args = Array.prototype.slice.call(arguments, 1); |
| handler.apply(this, args) |
| } |
| } else if (isObject(handler)) { |
| args = Array.prototype.slice.call(arguments, 1); |
| listeners = handler.slice(); |
| len = listeners.length; |
| for (i = 0; i < len; i++) listeners[i].apply(this, args) |
| } |
| return true |
| }; |
| EventEmitter.prototype.addListener = function(type, listener) { |
| var m; |
| if (!isFunction(listener)) throw TypeError("listener must be a function"); |
| if (!this._events) this._events = {}; |
| if (this._events.newListener) this.emit("newListener", type, isFunction(listener.listener) ? listener.listener : listener); |
| if (!this._events[type]) this._events[type] = listener; |
| else if (isObject(this._events[type])) this._events[type].push(listener); |
| else this._events[type] = [this._events[type], listener]; |
| if (isObject(this._events[type]) && !this._events[type].warned) { |
| if (!isUndefined(this._maxListeners)) { |
| m = this._maxListeners |
| } else { |
| m = EventEmitter.defaultMaxListeners |
| } |
| if (m && m > 0 && this._events[type].length > m) { |
| this._events[type].warned = true; |
| console.error("(node) warning: possible EventEmitter memory " + "leak detected. %d listeners added. " + "Use emitter.setMaxListeners() to increase limit.", this._events[type].length); |
| if (typeof console.trace === "function") { |
| console.trace() |
| } |
| } |
| } |
| return this |
| }; |
| EventEmitter.prototype.on = EventEmitter.prototype.addListener; |
| EventEmitter.prototype.once = function(type, listener) { |
| if (!isFunction(listener)) throw TypeError("listener must be a function"); |
| var fired = false; |
| |
| function g() { |
| this.removeListener(type, g); |
| if (!fired) { |
| fired = true; |
| listener.apply(this, arguments) |
| } |
| } |
| g.listener = listener; |
| this.on(type, g); |
| return this |
| }; |
| EventEmitter.prototype.removeListener = function(type, listener) { |
| var list, position, length, i; |
| if (!isFunction(listener)) throw TypeError("listener must be a function"); |
| if (!this._events || !this._events[type]) return this; |
| list = this._events[type]; |
| length = list.length; |
| position = -1; |
| if (list === listener || isFunction(list.listener) && list.listener === listener) { |
| delete this._events[type]; |
| if (this._events.removeListener) this.emit("removeListener", type, listener) |
| } else if (isObject(list)) { |
| for (i = length; i-- > 0;) { |
| if (list[i] === listener || list[i].listener && list[i].listener === listener) { |
| position = i; |
| break |
| } |
| } |
| if (position < 0) return this; |
| if (list.length === 1) { |
| list.length = 0; |
| delete this._events[type] |
| } else { |
| list.splice(position, 1) |
| } |
| if (this._events.removeListener) this.emit("removeListener", type, listener) |
| } |
| return this |
| }; |
| EventEmitter.prototype.removeAllListeners = function(type) { |
| var key, listeners; |
| if (!this._events) return this; |
| if (!this._events.removeListener) { |
| if (arguments.length === 0) this._events = {}; |
| else if (this._events[type]) delete this._events[type]; |
| return this |
| } |
| if (arguments.length === 0) { |
| for (key in this._events) { |
| if (key === "removeListener") continue; |
| this.removeAllListeners(key) |
| } |
| this.removeAllListeners("removeListener"); |
| this._events = {}; |
| return this |
| } |
| listeners = this._events[type]; |
| if (isFunction(listeners)) { |
| this.removeListener(type, listeners) |
| } else if (listeners) { |
| while (listeners.length) this.removeListener(type, listeners[listeners.length - 1]) |
| } |
| delete this._events[type]; |
| return this |
| }; |
| EventEmitter.prototype.listeners = function(type) { |
| var ret; |
| if (!this._events || !this._events[type]) ret = []; |
| else if (isFunction(this._events[type])) ret = [this._events[type]]; |
| else ret = this._events[type].slice(); |
| return ret |
| }; |
| EventEmitter.prototype.listenerCount = function(type) { |
| if (this._events) { |
| var evlistener = this._events[type]; |
| if (isFunction(evlistener)) return 1; |
| else if (evlistener) return evlistener.length |
| } |
| return 0 |
| }; |
| EventEmitter.listenerCount = function(emitter, type) { |
| return emitter.listenerCount(type) |
| }; |
| |
| function isFunction(arg) { |
| return typeof arg === "function" |
| } |
| |
| function isNumber(arg) { |
| return typeof arg === "number" |
| } |
| |
| function isObject(arg) { |
| return typeof arg === "object" && arg !== null |
| } |
| |
| function isUndefined(arg) { |
| return arg === void 0 |
| } |
| }, {}], |
| 2: [function(require, module, exports) { |
| var UA, browser, mode, platform, ua; |
| ua = navigator.userAgent.toLowerCase(); |
| platform = navigator.platform.toLowerCase(); |
| UA = ua.match(/(opera|ie|firefox|chrome|version)[\s\/:]([\w\d\.]+)?.*?(safari|version[\s\/:]([\w\d\.]+)|$)/) || [null, "unknown", 0]; |
| mode = UA[1] === "ie" && document.documentMode; |
| browser = { |
| name: UA[1] === "version" ? UA[3] : UA[1], |
| version: mode || parseFloat(UA[1] === "opera" && UA[4] ? UA[4] : UA[2]), |
| platform: { |
| name: ua.match(/ip(?:ad|od|hone)/) ? "ios" : (ua.match(/(?:webos|android)/) || platform.match(/mac|win|linux/) || ["other"])[0] |
| } |
| }; |
| browser[browser.name] = true; |
| browser[browser.name + parseInt(browser.version, 10)] = true; |
| browser.platform[browser.platform.name] = true; |
| module.exports = browser |
| }, {}], |
| 3: [function(require, module, exports) { |
| var EventEmitter, GIF, browser, extend = function(child, parent) { |
| for (var key in parent) { |
| if (hasProp.call(parent, key)) child[key] = parent[key] |
| } |
| |
| function ctor() { |
| this.constructor = child |
| } |
| ctor.prototype = parent.prototype; |
| child.prototype = new ctor; |
| child.__super__ = parent.prototype; |
| return child |
| }, |
| hasProp = {}.hasOwnProperty, |
| indexOf = [].indexOf || function(item) { |
| for (var i = 0, l = this.length; i < l; i++) { |
| if (i in this && this[i] === item) return i |
| } |
| return -1 |
| }, |
| slice = [].slice; |
| EventEmitter = require("events").EventEmitter; |
| browser = require("./browser.coffee"); |
| GIF = function(superClass) { |
| var defaults, frameDefaults; |
| extend(GIF, superClass); |
| defaults = { |
| workerScript: "gif.worker.js", |
| workers: 2, |
| repeat: 0, |
| background: "#fff", |
| quality: 10, |
| width: null, |
| height: null, |
| transparent: null, |
| debug: false, |
| dither: false |
| }; |
| frameDefaults = { |
| delay: 500, |
| copy: false |
| }; |
| |
| function GIF(options) { |
| var base, key, value; |
| this.running = false; |
| this.options = {}; |
| this.frames = []; |
| this.freeWorkers = []; |
| this.activeWorkers = []; |
| this.setOptions(options); |
| for (key in defaults) { |
| value = defaults[key]; |
| if ((base = this.options)[key] == null) { |
| base[key] = value |
| } |
| } |
| } |
| GIF.prototype.setOption = function(key, value) { |
| this.options[key] = value; |
| if (this._canvas != null && (key === "width" || key === "height")) { |
| return this._canvas[key] = value |
| } |
| }; |
| GIF.prototype.setOptions = function(options) { |
| var key, results, value; |
| results = []; |
| for (key in options) { |
| if (!hasProp.call(options, key)) continue; |
| value = options[key]; |
| results.push(this.setOption(key, value)) |
| } |
| return results |
| }; |
| GIF.prototype.addFrame = function(image, options) { |
| var frame, key; |
| if (options == null) { |
| options = {} |
| } |
| frame = {}; |
| frame.transparent = this.options.transparent; |
| for (key in frameDefaults) { |
| frame[key] = options[key] || frameDefaults[key] |
| } |
| if (this.options.width == null) { |
| this.setOption("width", image.width) |
| } |
| if (this.options.height == null) { |
| this.setOption("height", image.height) |
| } |
| if (typeof ImageData !== "undefined" && ImageData !== null && image instanceof ImageData) { |
| frame.data = image.data |
| } else if (typeof CanvasRenderingContext2D !== "undefined" && CanvasRenderingContext2D !== null && image instanceof CanvasRenderingContext2D || typeof WebGLRenderingContext !== "undefined" && WebGLRenderingContext !== null && image instanceof WebGLRenderingContext) { |
| if (options.copy) { |
| frame.data = this.getContextData(image) |
| } else { |
| frame.context = image |
| } |
| } else if (image.childNodes != null) { |
| if (options.copy) { |
| frame.data = this.getImageData(image) |
| } else { |
| frame.image = image |
| } |
| } else { |
| throw new Error("Invalid image") |
| } |
| return this.frames.push(frame) |
| }; |
| GIF.prototype.render = function() { |
| var i, j, numWorkers, ref; |
| if (this.running) { |
| throw new Error("Already running") |
| } |
| if (this.options.width == null || this.options.height == null) { |
| throw new Error("Width and height must be set prior to rendering") |
| } |
| this.running = true; |
| this.nextFrame = 0; |
| this.finishedFrames = 0; |
| this.imageParts = function() { |
| var j, ref, results; |
| results = []; |
| for (i = j = 0, ref = this.frames.length; 0 <= ref ? j < ref : j > ref; i = 0 <= ref ? ++j : --j) { |
| results.push(null) |
| } |
| return results |
| }.call(this); |
| numWorkers = this.spawnWorkers(); |
| if (this.options.globalPalette === true) { |
| this.renderNextFrame() |
| } else { |
| for (i = j = 0, ref = numWorkers; 0 <= ref ? j < ref : j > ref; i = 0 <= ref ? ++j : --j) { |
| this.renderNextFrame() |
| } |
| } |
| this.emit("start"); |
| return this.emit("progress", 0) |
| }; |
| GIF.prototype.abort = function() { |
| var worker; |
| while (true) { |
| worker = this.activeWorkers.shift(); |
| if (worker == null) { |
| break |
| } |
| this.log("killing active worker"); |
| worker.terminate() |
| } |
| this.running = false; |
| return this.emit("abort") |
| }; |
| GIF.prototype.spawnWorkers = function() { |
| var j, numWorkers, ref, results; |
| numWorkers = Math.min(this.options.workers, this.frames.length); |
| (function() { |
| results = []; |
| for (var j = ref = this.freeWorkers.length; ref <= numWorkers ? j < numWorkers : j > numWorkers; ref <= numWorkers ? j++ : j--) { |
| results.push(j) |
| } |
| return results |
| }).apply(this).forEach(function(_this) { |
| return function(i) { |
| var worker; |
| _this.log("spawning worker " + i); |
| worker = new Worker(_this.options.workerScript); |
| worker.onmessage = function(event) { |
| _this.activeWorkers.splice(_this.activeWorkers.indexOf(worker), 1); |
| _this.freeWorkers.push(worker); |
| return _this.frameFinished(event.data) |
| }; |
| return _this.freeWorkers.push(worker) |
| } |
| }(this)); |
| return numWorkers |
| }; |
| GIF.prototype.frameFinished = function(frame) { |
| var i, j, ref; |
| this.log("frame " + frame.index + " finished - " + this.activeWorkers.length + " active"); |
| this.finishedFrames++; |
| this.emit("progress", this.finishedFrames / this.frames.length); |
| this.imageParts[frame.index] = frame; |
| if (this.options.globalPalette === true) { |
| this.options.globalPalette = frame.globalPalette; |
| this.log("global palette analyzed"); |
| if (this.frames.length > 2) { |
| for (i = j = 1, ref = this.freeWorkers.length; 1 <= ref ? j < ref : j > ref; i = 1 <= ref ? ++j : --j) { |
| this.renderNextFrame() |
| } |
| } |
| } |
| if (indexOf.call(this.imageParts, null) >= 0) { |
| return this.renderNextFrame() |
| } else { |
| return this.finishRendering() |
| } |
| }; |
| GIF.prototype.finishRendering = function() { |
| var data, frame, i, image, j, k, l, len, len1, len2, len3, offset, page, ref, ref1, ref2; |
| len = 0; |
| ref = this.imageParts; |
| for (j = 0, len1 = ref.length; j < len1; j++) { |
| frame = ref[j]; |
| len += (frame.data.length - 1) * frame.pageSize + frame.cursor |
| } |
| len += frame.pageSize - frame.cursor; |
| this.log("rendering finished - filesize " + Math.round(len / 1e3) + "kb"); |
| data = new Uint8Array(len); |
| offset = 0; |
| ref1 = this.imageParts; |
| for (k = 0, len2 = ref1.length; k < len2; k++) { |
| frame = ref1[k]; |
| ref2 = frame.data; |
| for (i = l = 0, len3 = ref2.length; l < len3; i = ++l) { |
| page = ref2[i]; |
| data.set(page, offset); |
| if (i === frame.data.length - 1) { |
| offset += frame.cursor |
| } else { |
| offset += frame.pageSize |
| } |
| } |
| } |
| image = new Blob([data], { |
| type: "image/gif" |
| }); |
| return this.emit("finished", image, data) |
| }; |
| GIF.prototype.renderNextFrame = function() { |
| var frame, task, worker; |
| if (this.freeWorkers.length === 0) { |
| throw new Error("No free workers") |
| } |
| if (this.nextFrame >= this.frames.length) { |
| return |
| } |
| frame = this.frames[this.nextFrame++]; |
| worker = this.freeWorkers.shift(); |
| task = this.getTask(frame); |
| this.log("starting frame " + (task.index + 1) + " of " + this.frames.length); |
| this.activeWorkers.push(worker); |
| return worker.postMessage(task) |
| }; |
| GIF.prototype.getContextData = function(ctx) { |
| return ctx.getImageData(0, 0, this.options.width, this.options.height).data |
| }; |
| GIF.prototype.getImageData = function(image) { |
| var ctx; |
| if (this._canvas == null) { |
| this._canvas = document.createElement("canvas"); |
| this._canvas.width = this.options.width; |
| this._canvas.height = this.options.height |
| } |
| ctx = this._canvas.getContext("2d"); |
| ctx.fillStyle = this.options.background; |
| ctx.fillRect(0, 0, this.options.width, this.options.height); |
| ctx.drawImage(image, 0, 0); |
| return this.getContextData(ctx) |
| }; |
| GIF.prototype.getTask = function(frame) { |
| var index, task; |
| index = this.frames.indexOf(frame); |
| task = { |
| index: index, |
| last: index === this.frames.length - 1, |
| delay: frame.delay, |
| transparent: frame.transparent, |
| width: this.options.width, |
| height: this.options.height, |
| quality: this.options.quality, |
| dither: this.options.dither, |
| globalPalette: this.options.globalPalette, |
| repeat: this.options.repeat, |
| canTransfer: browser.name === "chrome" |
| }; |
| if (frame.data != null) { |
| task.data = frame.data |
| } else if (frame.context != null) { |
| task.data = this.getContextData(frame.context) |
| } else if (frame.image != null) { |
| task.data = this.getImageData(frame.image) |
| } else { |
| throw new Error("Invalid frame") |
| } |
| return task |
| }; |
| GIF.prototype.log = function() { |
| var args; |
| args = 1 <= arguments.length ? slice.call(arguments, 0) : []; |
| if (!this.options.debug) { |
| return |
| } |
| return console.log.apply(console, args) |
| }; |
| return GIF |
| }(EventEmitter); |
| module.exports = GIF |
| }, { |
| "./browser.coffee": 2, |
| events: 1 |
| }] |
| }, {}, [3])(3) |
| }); |
| //# sourceMappingURL=gif.js.map |