From 8021a86315e0dc37d5ac77437fad022dd6f7cc8b Mon Sep 17 00:00:00 2001 From: Michael Hardeman Date: Tue, 7 Oct 2025 12:06:14 -0400 Subject: [PATCH 1/3] Cleanup and Fixes: 1. Removed JQuery Dependency 2. Fixed references to CDN that no longer exists 3. Fixed demo and moved it up one directory level so it can use the local files. 4. Removed most of the rollup plugins. reduced node_modules weight by about 90% --- README.md | 14 +- demo.html | 69 +++ demo/demo.js | 50 -- demo/index.html | 19 - lib/agent.js | 168 +++--- lib/animator.js | 22 +- lib/balloon.js | 91 ++-- lib/index.js | 2 - lib/load.js | 165 +++--- lib/queue.js | 11 +- package-lock.json | 577 ++++++++++++++++++++ package.json | 17 +- rollup.config.js | 74 ++- yarn.lock | 1310 +++++---------------------------------------- 14 files changed, 1070 insertions(+), 1519 deletions(-) create mode 100755 demo.html delete mode 100755 demo/demo.js delete mode 100755 demo/index.html create mode 100644 package-lock.json diff --git a/README.md b/README.md index e02a1e1..ec19a2e 100755 --- a/README.md +++ b/README.md @@ -1,14 +1,14 @@ # Clippy > Add Clippy or his friends to any website for instant nostalgia. This project is a fresh rewrite of [Clippy.JS](http://smore.com/clippy-js) in ES6. -([Read More](http://smore.com/clippy-js)) +([Read More](http://smore.com/clippy-js)) ## Demos Please be patient for first load. It may take some time as agents are loaded one by one. - [Simple JSFiddle](https://jsfiddle.net/pi0/rtw8p05k) -- [Agents Zoo](https://pi0.github.io/clippyjs/demo/index.html) +- [Agents Zoo](https://pi0.github.io/clippyjs/demo/index.html) ![image](https://user-images.githubusercontent.com/5158436/27002340-c221cc06-4df4-11e7-9438-050a3ad8ecde.png) [![FOSSA Status](https://app.fossa.io/api/projects/git%2Bhttps%3A%2F%2Fgithub.com%2Fpi0%2Fclippyjs.svg?type=shield)](https://app.fossa.io/projects/git%2Bhttps%3A%2F%2Fgithub.com%2Fpi0%2Fclippyjs?ref=badge_shield) @@ -21,12 +21,8 @@ For using in raw HTML/JS: ```html - - - - - - + + + + + \ No newline at end of file diff --git a/demo/demo.js b/demo/demo.js deleted file mode 100755 index 0d8e2b6..0000000 --- a/demo/demo.js +++ /dev/null @@ -1,50 +0,0 @@ -var availableAgents = ['Bonzi', 'Clippy', 'F1', 'Genie', 'Genius', 'Links', 'Merlin', 'Peedy', 'Rocky', 'Rover'] - -var talks = [ - 'How can i help you?', - 'Nice day!', - 'Glad to meet you.', - 'At your service', - 'Helloo' -] - -const randPos = () => .2 + Math.random() * .6 - -function nextAgent () { - let agentName = availableAgents.pop() - if (!agentName) return; - - clippy.load(agentName, agent => { - window[agentName] = agent - - const move = () => { - agent.moveTo($(document).width() * randPos(), $(document).height() * randPos()) - } - - move() - - agent.show(); - - // Speak on click and start - const speak = () => { - agent.speak('I am ' + agentName + ', ' + talks[~~(Math.random() * talks.length)]) - agent.animate() - } - $(agent._el).click(() => speak()) - speak() - - // Animate randomly - setInterval(() => { - agent.animate() - }, 3000 + (Math.random() * 4000)) - - // Move randomly - setInterval(() => { - move() - }, 3000 + (Math.random() * 4000)) - - setTimeout(nextAgent, 2000) - }); -} - -nextAgent() \ No newline at end of file diff --git a/demo/index.html b/demo/index.html deleted file mode 100755 index 8823c68..0000000 --- a/demo/index.html +++ /dev/null @@ -1,19 +0,0 @@ - - - - - - - - - - - \ No newline at end of file diff --git a/lib/agent.js b/lib/agent.js index 9afb042..c307811 100755 --- a/lib/agent.js +++ b/lib/agent.js @@ -1,18 +1,19 @@ -import $ from 'jquery' import Queue from './queue' import Animator from './animator' import Balloon from './balloon' export default class Agent { - constructor (path,data,sounds) { + constructor (path, data, sounds) { this.path = path; - this._queue = new Queue($.proxy(this._onQueueEmpty, this)); + this._queue = new Queue(this._onQueueEmpty.bind(this)); - this._el = $('
').hide(); + this._el = document.createElement('div'); + this._el.className = 'clippy'; + this._el.style.display = 'none'; - $(document.body).append(this._el); + document.body.appendChild(this._el); this._animator = new Animator(this._el, path, data, sounds); @@ -45,7 +46,7 @@ export default class Agent { let el = this._el; this.stop(); if (fast) { - this._el.hide(); + this._el.style.display = 'none'; this.stop(); this.pause(); if (callback) callback(); @@ -53,7 +54,7 @@ export default class Agent { } return this._playInternal('Hide', function () { - el.hide(); + el.style.display = 'none'; this.pause(); if (callback) callback(); }) @@ -68,7 +69,8 @@ export default class Agent { this._addToQueue(function (complete) { // the simple case if (duration === 0) { - this._el.css({ top: y, left: x }); + this._el.style.top = y + 'px'; + this._el.style.left = x + 'px'; this.reposition(); complete(); return; @@ -76,36 +78,65 @@ export default class Agent { // no animations if (!this.hasAnimation(anim)) { - this._el.animate({ top: y, left: x }, duration, complete); + this._animate(this._el, { top: y, left: x }, duration, complete); return; } - let callback = $.proxy(function (name, state) { + let callback = (name, state) => { // when exited, complete if (state === Animator.States.EXITED) { complete(); } // if waiting, if (state === Animator.States.WAITING) { - this._el.animate({ top: y, left: x }, duration, $.proxy(function () { + this._animate(this._el, { top: y, left: x }, duration, () => { // after we're done with the movement, do the exit animation this._animator.exitAnimation(); - }, this)); + }); } - - }, this); + }; this._playInternal(anim, callback); }, this); } + _animate(element, props, duration, callback) { + const start = performance.now(); + const startProps = {}; + + for (let prop in props) { + const currentValue = parseFloat(getComputedStyle(element)[prop]) || 0; + startProps[prop] = currentValue; + } + + const animate = (currentTime) => { + const elapsed = currentTime - start; + const progress = Math.min(elapsed / duration, 1); + + for (let prop in props) { + const startValue = startProps[prop]; + const endValue = props[prop]; + const currentValue = startValue + (endValue - startValue) * progress; + element.style[prop] = currentValue + 'px'; + } + + if (progress < 1) { + requestAnimationFrame(animate); + } else if (callback) { + callback(); + } + }; + + requestAnimationFrame(animate); + } + _playInternal (animation, callback) { // if we're inside an idle animation, - if (this._isIdleAnimation() && this._idleDfd && this._idleDfd.state() === 'pending') { - this._idleDfd.done($.proxy(function () { + if (this._isIdleAnimation() && this._idleDfd && this._idleDfd.state === 'pending') { + this._idleDfd.then(() => { this._playInternal(animation, callback); - }, this)) + }); } this._animator.showAnimation(animation, callback); @@ -130,11 +161,11 @@ export default class Agent { // if has timeout, register a timeout function if (timeout) { - window.setTimeout($.proxy(function () { + window.setTimeout(() => { if (completed) return; // exit after timeout this._animator.exitAnimation(); - }, this), timeout) + }, timeout) } this._playInternal(animation, callback); @@ -151,16 +182,17 @@ export default class Agent { this._hidden = false; if (fast) { - this._el.show(); + this._el.style.display = 'block'; this.resume(); this._onQueueEmpty(); return; } - if (this._el.css('top') === 'auto' || !this._el.css('left') === 'auto') { - let left = $(window).width() * 0.8; - let top = ($(window).height() + $(document).scrollTop()) * 0.8; - this._el.css({ top: top, left: left }); + if (this._el.style.top === 'auto' || this._el.style.left === 'auto') { + let left = window.innerWidth * 0.8; + let top = (window.innerHeight + window.pageYOffset) * 0.8; + this._el.style.top = top + 'px'; + this._el.style.left = left + 'px'; } this.resume(); @@ -230,7 +262,7 @@ export default class Agent { /*** * Play a random animation - * @return {jQuery.Deferred} + * @return {Boolean} */ animate () { let animations = this.animations(); @@ -252,12 +284,12 @@ export default class Agent { * @private */ _getDirection (x, y) { - let offset = this._el.offset(); - let h = this._el.height(); - let w = this._el.width(); + let rect = this._el.getBoundingClientRect(); + let h = this._el.offsetHeight; + let w = this._el.offsetWidth; - let centerX = (offset.left + w / 2); - let centerY = (offset.top + h / 2); + let centerX = (rect.left + w / 2); + let centerY = (rect.top + h / 2); let a = centerY - y; @@ -285,9 +317,22 @@ export default class Agent { _onQueueEmpty () { if (this._hidden || this._isIdleAnimation()) return; let idleAnim = this._getIdleAnimation(); - this._idleDfd = $.Deferred(); + this._idleDfd = this._createDeferred(); - this._animator.showAnimation(idleAnim, $.proxy(this._onIdleComplete, this)); + this._animator.showAnimation(idleAnim, this._onIdleComplete.bind(this)); + } + + _createDeferred() { + let resolve, reject; + const promise = new Promise((res, rej) => { + resolve = res; + reject = rej; + }); + promise.resolve = resolve; + promise.reject = reject; + promise.state = 'pending'; + promise.then(() => { promise.state = 'resolved'; }, () => { promise.state = 'rejected'; }); + return promise; } _onIdleComplete (name, state) { @@ -330,11 +375,11 @@ export default class Agent { /**************************** Events ************************************/ _setupEvents () { - $(window).on('resize', $.proxy(this.reposition, this)); + window.addEventListener('resize', this.reposition.bind(this)); - this._el.on('mousedown', $.proxy(this._onMouseDown, this)); + this._el.addEventListener('mousedown', this._onMouseDown.bind(this)); - this._el.on('dblclick', $.proxy(this._onDoubleClick, this)); + this._el.addEventListener('dblclick', this._onDoubleClick.bind(this)); } _onDoubleClick () { @@ -344,18 +389,16 @@ export default class Agent { } reposition () { - if (!this._el.is(':visible')) return; - let o = this._el.offset(); - let bH = this._el.outerHeight(); - let bW = this._el.outerWidth(); - - let wW = $(window).width(); - let wH = $(window).height(); - let sT = $(window).scrollTop(); - let sL = $(window).scrollLeft(); - - let top = o.top - sT; - let left = o.left - sL; + if (this._el.style.display === 'none') return; + let o = this._el.getBoundingClientRect(); + let bH = this._el.offsetHeight; + let bW = this._el.offsetWidth; + + let wW = window.innerWidth; + let wH = window.innerHeight; + + let top = o.top; + let left = o.left; let m = 5; if (top - m < 0) { top = m; @@ -369,7 +412,8 @@ export default class Agent { left = wW - bW - m; } - this._el.css({ left: left, top: top }); + this._el.style.left = left + 'px'; + this._el.style.top = top + 'px'; // reposition balloon this._balloon.reposition(); } @@ -388,29 +432,30 @@ export default class Agent { this._balloon.hide(true); this._offset = this._calculateClickOffset(e); - this._moveHandle = $.proxy(this._dragMove, this); - this._upHandle = $.proxy(this._finishDrag, this); + this._moveHandle = this._dragMove.bind(this); + this._upHandle = this._finishDrag.bind(this); - $(window).on('mousemove', this._moveHandle); - $(window).on('mouseup', this._upHandle); + window.addEventListener('mousemove', this._moveHandle); + window.addEventListener('mouseup', this._upHandle); - this._dragUpdateLoop = window.setTimeout($.proxy(this._updateLocation, this), 10); + this._dragUpdateLoop = window.setTimeout(this._updateLocation.bind(this), 10); } _calculateClickOffset (e) { let mouseX = e.pageX; let mouseY = e.pageY; - let o = this._el.offset(); + let o = this._el.getBoundingClientRect(); return { - top: mouseY - o.top, - left: mouseX - o.left + top: mouseY - (o.top + window.pageYOffset), + left: mouseX - (o.left + window.pageXOffset) } } _updateLocation () { - this._el.css({ top: this._targetY, left: this._targetX }); - this._dragUpdateLoop = window.setTimeout($.proxy(this._updateLocation, this), 10); + this._el.style.top = this._targetY + 'px'; + this._el.style.left = this._targetX + 'px'; + this._dragUpdateLoop = window.setTimeout(this._updateLocation.bind(this), 10); } _dragMove (e) { @@ -424,8 +469,8 @@ export default class Agent { _finishDrag () { window.clearTimeout(this._dragUpdateLoop); // remove handles - $(window).off('mousemove', this._moveHandle); - $(window).off('mouseup', this._upHandle); + window.removeEventListener('mousemove', this._moveHandle); + window.removeEventListener('mouseup', this._upHandle); // resume animations this._balloon.show(); this.reposition(); @@ -434,7 +479,7 @@ export default class Agent { } _addToQueue (func, scope) { - if (scope) func = $.proxy(func, scope); + if (scope) func = func.bind(scope); this._queue.queue(func); } @@ -450,5 +495,4 @@ export default class Agent { this._animator.resume(); this._balloon.resume(); } - } \ No newline at end of file diff --git a/lib/animator.js b/lib/animator.js index 1149448..e34b157 100755 --- a/lib/animator.js +++ b/lib/animator.js @@ -1,5 +1,3 @@ -import $ from 'jquery' - export default class Animator { constructor (el, path, data, sounds) { @@ -20,8 +18,8 @@ export default class Animator { this._setupElement(this._el); for (let i = 1; i < this._data.overlayCount; i++) { - let inner = this._setupElement($('
')); - curr.append(inner); + let inner = this._setupElement(document.createElement('div')); + curr.appendChild(inner); this._overlays.push(inner); curr = inner; } @@ -29,9 +27,10 @@ export default class Animator { _setupElement (el) { let frameSize = this._data.framesize; - el.css('display', "none"); - el.css({ width: frameSize[0], height: frameSize[1] }); - el.css('background', "url('" + this._path + "/map.png') no-repeat"); + el.style.display = 'none'; + el.style.width = frameSize[0] + 'px'; + el.style.height = frameSize[1] + 'px'; + el.style.background = "url('" + this._path + "/map.png') no-repeat"; return el; } @@ -95,10 +94,11 @@ export default class Animator { if (i < images.length) { let xy = images[i]; let bg = -xy[0] + 'px ' + -xy[1] + 'px'; - this._overlays[i].css({ 'background-position': bg, 'display': 'block' }); + this._overlays[i].style.backgroundPosition = bg; + this._overlays[i].style.display = 'block'; } else { - this._overlays[i].css('display', 'none'); + this._overlays[i].style.display = 'none'; } } @@ -157,7 +157,7 @@ export default class Animator { this._draw(); this._playSound(); - this._loop = window.setTimeout($.proxy(this._step, this), this._currentFrame.duration); + this._loop = window.setTimeout(this._step.bind(this), this._currentFrame.duration); // fire events if the frames changed and we reached an end @@ -187,4 +187,4 @@ export default class Animator { } -Animator.States = { WAITING: 1, EXITED: 0 }; +Animator.States = { WAITING: 1, EXITED: 0 }; \ No newline at end of file diff --git a/lib/balloon.js b/lib/balloon.js index 614e4bb..f52a79b 100755 --- a/lib/balloon.js +++ b/lib/balloon.js @@ -1,5 +1,3 @@ -import $ from 'jquery' - export default class Balloon { constructor (targetEl) { this._targetEl = targetEl; @@ -12,11 +10,20 @@ export default class Balloon { } _setup () { + this._balloon = document.createElement('div'); + this._balloon.className = 'clippy-balloon'; + this._balloon.style.display = 'none'; + + const tip = document.createElement('div'); + tip.className = 'clippy-tip'; - this._balloon = $('
').hide(); - this._content = this._balloon.find('.clippy-content'); + this._content = document.createElement('div'); + this._content.className = 'clippy-content'; - $(document.body).append(this._balloon); + this._balloon.appendChild(tip); + this._balloon.appendChild(this._content); + + document.body.appendChild(this._balloon); } reposition () { @@ -35,19 +42,14 @@ export default class Balloon { * @private */ _position (side) { - let o = this._targetEl.offset(); - let h = this._targetEl.height(); - let w = this._targetEl.width(); - o.top -= $(window).scrollTop(); - o.left -= $(window).scrollLeft(); + let o = this._targetEl.getBoundingClientRect(); + let h = this._targetEl.offsetHeight; + let w = this._targetEl.offsetWidth; - let bH = this._balloon.outerHeight(); - let bW = this._balloon.outerWidth(); + let bH = this._balloon.offsetHeight; + let bW = this._balloon.offsetWidth; - this._balloon.removeClass('clippy-top-left'); - this._balloon.removeClass('clippy-top-right'); - this._balloon.removeClass('clippy-bottom-right'); - this._balloon.removeClass('clippy-bottom-left'); + this._balloon.classList.remove('clippy-top-left', 'clippy-top-right', 'clippy-bottom-right', 'clippy-bottom-left'); let left, top; switch (side) { @@ -73,22 +75,21 @@ export default class Balloon { break; } - this._balloon.css({ top: top, left: left }); - this._balloon.addClass('clippy-' + side); + this._balloon.style.top = top + 'px'; + this._balloon.style.left = left + 'px'; + this._balloon.classList.add('clippy-' + side); } _isOut () { - let o = this._balloon.offset(); - let bH = this._balloon.outerHeight(); - let bW = this._balloon.outerWidth(); + let o = this._balloon.getBoundingClientRect(); + let bH = this._balloon.offsetHeight; + let bW = this._balloon.offsetWidth; - let wW = $(window).width(); - let wH = $(window).height(); - let sT = $(document).scrollTop(); - let sL = $(document).scrollLeft(); + let wW = window.innerWidth; + let wH = window.innerHeight; - let top = o.top - sT; - let left = o.left - sL; + let top = o.top; + let left = o.left; let m = 5; if (top - m < 0 || left - m < 0) return true; return (top + bH + m) > wH || (left + bW + m) > wW; @@ -99,14 +100,14 @@ export default class Balloon { this.show(); let c = this._content; // set height to auto - c.height('auto'); - c.width('auto'); + c.style.height = 'auto'; + c.style.width = 'auto'; // add the text - c.text(text); + c.textContent = text; // set height - c.height(c.height()); - c.width(c.width()); - c.text(''); + c.style.height = c.offsetHeight + 'px'; + c.style.width = c.offsetWidth + 'px'; + c.textContent = ''; this.reposition(); this._complete = complete; @@ -115,21 +116,21 @@ export default class Balloon { show () { if (this._hidden) return; - this._balloon.show(); + this._balloon.style.display = 'block'; } hide (fast) { if (fast) { - this._balloon.hide(); + this._balloon.style.display = 'none'; return; } - this._hiding = window.setTimeout($.proxy(this._finishHideBalloon, this), this.CLOSE_BALLOON_DELAY); + this._hiding = window.setTimeout(this._finishHideBalloon.bind(this), this.CLOSE_BALLOON_DELAY); } _finishHideBalloon () { if (this._active) return; - this._balloon.hide(); + this._balloon.style.display = 'none'; this._hidden = true; this._hiding = null; } @@ -142,8 +143,7 @@ export default class Balloon { let el = this._content; let idx = 1; - - this._addWord = $.proxy(function () { + this._addWord = () => { if (!this._active) return; if (idx > words.length) { delete this._addWord; @@ -153,14 +153,13 @@ export default class Balloon { this.hide(); } } else { - el.text(words.slice(0, idx).join(' ')); + el.textContent = words.slice(0, idx).join(' '); idx++; - this._loop = window.setTimeout($.proxy(this._addWord, this), time); + this._loop = window.setTimeout(this._addWord.bind(this), time); } - }, this); + }; this._addWord(); - } close () { @@ -183,9 +182,7 @@ export default class Balloon { if (this._addWord) { this._addWord(); } else if (!this._hold && !this._hidden) { - this._hiding = window.setTimeout($.proxy(this._finishHideBalloon, this), this.CLOSE_BALLOON_DELAY); + this._hiding = window.setTimeout(this._finishHideBalloon.bind(this), this.CLOSE_BALLOON_DELAY); } } -} - - +} \ No newline at end of file diff --git a/lib/index.js b/lib/index.js index 3d0e8e1..3a9081c 100755 --- a/lib/index.js +++ b/lib/index.js @@ -19,5 +19,3 @@ export default clippy if (typeof window !== 'undefined') { window.clippy = clippy } - - diff --git a/lib/load.js b/lib/load.js index 35a63c8..a3d412a 100755 --- a/lib/load.js +++ b/lib/load.js @@ -1,121 +1,118 @@ -import $ from 'jquery' import Agent from './agent' -export class load { - constructor (name, successCb, failCb, base_path) { - base_path = base_path || window.CLIPPY_CDN || 'https://gitcdn.xyz/repo/pi0/clippyjs/master/assets/agents/' +const _maps = {}; +const _sounds = {}; +const _data = {}; +const _dataCallbacks = {}; +const _soundsCallbacks = {}; - let path = base_path + name; - let mapDfd = load._loadMap(path); - let agentDfd = load._loadAgent(name, path); - let soundsDfd = load._loadSounds(name, path); - - let data; - agentDfd.done(function (d) { - data = d; - }); - - let sounds; - - soundsDfd.done(function (d) { - sounds = d; - }); - - // wrapper to the success callback - let cb = function () { - let a = new Agent(path, data, sounds); - successCb(a); - }; - - $.when(mapDfd, agentDfd, soundsDfd).done(cb).fail(failCb); - } - - static _loadMap (path) { - let dfd = load._maps[path]; - if (dfd) return dfd; - - // set dfd if not defined - dfd = load._maps[path] = $.Deferred(); +function _loadMap(path) { + let dfd = _maps[path]; + if (dfd) return dfd; + // set dfd if not defined + dfd = _maps[path] = new Promise((resolve, reject) => { let src = path + '/map.png'; let img = new Image(); - img.onload = dfd.resolve; - img.onerror = dfd.reject; + img.onload = resolve; + img.onerror = reject; // start loading the map; img.setAttribute('src', src); + }); - return dfd.promise(); - } - - static _loadSounds (name, path) { - let dfd = load._sounds[name]; - if (dfd) return dfd; + return dfd; +} - // set dfd if not defined - dfd = load._sounds[name] = $.Deferred(); +function _loadSounds(name, path) { + let dfd = _sounds[name]; + if (dfd) return dfd; + // set dfd if not defined + dfd = _sounds[name] = new Promise((resolve, reject) => { let audio = document.createElement('audio'); let canPlayMp3 = !!audio.canPlayType && "" !== audio.canPlayType('audio/mpeg'); let canPlayOgg = !!audio.canPlayType && "" !== audio.canPlayType('audio/ogg; codecs="vorbis"'); if (!canPlayMp3 && !canPlayOgg) { - dfd.resolve({}); + resolve({}); } else { let src = path + (canPlayMp3 ? '/sounds-mp3.js' : '/sounds-ogg.js'); + // Store resolve/reject for later use + _soundsCallbacks[name] = { resolve, reject }; // load - load._loadScript(src); + _loadScript(src); } + }); - return dfd.promise() - } + return dfd; +} - static _loadAgent (name, path) { - let dfd = load._data[name]; - if (dfd) return dfd; +function _loadAgent(name, path) { + let dfd = _data[name]; + if (dfd) return dfd; - dfd = load._getAgentDfd(name); + // Create the promise and store it + dfd = _data[name] = new Promise((resolve, reject) => { + // Store resolve/reject for external access via ready() + _dataCallbacks[name] = { resolve, reject }; + }); - let src = path + '/agent.js'; + let src = path + '/agent.js'; - load._loadScript(src); + _loadScript(src); - return dfd.promise(); - } - - static _loadScript (src) { - let script = document.createElement('script'); - script.setAttribute('src', src); - script.setAttribute('async', 'async'); - script.setAttribute('type', 'text/javascript'); + return dfd; +} - document.head.appendChild(script); - } +function _loadScript(src) { + let script = document.createElement('script'); + script.setAttribute('src', src); + script.setAttribute('async', 'async'); + script.setAttribute('type', 'text/javascript'); - static _getAgentDfd (name) { - let dfd = load._data[name]; - if (!dfd) { - dfd = load._data[name] = $.Deferred(); - } - return dfd; - } + document.head.appendChild(script); } -load._maps = {}; -load._sounds = {}; -load._data = {}; +export function load(name, successCb, failCb, base_path) { + base_path = base_path || window.CLIPPY_CDN || './assets/agents/' + + let path = base_path + name; + let mapDfd = _loadMap(path); + let agentDfd = _loadAgent(name, path); + let soundsDfd = _loadSounds(name, path); + + let data; + agentDfd.then(function (d) { + data = d; + }); -export function ready (name, data) { - let dfd = load._getAgentDfd(name); - dfd.resolve(data); + let sounds; + + soundsDfd.then(function (d) { + sounds = d; + }); + + // wrapper to the success callback + let cb = function () { + let a = new Agent(path, data, sounds); + successCb(a); + }; + + Promise.all([mapDfd, agentDfd, soundsDfd]).then(cb).catch(failCb); } -export function soundsReady (name, data) { - let dfd = load._sounds[name]; - if (!dfd) { - dfd = load._sounds[name] = $.Deferred(); +export function ready(name, data) { + let callbacks = _dataCallbacks[name]; + if (callbacks && callbacks.resolve) { + callbacks.resolve(data); } - - dfd.resolve(data); } + +export function soundsReady(name, data) { + let callbacks = _soundsCallbacks[name]; + if (callbacks && callbacks.resolve) { + callbacks.resolve(data); + } +} \ No newline at end of file diff --git a/lib/queue.js b/lib/queue.js index f557eea..f099364 100755 --- a/lib/queue.js +++ b/lib/queue.js @@ -1,5 +1,3 @@ -import $ from 'jquery' - export default class Queue { constructor (onEmptyCallback) { this._queue = []; @@ -9,7 +7,7 @@ export default class Queue { /*** * * @param {function(Function)} func - * @returns {jQuery.Deferred} + * @returns {Promise} */ queue (func) { this._queue.push(func); @@ -31,7 +29,7 @@ export default class Queue { this._active = true; // execute function - let completeFunction = $.proxy(this.next, this); + let completeFunction = this.next.bind(this); f(completeFunction); } @@ -43,7 +41,4 @@ export default class Queue { this._active = false; this._progressQueue(); } -} - - - +} \ No newline at end of file diff --git a/package-lock.json b/package-lock.json new file mode 100644 index 0000000..6edbbd5 --- /dev/null +++ b/package-lock.json @@ -0,0 +1,577 @@ +{ + "name": "clippyjs", + "version": "0.0.3", + "lockfileVersion": 3, + "requires": true, + "packages": { + "": { + "name": "clippyjs", + "version": "0.0.3", + "license": "MIT", + "devDependencies": { + "@rollup/plugin-terser": "^0.4.4", + "rollup": "^4.28.1" + } + }, + "node_modules/@jridgewell/gen-mapping": { + "version": "0.3.13", + "resolved": "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.13.tgz", + "integrity": "sha512-2kkt/7niJ6MgEPxF0bYdQ6etZaA+fQvDcLKckhy1yIQOzaoKjBBjSj63/aLVjYE3qhRt5dvM+uUyfCg6UKCBbA==", + "dev": true, + "license": "MIT", + "dependencies": { + "@jridgewell/sourcemap-codec": "^1.5.0", + "@jridgewell/trace-mapping": "^0.3.24" + } + }, + "node_modules/@jridgewell/resolve-uri": { + "version": "3.1.2", + "resolved": "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.2.tgz", + "integrity": "sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw==", + "dev": true, + "license": "MIT", + "engines": { + "node": ">=6.0.0" + } + }, + "node_modules/@jridgewell/source-map": { + "version": "0.3.11", + "resolved": "https://registry.npmjs.org/@jridgewell/source-map/-/source-map-0.3.11.tgz", + "integrity": "sha512-ZMp1V8ZFcPG5dIWnQLr3NSI1MiCU7UETdS/A0G8V/XWHvJv3ZsFqutJn1Y5RPmAPX6F3BiE397OqveU/9NCuIA==", + "dev": true, + "license": "MIT", + "dependencies": { + "@jridgewell/gen-mapping": "^0.3.5", + "@jridgewell/trace-mapping": "^0.3.25" + } + }, + "node_modules/@jridgewell/sourcemap-codec": { + "version": "1.5.5", + "resolved": "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.5.5.tgz", + "integrity": "sha512-cYQ9310grqxueWbl+WuIUIaiUaDcj7WOq5fVhEljNVgRfOUhY9fy2zTvfoqWsnebh8Sl70VScFbICvJnLKB0Og==", + "dev": true, + "license": "MIT" + }, + "node_modules/@jridgewell/trace-mapping": { + "version": "0.3.31", + "resolved": "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.31.tgz", + "integrity": "sha512-zzNR+SdQSDJzc8joaeP8QQoCQr8NuYx2dIIytl1QeBEZHJ9uW6hebsrYgbz8hJwUQao3TWCMtmfV8Nu1twOLAw==", + "dev": true, + "license": "MIT", + "dependencies": { + "@jridgewell/resolve-uri": "^3.1.0", + "@jridgewell/sourcemap-codec": "^1.4.14" + } + }, + "node_modules/@rollup/plugin-terser": { + "version": "0.4.4", + "resolved": "https://registry.npmjs.org/@rollup/plugin-terser/-/plugin-terser-0.4.4.tgz", + "integrity": "sha512-XHeJC5Bgvs8LfukDwWZp7yeqin6ns8RTl2B9avbejt6tZqsqvVoWI7ZTQrcNsfKEDWBTnTxM8nMDkO2IFFbd0A==", + "dev": true, + "license": "MIT", + "dependencies": { + "serialize-javascript": "^6.0.1", + "smob": "^1.0.0", + "terser": "^5.17.4" + }, + "engines": { + "node": ">=14.0.0" + }, + "peerDependencies": { + "rollup": "^2.0.0||^3.0.0||^4.0.0" + }, + "peerDependenciesMeta": { + "rollup": { + "optional": true + } + } + }, + "node_modules/@rollup/rollup-android-arm-eabi": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm-eabi/-/rollup-android-arm-eabi-4.52.4.tgz", + "integrity": "sha512-BTm2qKNnWIQ5auf4deoetINJm2JzvihvGb9R6K/ETwKLql/Bb3Eg2H1FBp1gUb4YGbydMA3jcmQTR73q7J+GAA==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ] + }, + "node_modules/@rollup/rollup-android-arm64": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-android-arm64/-/rollup-android-arm64-4.52.4.tgz", + "integrity": "sha512-P9LDQiC5vpgGFgz7GSM6dKPCiqR3XYN1WwJKA4/BUVDjHpYsf3iBEmVz62uyq20NGYbiGPR5cNHI7T1HqxNs2w==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "android" + ] + }, + "node_modules/@rollup/rollup-darwin-arm64": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-arm64/-/rollup-darwin-arm64-4.52.4.tgz", + "integrity": "sha512-QRWSW+bVccAvZF6cbNZBJwAehmvG9NwfWHwMy4GbWi/BQIA/laTIktebT2ipVjNncqE6GLPxOok5hsECgAxGZg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ] + }, + "node_modules/@rollup/rollup-darwin-x64": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-darwin-x64/-/rollup-darwin-x64-4.52.4.tgz", + "integrity": "sha512-hZgP05pResAkRJxL1b+7yxCnXPGsXU0fG9Yfd6dUaoGk+FhdPKCJ5L1Sumyxn8kvw8Qi5PvQ8ulenUbRjzeCTw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ] + }, + "node_modules/@rollup/rollup-freebsd-arm64": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-arm64/-/rollup-freebsd-arm64-4.52.4.tgz", + "integrity": "sha512-xmc30VshuBNUd58Xk4TKAEcRZHaXlV+tCxIXELiE9sQuK3kG8ZFgSPi57UBJt8/ogfhAF5Oz4ZSUBN77weM+mQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ] + }, + "node_modules/@rollup/rollup-freebsd-x64": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-freebsd-x64/-/rollup-freebsd-x64-4.52.4.tgz", + "integrity": "sha512-WdSLpZFjOEqNZGmHflxyifolwAiZmDQzuOzIq9L27ButpCVpD7KzTRtEG1I0wMPFyiyUdOO+4t8GvrnBLQSwpw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "freebsd" + ] + }, + "node_modules/@rollup/rollup-linux-arm-gnueabihf": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-gnueabihf/-/rollup-linux-arm-gnueabihf-4.52.4.tgz", + "integrity": "sha512-xRiOu9Of1FZ4SxVbB0iEDXc4ddIcjCv2aj03dmW8UrZIW7aIQ9jVJdLBIhxBI+MaTnGAKyvMwPwQnoOEvP7FgQ==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm-musleabihf": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm-musleabihf/-/rollup-linux-arm-musleabihf-4.52.4.tgz", + "integrity": "sha512-FbhM2p9TJAmEIEhIgzR4soUcsW49e9veAQCziwbR+XWB2zqJ12b4i/+hel9yLiD8pLncDH4fKIPIbt5238341Q==", + "cpu": [ + "arm" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm64-gnu": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-gnu/-/rollup-linux-arm64-gnu-4.52.4.tgz", + "integrity": "sha512-4n4gVwhPHR9q/g8lKCyz0yuaD0MvDf7dV4f9tHt0C73Mp8h38UCtSCSE6R9iBlTbXlmA8CjpsZoujhszefqueg==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-arm64-musl": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-arm64-musl/-/rollup-linux-arm64-musl-4.52.4.tgz", + "integrity": "sha512-u0n17nGA0nvi/11gcZKsjkLj1QIpAuPFQbR48Subo7SmZJnGxDpspyw2kbpuoQnyK+9pwf3pAoEXerJs/8Mi9g==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-loong64-gnu": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-loong64-gnu/-/rollup-linux-loong64-gnu-4.52.4.tgz", + "integrity": "sha512-0G2c2lpYtbTuXo8KEJkDkClE/+/2AFPdPAbmaHoE870foRFs4pBrDehilMcrSScrN/fB/1HTaWO4bqw+ewBzMQ==", + "cpu": [ + "loong64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-ppc64-gnu": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-ppc64-gnu/-/rollup-linux-ppc64-gnu-4.52.4.tgz", + "integrity": "sha512-teSACug1GyZHmPDv14VNbvZFX779UqWTsd7KtTM9JIZRDI5NUwYSIS30kzI8m06gOPB//jtpqlhmraQ68b5X2g==", + "cpu": [ + "ppc64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-riscv64-gnu": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-gnu/-/rollup-linux-riscv64-gnu-4.52.4.tgz", + "integrity": "sha512-/MOEW3aHjjs1p4Pw1Xk4+3egRevx8Ji9N6HUIA1Ifh8Q+cg9dremvFCUbOX2Zebz80BwJIgCBUemjqhU5XI5Eg==", + "cpu": [ + "riscv64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-riscv64-musl": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-riscv64-musl/-/rollup-linux-riscv64-musl-4.52.4.tgz", + "integrity": "sha512-1HHmsRyh845QDpEWzOFtMCph5Ts+9+yllCrREuBR/vg2RogAQGGBRC8lDPrPOMnrdOJ+mt1WLMOC2Kao/UwcvA==", + "cpu": [ + "riscv64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-s390x-gnu": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-s390x-gnu/-/rollup-linux-s390x-gnu-4.52.4.tgz", + "integrity": "sha512-seoeZp4L/6D1MUyjWkOMRU6/iLmCU2EjbMTyAG4oIOs1/I82Y5lTeaxW0KBfkUdHAWN7j25bpkt0rjnOgAcQcA==", + "cpu": [ + "s390x" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-x64-gnu": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.52.4.tgz", + "integrity": "sha512-Wi6AXf0k0L7E2gteNsNHUs7UMwCIhsCTs6+tqQ5GPwVRWMaflqGec4Sd8n6+FNFDw9vGcReqk2KzBDhCa1DLYg==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-linux-x64-musl": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.52.4.tgz", + "integrity": "sha512-dtBZYjDmCQ9hW+WgEkaffvRRCKm767wWhxsFW3Lw86VXz/uJRuD438/XvbZT//B96Vs8oTA8Q4A0AfHbrxP9zw==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "linux" + ] + }, + "node_modules/@rollup/rollup-openharmony-arm64": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-openharmony-arm64/-/rollup-openharmony-arm64-4.52.4.tgz", + "integrity": "sha512-1ox+GqgRWqaB1RnyZXL8PD6E5f7YyRUJYnCqKpNzxzP0TkaUh112NDrR9Tt+C8rJ4x5G9Mk8PQR3o7Ku2RKqKA==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "openharmony" + ] + }, + "node_modules/@rollup/rollup-win32-arm64-msvc": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-arm64-msvc/-/rollup-win32-arm64-msvc-4.52.4.tgz", + "integrity": "sha512-8GKr640PdFNXwzIE0IrkMWUNUomILLkfeHjXBi/nUvFlpZP+FA8BKGKpacjW6OUUHaNI6sUURxR2U2g78FOHWQ==", + "cpu": [ + "arm64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@rollup/rollup-win32-ia32-msvc": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-ia32-msvc/-/rollup-win32-ia32-msvc-4.52.4.tgz", + "integrity": "sha512-AIy/jdJ7WtJ/F6EcfOb2GjR9UweO0n43jNObQMb6oGxkYTfLcnN7vYYpG+CN3lLxrQkzWnMOoNSHTW54pgbVxw==", + "cpu": [ + "ia32" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@rollup/rollup-win32-x64-gnu": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-gnu/-/rollup-win32-x64-gnu-4.52.4.tgz", + "integrity": "sha512-UF9KfsH9yEam0UjTwAgdK0anlQ7c8/pWPU2yVjyWcF1I1thABt6WXE47cI71pGiZ8wGvxohBoLnxM04L/wj8mQ==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@rollup/rollup-win32-x64-msvc": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/@rollup/rollup-win32-x64-msvc/-/rollup-win32-x64-msvc-4.52.4.tgz", + "integrity": "sha512-bf9PtUa0u8IXDVxzRToFQKsNCRz9qLYfR/MpECxl4mRoWYjAeFjgxj1XdZr2M/GNVpT05p+LgQOHopYDlUu6/w==", + "cpu": [ + "x64" + ], + "dev": true, + "license": "MIT", + "optional": true, + "os": [ + "win32" + ] + }, + "node_modules/@types/estree": { + "version": "1.0.8", + "resolved": "https://registry.npmjs.org/@types/estree/-/estree-1.0.8.tgz", + "integrity": "sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w==", + "dev": true, + "license": "MIT" + }, + "node_modules/buffer-from": { + "version": "1.1.2", + "resolved": "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz", + "integrity": "sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ==", + "dev": true, + "license": "MIT" + }, + "node_modules/randombytes": { + "version": "2.1.0", + "resolved": "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz", + "integrity": "sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "safe-buffer": "^5.1.0" + } + }, + "node_modules/randombytes/node_modules/safe-buffer": { + "version": "5.2.1", + "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz", + "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", + "dev": true, + "funding": [ + { + "type": "github", + "url": "https://github.com/sponsors/feross" + }, + { + "type": "patreon", + "url": "https://www.patreon.com/feross" + }, + { + "type": "consulting", + "url": "https://feross.org/support" + } + ], + "license": "MIT" + }, + "node_modules/rollup": { + "version": "4.52.4", + "resolved": "https://registry.npmjs.org/rollup/-/rollup-4.52.4.tgz", + "integrity": "sha512-CLEVl+MnPAiKh5pl4dEWSyMTpuflgNQiLGhMv8ezD5W/qP8AKvmYpCOKRRNOh7oRKnauBZ4SyeYkMS+1VSyKwQ==", + "dev": true, + "license": "MIT", + "dependencies": { + "@types/estree": "1.0.8" + }, + "bin": { + "rollup": "dist/bin/rollup" + }, + "engines": { + "node": ">=18.0.0", + "npm": ">=8.0.0" + }, + "optionalDependencies": { + "@rollup/rollup-android-arm-eabi": "4.52.4", + "@rollup/rollup-android-arm64": "4.52.4", + "@rollup/rollup-darwin-arm64": "4.52.4", + "@rollup/rollup-darwin-x64": "4.52.4", + "@rollup/rollup-freebsd-arm64": "4.52.4", + "@rollup/rollup-freebsd-x64": "4.52.4", + "@rollup/rollup-linux-arm-gnueabihf": "4.52.4", + "@rollup/rollup-linux-arm-musleabihf": "4.52.4", + "@rollup/rollup-linux-arm64-gnu": "4.52.4", + "@rollup/rollup-linux-arm64-musl": "4.52.4", + "@rollup/rollup-linux-loong64-gnu": "4.52.4", + "@rollup/rollup-linux-ppc64-gnu": "4.52.4", + "@rollup/rollup-linux-riscv64-gnu": "4.52.4", + "@rollup/rollup-linux-riscv64-musl": "4.52.4", + "@rollup/rollup-linux-s390x-gnu": "4.52.4", + "@rollup/rollup-linux-x64-gnu": "4.52.4", + "@rollup/rollup-linux-x64-musl": "4.52.4", + "@rollup/rollup-openharmony-arm64": "4.52.4", + "@rollup/rollup-win32-arm64-msvc": "4.52.4", + "@rollup/rollup-win32-ia32-msvc": "4.52.4", + "@rollup/rollup-win32-x64-gnu": "4.52.4", + "@rollup/rollup-win32-x64-msvc": "4.52.4", + "fsevents": "~2.3.2" + } + }, + "node_modules/rollup/node_modules/fsevents": { + "version": "2.3.3", + "resolved": "https://registry.npmjs.org/fsevents/-/fsevents-2.3.3.tgz", + "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", + "dev": true, + "hasInstallScript": true, + "license": "MIT", + "optional": true, + "os": [ + "darwin" + ], + "engines": { + "node": "^8.16.0 || ^10.6.0 || >=11.0.0" + } + }, + "node_modules/serialize-javascript": { + "version": "6.0.2", + "resolved": "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-6.0.2.tgz", + "integrity": "sha512-Saa1xPByTTq2gdeFZYLLo+RFE35NHZkAbqZeWNd3BpzppeVisAqpDjcp8dyf6uIvEqJRd46jemmyA4iFIeVk8g==", + "dev": true, + "license": "BSD-3-Clause", + "dependencies": { + "randombytes": "^2.1.0" + } + }, + "node_modules/smob": { + "version": "1.5.0", + "resolved": "https://registry.npmjs.org/smob/-/smob-1.5.0.tgz", + "integrity": "sha512-g6T+p7QO8npa+/hNx9ohv1E5pVCmWrVCUzUXJyLdMmftX6ER0oiWY/w9knEonLpnOp6b6FenKnMfR8gqwWdwig==", + "dev": true, + "license": "MIT" + }, + "node_modules/source-map-support": { + "version": "0.5.21", + "resolved": "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.21.tgz", + "integrity": "sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w==", + "dev": true, + "license": "MIT", + "dependencies": { + "buffer-from": "^1.0.0", + "source-map": "^0.6.0" + } + }, + "node_modules/source-map-support/node_modules/source-map": { + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", + "dev": true, + "license": "BSD-3-Clause", + "engines": { + "node": ">=0.10.0" + } + }, + "node_modules/terser": { + "version": "5.44.0", + "resolved": "https://registry.npmjs.org/terser/-/terser-5.44.0.tgz", + "integrity": "sha512-nIVck8DK+GM/0Frwd+nIhZ84pR/BX7rmXMfYwyg+Sri5oGVE99/E3KvXqpC2xHFxyqXyGHTKBSioxxplrO4I4w==", + "dev": true, + "license": "BSD-2-Clause", + "dependencies": { + "@jridgewell/source-map": "^0.3.3", + "acorn": "^8.15.0", + "commander": "^2.20.0", + "source-map-support": "~0.5.20" + }, + "bin": { + "terser": "bin/terser" + }, + "engines": { + "node": ">=10" + } + }, + "node_modules/terser/node_modules/acorn": { + "version": "8.15.0", + "resolved": "https://registry.npmjs.org/acorn/-/acorn-8.15.0.tgz", + "integrity": "sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg==", + "dev": true, + "license": "MIT", + "bin": { + "acorn": "bin/acorn" + }, + "engines": { + "node": ">=0.4.0" + } + }, + "node_modules/terser/node_modules/commander": { + "version": "2.20.3", + "resolved": "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz", + "integrity": "sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ==", + "dev": true, + "license": "MIT" + } + } +} diff --git a/package.json b/package.json index 629fdd7..49435d5 100755 --- a/package.json +++ b/package.json @@ -3,9 +3,7 @@ "version": "0.0.3", "description": "Add Clippy or his friends to any website for instant nostalgia.", "main": "dist/clippy.js", - "web": "dist/clippy.js", "module": "dist/clippy.esm.js", - "jsnext:main": "dist/clippy.esm.js", "scripts": { "build": "rollup -c", "watch": "rollup -c -w", @@ -20,16 +18,9 @@ "url": "https://github.com/pi0/clippyjs/issues" }, "homepage": "https://github.com/pi0/clippyjs#readme", - "dependencies": { - "jquery": "^3.2.1" - }, + "dependencies": {}, "devDependencies": { - "rollup": "^0.42.0", - "rollup-plugin-buble": "^0.15.0", - "rollup-plugin-commonjs": "^8.0.2", - "rollup-plugin-node-resolve": "^3.0.0", - "rollup-plugin-uglify": "^2.0.1", - "rollup-watch": "^4.0.0", - "uglify-js-harmony": "^2.7.7" + "@rollup/plugin-terser": "^0.4.4", + "rollup": "^4.28.1" } -} +} \ No newline at end of file diff --git a/rollup.config.js b/rollup.config.js index f28f821..6e5084e 100755 --- a/rollup.config.js +++ b/rollup.config.js @@ -1,44 +1,36 @@ -const fs = require('fs'); -const path = require('path'); -const buble = require('rollup-plugin-buble'); -const resolve = require('rollup-plugin-node-resolve'); -const commonjs = require('rollup-plugin-commonjs'); -const uglify = require('rollup-plugin-uglify'); -// const { minify } = require('uglify-js-harmony'); -const { dependencies } = require('./package.json'); +import terser from '@rollup/plugin-terser'; -const name = 'clippy' -const dist = path.resolve(__dirname, 'dist'); +const name = 'clippy'; -// Ensure dist directory exists -if (!fs.existsSync(dist)) { - fs.mkdirSync(dist); -} - -module.exports = { - entry: path.resolve(__dirname, 'lib/index.js'), - external: Object.keys(dependencies), - moduleName: name, - plugins: [ - buble(), - resolve({ external: ['vue'] }), - commonjs(), - // uglify({}, minify) - ], - globals: { - jquery: '$' +export default [ + // UMD build + { + input: 'lib/index.js', + output: { + file: 'dist/clippy.js', + format: 'umd', + name: name, + sourcemap: true + } + }, + // UMD build (minified) + { + input: 'lib/index.js', + output: { + file: 'dist/clippy.min.js', + format: 'umd', + name: name, + sourcemap: true }, - targets: [ - { - format: 'umd', - moduleName: name, - dest: path.resolve(dist, name + '.js'), - sourceMap: true - }, - { - format: 'es', - dest: path.resolve(dist, name + '.esm.js'), - sourceMap: true - } - ] -}; + plugins: [terser()] + }, + // ES Module build + { + input: 'lib/index.js', + output: { + file: 'dist/clippy.esm.js', + format: 'es', + sourcemap: true + } + } +]; \ No newline at end of file diff --git a/yarn.lock b/yarn.lock index 52c1641..bc64fc9 100755 --- a/yarn.lock +++ b/yarn.lock @@ -2,1184 +2,148 @@ # yarn lockfile v1 -abbrev@1: - version "1.1.0" - resolved "https://registry.yarnpkg.com/abbrev/-/abbrev-1.1.0.tgz#d0554c2256636e2f56e7c2e5ad183f859428d81f" - -acorn-jsx@^3.0.1: - version "3.0.1" - resolved "https://registry.yarnpkg.com/acorn-jsx/-/acorn-jsx-3.0.1.tgz#afdf9488fb1ecefc8348f6fb22f464e32a58b36b" - dependencies: - acorn "^3.0.4" - -acorn-object-spread@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/acorn-object-spread/-/acorn-object-spread-1.0.0.tgz#48ead0f4a8eb16995a17a0db9ffc6acaada4ba68" - dependencies: - acorn "^3.1.0" - -acorn@^3.0.4, acorn@^3.1.0, acorn@^3.3.0: - version "3.3.0" - resolved "https://registry.yarnpkg.com/acorn/-/acorn-3.3.0.tgz#45e37fb39e8da3f25baee3ff5369e2bb5f22017a" - -acorn@^4.0.1: - version "4.0.13" - resolved "https://registry.yarnpkg.com/acorn/-/acorn-4.0.13.tgz#105495ae5361d697bd195c825192e1ad7f253787" - -ajv@^4.9.1: - version "4.11.8" - resolved "https://registry.yarnpkg.com/ajv/-/ajv-4.11.8.tgz#82ffb02b29e662ae53bdc20af15947706739c536" - dependencies: - co "^4.6.0" - json-stable-stringify "^1.0.1" - -align-text@^0.1.1, align-text@^0.1.3: - version "0.1.4" - resolved "https://registry.yarnpkg.com/align-text/-/align-text-0.1.4.tgz#0cd90a561093f35d0a99256c22b7069433fad117" - dependencies: - kind-of "^3.0.2" - longest "^1.0.1" - repeat-string "^1.5.2" - -ansi-regex@^2.0.0: - version "2.1.1" - resolved "https://registry.yarnpkg.com/ansi-regex/-/ansi-regex-2.1.1.tgz#c3b33ab5ee360d86e0e628f0468ae7ef27d654df" - -ansi-styles@^2.2.1: - version "2.2.1" - resolved "https://registry.yarnpkg.com/ansi-styles/-/ansi-styles-2.2.1.tgz#b432dd3358b634cf75e1e4664368240533c1ddbe" - -anymatch@^1.3.0: - version "1.3.0" - resolved "https://registry.yarnpkg.com/anymatch/-/anymatch-1.3.0.tgz#a3e52fa39168c825ff57b0248126ce5a8ff95507" - dependencies: - arrify "^1.0.0" - micromatch "^2.1.5" - -aproba@^1.0.3: +"@jridgewell/gen-mapping@^0.3.5": + version "0.3.13" + resolved "https://registry.npmjs.org/@jridgewell/gen-mapping/-/gen-mapping-0.3.13.tgz" + integrity sha512-2kkt/7niJ6MgEPxF0bYdQ6etZaA+fQvDcLKckhy1yIQOzaoKjBBjSj63/aLVjYE3qhRt5dvM+uUyfCg6UKCBbA== + dependencies: + "@jridgewell/sourcemap-codec" "^1.5.0" + "@jridgewell/trace-mapping" "^0.3.24" + +"@jridgewell/resolve-uri@^3.1.0": + version "3.1.2" + resolved "https://registry.npmjs.org/@jridgewell/resolve-uri/-/resolve-uri-3.1.2.tgz" + integrity sha512-bRISgCIjP20/tbWSPWMEi54QVPRZExkuD9lJL+UIxUKtwVJA8wW1Trb1jMs1RFXo1CBTNZ/5hpC9QvmKWdopKw== + +"@jridgewell/source-map@^0.3.3": + version "0.3.11" + resolved "https://registry.npmjs.org/@jridgewell/source-map/-/source-map-0.3.11.tgz" + integrity sha512-ZMp1V8ZFcPG5dIWnQLr3NSI1MiCU7UETdS/A0G8V/XWHvJv3ZsFqutJn1Y5RPmAPX6F3BiE397OqveU/9NCuIA== + dependencies: + "@jridgewell/gen-mapping" "^0.3.5" + "@jridgewell/trace-mapping" "^0.3.25" + +"@jridgewell/sourcemap-codec@^1.4.14", "@jridgewell/sourcemap-codec@^1.5.0": + version "1.5.5" + resolved "https://registry.npmjs.org/@jridgewell/sourcemap-codec/-/sourcemap-codec-1.5.5.tgz" + integrity sha512-cYQ9310grqxueWbl+WuIUIaiUaDcj7WOq5fVhEljNVgRfOUhY9fy2zTvfoqWsnebh8Sl70VScFbICvJnLKB0Og== + +"@jridgewell/trace-mapping@^0.3.24", "@jridgewell/trace-mapping@^0.3.25": + version "0.3.31" + resolved "https://registry.npmjs.org/@jridgewell/trace-mapping/-/trace-mapping-0.3.31.tgz" + integrity sha512-zzNR+SdQSDJzc8joaeP8QQoCQr8NuYx2dIIytl1QeBEZHJ9uW6hebsrYgbz8hJwUQao3TWCMtmfV8Nu1twOLAw== + dependencies: + "@jridgewell/resolve-uri" "^3.1.0" + "@jridgewell/sourcemap-codec" "^1.4.14" + +"@rollup/plugin-terser@^0.4.4": + version "0.4.4" + resolved "https://registry.npmjs.org/@rollup/plugin-terser/-/plugin-terser-0.4.4.tgz" + integrity sha512-XHeJC5Bgvs8LfukDwWZp7yeqin6ns8RTl2B9avbejt6tZqsqvVoWI7ZTQrcNsfKEDWBTnTxM8nMDkO2IFFbd0A== + dependencies: + serialize-javascript "^6.0.1" + smob "^1.0.0" + terser "^5.17.4" + +"@rollup/rollup-linux-x64-gnu@4.52.4": + version "4.52.4" + resolved "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.52.4.tgz" + integrity sha512-Wi6AXf0k0L7E2gteNsNHUs7UMwCIhsCTs6+tqQ5GPwVRWMaflqGec4Sd8n6+FNFDw9vGcReqk2KzBDhCa1DLYg== + +"@types/estree@1.0.8": + version "1.0.8" + resolved "https://registry.npmjs.org/@types/estree/-/estree-1.0.8.tgz" + integrity sha512-dWHzHa2WqEXI/O1E9OjrocMTKJl2mSrEolh1Iomrv6U+JuNwaHXsXx9bLu5gG7BUWFIN0skIQJQ/L1rIex4X6w== + +acorn@^8.15.0: + version "8.15.0" + resolved "https://registry.npmjs.org/acorn/-/acorn-8.15.0.tgz" + integrity sha512-NZyJarBfL7nWwIq+FDL6Zp/yHEhePMNnnJ0y3qfieCrmNvYct8uvtiV41UvlSe6apAfk0fY1FbWx+NwfmpvtTg== + +buffer-from@^1.0.0: version "1.1.2" - resolved "https://registry.yarnpkg.com/aproba/-/aproba-1.1.2.tgz#45c6629094de4e96f693ef7eab74ae079c240fc1" - -are-we-there-yet@~1.1.2: - version "1.1.4" - resolved "https://registry.yarnpkg.com/are-we-there-yet/-/are-we-there-yet-1.1.4.tgz#bb5dca382bb94f05e15194373d16fd3ba1ca110d" - dependencies: - delegates "^1.0.0" - readable-stream "^2.0.6" - -arr-diff@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/arr-diff/-/arr-diff-2.0.0.tgz#8f3b827f955a8bd669697e4a4256ac3ceae356cf" - dependencies: - arr-flatten "^1.0.1" - -arr-flatten@^1.0.1: - version "1.0.3" - resolved "https://registry.yarnpkg.com/arr-flatten/-/arr-flatten-1.0.3.tgz#a274ed85ac08849b6bd7847c4580745dc51adfb1" - -array-unique@^0.2.1: - version "0.2.1" - resolved "https://registry.yarnpkg.com/array-unique/-/array-unique-0.2.1.tgz#a1d97ccafcbc2625cc70fadceb36a50c58b01a53" - -arrify@^1.0.0: - version "1.0.1" - resolved "https://registry.yarnpkg.com/arrify/-/arrify-1.0.1.tgz#898508da2226f380df904728456849c1501a4b0d" - -asn1@~0.2.3: - version "0.2.3" - resolved "https://registry.yarnpkg.com/asn1/-/asn1-0.2.3.tgz#dac8787713c9966849fc8180777ebe9c1ddf3b86" - -assert-plus@1.0.0, assert-plus@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/assert-plus/-/assert-plus-1.0.0.tgz#f12e0f3c5d77b0b1cdd9146942e4e96c1e4dd525" - -assert-plus@^0.2.0: - version "0.2.0" - resolved "https://registry.yarnpkg.com/assert-plus/-/assert-plus-0.2.0.tgz#d74e1b87e7affc0db8aadb7021f3fe48101ab234" - -async-each@^1.0.0: - version "1.0.1" - resolved "https://registry.yarnpkg.com/async-each/-/async-each-1.0.1.tgz#19d386a1d9edc6e7c1c85d388aedbcc56d33602d" - -async@~0.2.6: - version "0.2.10" - resolved "https://registry.yarnpkg.com/async/-/async-0.2.10.tgz#b6bbe0b0674b9d719708ca38de8c237cb526c3d1" - -asynckit@^0.4.0: - version "0.4.0" - resolved "https://registry.yarnpkg.com/asynckit/-/asynckit-0.4.0.tgz#c79ed97f7f34cb8f2ba1bc9790bcc366474b4b79" - -aws-sign2@~0.6.0: - version "0.6.0" - resolved "https://registry.yarnpkg.com/aws-sign2/-/aws-sign2-0.6.0.tgz#14342dd38dbcc94d0e5b87d763cd63612c0e794f" - -aws4@^1.2.1: - version "1.6.0" - resolved "https://registry.yarnpkg.com/aws4/-/aws4-1.6.0.tgz#83ef5ca860b2b32e4a0deedee8c771b9db57471e" - -balanced-match@^0.4.1: - version "0.4.2" - resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-0.4.2.tgz#cb3f3e3c732dc0f01ee70b403f302e61d7709838" - -bcrypt-pbkdf@^1.0.0: - version "1.0.1" - resolved "https://registry.yarnpkg.com/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.1.tgz#63bc5dcb61331b92bc05fd528953c33462a06f8d" - dependencies: - tweetnacl "^0.14.3" - -binary-extensions@^1.0.0: - version "1.8.0" - resolved "https://registry.yarnpkg.com/binary-extensions/-/binary-extensions-1.8.0.tgz#48ec8d16df4377eae5fa5884682480af4d95c774" - -block-stream@*: - version "0.0.9" - resolved "https://registry.yarnpkg.com/block-stream/-/block-stream-0.0.9.tgz#13ebfe778a03205cfe03751481ebb4b3300c126a" - dependencies: - inherits "~2.0.0" - -boom@2.x.x: - version "2.10.1" - resolved "https://registry.yarnpkg.com/boom/-/boom-2.10.1.tgz#39c8918ceff5799f83f9492a848f625add0c766f" - dependencies: - hoek "2.x.x" - -brace-expansion@^1.1.7: - version "1.1.7" - resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-1.1.7.tgz#3effc3c50e000531fb720eaff80f0ae8ef23cf59" - dependencies: - balanced-match "^0.4.1" - concat-map "0.0.1" - -braces@^1.8.2: - version "1.8.5" - resolved "https://registry.yarnpkg.com/braces/-/braces-1.8.5.tgz#ba77962e12dff969d6b76711e914b737857bf6a7" - dependencies: - expand-range "^1.8.1" - preserve "^0.2.0" - repeat-element "^1.1.2" - -browser-resolve@^1.11.0: - version "1.11.2" - resolved "https://registry.yarnpkg.com/browser-resolve/-/browser-resolve-1.11.2.tgz#8ff09b0a2c421718a1051c260b32e48f442938ce" - dependencies: - resolve "1.1.7" - -buble@^0.15.0: - version "0.15.2" - resolved "https://registry.yarnpkg.com/buble/-/buble-0.15.2.tgz#547fc47483f8e5e8176d82aa5ebccb183b02d613" - dependencies: - acorn "^3.3.0" - acorn-jsx "^3.0.1" - acorn-object-spread "^1.0.0" - chalk "^1.1.3" - magic-string "^0.14.0" - minimist "^1.2.0" - os-homedir "^1.0.1" - -builtin-modules@^1.1.0: - version "1.1.1" - resolved "https://registry.yarnpkg.com/builtin-modules/-/builtin-modules-1.1.1.tgz#270f076c5a72c02f5b65a47df94c5fe3a278892f" - -camelcase@^1.0.2: - version "1.2.1" - resolved "https://registry.yarnpkg.com/camelcase/-/camelcase-1.2.1.tgz#9bb5304d2e0b56698b2c758b08a3eaa9daa58a39" - -caseless@~0.12.0: - version "0.12.0" - resolved "https://registry.yarnpkg.com/caseless/-/caseless-0.12.0.tgz#1b681c21ff84033c826543090689420d187151dc" - -center-align@^0.1.1: - version "0.1.3" - resolved "https://registry.yarnpkg.com/center-align/-/center-align-0.1.3.tgz#aa0d32629b6ee972200411cbd4461c907bc2b7ad" - dependencies: - align-text "^0.1.3" - lazy-cache "^1.0.3" - -chalk@^1.1.3: - version "1.1.3" - resolved "https://registry.yarnpkg.com/chalk/-/chalk-1.1.3.tgz#a8115c55e4a702fe4d150abd3872822a7e09fc98" - dependencies: - ansi-styles "^2.2.1" - escape-string-regexp "^1.0.2" - has-ansi "^2.0.0" - strip-ansi "^3.0.0" - supports-color "^2.0.0" - -chokidar@^1.7.0: - version "1.7.0" - resolved "https://registry.yarnpkg.com/chokidar/-/chokidar-1.7.0.tgz#798e689778151c8076b4b360e5edd28cda2bb468" - dependencies: - anymatch "^1.3.0" - async-each "^1.0.0" - glob-parent "^2.0.0" - inherits "^2.0.1" - is-binary-path "^1.0.0" - is-glob "^2.0.0" - path-is-absolute "^1.0.0" - readdirp "^2.0.0" - optionalDependencies: - fsevents "^1.0.0" - -cliui@^2.1.0: - version "2.1.0" - resolved "https://registry.yarnpkg.com/cliui/-/cliui-2.1.0.tgz#4b475760ff80264c762c3a1719032e91c7fea0d1" - dependencies: - center-align "^0.1.1" - right-align "^0.1.1" - wordwrap "0.0.2" - -co@^4.6.0: - version "4.6.0" - resolved "https://registry.yarnpkg.com/co/-/co-4.6.0.tgz#6ea6bdf3d853ae54ccb8e47bfa0bf3f9031fb184" - -code-point-at@^1.0.0: - version "1.1.0" - resolved "https://registry.yarnpkg.com/code-point-at/-/code-point-at-1.1.0.tgz#0d070b4d043a5bea33a2f1a40e2edb3d9a4ccf77" - -combined-stream@^1.0.5, combined-stream@~1.0.5: - version "1.0.5" - resolved "https://registry.yarnpkg.com/combined-stream/-/combined-stream-1.0.5.tgz#938370a57b4a51dea2c77c15d5c5fdf895164009" - dependencies: - delayed-stream "~1.0.0" - -commander@~2.9.0: - version "2.9.0" - resolved "https://registry.yarnpkg.com/commander/-/commander-2.9.0.tgz#9c99094176e12240cb22d6c5146098400fe0f7d4" - dependencies: - graceful-readlink ">= 1.0.0" - -concat-map@0.0.1: - version "0.0.1" - resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b" - -console-control-strings@^1.0.0, console-control-strings@~1.1.0: - version "1.1.0" - resolved "https://registry.yarnpkg.com/console-control-strings/-/console-control-strings-1.1.0.tgz#3d7cf4464db6446ea644bf4b39507f9851008e8e" - -core-util-is@~1.0.0: - version "1.0.2" - resolved "https://registry.yarnpkg.com/core-util-is/-/core-util-is-1.0.2.tgz#b5fd54220aa2bc5ab57aab7140c940754503c1a7" - -cryptiles@2.x.x: - version "2.0.5" - resolved "https://registry.yarnpkg.com/cryptiles/-/cryptiles-2.0.5.tgz#3bdfecdc608147c1c67202fa291e7dca59eaa3b8" - dependencies: - boom "2.x.x" - -dashdash@^1.12.0: - version "1.14.1" - resolved "https://registry.yarnpkg.com/dashdash/-/dashdash-1.14.1.tgz#853cfa0f7cbe2fed5de20326b8dd581035f6e2f0" - dependencies: - assert-plus "^1.0.0" - -debug@^2.2.0: - version "2.6.8" - resolved "https://registry.yarnpkg.com/debug/-/debug-2.6.8.tgz#e731531ca2ede27d188222427da17821d68ff4fc" - dependencies: - ms "2.0.0" - -decamelize@^1.0.0: - version "1.2.0" - resolved "https://registry.yarnpkg.com/decamelize/-/decamelize-1.2.0.tgz#f6534d15148269b20352e7bee26f501f9a191290" - -deep-extend@~0.4.0: - version "0.4.2" - resolved "https://registry.yarnpkg.com/deep-extend/-/deep-extend-0.4.2.tgz#48b699c27e334bf89f10892be432f6e4c7d34a7f" - -delayed-stream@~1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/delayed-stream/-/delayed-stream-1.0.0.tgz#df3ae199acadfb7d440aaae0b29e2272b24ec619" - -delegates@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/delegates/-/delegates-1.0.0.tgz#84c6e159b81904fdca59a0ef44cd870d31250f9a" - -ecc-jsbn@~0.1.1: - version "0.1.1" - resolved "https://registry.yarnpkg.com/ecc-jsbn/-/ecc-jsbn-0.1.1.tgz#0fc73a9ed5f0d53c38193398523ef7e543777505" - dependencies: - jsbn "~0.1.0" - -escape-string-regexp@^1.0.2: - version "1.0.5" - resolved "https://registry.yarnpkg.com/escape-string-regexp/-/escape-string-regexp-1.0.5.tgz#1b61c0562190a8dff6ae3bb2cf0200ca130b86d4" - -estree-walker@^0.2.1: - version "0.2.1" - resolved "https://registry.yarnpkg.com/estree-walker/-/estree-walker-0.2.1.tgz#bdafe8095383d8414d5dc2ecf4c9173b6db9412e" - -estree-walker@^0.3.0: - version "0.3.1" - resolved "https://registry.yarnpkg.com/estree-walker/-/estree-walker-0.3.1.tgz#e6b1a51cf7292524e7237c312e5fe6660c1ce1aa" - -expand-brackets@^0.1.4: - version "0.1.5" - resolved "https://registry.yarnpkg.com/expand-brackets/-/expand-brackets-0.1.5.tgz#df07284e342a807cd733ac5af72411e581d1177b" - dependencies: - is-posix-bracket "^0.1.0" - -expand-range@^1.8.1: - version "1.8.2" - resolved "https://registry.yarnpkg.com/expand-range/-/expand-range-1.8.2.tgz#a299effd335fe2721ebae8e257ec79644fc85337" - dependencies: - fill-range "^2.1.0" - -extend@~3.0.0: - version "3.0.1" - resolved "https://registry.yarnpkg.com/extend/-/extend-3.0.1.tgz#a755ea7bc1adfcc5a31ce7e762dbaadc5e636444" - -extglob@^0.3.1: - version "0.3.2" - resolved "https://registry.yarnpkg.com/extglob/-/extglob-0.3.2.tgz#2e18ff3d2f49ab2765cec9023f011daa8d8349a1" - dependencies: - is-extglob "^1.0.0" - -extsprintf@1.0.2: - version "1.0.2" - resolved "https://registry.yarnpkg.com/extsprintf/-/extsprintf-1.0.2.tgz#e1080e0658e300b06294990cc70e1502235fd550" - -filename-regex@^2.0.0: - version "2.0.1" - resolved "https://registry.yarnpkg.com/filename-regex/-/filename-regex-2.0.1.tgz#c1c4b9bee3e09725ddb106b75c1e301fe2f18b26" - -fill-range@^2.1.0: - version "2.2.3" - resolved "https://registry.yarnpkg.com/fill-range/-/fill-range-2.2.3.tgz#50b77dfd7e469bc7492470963699fe7a8485a723" - dependencies: - is-number "^2.1.0" - isobject "^2.0.0" - randomatic "^1.1.3" - repeat-element "^1.1.2" - repeat-string "^1.5.2" - -for-in@^1.0.1: - version "1.0.2" - resolved "https://registry.yarnpkg.com/for-in/-/for-in-1.0.2.tgz#81068d295a8142ec0ac726c6e2200c30fb6d5e80" - -for-own@^0.1.4: - version "0.1.5" - resolved "https://registry.yarnpkg.com/for-own/-/for-own-0.1.5.tgz#5265c681a4f294dabbf17c9509b6763aa84510ce" - dependencies: - for-in "^1.0.1" - -forever-agent@~0.6.1: - version "0.6.1" - resolved "https://registry.yarnpkg.com/forever-agent/-/forever-agent-0.6.1.tgz#fbc71f0c41adeb37f96c577ad1ed42d8fdacca91" - -form-data@~2.1.1: - version "2.1.4" - resolved "https://registry.yarnpkg.com/form-data/-/form-data-2.1.4.tgz#33c183acf193276ecaa98143a69e94bfee1750d1" - dependencies: - asynckit "^0.4.0" - combined-stream "^1.0.5" - mime-types "^2.1.12" - -fs.realpath@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/fs.realpath/-/fs.realpath-1.0.0.tgz#1504ad2523158caa40db4a2787cb01411994ea4f" - -fsevents@^1.0.0: - version "1.1.1" - resolved "https://registry.yarnpkg.com/fsevents/-/fsevents-1.1.1.tgz#f19fd28f43eeaf761680e519a203c4d0b3d31aff" - dependencies: - nan "^2.3.0" - node-pre-gyp "^0.6.29" - -fstream-ignore@^1.0.5: - version "1.0.5" - resolved "https://registry.yarnpkg.com/fstream-ignore/-/fstream-ignore-1.0.5.tgz#9c31dae34767018fe1d249b24dada67d092da105" - dependencies: - fstream "^1.0.0" - inherits "2" - minimatch "^3.0.0" - -fstream@^1.0.0, fstream@^1.0.10, fstream@^1.0.2: - version "1.0.11" - resolved "https://registry.yarnpkg.com/fstream/-/fstream-1.0.11.tgz#5c1fb1f117477114f0632a0eb4b71b3cb0fd3171" - dependencies: - graceful-fs "^4.1.2" - inherits "~2.0.0" - mkdirp ">=0.5 0" - rimraf "2" - -gauge@~2.7.3: - version "2.7.4" - resolved "https://registry.yarnpkg.com/gauge/-/gauge-2.7.4.tgz#2c03405c7538c39d7eb37b317022e325fb018bf7" - dependencies: - aproba "^1.0.3" - console-control-strings "^1.0.0" - has-unicode "^2.0.0" - object-assign "^4.1.0" - signal-exit "^3.0.0" - string-width "^1.0.1" - strip-ansi "^3.0.1" - wide-align "^1.1.0" - -getpass@^0.1.1: - version "0.1.7" - resolved "https://registry.yarnpkg.com/getpass/-/getpass-0.1.7.tgz#5eff8e3e684d569ae4cb2b1282604e8ba62149fa" - dependencies: - assert-plus "^1.0.0" - -glob-base@^0.3.0: - version "0.3.0" - resolved "https://registry.yarnpkg.com/glob-base/-/glob-base-0.3.0.tgz#dbb164f6221b1c0b1ccf82aea328b497df0ea3c4" - dependencies: - glob-parent "^2.0.0" - is-glob "^2.0.0" - -glob-parent@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/glob-parent/-/glob-parent-2.0.0.tgz#81383d72db054fcccf5336daa902f182f6edbb28" - dependencies: - is-glob "^2.0.0" - -glob@^7.0.5: - version "7.1.2" - resolved "https://registry.yarnpkg.com/glob/-/glob-7.1.2.tgz#c19c9df9a028702d678612384a6552404c636d15" - dependencies: - fs.realpath "^1.0.0" - inflight "^1.0.4" - inherits "2" - minimatch "^3.0.4" - once "^1.3.0" - path-is-absolute "^1.0.0" - -graceful-fs@^4.1.2: - version "4.1.11" - resolved "https://registry.yarnpkg.com/graceful-fs/-/graceful-fs-4.1.11.tgz#0e8bdfe4d1ddb8854d64e04ea7c00e2a026e5658" - -"graceful-readlink@>= 1.0.0": - version "1.0.1" - resolved "https://registry.yarnpkg.com/graceful-readlink/-/graceful-readlink-1.0.1.tgz#4cafad76bc62f02fa039b2f94e9a3dd3a391a725" - -har-schema@^1.0.5: - version "1.0.5" - resolved "https://registry.yarnpkg.com/har-schema/-/har-schema-1.0.5.tgz#d263135f43307c02c602afc8fe95970c0151369e" - -har-validator@~4.2.1: - version "4.2.1" - resolved "https://registry.yarnpkg.com/har-validator/-/har-validator-4.2.1.tgz#33481d0f1bbff600dd203d75812a6a5fba002e2a" - dependencies: - ajv "^4.9.1" - har-schema "^1.0.5" - -has-ansi@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/has-ansi/-/has-ansi-2.0.0.tgz#34f5049ce1ecdf2b0649af3ef24e45ed35416d91" - dependencies: - ansi-regex "^2.0.0" - -has-unicode@^2.0.0: - version "2.0.1" - resolved "https://registry.yarnpkg.com/has-unicode/-/has-unicode-2.0.1.tgz#e0e6fe6a28cf51138855e086d1691e771de2a8b9" - -hawk@~3.1.3: - version "3.1.3" - resolved "https://registry.yarnpkg.com/hawk/-/hawk-3.1.3.tgz#078444bd7c1640b0fe540d2c9b73d59678e8e1c4" - dependencies: - boom "2.x.x" - cryptiles "2.x.x" - hoek "2.x.x" - sntp "1.x.x" - -hoek@2.x.x: - version "2.16.3" - resolved "https://registry.yarnpkg.com/hoek/-/hoek-2.16.3.tgz#20bb7403d3cea398e91dc4710a8ff1b8274a25ed" - -http-signature@~1.1.0: - version "1.1.1" - resolved "https://registry.yarnpkg.com/http-signature/-/http-signature-1.1.1.tgz#df72e267066cd0ac67fb76adf8e134a8fbcf91bf" - dependencies: - assert-plus "^0.2.0" - jsprim "^1.2.2" - sshpk "^1.7.0" - -inflight@^1.0.4: - version "1.0.6" - resolved "https://registry.yarnpkg.com/inflight/-/inflight-1.0.6.tgz#49bd6331d7d02d0c09bc910a1075ba8165b56df9" - dependencies: - once "^1.3.0" - wrappy "1" - -inherits@2, inherits@^2.0.1, inherits@~2.0.0, inherits@~2.0.1: - version "2.0.3" - resolved "https://registry.yarnpkg.com/inherits/-/inherits-2.0.3.tgz#633c2c83e3da42a502f52466022480f4208261de" - -ini@~1.3.0: - version "1.3.4" - resolved "https://registry.yarnpkg.com/ini/-/ini-1.3.4.tgz#0537cb79daf59b59a1a517dff706c86ec039162e" - -is-binary-path@^1.0.0: - version "1.0.1" - resolved "https://registry.yarnpkg.com/is-binary-path/-/is-binary-path-1.0.1.tgz#75f16642b480f187a711c814161fd3a4a7655898" - dependencies: - binary-extensions "^1.0.0" - -is-buffer@^1.1.5: - version "1.1.5" - resolved "https://registry.yarnpkg.com/is-buffer/-/is-buffer-1.1.5.tgz#1f3b26ef613b214b88cbca23cc6c01d87961eecc" - -is-dotfile@^1.0.0: - version "1.0.3" - resolved "https://registry.yarnpkg.com/is-dotfile/-/is-dotfile-1.0.3.tgz#a6a2f32ffd2dfb04f5ca25ecd0f6b83cf798a1e1" - -is-equal-shallow@^0.1.3: - version "0.1.3" - resolved "https://registry.yarnpkg.com/is-equal-shallow/-/is-equal-shallow-0.1.3.tgz#2238098fc221de0bcfa5d9eac4c45d638aa1c534" - dependencies: - is-primitive "^2.0.0" - -is-extendable@^0.1.1: - version "0.1.1" - resolved "https://registry.yarnpkg.com/is-extendable/-/is-extendable-0.1.1.tgz#62b110e289a471418e3ec36a617d472e301dfc89" - -is-extglob@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/is-extglob/-/is-extglob-1.0.0.tgz#ac468177c4943405a092fc8f29760c6ffc6206c0" - -is-fullwidth-code-point@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/is-fullwidth-code-point/-/is-fullwidth-code-point-1.0.0.tgz#ef9e31386f031a7f0d643af82fde50c457ef00cb" - dependencies: - number-is-nan "^1.0.0" - -is-glob@^2.0.0, is-glob@^2.0.1: - version "2.0.1" - resolved "https://registry.yarnpkg.com/is-glob/-/is-glob-2.0.1.tgz#d096f926a3ded5600f3fdfd91198cb0888c2d863" - dependencies: - is-extglob "^1.0.0" - -is-module@^1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/is-module/-/is-module-1.0.0.tgz#3258fb69f78c14d5b815d664336b4cffb6441591" - -is-number@^2.1.0: - version "2.1.0" - resolved "https://registry.yarnpkg.com/is-number/-/is-number-2.1.0.tgz#01fcbbb393463a548f2f466cce16dece49db908f" - dependencies: - kind-of "^3.0.2" - -is-number@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/is-number/-/is-number-3.0.0.tgz#24fd6201a4782cf50561c810276afc7d12d71195" - dependencies: - kind-of "^3.0.2" + resolved "https://registry.npmjs.org/buffer-from/-/buffer-from-1.1.2.tgz" + integrity sha512-E+XQCRwSbaaiChtv6k6Dwgc+bx+Bs6vuKJHHl5kox/BaKbhiXzqQOwK4cO22yElGp2OCmjwVhT3HmxgyPGnJfQ== -is-posix-bracket@^0.1.0: - version "0.1.1" - resolved "https://registry.yarnpkg.com/is-posix-bracket/-/is-posix-bracket-0.1.1.tgz#3334dc79774368e92f016e6fbc0a88f5cd6e6bc4" +commander@^2.20.0: + version "2.20.3" + resolved "https://registry.npmjs.org/commander/-/commander-2.20.3.tgz" + integrity sha512-GpVkmM8vF2vQUkj2LvZmD35JxeJOLCwJ9cUkugyk2nuhbv3+mJvpLYYt+0+USMxE+oj+ey/lJEnhZw75x/OMcQ== -is-primitive@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/is-primitive/-/is-primitive-2.0.0.tgz#207bab91638499c07b2adf240a41a87210034575" - -is-typedarray@~1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/is-typedarray/-/is-typedarray-1.0.0.tgz#e479c80858df0c1b11ddda6940f96011fcda4a9a" - -isarray@1.0.0, isarray@~1.0.0: - version "1.0.0" - resolved "https://registry.yarnpkg.com/isarray/-/isarray-1.0.0.tgz#bb935d48582cba168c06834957a54a3e07124f11" - -isobject@^2.0.0: +randombytes@^2.1.0: version "2.1.0" - resolved "https://registry.yarnpkg.com/isobject/-/isobject-2.1.0.tgz#f065561096a3f1da2ef46272f815c840d87e0c89" - dependencies: - isarray "1.0.0" - -isstream@~0.1.2: - version "0.1.2" - resolved "https://registry.yarnpkg.com/isstream/-/isstream-0.1.2.tgz#47e63f7af55afa6f92e1500e690eb8b8529c099a" - -jquery@^3.2.1: - version "3.2.1" - resolved "https://registry.yarnpkg.com/jquery/-/jquery-3.2.1.tgz#5c4d9de652af6cd0a770154a631bba12b015c787" - -jsbn@~0.1.0: - version "0.1.1" - resolved "https://registry.yarnpkg.com/jsbn/-/jsbn-0.1.1.tgz#a5e654c2e5a2deb5f201d96cefbca80c0ef2f513" - -json-schema@0.2.3: - version "0.2.3" - resolved "https://registry.yarnpkg.com/json-schema/-/json-schema-0.2.3.tgz#b480c892e59a2f05954ce727bd3f2a4e882f9e13" - -json-stable-stringify@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/json-stable-stringify/-/json-stable-stringify-1.0.1.tgz#9a759d39c5f2ff503fd5300646ed445f88c4f9af" - dependencies: - jsonify "~0.0.0" - -json-stringify-safe@~5.0.1: - version "5.0.1" - resolved "https://registry.yarnpkg.com/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz#1296a2d58fd45f19a0f6ce01d65701e2c735b6eb" - -jsonify@~0.0.0: - version "0.0.0" - resolved "https://registry.yarnpkg.com/jsonify/-/jsonify-0.0.0.tgz#2c74b6ee41d93ca51b7b5aaee8f503631d252a73" - -jsprim@^1.2.2: - version "1.4.0" - resolved "https://registry.yarnpkg.com/jsprim/-/jsprim-1.4.0.tgz#a3b87e40298d8c380552d8cc7628a0bb95a22918" - dependencies: - assert-plus "1.0.0" - extsprintf "1.0.2" - json-schema "0.2.3" - verror "1.3.6" - -kind-of@^3.0.2: - version "3.2.2" - resolved "https://registry.yarnpkg.com/kind-of/-/kind-of-3.2.2.tgz#31ea21a734bab9bbb0f32466d893aea51e4a3c64" + resolved "https://registry.npmjs.org/randombytes/-/randombytes-2.1.0.tgz" + integrity sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ== dependencies: - is-buffer "^1.1.5" + safe-buffer "^5.1.0" -kind-of@^4.0.0: - version "4.0.0" - resolved "https://registry.yarnpkg.com/kind-of/-/kind-of-4.0.0.tgz#20813df3d712928b207378691a45066fae72dd57" +rollup@^2.0.0||^3.0.0||^4.0.0, rollup@^4.28.1: + version "4.52.4" + resolved "https://registry.npmjs.org/rollup/-/rollup-4.52.4.tgz" + integrity sha512-CLEVl+MnPAiKh5pl4dEWSyMTpuflgNQiLGhMv8ezD5W/qP8AKvmYpCOKRRNOh7oRKnauBZ4SyeYkMS+1VSyKwQ== dependencies: - is-buffer "^1.1.5" - -lazy-cache@^1.0.3: - version "1.0.4" - resolved "https://registry.yarnpkg.com/lazy-cache/-/lazy-cache-1.0.4.tgz#a1d78fc3a50474cb80845d3b3b6e1da49a446e8e" - -longest@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/longest/-/longest-1.0.1.tgz#30a0b2da38f73770e8294a0d22e6625ed77d0097" - -magic-string@^0.14.0: - version "0.14.0" - resolved "https://registry.yarnpkg.com/magic-string/-/magic-string-0.14.0.tgz#57224aef1701caeed273b17a39a956e72b172462" - dependencies: - vlq "^0.2.1" - -magic-string@^0.19.0: - version "0.19.1" - resolved "https://registry.yarnpkg.com/magic-string/-/magic-string-0.19.1.tgz#14d768013caf2ec8fdea16a49af82fc377e75201" - dependencies: - vlq "^0.2.1" - -micromatch@^2.1.5, micromatch@^2.3.11: - version "2.3.11" - resolved "https://registry.yarnpkg.com/micromatch/-/micromatch-2.3.11.tgz#86677c97d1720b363431d04d0d15293bd38c1565" - dependencies: - arr-diff "^2.0.0" - array-unique "^0.2.1" - braces "^1.8.2" - expand-brackets "^0.1.4" - extglob "^0.3.1" - filename-regex "^2.0.0" - is-extglob "^1.0.0" - is-glob "^2.0.1" - kind-of "^3.0.2" - normalize-path "^2.0.1" - object.omit "^2.0.0" - parse-glob "^3.0.4" - regex-cache "^0.4.2" - -mime-db@~1.27.0: - version "1.27.0" - resolved "https://registry.yarnpkg.com/mime-db/-/mime-db-1.27.0.tgz#820f572296bbd20ec25ed55e5b5de869e5436eb1" - -mime-types@^2.1.12, mime-types@~2.1.7: - version "2.1.15" - resolved "https://registry.yarnpkg.com/mime-types/-/mime-types-2.1.15.tgz#a4ebf5064094569237b8cf70046776d09fc92aed" - dependencies: - mime-db "~1.27.0" - -minimatch@^3.0.0, minimatch@^3.0.2, minimatch@^3.0.4: - version "3.0.4" - resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.0.4.tgz#5166e286457f03306064be5497e8dbb0c3d32083" - dependencies: - brace-expansion "^1.1.7" - -minimist@0.0.8: - version "0.0.8" - resolved "https://registry.yarnpkg.com/minimist/-/minimist-0.0.8.tgz#857fcabfc3397d2625b8228262e86aa7a011b05d" - -minimist@^1.2.0: - version "1.2.0" - resolved "https://registry.yarnpkg.com/minimist/-/minimist-1.2.0.tgz#a35008b20f41383eec1fb914f4cd5df79a264284" - -"mkdirp@>=0.5 0", mkdirp@^0.5.1: - version "0.5.1" - resolved "https://registry.yarnpkg.com/mkdirp/-/mkdirp-0.5.1.tgz#30057438eac6cf7f8c4767f38648d6697d75c903" - dependencies: - minimist "0.0.8" - -ms@2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/ms/-/ms-2.0.0.tgz#5608aeadfc00be6c2901df5f9861788de0d597c8" - -nan@^2.3.0: - version "2.6.2" - resolved "https://registry.yarnpkg.com/nan/-/nan-2.6.2.tgz#e4ff34e6c95fdfb5aecc08de6596f43605a7db45" - -node-pre-gyp@^0.6.29: - version "0.6.36" - resolved "https://registry.yarnpkg.com/node-pre-gyp/-/node-pre-gyp-0.6.36.tgz#db604112cb74e0d477554e9b505b17abddfab786" - dependencies: - mkdirp "^0.5.1" - nopt "^4.0.1" - npmlog "^4.0.2" - rc "^1.1.7" - request "^2.81.0" - rimraf "^2.6.1" - semver "^5.3.0" - tar "^2.2.1" - tar-pack "^3.4.0" - -nopt@^4.0.1: - version "4.0.1" - resolved "https://registry.yarnpkg.com/nopt/-/nopt-4.0.1.tgz#d0d4685afd5415193c8c7505602d0d17cd64474d" - dependencies: - abbrev "1" - osenv "^0.1.4" - -normalize-path@^2.0.1: - version "2.1.1" - resolved "https://registry.yarnpkg.com/normalize-path/-/normalize-path-2.1.1.tgz#1ab28b556e198363a8c1a6f7e6fa20137fe6aed9" - dependencies: - remove-trailing-separator "^1.0.1" - -npmlog@^4.0.2: - version "4.1.0" - resolved "https://registry.yarnpkg.com/npmlog/-/npmlog-4.1.0.tgz#dc59bee85f64f00ed424efb2af0783df25d1c0b5" - dependencies: - are-we-there-yet "~1.1.2" - console-control-strings "~1.1.0" - gauge "~2.7.3" - set-blocking "~2.0.0" - -number-is-nan@^1.0.0: - version "1.0.1" - resolved "https://registry.yarnpkg.com/number-is-nan/-/number-is-nan-1.0.1.tgz#097b602b53422a522c1afb8790318336941a011d" - -oauth-sign@~0.8.1: - version "0.8.2" - resolved "https://registry.yarnpkg.com/oauth-sign/-/oauth-sign-0.8.2.tgz#46a6ab7f0aead8deae9ec0565780b7d4efeb9d43" - -object-assign@^4.1.0: - version "4.1.1" - resolved "https://registry.yarnpkg.com/object-assign/-/object-assign-4.1.1.tgz#2109adc7965887cfc05cbbd442cac8bfbb360863" - -object.omit@^2.0.0: - version "2.0.1" - resolved "https://registry.yarnpkg.com/object.omit/-/object.omit-2.0.1.tgz#1a9c744829f39dbb858c76ca3579ae2a54ebd1fa" - dependencies: - for-own "^0.1.4" - is-extendable "^0.1.1" - -once@^1.3.0, once@^1.3.3: - version "1.4.0" - resolved "https://registry.yarnpkg.com/once/-/once-1.4.0.tgz#583b1aa775961d4b113ac17d9c50baef9dd76bd1" - dependencies: - wrappy "1" - -os-homedir@^1.0.0, os-homedir@^1.0.1: - version "1.0.2" - resolved "https://registry.yarnpkg.com/os-homedir/-/os-homedir-1.0.2.tgz#ffbc4988336e0e833de0c168c7ef152121aa7fb3" - -os-tmpdir@^1.0.0: - version "1.0.2" - resolved "https://registry.yarnpkg.com/os-tmpdir/-/os-tmpdir-1.0.2.tgz#bbe67406c79aa85c5cfec766fe5734555dfa1274" - -osenv@^0.1.4: - version "0.1.4" - resolved "https://registry.yarnpkg.com/osenv/-/osenv-0.1.4.tgz#42fe6d5953df06c8064be6f176c3d05aaaa34644" - dependencies: - os-homedir "^1.0.0" - os-tmpdir "^1.0.0" - -parse-glob@^3.0.4: - version "3.0.4" - resolved "https://registry.yarnpkg.com/parse-glob/-/parse-glob-3.0.4.tgz#b2c376cfb11f35513badd173ef0bb6e3a388391c" - dependencies: - glob-base "^0.3.0" - is-dotfile "^1.0.0" - is-extglob "^1.0.0" - is-glob "^2.0.0" - -path-is-absolute@^1.0.0: - version "1.0.1" - resolved "https://registry.yarnpkg.com/path-is-absolute/-/path-is-absolute-1.0.1.tgz#174b9268735534ffbc7ace6bf53a5a9e1b5c5f5f" - -path-parse@^1.0.5: - version "1.0.5" - resolved "https://registry.yarnpkg.com/path-parse/-/path-parse-1.0.5.tgz#3c1adf871ea9cd6c9431b6ea2bd74a0ff055c4c1" - -performance-now@^0.2.0: - version "0.2.0" - resolved "https://registry.yarnpkg.com/performance-now/-/performance-now-0.2.0.tgz#33ef30c5c77d4ea21c5a53869d91b56d8f2555e5" - -preserve@^0.2.0: - version "0.2.0" - resolved "https://registry.yarnpkg.com/preserve/-/preserve-0.2.0.tgz#815ed1f6ebc65926f865b310c0713bcb3315ce4b" - -process-nextick-args@~1.0.6: - version "1.0.7" - resolved "https://registry.yarnpkg.com/process-nextick-args/-/process-nextick-args-1.0.7.tgz#150e20b756590ad3f91093f25a4f2ad8bff30ba3" - -punycode@^1.4.1: - version "1.4.1" - resolved "https://registry.yarnpkg.com/punycode/-/punycode-1.4.1.tgz#c0d5a63b2718800ad8e1eb0fa5269c84dd41845e" - -qs@~6.4.0: - version "6.4.0" - resolved "https://registry.yarnpkg.com/qs/-/qs-6.4.0.tgz#13e26d28ad6b0ffaa91312cd3bf708ed351e7233" - -randomatic@^1.1.3: - version "1.1.7" - resolved "https://registry.yarnpkg.com/randomatic/-/randomatic-1.1.7.tgz#c7abe9cc8b87c0baa876b19fde83fd464797e38c" - dependencies: - is-number "^3.0.0" - kind-of "^4.0.0" - -rc@^1.1.7: - version "1.2.1" - resolved "https://registry.yarnpkg.com/rc/-/rc-1.2.1.tgz#2e03e8e42ee450b8cb3dce65be1bf8974e1dfd95" - dependencies: - deep-extend "~0.4.0" - ini "~1.3.0" - minimist "^1.2.0" - strip-json-comments "~2.0.1" - -readable-stream@^2.0.2, readable-stream@^2.0.6, readable-stream@^2.1.4: - version "2.2.11" - resolved "https://registry.yarnpkg.com/readable-stream/-/readable-stream-2.2.11.tgz#0796b31f8d7688007ff0b93a8088d34aa17c0f72" - dependencies: - core-util-is "~1.0.0" - inherits "~2.0.1" - isarray "~1.0.0" - process-nextick-args "~1.0.6" - safe-buffer "~5.0.1" - string_decoder "~1.0.0" - util-deprecate "~1.0.1" - -readdirp@^2.0.0: - version "2.1.0" - resolved "https://registry.yarnpkg.com/readdirp/-/readdirp-2.1.0.tgz#4ed0ad060df3073300c48440373f72d1cc642d78" - dependencies: - graceful-fs "^4.1.2" - minimatch "^3.0.2" - readable-stream "^2.0.2" - set-immediate-shim "^1.0.1" - -regex-cache@^0.4.2: - version "0.4.3" - resolved "https://registry.yarnpkg.com/regex-cache/-/regex-cache-0.4.3.tgz#9b1a6c35d4d0dfcef5711ae651e8e9d3d7114145" - dependencies: - is-equal-shallow "^0.1.3" - is-primitive "^2.0.0" - -remove-trailing-separator@^1.0.1: - version "1.0.2" - resolved "https://registry.yarnpkg.com/remove-trailing-separator/-/remove-trailing-separator-1.0.2.tgz#69b062d978727ad14dc6b56ba4ab772fd8d70511" - -repeat-element@^1.1.2: - version "1.1.2" - resolved "https://registry.yarnpkg.com/repeat-element/-/repeat-element-1.1.2.tgz#ef089a178d1483baae4d93eb98b4f9e4e11d990a" - -repeat-string@^1.5.2: - version "1.6.1" - resolved "https://registry.yarnpkg.com/repeat-string/-/repeat-string-1.6.1.tgz#8dcae470e1c88abc2d600fff4a776286da75e637" - -request@^2.81.0: - version "2.81.0" - resolved "https://registry.yarnpkg.com/request/-/request-2.81.0.tgz#c6928946a0e06c5f8d6f8a9333469ffda46298a0" - dependencies: - aws-sign2 "~0.6.0" - aws4 "^1.2.1" - caseless "~0.12.0" - combined-stream "~1.0.5" - extend "~3.0.0" - forever-agent "~0.6.1" - form-data "~2.1.1" - har-validator "~4.2.1" - hawk "~3.1.3" - http-signature "~1.1.0" - is-typedarray "~1.0.0" - isstream "~0.1.2" - json-stringify-safe "~5.0.1" - mime-types "~2.1.7" - oauth-sign "~0.8.1" - performance-now "^0.2.0" - qs "~6.4.0" - safe-buffer "^5.0.1" - stringstream "~0.0.4" - tough-cookie "~2.3.0" - tunnel-agent "^0.6.0" - uuid "^3.0.0" - -require-relative@0.8.7: - version "0.8.7" - resolved "https://registry.yarnpkg.com/require-relative/-/require-relative-0.8.7.tgz#7999539fc9e047a37928fa196f8e1563dabd36de" - -resolve@1.1.7: - version "1.1.7" - resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.1.7.tgz#203114d82ad2c5ed9e8e0411b3932875e889e97b" - -resolve@^1.1.6, resolve@^1.1.7: - version "1.3.3" - resolved "https://registry.yarnpkg.com/resolve/-/resolve-1.3.3.tgz#655907c3469a8680dc2de3a275a8fdd69691f0e5" - dependencies: - path-parse "^1.0.5" - -right-align@^0.1.1: - version "0.1.3" - resolved "https://registry.yarnpkg.com/right-align/-/right-align-0.1.3.tgz#61339b722fe6a3515689210d24e14c96148613ef" - dependencies: - align-text "^0.1.1" - -rimraf@2, rimraf@^2.5.1, rimraf@^2.6.1: - version "2.6.1" - resolved "https://registry.yarnpkg.com/rimraf/-/rimraf-2.6.1.tgz#c2338ec643df7a1b7fe5c54fa86f57428a55f33d" - dependencies: - glob "^7.0.5" - -rollup-plugin-buble@^0.15.0: - version "0.15.0" - resolved "https://registry.yarnpkg.com/rollup-plugin-buble/-/rollup-plugin-buble-0.15.0.tgz#83c3e89c7fd2266c7918f41ba3980313519c7fd0" - dependencies: - buble "^0.15.0" - rollup-pluginutils "^1.5.0" - -rollup-plugin-commonjs@^8.0.2: - version "8.0.2" - resolved "https://registry.yarnpkg.com/rollup-plugin-commonjs/-/rollup-plugin-commonjs-8.0.2.tgz#98b1589bfe32a6c0f67790b60c0b499972afed89" - dependencies: - acorn "^4.0.1" - estree-walker "^0.3.0" - magic-string "^0.19.0" - resolve "^1.1.7" - rollup-pluginutils "^2.0.1" - -rollup-plugin-node-resolve@^3.0.0: - version "3.0.0" - resolved "https://registry.yarnpkg.com/rollup-plugin-node-resolve/-/rollup-plugin-node-resolve-3.0.0.tgz#8b897c4c3030d5001277b0514b25d2ca09683ee0" - dependencies: - browser-resolve "^1.11.0" - builtin-modules "^1.1.0" - is-module "^1.0.0" - resolve "^1.1.6" - -rollup-plugin-uglify@^2.0.1: - version "2.0.1" - resolved "https://registry.yarnpkg.com/rollup-plugin-uglify/-/rollup-plugin-uglify-2.0.1.tgz#67b37ad1efdafbd83af4c36b40c189ee4866c969" - dependencies: - uglify-js "^3.0.9" - -rollup-pluginutils@^1.5.0: - version "1.5.2" - resolved "https://registry.yarnpkg.com/rollup-pluginutils/-/rollup-pluginutils-1.5.2.tgz#1e156e778f94b7255bfa1b3d0178be8f5c552408" - dependencies: - estree-walker "^0.2.1" - minimatch "^3.0.2" - -rollup-pluginutils@^2.0.1: - version "2.0.1" - resolved "https://registry.yarnpkg.com/rollup-pluginutils/-/rollup-pluginutils-2.0.1.tgz#7ec95b3573f6543a46a6461bd9a7c544525d0fc0" - dependencies: - estree-walker "^0.3.0" - micromatch "^2.3.11" - -rollup-watch@^4.0.0: - version "4.0.0" - resolved "https://registry.yarnpkg.com/rollup-watch/-/rollup-watch-4.0.0.tgz#309051b9403b9e5445c5746c9eba9a466951d39e" - dependencies: - chokidar "^1.7.0" - require-relative "0.8.7" - -rollup@^0.42.0: - version "0.42.0" - resolved "https://registry.yarnpkg.com/rollup/-/rollup-0.42.0.tgz#56e791b3a2f3dd7190bbb80a375675f2fe0f9b23" - dependencies: - source-map-support "^0.4.0" - -safe-buffer@^5.0.1, safe-buffer@~5.0.1: - version "5.0.1" - resolved "https://registry.yarnpkg.com/safe-buffer/-/safe-buffer-5.0.1.tgz#d263ca54696cd8a306b5ca6551e92de57918fbe7" - -semver@^5.3.0: - version "5.3.0" - resolved "https://registry.yarnpkg.com/semver/-/semver-5.3.0.tgz#9b2ce5d3de02d17c6012ad326aa6b4d0cf54f94f" - -set-blocking@~2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/set-blocking/-/set-blocking-2.0.0.tgz#045f9782d011ae9a6803ddd382b24392b3d890f7" - -set-immediate-shim@^1.0.1: - version "1.0.1" - resolved "https://registry.yarnpkg.com/set-immediate-shim/-/set-immediate-shim-1.0.1.tgz#4b2b1b27eb808a9f8dcc481a58e5e56f599f3f61" - -signal-exit@^3.0.0: - version "3.0.2" - resolved "https://registry.yarnpkg.com/signal-exit/-/signal-exit-3.0.2.tgz#b5fdc08f1287ea1178628e415e25132b73646c6d" - -sntp@1.x.x: - version "1.0.9" - resolved "https://registry.yarnpkg.com/sntp/-/sntp-1.0.9.tgz#6541184cc90aeea6c6e7b35e2659082443c66198" - dependencies: - hoek "2.x.x" - -source-map-support@^0.4.0: - version "0.4.15" - resolved "https://registry.yarnpkg.com/source-map-support/-/source-map-support-0.4.15.tgz#03202df65c06d2bd8c7ec2362a193056fef8d3b1" - dependencies: - source-map "^0.5.6" - -source-map@^0.5.6, source-map@~0.5.1: - version "0.5.6" - resolved "https://registry.yarnpkg.com/source-map/-/source-map-0.5.6.tgz#75ce38f52bf0733c5a7f0c118d81334a2bb5f412" - -sshpk@^1.7.0: - version "1.13.1" - resolved "https://registry.yarnpkg.com/sshpk/-/sshpk-1.13.1.tgz#512df6da6287144316dc4c18fe1cf1d940739be3" - dependencies: - asn1 "~0.2.3" - assert-plus "^1.0.0" - dashdash "^1.12.0" - getpass "^0.1.1" + "@types/estree" "1.0.8" optionalDependencies: - bcrypt-pbkdf "^1.0.0" - ecc-jsbn "~0.1.1" - jsbn "~0.1.0" - tweetnacl "~0.14.0" - -string-width@^1.0.1, string-width@^1.0.2: - version "1.0.2" - resolved "https://registry.yarnpkg.com/string-width/-/string-width-1.0.2.tgz#118bdf5b8cdc51a2a7e70d211e07e2b0b9b107d3" - dependencies: - code-point-at "^1.0.0" - is-fullwidth-code-point "^1.0.0" - strip-ansi "^3.0.0" - -string_decoder@~1.0.0: - version "1.0.2" - resolved "https://registry.yarnpkg.com/string_decoder/-/string_decoder-1.0.2.tgz#b29e1f4e1125fa97a10382b8a533737b7491e179" - dependencies: - safe-buffer "~5.0.1" - -stringstream@~0.0.4: - version "0.0.5" - resolved "https://registry.yarnpkg.com/stringstream/-/stringstream-0.0.5.tgz#4e484cd4de5a0bbbee18e46307710a8a81621878" - -strip-ansi@^3.0.0, strip-ansi@^3.0.1: - version "3.0.1" - resolved "https://registry.yarnpkg.com/strip-ansi/-/strip-ansi-3.0.1.tgz#6a385fb8853d952d5ff05d0e8aaf94278dc63dcf" - dependencies: - ansi-regex "^2.0.0" - -strip-json-comments@~2.0.1: - version "2.0.1" - resolved "https://registry.yarnpkg.com/strip-json-comments/-/strip-json-comments-2.0.1.tgz#3c531942e908c2697c0ec344858c286c7ca0a60a" - -supports-color@^2.0.0: - version "2.0.0" - resolved "https://registry.yarnpkg.com/supports-color/-/supports-color-2.0.0.tgz#535d045ce6b6363fa40117084629995e9df324c7" - -tar-pack@^3.4.0: - version "3.4.0" - resolved "https://registry.yarnpkg.com/tar-pack/-/tar-pack-3.4.0.tgz#23be2d7f671a8339376cbdb0b8fe3fdebf317984" - dependencies: - debug "^2.2.0" - fstream "^1.0.10" - fstream-ignore "^1.0.5" - once "^1.3.3" - readable-stream "^2.1.4" - rimraf "^2.5.1" - tar "^2.2.1" - uid-number "^0.0.6" - -tar@^2.2.1: - version "2.2.1" - resolved "https://registry.yarnpkg.com/tar/-/tar-2.2.1.tgz#8e4d2a256c0e2185c6b18ad694aec968b83cb1d1" - dependencies: - block-stream "*" - fstream "^1.0.2" - inherits "2" - -tough-cookie@~2.3.0: - version "2.3.2" - resolved "https://registry.yarnpkg.com/tough-cookie/-/tough-cookie-2.3.2.tgz#f081f76e4c85720e6c37a5faced737150d84072a" - dependencies: - punycode "^1.4.1" - -tunnel-agent@^0.6.0: - version "0.6.0" - resolved "https://registry.yarnpkg.com/tunnel-agent/-/tunnel-agent-0.6.0.tgz#27a5dea06b36b04a0a9966774b290868f0fc40fd" - dependencies: - safe-buffer "^5.0.1" - -tweetnacl@^0.14.3, tweetnacl@~0.14.0: - version "0.14.5" - resolved "https://registry.yarnpkg.com/tweetnacl/-/tweetnacl-0.14.5.tgz#5ae68177f192d4456269d108afa93ff8743f4f64" - -uglify-js-harmony@^2.7.7: - version "2.7.7" - resolved "https://registry.yarnpkg.com/uglify-js-harmony/-/uglify-js-harmony-2.7.7.tgz#6a43993211fa5da2f1e58416d61f329327eef335" - dependencies: - async "~0.2.6" - source-map "~0.5.1" - uglify-to-browserify "~1.0.0" - yargs "~3.10.0" - -uglify-js@^3.0.9: - version "3.0.15" - resolved "https://registry.yarnpkg.com/uglify-js/-/uglify-js-3.0.15.tgz#aacb323a846b234602270dead8a32441a8806f42" - dependencies: - commander "~2.9.0" - source-map "~0.5.1" - -uglify-to-browserify@~1.0.0: - version "1.0.2" - resolved "https://registry.yarnpkg.com/uglify-to-browserify/-/uglify-to-browserify-1.0.2.tgz#6e0924d6bda6b5afe349e39a6d632850a0f882b7" - -uid-number@^0.0.6: - version "0.0.6" - resolved "https://registry.yarnpkg.com/uid-number/-/uid-number-0.0.6.tgz#0ea10e8035e8eb5b8e4449f06da1c730663baa81" - -util-deprecate@~1.0.1: - version "1.0.2" - resolved "https://registry.yarnpkg.com/util-deprecate/-/util-deprecate-1.0.2.tgz#450d4dc9fa70de732762fbd2d4a28981419a0ccf" - -uuid@^3.0.0: - version "3.0.1" - resolved "https://registry.yarnpkg.com/uuid/-/uuid-3.0.1.tgz#6544bba2dfda8c1cf17e629a3a305e2bb1fee6c1" - -verror@1.3.6: - version "1.3.6" - resolved "https://registry.yarnpkg.com/verror/-/verror-1.3.6.tgz#cff5df12946d297d2baaefaa2689e25be01c005c" - dependencies: - extsprintf "1.0.2" - -vlq@^0.2.1: - version "0.2.2" - resolved "https://registry.yarnpkg.com/vlq/-/vlq-0.2.2.tgz#e316d5257b40b86bb43cb8d5fea5d7f54d6b0ca1" - -wide-align@^1.1.0: - version "1.1.2" - resolved "https://registry.yarnpkg.com/wide-align/-/wide-align-1.1.2.tgz#571e0f1b0604636ebc0dfc21b0339bbe31341710" - dependencies: - string-width "^1.0.2" - -window-size@0.1.0: - version "0.1.0" - resolved "https://registry.yarnpkg.com/window-size/-/window-size-0.1.0.tgz#5438cd2ea93b202efa3a19fe8887aee7c94f9c9d" - -wordwrap@0.0.2: - version "0.0.2" - resolved "https://registry.yarnpkg.com/wordwrap/-/wordwrap-0.0.2.tgz#b79669bb42ecb409f83d583cad52ca17eaa1643f" - -wrappy@1: - version "1.0.2" - resolved "https://registry.yarnpkg.com/wrappy/-/wrappy-1.0.2.tgz#b5243d8f3ec1aa35f1364605bc0d1036e30ab69f" - -yargs@~3.10.0: - version "3.10.0" - resolved "https://registry.yarnpkg.com/yargs/-/yargs-3.10.0.tgz#f7ee7bd857dd7c1d2d38c0e74efbd681d1431fd1" - dependencies: - camelcase "^1.0.2" - cliui "^2.1.0" - decamelize "^1.0.0" - window-size "0.1.0" + "@rollup/rollup-android-arm-eabi" "4.52.4" + "@rollup/rollup-android-arm64" "4.52.4" + "@rollup/rollup-darwin-arm64" "4.52.4" + "@rollup/rollup-darwin-x64" "4.52.4" + "@rollup/rollup-freebsd-arm64" "4.52.4" + "@rollup/rollup-freebsd-x64" "4.52.4" + "@rollup/rollup-linux-arm-gnueabihf" "4.52.4" + "@rollup/rollup-linux-arm-musleabihf" "4.52.4" + "@rollup/rollup-linux-arm64-gnu" "4.52.4" + "@rollup/rollup-linux-arm64-musl" "4.52.4" + "@rollup/rollup-linux-loong64-gnu" "4.52.4" + "@rollup/rollup-linux-ppc64-gnu" "4.52.4" + "@rollup/rollup-linux-riscv64-gnu" "4.52.4" + "@rollup/rollup-linux-riscv64-musl" "4.52.4" + "@rollup/rollup-linux-s390x-gnu" "4.52.4" + "@rollup/rollup-linux-x64-gnu" "4.52.4" + "@rollup/rollup-linux-x64-musl" "4.52.4" + "@rollup/rollup-openharmony-arm64" "4.52.4" + "@rollup/rollup-win32-arm64-msvc" "4.52.4" + "@rollup/rollup-win32-ia32-msvc" "4.52.4" + "@rollup/rollup-win32-x64-gnu" "4.52.4" + "@rollup/rollup-win32-x64-msvc" "4.52.4" + fsevents "~2.3.2" + +safe-buffer@^5.1.0: + version "5.2.1" + resolved "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.2.1.tgz" + integrity sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ== + +serialize-javascript@^6.0.1: + version "6.0.2" + resolved "https://registry.npmjs.org/serialize-javascript/-/serialize-javascript-6.0.2.tgz" + integrity sha512-Saa1xPByTTq2gdeFZYLLo+RFE35NHZkAbqZeWNd3BpzppeVisAqpDjcp8dyf6uIvEqJRd46jemmyA4iFIeVk8g== + dependencies: + randombytes "^2.1.0" + +smob@^1.0.0: + version "1.5.0" + resolved "https://registry.npmjs.org/smob/-/smob-1.5.0.tgz" + integrity sha512-g6T+p7QO8npa+/hNx9ohv1E5pVCmWrVCUzUXJyLdMmftX6ER0oiWY/w9knEonLpnOp6b6FenKnMfR8gqwWdwig== + +source-map-support@~0.5.20: + version "0.5.21" + resolved "https://registry.npmjs.org/source-map-support/-/source-map-support-0.5.21.tgz" + integrity sha512-uBHU3L3czsIyYXKX88fdrGovxdSCoTGDRZ6SYXtSRxLZUzHg5P/66Ht6uoUlHu9EZod+inXhKo3qQgwXUT/y1w== + dependencies: + buffer-from "^1.0.0" + source-map "^0.6.0" + +source-map@^0.6.0: + version "0.6.1" + resolved "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz" + integrity sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g== + +terser@^5.17.4: + version "5.44.0" + resolved "https://registry.npmjs.org/terser/-/terser-5.44.0.tgz" + integrity sha512-nIVck8DK+GM/0Frwd+nIhZ84pR/BX7rmXMfYwyg+Sri5oGVE99/E3KvXqpC2xHFxyqXyGHTKBSioxxplrO4I4w== + dependencies: + "@jridgewell/source-map" "^0.3.3" + acorn "^8.15.0" + commander "^2.20.0" + source-map-support "~0.5.20" From 5dc6c973f386842cd308870c4ff04d130a3655ed Mon Sep 17 00:00:00 2001 From: Michael Hardeman Date: Tue, 7 Oct 2025 12:15:16 -0400 Subject: [PATCH 2/3] Had AI add jsdoc comments. Also fixed modules warning. --- lib/agent.js | 241 +++++++++++++++++++++++++++++++----------------- lib/animator.js | 94 +++++++++++++++---- lib/balloon.js | 67 +++++++++++--- lib/load.js | 55 +++++++++-- lib/queue.js | 26 ++++-- package.json | 1 + 6 files changed, 353 insertions(+), 131 deletions(-) diff --git a/lib/agent.js b/lib/agent.js index c307811..e891f41 100755 --- a/lib/agent.js +++ b/lib/agent.js @@ -2,8 +2,15 @@ import Queue from './queue' import Animator from './animator' import Balloon from './balloon' +/** + * Agent class represents an animated character that can move, speak, and perform actions + */ export default class Agent { - + /** + * @param {string} path - Path to the agent's asset directory + * @param {Object} data - Agent animation data + * @param {Object} sounds - Map of sound names to audio URLs + */ constructor (path, data, sounds) { this.path = path; @@ -16,16 +23,16 @@ export default class Agent { document.body.appendChild(this._el); this._animator = new Animator(this._el, path, data, sounds); - this._balloon = new Balloon(this._el); this._setupEvents(); } - /*** - * - * @param {Number} x - * @param {Number} y + /** + * Make the agent gesture towards a specific point + * @param {number} x - X coordinate + * @param {number} y - Y coordinate + * @returns {boolean} - True if gesture animation was played */ gestureAt (x, y) { let d = this._getDirection(x, y); @@ -36,10 +43,10 @@ export default class Agent { return this.play(animation); } - /*** - * - * @param {Boolean=} fast - * + /** + * Hide the agent + * @param {boolean} [fast] - If true, hide immediately without animation + * @param {Function} [callback] - Called when hide is complete */ hide (fast, callback) { this._hidden = true; @@ -60,14 +67,18 @@ export default class Agent { }) } - + /** + * Move the agent to a specific position + * @param {number} x - Target X coordinate + * @param {number} y - Target Y coordinate + * @param {number} [duration=1000] - Movement duration in milliseconds + */ moveTo (x, y, duration) { let dir = this._getDirection(x, y); let anim = 'Move' + dir; if (duration === undefined) duration = 1000; this._addToQueue(function (complete) { - // the simple case if (duration === 0) { this._el.style.top = y + 'px'; this._el.style.left = x + 'px'; @@ -76,21 +87,17 @@ export default class Agent { return; } - // no animations if (!this.hasAnimation(anim)) { this._animate(this._el, { top: y, left: x }, duration, complete); return; } let callback = (name, state) => { - // when exited, complete if (state === Animator.States.EXITED) { complete(); } - // if waiting, if (state === Animator.States.WAITING) { this._animate(this._el, { top: y, left: x }, duration, () => { - // after we're done with the movement, do the exit animation this._animator.exitAnimation(); }); } @@ -100,6 +107,14 @@ export default class Agent { }, this); } + /** + * Animate element properties over time using requestAnimationFrame + * @param {HTMLElement} element - Element to animate + * @param {Object} props - Properties to animate (e.g., {top: 100, left: 200}) + * @param {number} duration - Animation duration in milliseconds + * @param {Function} [callback] - Called when animation completes + * @private + */ _animate(element, props, duration, callback) { const start = performance.now(); const startProps = {}; @@ -130,9 +145,14 @@ export default class Agent { requestAnimationFrame(animate); } + /** + * Internal animation playback that handles idle animation interruption + * @param {string} animation - Animation name + * @param {Function} callback - State change callback + * @private + */ _playInternal (animation, callback) { - - // if we're inside an idle animation, + // Wait for idle animation to complete before starting new animation if (this._isIdleAnimation() && this._idleDfd && this._idleDfd.state === 'pending') { this._idleDfd.then(() => { this._playInternal(animation, callback); @@ -142,15 +162,21 @@ export default class Agent { this._animator.showAnimation(animation, callback); } + /** + * Play a named animation + * @param {string} animation - Animation name + * @param {number} [timeout=5000] - Timeout in milliseconds before auto-exiting + * @param {Function} [cb] - Callback when animation completes + * @returns {boolean} - True if animation exists and was queued + */ play (animation, timeout, cb) { if (!this.hasAnimation(animation)) return false; if (timeout === undefined) timeout = 5000; - this._addToQueue(function (complete) { let completed = false; - // handle callback + let callback = function (name, state) { if (state === Animator.States.EXITED) { completed = true; @@ -159,11 +185,9 @@ export default class Agent { } }; - // if has timeout, register a timeout function if (timeout) { window.setTimeout(() => { if (completed) return; - // exit after timeout this._animator.exitAnimation(); }, timeout) } @@ -174,12 +198,11 @@ export default class Agent { return true; } - /*** - * - * @param {Boolean=} fast + /** + * Show the agent + * @param {boolean} [fast] - If true, show immediately without animation */ show (fast) { - this._hidden = false; if (fast) { this._el.style.display = 'block'; @@ -199,9 +222,10 @@ export default class Agent { return this.play('Show'); } - /*** - * - * @param {String} text + /** + * Make the agent speak text in a speech balloon + * @param {string} text - Text to display + * @param {boolean} [hold] - If true, keep balloon open until manually closed */ speak (text, hold) { this._addToQueue(function (complete) { @@ -209,14 +233,17 @@ export default class Agent { }, this); } - - /*** - * Close the current balloon + /** + * Close the current speech balloon */ closeBalloon () { this._balloon.hide(); } + /** + * Add a delay to the action queue + * @param {number} [time=250] - Delay in milliseconds + */ delay (time) { time = time || 250; @@ -226,61 +253,59 @@ export default class Agent { }); } - /*** - * Skips the current animation + /** + * Skip the current animation */ stopCurrent () { this._animator.exitAnimation(); this._balloon.close(); } - + /** + * Stop all animations and clear the queue + */ stop () { - // clear the queue this._queue.clear(); this._animator.exitAnimation(); this._balloon.hide(); } - /*** - * - * @param {String} name - * @returns {Boolean} + /** + * Check if an animation exists + * @param {string} name - Animation name + * @returns {boolean} */ hasAnimation (name) { return this._animator.hasAnimation(name); } - /*** - * Gets a list of animation names - * - * @return {Array.} + /** + * Get list of all available animations + * @returns {string[]} */ animations () { return this._animator.animations(); } - /*** - * Play a random animation - * @return {Boolean} + /** + * Play a random non-idle animation + * @returns {boolean} */ animate () { let animations = this.animations(); let anim = animations[Math.floor(Math.random() * animations.length)]; - // skip idle animations + if (anim.indexOf('Idle') === 0) { return this.animate(); } return this.play(anim); } - /**************************** Utils ************************************/ - - /*** - * - * @param {Number} x - * @param {Number} y - * @return {String} + /** + * Calculate direction from agent to a point + * @param {number} x - Target X coordinate + * @param {number} y - Target Y coordinate + * @returns {string} - Direction: 'Up', 'Down', 'Left', 'Right', or 'Top' * @private */ _getDirection (x, y) { @@ -291,37 +316,38 @@ export default class Agent { let centerX = (rect.left + w / 2); let centerY = (rect.top + h / 2); - let a = centerY - y; let b = centerX - x; let r = Math.round((180 * Math.atan2(a, b)) / Math.PI); - // Left and Right are for the character, not the screen :-/ + // Note: Left and Right are from the character's perspective if (-45 <= r && r < 45) return 'Right'; if (45 <= r && r < 135) return 'Up'; if (135 <= r && r <= 180 || -180 <= r && r < -135) return 'Left'; if (-135 <= r && r < -45) return 'Down'; - // sanity check return 'Top'; } - /**************************** Queue and Idle handling ************************************/ - - /*** - * Handle empty queue. - * We need to transition the animation to an idle state + /** + * Handle empty queue by transitioning to idle animation * @private */ _onQueueEmpty () { if (this._hidden || this._isIdleAnimation()) return; + let idleAnim = this._getIdleAnimation(); this._idleDfd = this._createDeferred(); this._animator.showAnimation(idleAnim, this._onIdleComplete.bind(this)); } + /** + * Create a deferred promise with exposed resolve/reject + * @returns {Promise} - Promise with resolve, reject, and state properties + * @private + */ _createDeferred() { let resolve, reject; const promise = new Promise((res, rej) => { @@ -335,15 +361,21 @@ export default class Agent { return promise; } + /** + * Handle idle animation completion + * @param {string} name - Animation name + * @param {number} state - Animation state + * @private + */ _onIdleComplete (name, state) { if (state === Animator.States.EXITED) { this._idleDfd.resolve(); } } - /*** - * Is the current animation is Idle? - * @return {Boolean} + /** + * Check if currently playing an idle animation + * @returns {boolean} * @private */ _isIdleAnimation () { @@ -351,10 +383,9 @@ export default class Agent { return c && c.indexOf('Idle') === 0; } - /** - * Gets a random Idle animation - * @return {String} + * Get a random idle animation name + * @returns {string} * @private */ _getIdleAnimation () { @@ -367,29 +398,36 @@ export default class Agent { } } - // pick one let idx = Math.floor(Math.random() * r.length); return r[idx]; } - /**************************** Events ************************************/ - + /** + * Setup event listeners for resizing and interaction + * @private + */ _setupEvents () { window.addEventListener('resize', this.reposition.bind(this)); - this._el.addEventListener('mousedown', this._onMouseDown.bind(this)); - this._el.addEventListener('dblclick', this._onDoubleClick.bind(this)); } + /** + * Handle double-click to trigger ClickedOn animation or random animation + * @private + */ _onDoubleClick () { if (!this.play('ClickedOn')) { this.animate(); } } + /** + * Reposition agent to stay within viewport bounds + */ reposition () { if (this._el.style.display === 'none') return; + let o = this._el.getBoundingClientRect(); let bH = this._el.offsetHeight; let bW = this._el.offsetWidth; @@ -400,6 +438,7 @@ export default class Agent { let top = o.top; let left = o.left; let m = 5; + if (top - m < 0) { top = m; } else if ((top + bH + m) > wH) { @@ -414,20 +453,25 @@ export default class Agent { this._el.style.left = left + 'px'; this._el.style.top = top + 'px'; - // reposition balloon this._balloon.reposition(); } + /** + * Handle mouse down to start dragging + * @param {MouseEvent} e + * @private + */ _onMouseDown (e) { e.preventDefault(); this._startDrag(e); } - - /**************************** Drag ************************************/ - + /** + * Initialize drag operation + * @param {MouseEvent} e + * @private + */ _startDrag (e) { - // pause animations this.pause(); this._balloon.hide(true); this._offset = this._calculateClickOffset(e); @@ -441,6 +485,12 @@ export default class Agent { this._dragUpdateLoop = window.setTimeout(this._updateLocation.bind(this), 10); } + /** + * Calculate offset between click position and agent position + * @param {MouseEvent} e + * @returns {{top: number, left: number}} + * @private + */ _calculateClickOffset (e) { let mouseX = e.pageX; let mouseY = e.pageY; @@ -449,15 +499,23 @@ export default class Agent { top: mouseY - (o.top + window.pageYOffset), left: mouseX - (o.left + window.pageXOffset) } - } + /** + * Update agent position during drag + * @private + */ _updateLocation () { this._el.style.top = this._targetY + 'px'; this._el.style.left = this._targetX + 'px'; this._dragUpdateLoop = window.setTimeout(this._updateLocation.bind(this), 10); } + /** + * Handle mouse move during drag + * @param {MouseEvent} e + * @private + */ _dragMove (e) { e.preventDefault(); let x = e.clientX - this._offset.left; @@ -466,31 +524,42 @@ export default class Agent { this._targetY = y; } + /** + * Complete drag operation + * @private + */ _finishDrag () { window.clearTimeout(this._dragUpdateLoop); - // remove handles window.removeEventListener('mousemove', this._moveHandle); window.removeEventListener('mouseup', this._upHandle); - // resume animations + this._balloon.show(); this.reposition(); this.resume(); - } + /** + * Add a function to the action queue + * @param {Function} func - Function to queue + * @param {Object} [scope] - Scope to bind function to + * @private + */ _addToQueue (func, scope) { if (scope) func = func.bind(scope); this._queue.queue(func); } - /**************************** Pause and Resume ************************************/ - + /** + * Pause animations and balloon + */ pause () { this._animator.pause(); this._balloon.pause(); - } + /** + * Resume animations and balloon + */ resume () { this._animator.resume(); this._balloon.resume(); diff --git a/lib/animator.js b/lib/animator.js index e34b157..9af0a2b 100755 --- a/lib/animator.js +++ b/lib/animator.js @@ -1,5 +1,13 @@ +/** + * Animator class handles frame-by-frame animation playback using sprite sheets + */ export default class Animator { - + /** + * @param {HTMLElement} el - The element to animate + * @param {string} path - Path to the agent's asset directory + * @param {Object} data - Agent animation data (frames, overlays, sounds) + * @param {Object} sounds - Map of sound names to audio URLs + */ constructor (el, path, data, sounds) { this._el = el; this._data = data; @@ -17,6 +25,8 @@ export default class Animator { let curr = this._el; this._setupElement(this._el); + + // Create overlay elements for multi-layer animations for (let i = 1; i < this._data.overlayCount; i++) { let inner = this._setupElement(document.createElement('div')); curr.appendChild(inner); @@ -25,6 +35,12 @@ export default class Animator { } } + /** + * Configure an element for sprite sheet animation + * @param {HTMLElement} el - Element to setup + * @returns {HTMLElement} + * @private + */ _setupElement (el) { let frameSize = this._data.framesize; el.style.display = 'none'; @@ -35,6 +51,10 @@ export default class Animator { return el; } + /** + * Get list of all available animation names + * @returns {string[]} + */ animations () { let r = []; let d = this._data.animations; @@ -44,25 +64,41 @@ export default class Animator { return r; } + /** + * Preload audio files for animations + * @param {Object} sounds - Map of sound names to URLs + */ preloadSounds (sounds) { - for (let i = 0; i < this._data.sounds.length; i++) { let snd = this._data.sounds[i]; let uri = sounds[snd]; if (!uri) continue; this._sounds[snd] = new Audio(uri); - } } + /** + * Check if an animation exists + * @param {string} name - Animation name + * @returns {boolean} + */ hasAnimation (name) { return !!this._data.animations[name]; } + /** + * Signal that current animation should exit at next opportunity + */ exitAnimation () { this._exiting = true; } + /** + * Start playing an animation + * @param {string} animationName - Name of the animation to play + * @param {Function} stateChangeCallback - Called with (name, state) when animation state changes + * @returns {boolean} - True if animation exists and was started + */ showAnimation (animationName, stateChangeCallback) { this._exiting = false; @@ -73,7 +109,6 @@ export default class Animator { this._currentAnimation = this._data.animations[animationName]; this.currentAnimationName = animationName; - if (!this._started) { this._step(); this._started = true; @@ -86,6 +121,10 @@ export default class Animator { return true; } + /** + * Render the current frame by positioning sprite sheet backgrounds + * @private + */ _draw () { let images = []; if (this._currentFrame) images = this._currentFrame.images || []; @@ -100,21 +139,26 @@ export default class Animator { else { this._overlays[i].style.display = 'none'; } - } } + /** + * Determine the next frame index based on branching logic + * @returns {number|undefined} + * @private + */ _getNextAnimationFrame () { if (!this._currentAnimation) return undefined; - // No current frame. start animation. if (!this._currentFrame) return 0; + let currentFrame = this._currentFrame; let branching = this._currentFrame.branching; - + // Exit branching takes priority if (this._exiting && currentFrame.exitBranch !== undefined) { return currentFrame.exitBranch; } + // Weighted random branching else if (branching) { let rnd = Math.random() * 100; for (let i = 0; i < branching.branches.length; i++) { @@ -122,7 +166,6 @@ export default class Animator { if (rnd <= branch.weight) { return branch.frameIndex; } - rnd -= branch.weight; } } @@ -130,7 +173,10 @@ export default class Animator { return this._currentFrameIndex + 1; } - + /** + * Play the sound associated with the current frame + * @private + */ _playSound () { let s = this._currentFrame.sound; if (!s) return; @@ -138,18 +184,27 @@ export default class Animator { if (audio) audio.play(); } + /** + * Check if we're at the last frame of the animation + * @returns {boolean} + * @private + */ _atLastFrame () { return this._currentFrameIndex >= this._currentAnimation.frames.length - 1; } - + /** + * Advance to the next animation frame + * @private + */ _step () { if (!this._currentAnimation) return; + let newFrameIndex = Math.min(this._getNextAnimationFrame(), this._currentAnimation.frames.length - 1); let frameChanged = !this._currentFrame || this._currentFrameIndex !== newFrameIndex; this._currentFrameIndex = newFrameIndex; - // always switch frame data, unless we're at the last frame of an animation with a useExitBranching flag. + // Update frame data unless we're waiting at the last frame with exit branching if (!(this._atLastFrame() && this._currentAnimation.useExitBranching)) { this._currentFrame = this._currentAnimation.frames[this._currentFrameIndex]; } @@ -159,8 +214,7 @@ export default class Animator { this._loop = window.setTimeout(this._step.bind(this), this._currentFrame.duration); - - // fire events if the frames changed and we reached an end + // Fire callbacks when animation reaches an end state if (this._endCallback && frameChanged && this._atLastFrame()) { if (this._currentAnimation.useExitBranching && !this._exiting) { this._endCallback(this.currentAnimationName, Animator.States.WAITING); @@ -171,14 +225,14 @@ export default class Animator { } } - /*** + /** * Pause animation execution */ pause () { window.clearTimeout(this._loop); } - /*** + /** * Resume animation */ resume () { @@ -186,5 +240,11 @@ export default class Animator { } } - -Animator.States = { WAITING: 1, EXITED: 0 }; \ No newline at end of file +/** + * Animation state constants + * @enum {number} + */ +Animator.States = { + WAITING: 1, // Animation is waiting (e.g., for movement to complete) + EXITED: 0 // Animation has completed and exited +}; \ No newline at end of file diff --git a/lib/balloon.js b/lib/balloon.js index f52a79b..d680ef1 100755 --- a/lib/balloon.js +++ b/lib/balloon.js @@ -1,7 +1,12 @@ +/** + * Balloon class for displaying speech bubbles next to the agent + */ export default class Balloon { + /** + * @param {HTMLElement} targetEl - The agent element to attach the balloon to + */ constructor (targetEl) { this._targetEl = targetEl; - this._hidden = true; this._setup(); this.WORD_SPEAK_TIME = 200; @@ -9,6 +14,10 @@ export default class Balloon { this._BALLOON_MARGIN = 15; } + /** + * Create and append balloon DOM elements + * @private + */ _setup () { this._balloon = document.createElement('div'); this._balloon.className = 'clippy-balloon'; @@ -26,6 +35,9 @@ export default class Balloon { document.body.appendChild(this._balloon); } + /** + * Try different positions to keep balloon on screen + */ reposition () { let sides = ['top-left', 'top-right', 'bottom-left', 'bottom-right']; @@ -36,9 +48,9 @@ export default class Balloon { } } - /*** - * - * @param side + /** + * Position the balloon relative to the agent + * @param {string} side - One of: top-left, top-right, bottom-left, bottom-right * @private */ _position (side) { @@ -54,22 +66,18 @@ export default class Balloon { let left, top; switch (side) { case 'top-left': - // right side of the balloon next to the right side of the agent left = o.left + w - bW; top = o.top - bH - this._BALLOON_MARGIN; break; case 'top-right': - // left side of the balloon next to the left side of the agent left = o.left; top = o.top - bH - this._BALLOON_MARGIN; break; case 'bottom-right': - // right side of the balloon next to the right side of the agent left = o.left; top = o.top + h + this._BALLOON_MARGIN; break; case 'bottom-left': - // left side of the balloon next to the left side of the agent left = o.left + w - bW; top = o.top + h + this._BALLOON_MARGIN; break; @@ -80,6 +88,11 @@ export default class Balloon { this._balloon.classList.add('clippy-' + side); } + /** + * Check if balloon is positioned outside the viewport + * @returns {boolean} + * @private + */ _isOut () { let o = this._balloon.getBoundingClientRect(); let bH = this._balloon.offsetHeight; @@ -95,16 +108,21 @@ export default class Balloon { return (top + bH + m) > wH || (left + bW + m) > wW; } + /** + * Display text in the balloon with typewriter effect + * @param {Function} complete - Callback when speaking is done + * @param {string} text - Text to display + * @param {boolean} hold - If true, keep balloon open after speaking + */ speak (complete, text, hold) { this._hidden = false; this.show(); let c = this._content; - // set height to auto + + // Measure the text dimensions by temporarily setting it c.style.height = 'auto'; c.style.width = 'auto'; - // add the text c.textContent = text; - // set height c.style.height = c.offsetHeight + 'px'; c.style.width = c.offsetWidth + 'px'; c.textContent = ''; @@ -114,11 +132,18 @@ export default class Balloon { this._sayWords(text, hold, complete); } + /** + * Show the balloon + */ show () { if (this._hidden) return; this._balloon.style.display = 'block'; } + /** + * Hide the balloon + * @param {boolean} fast - If true, hide immediately without delay + */ hide (fast) { if (fast) { this._balloon.style.display = 'none'; @@ -128,6 +153,10 @@ export default class Balloon { this._hiding = window.setTimeout(this._finishHideBalloon.bind(this), this.CLOSE_BALLOON_DELAY); } + /** + * Complete the hide operation + * @private + */ _finishHideBalloon () { if (this._active) return; this._balloon.style.display = 'none'; @@ -135,6 +164,13 @@ export default class Balloon { this._hiding = null; } + /** + * Animate text appearing word by word + * @param {string} text - Text to animate + * @param {boolean} hold - If true, keep balloon open after speaking + * @param {Function} complete - Callback when animation is done + * @private + */ _sayWords (text, hold, complete) { this._active = true; this._hold = hold; @@ -162,6 +198,9 @@ export default class Balloon { this._addWord(); } + /** + * Close the balloon and trigger completion callback if held + */ close () { if (this._active) { this._hold = false; @@ -170,6 +209,9 @@ export default class Balloon { } } + /** + * Pause the balloon animation and hide timer + */ pause () { window.clearTimeout(this._loop); if (this._hiding) { @@ -178,6 +220,9 @@ export default class Balloon { } } + /** + * Resume the balloon animation or hide timer + */ resume () { if (this._addWord) { this._addWord(); diff --git a/lib/load.js b/lib/load.js index a3d412a..8888651 100755 --- a/lib/load.js +++ b/lib/load.js @@ -1,16 +1,22 @@ import Agent from './agent' +// Cache for loaded resources const _maps = {}; const _sounds = {}; const _data = {}; const _dataCallbacks = {}; const _soundsCallbacks = {}; +/** + * Load a sprite sheet map image + * @param {string} path - Path to agent directory + * @returns {Promise} - Resolves when image is loaded + * @private + */ function _loadMap(path) { let dfd = _maps[path]; if (dfd) return dfd; - // set dfd if not defined dfd = _maps[path] = new Promise((resolve, reject) => { let src = path + '/map.png'; let img = new Image(); @@ -18,18 +24,23 @@ function _loadMap(path) { img.onload = resolve; img.onerror = reject; - // start loading the map; img.setAttribute('src', src); }); return dfd; } +/** + * Load sound files for an agent + * @param {string} name - Agent name + * @param {string} path - Path to agent directory + * @returns {Promise} - Resolves with sound map or empty object + * @private + */ function _loadSounds(name, path) { let dfd = _sounds[name]; if (dfd) return dfd; - // set dfd if not defined dfd = _sounds[name] = new Promise((resolve, reject) => { let audio = document.createElement('audio'); let canPlayMp3 = !!audio.canPlayType && "" !== audio.canPlayType('audio/mpeg'); @@ -39,9 +50,7 @@ function _loadSounds(name, path) { resolve({}); } else { let src = path + (canPlayMp3 ? '/sounds-mp3.js' : '/sounds-ogg.js'); - // Store resolve/reject for later use _soundsCallbacks[name] = { resolve, reject }; - // load _loadScript(src); } }); @@ -49,23 +58,32 @@ function _loadSounds(name, path) { return dfd; } +/** + * Load agent animation data + * @param {string} name - Agent name + * @param {string} path - Path to agent directory + * @returns {Promise} - Resolves with agent data + * @private + */ function _loadAgent(name, path) { let dfd = _data[name]; if (dfd) return dfd; - // Create the promise and store it dfd = _data[name] = new Promise((resolve, reject) => { - // Store resolve/reject for external access via ready() _dataCallbacks[name] = { resolve, reject }; }); let src = path + '/agent.js'; - _loadScript(src); return dfd; } +/** + * Dynamically load a script file + * @param {string} src - Script URL + * @private + */ function _loadScript(src) { let script = document.createElement('script'); script.setAttribute('src', src); @@ -75,6 +93,13 @@ function _loadScript(src) { document.head.appendChild(script); } +/** + * Load an agent with all its assets + * @param {string} name - Agent name (e.g., 'Clippy', 'Merlin') + * @param {Function} successCb - Called with initialized Agent instance + * @param {Function} [failCb] - Called if loading fails + * @param {string} [base_path] - Custom base path for agent assets + */ export function load(name, successCb, failCb, base_path) { base_path = base_path || window.CLIPPY_CDN || './assets/agents/' @@ -89,12 +114,10 @@ export function load(name, successCb, failCb, base_path) { }); let sounds; - soundsDfd.then(function (d) { sounds = d; }); - // wrapper to the success callback let cb = function () { let a = new Agent(path, data, sounds); successCb(a); @@ -103,6 +126,12 @@ export function load(name, successCb, failCb, base_path) { Promise.all([mapDfd, agentDfd, soundsDfd]).then(cb).catch(failCb); } +/** + * Called by agent.js files to register agent data + * This function is called by dynamically loaded agent scripts + * @param {string} name - Agent name + * @param {Object} data - Agent animation data + */ export function ready(name, data) { let callbacks = _dataCallbacks[name]; if (callbacks && callbacks.resolve) { @@ -110,6 +139,12 @@ export function ready(name, data) { } } +/** + * Called by sound files to register sound data + * This function is called by dynamically loaded sound scripts + * @param {string} name - Agent name + * @param {Object} data - Sound URL mappings + */ export function soundsReady(name, data) { let callbacks = _soundsCallbacks[name]; if (callbacks && callbacks.resolve) { diff --git a/lib/queue.js b/lib/queue.js index f099364..55c3ff1 100755 --- a/lib/queue.js +++ b/lib/queue.js @@ -1,13 +1,18 @@ +/** + * Queue class for managing sequential async operations + */ export default class Queue { + /** + * @param {Function} onEmptyCallback - Called when queue becomes empty + */ constructor (onEmptyCallback) { this._queue = []; this._onEmptyCallback = onEmptyCallback; } - /*** - * - * @param {function(Function)} func - * @returns {Promise} + /** + * Add a function to the queue + * @param {Function} func - Function that receives a completion callback */ queue (func) { this._queue.push(func); @@ -17,9 +22,11 @@ export default class Queue { } } + /** + * Process the next item in the queue + * @private + */ _progressQueue () { - - // stop if nothing left in queue if (!this._queue.length) { this._onEmptyCallback(); return; @@ -28,15 +35,20 @@ export default class Queue { let f = this._queue.shift(); this._active = true; - // execute function let completeFunction = this.next.bind(this); f(completeFunction); } + /** + * Clear all items from the queue + */ clear () { this._queue = []; } + /** + * Mark current operation as complete and progress to next item + */ next () { this._active = false; this._progressQueue(); diff --git a/package.json b/package.json index 49435d5..13be9db 100755 --- a/package.json +++ b/package.json @@ -2,6 +2,7 @@ "name": "clippyjs", "version": "0.0.3", "description": "Add Clippy or his friends to any website for instant nostalgia.", + "type": "module", "main": "dist/clippy.js", "module": "dist/clippy.esm.js", "scripts": { From e88407b4ff56dd4dbe95607ca411f617b1a1243c Mon Sep 17 00:00:00 2001 From: Michael Hardeman Date: Tue, 7 Oct 2025 17:28:39 -0400 Subject: [PATCH 3/3] Adding Ollama chat Added a demo file where you can chat with a local ollama powered AI. --- demo-ollama.html | 688 +++++++++++++++++++++++++++++++++++++++++++++++ yarn.lock | 5 + 2 files changed, 693 insertions(+) create mode 100644 demo-ollama.html diff --git a/demo-ollama.html b/demo-ollama.html new file mode 100644 index 0000000..d2d3121 --- /dev/null +++ b/demo-ollama.html @@ -0,0 +1,688 @@ + + + + + ClippyJS + Ollama Chat + + + + +
+ +
+
+
+ ⚙️ + Settings +
+
+ + + +
+
+
+
+ Connection Settings +
+ + +
+
+ + +
+
+ +
+ Assistant Selection +
+ + +
+
+
+
+ + +
+
+
+ 💬 + Clippy Chat +
+
+ + + +
+
+
+
+
+

╔═══════════════════════════╗

+

║ Welcome to ClippyChat! ║

+

║ Powered by Ollama ║

+

╚═══════════════════════════╝

+

Loading your assistant...

+
+
+ +
+
+ + +
+ +
+
+
+
+ + Initializing... +
+
+
+
+ + + + + \ No newline at end of file diff --git a/yarn.lock b/yarn.lock index bc64fc9..33acfc6 100755 --- a/yarn.lock +++ b/yarn.lock @@ -50,6 +50,11 @@ resolved "https://registry.npmjs.org/@rollup/rollup-linux-x64-gnu/-/rollup-linux-x64-gnu-4.52.4.tgz" integrity sha512-Wi6AXf0k0L7E2gteNsNHUs7UMwCIhsCTs6+tqQ5GPwVRWMaflqGec4Sd8n6+FNFDw9vGcReqk2KzBDhCa1DLYg== +"@rollup/rollup-linux-x64-musl@4.52.4": + version "4.52.4" + resolved "https://registry.npmjs.org/@rollup/rollup-linux-x64-musl/-/rollup-linux-x64-musl-4.52.4.tgz" + integrity sha512-dtBZYjDmCQ9hW+WgEkaffvRRCKm767wWhxsFW3Lw86VXz/uJRuD438/XvbZT//B96Vs8oTA8Q4A0AfHbrxP9zw== + "@types/estree@1.0.8": version "1.0.8" resolved "https://registry.npmjs.org/@types/estree/-/estree-1.0.8.tgz"