This commit is contained in:
Luis Leiva 2017-11-19 21:39:06 +01:00
parent ee21fddc85
commit 56f7f91747
12 changed files with 594 additions and 561 deletions

26
.eslintrc.js Normal file
View File

@ -0,0 +1,26 @@
module.exports = {
'extends': 'google',
'env': {
'browser': true,
},
'rules': {
// --- BEGIN Disabled rules ---
'no-var': 0,
'padded-blocks': 0,
'prefer-rest-params': 0,
'spaced-comment': 0,
'guard-for-in': 0,
'one-var': 0,
'no-multi-spaces': 0,
'require-jsdoc': 0,
// --- BEGIN Errors ---
'no-tabs': 2,
'indent': ['error', 2],
'quotes': 2,
// --- BEGIN Warnings ---
'max-len': [1, 160],
'comma-dangle': 1,
'key-spacing': 1,
'valid-jsdoc': 1,
},
};

File diff suppressed because one or more lines are too long

View File

@ -1 +1 @@
!function(a){function b(a,b){b||(b=a.data(p).options),b.cssCursors&&(a[0].style.cursor=b.interactive?"pointer":"not-allowed"),this.onselectstart=function(){return!1}}function c(a,b){b=b.split(".");for(var c=0;c<b.length;c++){var d=b[c];a=a[d]}return a}function d(b){var c=a(b.target),d=c.offset();return{x:Math.round(b.pageX-d.left),y:Math.round(b.pageY-d.top)}}function e(a,b,c){var d=b.coords[a],e=(new Date).getTime();if(b.options.relTimestamps&&(0===b.strokes.length&&0===d.length&&(b.timestamp=e),e-=b.timestamp),d.push([c.x,c.y,e,+b.sketch.isDrawing]),b.options.filterCoords&&d.length>1){var f=d.length-1,g=d[f],h=d[f-1];g[0]==h[0]&&g[1]==h[1]&&d.splice(f,1)}}function f(a){return a.originalEvent.touches?!1:void l(a)}function g(a){return a.originalEvent.touches?!1:void m(a)}function h(a){return a.originalEvent.touches?!1:void n(a)}function i(a){o(a,l),a.preventDefault()}function j(a){o(a,m),a.preventDefault()}function k(a){o(a,n),a.preventDefault()}function l(b){if(3===b.which)return!1;var c=b.identifier||0,f=a(b.target),g=f.data(p),h=g.options;if(h.interactive){g.sketch.isDrawing=!0;var i=d(b);h.graphics.firstPointSize>0&&g.sketch.beginFill(h.graphics.fillStyle).fillCircle(i.x,i.y,h.graphics.firstPointSize).endFill();var j=g.coords[c];j||(j=[]),j.length>0&&g.strokes.push(j),g.coords[c]=[],e(c,g,i),"function"==typeof h.events.mousedown&&h.events.mousedown(f,g,b)}}function m(b){var c=b.identifier||0,f=a(b.target),g=f.data(p),h=g.options;if(h.interactive&&(h.mouseupMovements&&0!==g.strokes.length||g.sketch.isDrawing)){var i=d(b),j=g.coords[c],k=j[j.length-1];if(k){var l=g.sketch.beginPath();g.sketch.isDrawing?l.lineStyle(h.graphics.strokeStyle,h.graphics.lineWidth):h.mouseupMovements.visible!==!1&&l.lineStyle(h.mouseupMovements.strokeStyle||"#DDD",h.mouseupMovements.lineWidth||1),l.line(k[0],k[1],i.x,i.y).stroke().closePath()}e(c,g,i),"function"==typeof h.events.mousemove&&h.events.mousemove(f,g,b)}}function n(b){var c=b.identifier||0,d=a(b.target),e=d.data(p),f=e.options;f.interactive&&(e.sketch.isDrawing=!1,e.strokes.push(e.coords[c]),e.coords[c]=[],"function"==typeof f.events.mouseup&&f.events.mouseup(d,e,b))}function o(b,c){var d=a(b.target),e=d.data(p),f=e.options;if(f.multitouch)for(var g=b.originalEvent.changedTouches,h=0;h<g.length;h++){var i=g[h];i.type=b.type,i.identifier=h,c(i)}else{var i=b.originalEvent.touches[0];i.type=b.type,i.identifier=0,c(i)}}var p="sketchable",q={init:function(c){var d=a.extend(!0,{},a.fn.sketchable.defaults,c||{});return this.each(function(){var c=a(this),e=c.data(p);e||(c.bind("mousedown",f),c.bind("mousemove",g),c.bind("mouseup",h),c.bind("touchstart",i),c.bind("touchmove",j),c.bind("touchend",k),b(c,d));var l=new jSketch(this,d.graphics);c.data(p,{strokes:[],coords:{},timestamp:(new Date).getTime(),sketch:l,options:d}),d.events&&"function"==typeof d.events.init&&d.events.init(c,c.data(p));for(var m in a.fn.sketchable.plugins)a.fn.sketchable.plugins[m](c)})},config:function(c){return c?this.each(function(){var d=a(this),e=d.data(p);e.options=a.extend(!0,{},a.fn.sketchable.defaults,e.options,c),b(d)}):a(this).data(p)},strokes:function(b){if(b)return this.each(function(){var c=a(this),d=c.data(p);d.strokes=b});var c=a(this).data(p);return c.strokes},handler:function(b){return this.each(function(){var c=a(this),d=c.data(p);b(c,d)})},clear:function(){return this.each(function(){var b=a(this),c=b.data(p)||{},d=c.options;c.sketch&&(c.sketch.clear(),c.strokes=[],c.coords={}),d&&"function"==typeof d.events.clear&&d.events.clear(b,c)})},reset:function(b){return this.each(function(){var c=a(this),d=c.data(p)||{},e=d.options;c.sketchable("destroy").sketchable(b),e&&"function"==typeof e.events.reset&&e.events.reset(c,d)})},destroy:function(){return this.each(function(){var b=a(this),c=b.data(p)||{},d=c.options;b.unbind("mouseup",h),b.unbind("mousemove",g),b.unbind("mousedown",f),b.unbind("touchstart",i),b.unbind("touchmove",j),b.unbind("touchend",k),b.removeData(p),d&&"function"==typeof d.events.destroy&&d.events.destroy(b,c)})}};a.fn.sketchable=function(b){var d=Array.prototype.slice.call(arguments,1);if("object"==typeof b||!b)return q.init.apply(this,arguments);if(b.indexOf(".")>-1){var e=c(q,b);return e.apply(this,d)}return q[b]?q[b].apply(this,d):(a.error("Unknown method: "+b),this)},a.fn.sketchable.api=q,a.fn.sketchable.plugins={},a.fn.sketchable.defaults={interactive:!0,mouseupMovements:!1,relTimestamps:!1,multitouch:!0,cssCursors:!0,filterCoords:!1,events:{},graphics:{firstPointSize:3,lineWidth:3,strokeStyle:"#F0F",fillStyle:"#F0F",lineCap:"round",lineJoin:"round",miterLimit:10}}}(jQuery); !function(a){function b(a,b){b||(b=a.data(p).options),b.cssCursors&&(a[0].style.cursor=b.interactive?"pointer":"not-allowed"),this.onselectstart=function(){return!1}}function c(a,b){b=b.split(".");for(var c=0;c<b.length;c++){var d=b[c];a=a[d]}return a}function d(b){var c=a(b.target),d=c.offset();return{x:Math.round(b.pageX-d.left),y:Math.round(b.pageY-d.top)}}function e(a,b,c){var d=b.coords[a],e=(new Date).getTime();if(b.options.relTimestamps&&(0===b.strokes.length&&0===d.length&&(b.timestamp=e),e-=b.timestamp),d.push([c.x,c.y,e,+b.sketch.isDrawing]),b.options.filterCoords&&d.length>1){var f=d.length-1,g=d[f],h=d[f-1];g[0]==h[0]&&g[1]==h[1]&&d.splice(f,1)}}function f(a){return a.originalEvent.touches?!1:void l(a)}function g(a){return a.originalEvent.touches?!1:void m(a)}function h(a){return a.originalEvent.touches?!1:void n(a)}function i(a){o(a,l),a.preventDefault()}function j(a){o(a,m),a.preventDefault()}function k(a){o(a,n),a.preventDefault()}function l(b){if(3===b.which)return!1;var c=b.identifier||0,f=a(b.target),g=f.data(p),h=g.options;if(h.interactive){var i=d(b);"function"==typeof h.events.mousedownBefore&&h.events.mousedownBefore(f,g,b),h.graphics.firstPointSize>0&&g.sketch.beginFill(h.graphics.fillStyle).fillCircle(i.x,i.y,h.graphics.firstPointSize).endFill(),g.sketch.isDrawing=!0,g.sketch.beginPath();var j=g.coords[c];j||(j=[]),j.length>0&&g.strokes.push(j),g.coords[c]=[],e(c,g,i),"function"==typeof h.events.mousedown&&h.events.mousedown(f,g,b)}}function m(b){var c=b.identifier||0,f=a(b.target),g=f.data(p),h=g.options;if(h.interactive&&(h.mouseupMovements&&0!==g.strokes.length||g.sketch.isDrawing)){var i=d(b);"function"==typeof h.events.mousemoveBefore&&h.events.mousemoveBefore(f,g,b);var j=g.coords[c],k=j[j.length-1];if(k){var l=g.sketch;g.sketch.isDrawing?l.lineStyle(h.graphics.strokeStyle,h.graphics.lineWidth):h.mouseupMovements.visible!==!1&&l.lineStyle(h.mouseupMovements.strokeStyle||"#DDD",h.mouseupMovements.lineWidth||1),l.line(k[0],k[1],i.x,i.y).stroke()}e(c,g,i),"function"==typeof h.events.mousemove&&h.events.mousemove(f,g,b)}}function n(b){var c=b.identifier||0,d=a(b.target),e=d.data(p),f=e.options;f.interactive&&("function"==typeof f.events.mouseupBefore&&f.events.mouseupBefore(d,e,b),e.sketch.isDrawing=!1,e.sketch.closePath(),e.strokes.push(e.coords[c]),e.coords[c]=[],"function"==typeof f.events.mouseup&&f.events.mouseup(d,e,b))}function o(b,c){var d=a(b.target),e=d.data(p),f=e.options;if(f.multitouch)for(var g=b.originalEvent.changedTouches,h=0;h<g.length;h++){var i=g[h];i.type=b.type,i.identifier=h,c(i)}else{var i=b.originalEvent.touches[0];i.type=b.type,i.identifier=0,c(i)}}var p="sketchable",q={init:function(c){var d=a.extend(!0,{},a.fn.sketchable.defaults,c||{});return this.each(function(){var c=a(this),e=c.data(p);e||(c.bind("mousedown",f),c.bind("mousemove",g),c.bind("mouseup",h),c.bind("touchstart",i),c.bind("touchmove",j),c.bind("touchend",k),b(c,d));var l=new jSketch(this,d.graphics);c.data(p,{strokes:[],coords:{},timestamp:(new Date).getTime(),sketch:l,options:d}),"function"==typeof d.events.init&&d.events.init(c,c.data(p));for(var m in a.fn.sketchable.plugins)a.fn.sketchable.plugins[m](c)})},config:function(c){return c?this.each(function(){var d=a(this),e=d.data(p);e.options=a.extend(!0,{},a.fn.sketchable.defaults,e.options,c),b(d)}):a(this).data(p)},strokes:function(b){if(b)return this.each(function(){var c=a(this),d=c.data(p);d.strokes=b});var c=a(this).data(p);return c.strokes},handler:function(b){return this.each(function(){var c=a(this),d=c.data(p);b(c,d)})},clear:function(){return this.each(function(){var b=a(this),c=b.data(p),d=c.options;c.sketch&&(c.sketch.clear(),c.strokes=[],c.coords={}),"function"==typeof d.events.clear&&d.events.clear(b,c)})},reset:function(b){return this.each(function(){var c=a(this),d=c.data(p),e=d.options;c.sketchable("destroy").sketchable(b),"function"==typeof e.events.reset&&e.events.reset(c,d)})},destroy:function(){return this.each(function(){var b=a(this),c=b.data(p),d=c.options;b.unbind("mouseup",h),b.unbind("mousemove",g),b.unbind("mousedown",f),b.unbind("touchstart",i),b.unbind("touchmove",j),b.unbind("touchend",k),b.removeData(p),d&&"function"==typeof d.events.destroy&&d.events.destroy(b,c)})}};a.fn.sketchable=function(b){var d=Array.prototype.slice.call(arguments,1);if("object"==typeof b||!b)return q.init.apply(this,arguments);if(b.indexOf(".")>-1){var e=c(q,b);return e.apply(this,d)}return q[b]?q[b].apply(this,d):(a.error("Unknown method: "+b),this)},a.fn.sketchable.api=q,a.fn.sketchable.plugins={},a.fn.sketchable.defaults={interactive:!0,mouseupMovements:!1,relTimestamps:!1,multitouch:!0,cssCursors:!0,filterCoords:!1,events:{},graphics:{firstPointSize:3,lineWidth:3,strokeStyle:"#F0F",fillStyle:"#F0F",lineCap:"round",lineJoin:"round",miterLimit:10}}}(jQuery);

File diff suppressed because one or more lines are too long

View File

@ -1 +1 @@
!function(a){function b(a,b){if(!a)throw new Error("Sketchable requires a DOM element.");return"string"==typeof a&&(a=r.querySelector(a)),this.elem=a,this.init(b)}function c(b){var c=b.getBoundingClientRect(),d=r.body,e=r.documentElement,f=a.pageYOffset||e.scrollTop||d.scrollTop,g=a.pageXOffset||e.scrollLeft||d.scrollLeft,h=e.clientTop||d.clientTop||0,i=e.clientLeft||d.clientLeft||0,j=c.top+f-h,k=c.left+g-i;return{top:Math.round(j),left:Math.round(k)}}function d(a,b){b||(b=dataBind(a)[q].options),b.cssCursors&&(a.style.cursor=b.interactive?"pointer":"not-allowed"),a.onselectstart=function(){return!1}}function e(a){var b=a.target,d=c(b);return{x:Math.round(a.pageX-d.left),y:Math.round(a.pageY-d.top)}}function f(a,b,c){var d=b.coords[a],e=(new Date).getTime();if(b.options.relTimestamps&&(0===b.strokes.length&&0===d.length&&(b.timestamp=e),e-=b.timestamp),d.push([c.x,c.y,e,+b.sketch.isDrawing]),b.options.filterCoords&&d.length>1){var f=d.length-1,g=d[f],h=d[f-1];g[0]==h[0]&&g[1]==h[1]&&d.splice(f,1)}}function g(a){return a.touches?!1:void m(a)}function h(a){return a.touches?!1:void n(a)}function i(a){return a.touches?!1:void o(a)}function j(a){p(a,m),a.preventDefault()}function k(a){p(a,n),a.preventDefault()}function l(a){p(a,o),a.preventDefault()}function m(a){if(Event.isRightClick(a))return!1;var b=a.identifier||0,c=a.target,d=dataBind(c)[q],g=d.options;if(g.interactive){d.sketch.isDrawing=!0;var h=e(a);g.graphics.firstPointSize>0&&d.sketch.beginFill(g.graphics.fillStyle).fillCircle(h.x,h.y,g.graphics.firstPointSize).endFill();var i=d.coords[b];i||(i=[]),i.length>0&&d.strokes.push(i),d.coords[b]=[],f(b,d,h),"function"==typeof g.events.mousedown&&g.events.mousedown(c,d,a)}}function n(a){var b=a.identifier||0;if(elem=a.target,data=dataBind(elem)[q],options=data.options,options.interactive&&(options.mouseupMovements&&0!==data.strokes.length||data.sketch.isDrawing)){var c=e(a),d=data.coords[b],g=d[d.length-1];if(g){var h=data.sketch.beginPath();data.sketch.isDrawing?h.lineStyle(options.graphics.strokeStyle,options.graphics.lineWidth):options.mouseupMovements.visible!==!1&&h.lineStyle(options.mouseupMovements.strokeStyle||"#DDD",options.mouseupMovements.lineWidth||1),h.line(g[0],g[1],c.x,c.y).stroke().closePath()}f(b,data,c),"function"==typeof options.events.mousemove&&options.events.mousemove(elem,data,a)}}function o(a){var b=a.identifier||0;elem=a.target,data=dataBind(elem)[q],options=data.options,options.interactive&&(data.sketch.isDrawing=!1,data.strokes.push(data.coords[b]),data.coords[b]=[],"function"==typeof options.events.mouseup&&options.events.mouseup(elem,data,a))}function p(a,b){var c=a.target,d=dataBind(c)[q],e=d.options;if(e.multitouch)for(var f=a.changedTouches,g=0;g<f.length;g++){var h=f[g];h.type=a.type,h.identifier=g,b(h)}else{var h=a.touches[0];h.type=a.type,h.identifier=0,b(h)}a.preventDefault()}var q="sketchable",r=a.document;b.prototype={init:function(a){var a=deepExtend({},b.prototype.defaults,a||{}),c=this.elem,e=dataBind(c)[q];e||(Event.add(c,"mousedown",g),Event.add(c,"mousemove",h),Event.add(c,"mouseup",i),Event.add(c,"touchstart",j),Event.add(c,"touchmove",k),Event.add(c,"touchend",l),d(c,a));var f=new jSketch(c,a.graphics);dataBind(c)[q]=e={strokes:[],coords:{},timestamp:(new Date).getTime(),sketch:f,instance:this,options:a},"function"==typeof a.events.init&&a.events.init(c,e);for(var m in this.plugins)this.plugins[m](this);return this},config:function(a){var c=this.elem,e=dataBind(c)[q];return a?(e.options=deepExtend({},b.prototype.defaults,e.options,a),d(c),this):e},strokes:function(a){var b=this.elem;if(a){var c=dataBind(b)[q];return c.strokes=a,this}var c=dataBind(b)[q];return c.strokes},handler:function(a){var b=this.elem,c=dataBind(b)[q];return a(b,c),this},clear:function(){var a=this.elem,b=dataBind(a)[q],c=b.options;return b.sketch.clear(),b.strokes=[],b.coords={},"function"==typeof c.events.clear&&c.events.clear(a,b),this},reset:function(a){var b=this.elem,c=dataBind(b)[q],a=c.options;return this.destroy().init(a),"function"==typeof a.events.reset&&a.events.reset(b,c),this},destroy:function(){var a=this.elem,b=dataBind(a)[q],c=b.options;return Event.remove(a,"mouseup",i),Event.remove(a,"mousemove",h),Event.remove(a,"mousedown",g),Event.remove(a,"touchstart",j),Event.remove(a,"touchmove",k),Event.remove(a,"touchend",l),dataBind(a)[q]=null,"function"==typeof c.events.destroy&&c.events.destroy(a,b),this}},b.prototype.plugins={},b.prototype.defaults={interactive:!0,mouseupMovements:!1,relTimestamps:!1,multitouch:!0,cssCursors:!0,filterCoords:!1,events:{},graphics:{firstPointSize:3,lineWidth:3,strokeStyle:"#F0F",fillStyle:"#F0F",lineCap:"round",lineJoin:"round",miterLimit:10}},a.Sketchable=b}(this); !function(a){function b(a,b){if(!a)throw new Error("Sketchable requires a DOM element.");return"string"==typeof a&&(a=r.querySelector(a)),this.elem=a,this.init(b)}function c(b){var c=b.getBoundingClientRect(),d=r.body,e=r.documentElement,f=a.pageYOffset||e.scrollTop||d.scrollTop,g=a.pageXOffset||e.scrollLeft||d.scrollLeft,h=e.clientTop||d.clientTop||0,i=e.clientLeft||d.clientLeft||0,j=c.top+f-h,k=c.left+g-i;return{top:Math.round(j),left:Math.round(k)}}function d(a,b){b||(b=dataBind(a)[q].options),b.cssCursors&&(a.style.cursor=b.interactive?"pointer":"not-allowed"),a.onselectstart=function(){return!1}}function e(a){var b=a.target,d=c(b);return{x:Math.round(a.pageX-d.left),y:Math.round(a.pageY-d.top)}}function f(a,b,c){var d=b.coords[a],e=(new Date).getTime();if(b.options.relTimestamps&&(0===b.strokes.length&&0===d.length&&(b.timestamp=e),e-=b.timestamp),d.push([c.x,c.y,e,+b.sketch.isDrawing]),b.options.filterCoords&&d.length>1){var f=d.length-1,g=d[f],h=d[f-1];g[0]==h[0]&&g[1]==h[1]&&d.splice(f,1)}}function g(a){return a.touches?!1:void m(a)}function h(a){return a.touches?!1:void n(a)}function i(a){return a.touches?!1:void o(a)}function j(a){p(a,m),a.preventDefault()}function k(a){p(a,n),a.preventDefault()}function l(a){p(a,o),a.preventDefault()}function m(a){if(Event.isRightClick(a))return!1;var b=a.identifier||0,c=a.target,d=dataBind(c)[q],g=d.options;if(g.interactive){var h=e(a);"function"==typeof g.events.mousedownBefore&&g.events.mousedownBefore(c,d,a),g.graphics.firstPointSize>0&&d.sketch.beginFill(g.graphics.fillStyle).fillCircle(h.x,h.y,g.graphics.firstPointSize).endFill(),d.sketch.isDrawing=!0,d.sketch.beginPath();var i=d.coords[b];i||(i=[]),i.length>0&&d.strokes.push(i),d.coords[b]=[],f(b,d,h),"function"==typeof g.events.mousedown&&g.events.mousedown(c,d,a)}}function n(a){var b=a.identifier||0,c=a.target,d=dataBind(c)[q],g=d.options;if(g.interactive&&(g.mouseupMovements&&0!==d.strokes.length||d.sketch.isDrawing)){var h=e(a);"function"==typeof g.events.mousemoveBefore&&g.events.mousemoveBefore(c,d,a);var i=d.coords[b],j=i[i.length-1];if(j){var k=d.sketch;d.sketch.isDrawing?k.lineStyle(g.graphics.strokeStyle,g.graphics.lineWidth):g.mouseupMovements.visible!==!1&&k.lineStyle(g.mouseupMovements.strokeStyle||"#DDD",g.mouseupMovements.lineWidth||1),k.line(j[0],j[1],h.x,h.y).stroke()}f(b,d,h),"function"==typeof g.events.mousemove&&g.events.mousemove(c,d,a)}}function o(a){var b=a.identifier||0,c=a.target,d=dataBind(c)[q],e=d.options;e.interactive&&("function"==typeof e.events.mouseupBefore&&e.events.mouseupBefore(c,d,a),d.sketch.isDrawing=!1,d.sketch.closePath(),d.strokes.push(d.coords[b]),d.coords[b]=[],"function"==typeof e.events.mouseup&&e.events.mouseup(c,d,a))}function p(a,b){var c=a.target,d=dataBind(c)[q],e=d.options;if(e.multitouch)for(var f=a.changedTouches,g=0;g<f.length;g++){var h=f[g];h.type=a.type,h.identifier=g,b(h)}else{var h=a.touches[0];h.type=a.type,h.identifier=0,b(h)}a.preventDefault()}var q="sketchable",r=a.document;b.prototype={init:function(a){var c=deepExtend({},b.prototype.defaults,a||{}),e=this.elem,f=dataBind(e)[q];f||(Event.add(e,"mousedown",g),Event.add(e,"mousemove",h),Event.add(e,"mouseup",i),Event.add(e,"touchstart",j),Event.add(e,"touchmove",k),Event.add(e,"touchend",l),d(e,c));var m=new jSketch(e,c.graphics);dataBind(e)[q]=f={strokes:[],coords:{},timestamp:(new Date).getTime(),sketch:m,instance:this,options:c},"function"==typeof c.events.init&&c.events.init(e,f);for(var n in this.plugins)this.plugins[n](this);return this},config:function(a){var c=this.elem,e=dataBind(c)[q];return a?(e.options=deepExtend({},b.prototype.defaults,e.options,a),d(c),this):e},strokes:function(a){var b=this.elem,c=dataBind(b)[q];return a?(c.strokes=a,this):c.strokes},handler:function(a){var b=this.elem,c=dataBind(b)[q];return a(b,c),this},clear:function(){var a=this.elem,b=dataBind(a)[q],c=b.options;return b.sketch.clear(),b.strokes=[],b.coords={},"function"==typeof c.events.clear&&c.events.clear(a,b),this},reset:function(a){var b=this.elem,c=dataBind(b)[q],d=c.options;return this.destroy().init(a),"function"==typeof d.events.reset&&d.events.reset(b,c),this},destroy:function(){var a=this.elem,b=dataBind(a)[q],c=b.options;return Event.remove(a,"mouseup",i),Event.remove(a,"mousemove",h),Event.remove(a,"mousedown",g),Event.remove(a,"touchstart",j),Event.remove(a,"touchmove",k),Event.remove(a,"touchend",l),dataBind(a)[q]=null,"function"==typeof c.events.destroy&&c.events.destroy(a,b),this}},b.prototype.plugins={},b.prototype.defaults={interactive:!0,mouseupMovements:!1,relTimestamps:!1,multitouch:!0,cssCursors:!0,filterCoords:!1,events:{},graphics:{firstPointSize:3,lineWidth:3,strokeStyle:"#F0F",fillStyle:"#F0F",lineCap:"round",lineJoin:"round",miterLimit:10}},a.Sketchable=b}(this);

View File

@ -6,7 +6,7 @@
/** /**
* @method $ * @method $
* @description jQuery constructor. See {@link https://jquery.com} * @description jQuery constructor. See {@link https://jquery.com}
* @param {String} selector - jQuery selector. * @param {String} selector jQuery selector.
* @return {Object} jQuery * @return {Object} jQuery
*/ */
/** /**
@ -25,7 +25,7 @@
var api = { var api = {
/** /**
* Initialize the selected jQuery objects. * Initialize the selected jQuery objects.
* @param {Object} [options] - Configuration (default: {@link $.fn.sketchable.defaults}). * @param {Object} [opts] Configuration (default: {@link $.fn.sketchable.defaults}).
* @return jQuery * @return jQuery
* @memberof $.fn.sketchable * @memberof $.fn.sketchable
* @ignore * @ignore
@ -49,7 +49,7 @@
postProcess(elem, options); postProcess(elem, options);
} }
var sketch = new jSketch(this, options.graphics); var sketch = new jSketch(this, options.graphics); // eslint-disable-line new-cap
// Reconfigure element data. // Reconfigure element data.
elem.data(namespace, { elem.data(namespace, {
// All strokes will be stored here. // All strokes will be stored here.
@ -61,22 +61,20 @@
// Save a pointer to the drawing canvas (jSketch instance). // Save a pointer to the drawing canvas (jSketch instance).
sketch: sketch, sketch: sketch,
// Save also a pointer to the given options. // Save also a pointer to the given options.
options: options options: options,
}); });
// Trigger init event. // Trigger init event.
if (options.events && typeof options.events.init === 'function') { if (typeof options.events.init === 'function')
options.events.init(elem, elem.data(namespace)); options.events.init(elem, elem.data(namespace));
}
// Initialize plugins. // Initialize plugins.
for (var name in $.fn.sketchable.plugins) { for (var name in $.fn.sketchable.plugins)
$.fn.sketchable.plugins[name](elem); $.fn.sketchable.plugins[name](elem);
}
}); });
}, },
/** /**
* Change configuration of an existing jQuery Sketchable element. * Change configuration of an existing jQuery Sketchable element.
* @param {Object} [options] - Configuration (default: {@link $.fn.sketchable.defaults}). * @param {Object} [opts] Configuration (default: {@link $.fn.sketchable.defaults}).
* @return jQuery * @return jQuery
* @memberof $.fn.sketchable * @memberof $.fn.sketchable
* @example * @example
@ -97,7 +95,7 @@
}, },
/** /**
* Get/Set drawing data strokes sequence. * Get/Set drawing data strokes sequence.
* @param {Array} [arr] - Multidimensional array of [x,y,time,status] tuples; status = 0 (pen down) or 1 (pen up). * @param {Array} [arr] Multidimensional array of [x,y,time,status] tuples; status = 0 (pen down) or 1 (pen up).
* @return Strokes object on get, jQuery instance on set (with the new data attached). * @return Strokes object on get, jQuery instance on set (with the new data attached).
* @memberof $.fn.sketchable * @memberof $.fn.sketchable
* @example * @example
@ -119,7 +117,7 @@
}, },
/** /**
* Allow low-level manipulation of the sketchable canvas. * Allow low-level manipulation of the sketchable canvas.
* @param {Function} callback - Callback function, invoked with 2 arguments: elem (CANVAS element) and data (private element data). * @param {Function} callback Callback function, invoked with 2 arguments: elem (CANVAS element) and data (private element data).
* @return jQuery * @return jQuery
* @memberof $.fn.sketchable * @memberof $.fn.sketchable
* @example * @example
@ -149,20 +147,20 @@
*/ */
clear: function() { clear: function() {
return this.each(function() { return this.each(function() {
var elem = $(this), data = elem.data(namespace) || {}, options = data.options; var elem = $(this), data = elem.data(namespace), options = data.options;
if (data.sketch) { if (data.sketch) {
data.sketch.clear(); data.sketch.clear();
data.strokes = []; data.strokes = [];
data.coords = {}; data.coords = {};
} }
if (options && typeof options.events.clear === 'function') {
if (typeof options.events.clear === 'function')
options.events.clear(elem, data); options.events.clear(elem, data);
}
}); });
}, },
/** /**
* Reinitialize a sketchable canvas with given configuration options. * Reinitialize a sketchable canvas with given configuration options.
* @param {Object} [options] - Configuration (default: {@link $.fn.sketchable.defaults}). * @param {Object} [opts] Configuration (default: {@link $.fn.sketchable.defaults}).
* @return jQuery * @return jQuery
* @memberof $.fn.sketchable * @memberof $.fn.sketchable
* @example * @example
@ -174,13 +172,12 @@
*/ */
reset: function(opts) { reset: function(opts) {
return this.each(function() { return this.each(function() {
var elem = $(this), data = elem.data(namespace) || {}, options = data.options; var elem = $(this), data = elem.data(namespace), options = data.options;
elem.sketchable('destroy').sketchable(opts); elem.sketchable('destroy').sketchable(opts);
if (options && typeof options.events.reset === 'function') { if (typeof options.events.reset === 'function')
options.events.reset(elem, data); options.events.reset(elem, data);
}
}); });
}, },
/** /**
@ -194,7 +191,7 @@
*/ */
destroy: function() { destroy: function() {
return this.each(function() { return this.each(function() {
var elem = $(this), data = elem.data(namespace) || {}, options = data.options; var elem = $(this), data = elem.data(namespace), options = data.options;
elem.unbind('mouseup', mouseupHandler); elem.unbind('mouseup', mouseupHandler);
elem.unbind('mousemove', mousemoveHandler); elem.unbind('mousemove', mousemoveHandler);
@ -205,18 +202,17 @@
elem.removeData(namespace); elem.removeData(namespace);
if (options && typeof options.events.destroy === 'function') { if (options && typeof options.events.destroy === 'function')
options.events.destroy(elem, data); options.events.destroy(elem, data);
}
}); });
} },
}; };
/** /**
* Create a <tt>jQuery Sketchable</tt> instance. * Create a <tt>jQuery Sketchable</tt> instance.
* This is a jQuery wrapper for the <tt>jSketch</tt> drawing class. * This is a jQuery wrapper for the <tt>jSketch</tt> drawing class.
* @namespace $.fn.sketchable * @namespace $.fn.sketchable
* @param {String|Object} method - Method to invoke, or a configuration object. * @param {String|Object} method Method to invoke, or a configuration object.
* @return jQuery * @return jQuery
* @version 2.1 * @version 2.1
* @author Luis A. Leiva * @author Luis A. Leiva
@ -347,8 +343,8 @@
fillStyle: '#F0F', fillStyle: '#F0F',
lineCap: 'round', lineCap: 'round',
lineJoin: 'round', lineJoin: 'round',
miterLimit: 10 miterLimit: 10,
} },
}; };
/** /**
@ -361,7 +357,9 @@
elem[0].style.cursor = options.interactive ? 'pointer' : 'not-allowed'; elem[0].style.cursor = options.interactive ? 'pointer' : 'not-allowed';
} }
// Fix unwanted highlight "bug". Note: `this` is the actual DOM element. // Fix unwanted highlight "bug". Note: `this` is the actual DOM element.
this.onselectstart = function() { return false }; this.onselectstart = function() {
return false;
};
}; };
/** /**
@ -383,8 +381,8 @@
var elem = $(e.target), pos = elem.offset(); var elem = $(e.target), pos = elem.offset();
return { return {
x: Math.round(e.pageX - pos.left), x: Math.round(e.pageX - pos.left),
y: Math.round(e.pageY - pos.top) y: Math.round(e.pageY - pos.top),
} };
}; };
/** /**
@ -402,7 +400,7 @@
time -= data.timestamp; time -= data.timestamp;
} }
coords.push([ pt.x, pt.y, time, +data.sketch.isDrawing ]); coords.push([pt.x, pt.y, time, +data.sketch.isDrawing]);
// Check if consecutive points should be removed. // Check if consecutive points should be removed.
if (data.options.filterCoords && coords.length > 1) { if (data.options.filterCoords && coords.length > 1) {
@ -484,7 +482,10 @@
// Mark visually 1st point of stroke. // Mark visually 1st point of stroke.
if (options.graphics.firstPointSize > 0) { if (options.graphics.firstPointSize > 0) {
data.sketch.beginFill(options.graphics.fillStyle).fillCircle(p.x, p.y, options.graphics.firstPointSize).endFill(); data.sketch
.beginFill(options.graphics.fillStyle)
.fillCircle(p.x, p.y, options.graphics.firstPointSize)
.endFill();
} }
data.sketch.isDrawing = true; data.sketch.isDrawing = true;
@ -500,9 +501,8 @@
saveMousePos(idx, data, p); saveMousePos(idx, data, p);
if (typeof options.events.mousedown === 'function') { if (typeof options.events.mousedown === 'function')
options.events.mousedown(elem, data, e); options.events.mousedown(elem, data, e);
}
}; };
/** /**
@ -539,9 +539,8 @@
saveMousePos(idx, data, p); saveMousePos(idx, data, p);
if (typeof options.events.mousemove === 'function') { if (typeof options.events.mousemove === 'function')
options.events.mousemove(elem, data, e); options.events.mousemove(elem, data, e);
}
}; };
/** /**
@ -564,9 +563,8 @@
data.strokes.push(data.coords[idx]); data.strokes.push(data.coords[idx]);
data.coords[idx] = []; data.coords[idx] = [];
if (typeof options.events.mouseup === 'function') { if (typeof options.events.mouseup === 'function')
options.events.mouseup(elem, data, e); options.events.mouseup(elem, data, e);
}
}; };
/** /**

View File

@ -14,6 +14,7 @@
* and is part of the {@link $.fn.sketchable.plugins.memento} plugin. * and is part of the {@link $.fn.sketchable.plugins.memento} plugin.
* @class * @class
* @version 2.1 * @version 2.1
* @param {Sketchable} $instance jQuery Sketchable element.
* @example * @example
* var sketcher = $('canvas').sketchable(); * var sketcher = $('canvas').sketchable();
* // This is internally done by the plugin, plus some checks: * // This is internally done by the plugin, plus some checks:
@ -38,7 +39,7 @@
// Note: jSketch.drawImage after clear creates some flickering, // Note: jSketch.drawImage after clear creates some flickering,
// so use the native HTMLCanvasElement.drawImage method instead. // so use the native HTMLCanvasElement.drawImage method instead.
data.sketch.clear(); data.sketch.clear();
data.sketch.context.drawImage(snapshot, 0,0); data.sketch.context.drawImage(snapshot, 0, 0);
// Update strokes. // Update strokes.
data.strokes = strokes.slice(); data.strokes = strokes.slice();
}); });
@ -110,7 +111,7 @@
if (evt && evt.identifier > 0) { if (evt && evt.identifier > 0) {
stack[stpos].strokes = data.strokes.slice(); stack[stpos].strokes = data.strokes.slice();
} else { } else {
stack.push({ image: elem[0].toDataURL(), strokes: data.strokes.slice() }); stack.push({image: elem[0].toDataURL(), strokes: data.strokes.slice()});
stpos++; stpos++;
} }
}); });
@ -177,7 +178,7 @@
}, },
destroy: function(elem, data) { destroy: function(elem, data) {
data.memento.destroy(); data.memento.destroy();
} },
}; };
// A helper function to override user-defined event listeners. // A helper function to override user-defined event listeners.
@ -193,7 +194,7 @@
// Exec original function first, then exec our callback. // Exec original function first, then exec our callback.
fn.apply($instance, arguments); fn.apply($instance, arguments);
callbacks[evName].apply($instance, arguments); callbacks[evName].apply($instance, arguments);
} };
} else { } else {
// User has not defined this event, so attach our callback. // User has not defined this event, so attach our callback.
config.options.events[evName] = callbacks[evName]; config.options.events[evName] = callbacks[evName];
@ -263,8 +264,8 @@
restore: function(state) { restore: function(state) {
var data = $(this).data(namespace); var data = $(this).data(namespace);
return data.memento.restore(state); return data.memento.restore(state);
} },
} },
}); });
// Initialize plugin here. // Initialize plugin here.

View File

@ -80,7 +80,7 @@
lineWidth: this.data.lineWidth || 2, lineWidth: this.data.lineWidth || 2,
lineCap: this.data.lineCap || 'round', lineCap: this.data.lineCap || 'round',
lineJoin: this.data.lineJoin || 'round', lineJoin: this.data.lineJoin || 'round',
miterLimit: this.data.miterLimit || 10 miterLimit: this.data.miterLimit || 10,
}).restoreGraphics(); }).restoreGraphics();
}, },
/** /**
@ -107,7 +107,7 @@
*/ */
background: function(color) { background: function(color) {
this.beginFill(color); this.beginFill(color);
this.context.fillRect(0,0, this.stageWidth,this.stageHeight); this.context.fillRect(0, 0, this.stageWidth, this.stageHeight);
this.endFill(); this.endFill();
return this; return this;
}, },
@ -120,7 +120,7 @@
* @memberof jSketch * @memberof jSketch
*/ */
stage: function(width, height, bgcolor) { stage: function(width, height, bgcolor) {
this.size(width,height).background(bgcolor); this.size(width, height).background(bgcolor);
return this; return this;
}, },
/** /**
@ -159,7 +159,7 @@
lineWidth: thickness || this.data.lineWidth, lineWidth: thickness || this.data.lineWidth,
lineCap: capStyle || this.data.lineCap, lineCap: capStyle || this.data.lineCap,
lineJoin: joinStyle || this.data.lineJoin, lineJoin: joinStyle || this.data.lineJoin,
miterLimit: miter || this.data.miterLimit miterLimit: miter || this.data.miterLimit,
}).restoreGraphics(); }).restoreGraphics();
}, },
/** /**
@ -170,7 +170,7 @@
* @memberof jSketch * @memberof jSketch
*/ */
moveTo: function(x, y) { moveTo: function(x, y) {
this.context.moveTo(x,y); this.context.moveTo(x, y);
return this; return this;
}, },
/** /**
@ -181,7 +181,7 @@
* @memberof jSketch * @memberof jSketch
*/ */
lineTo: function(x, y) { lineTo: function(x, y) {
this.context.lineTo(x,y); this.context.lineTo(x, y);
return this; return this;
}, },
/** /**
@ -193,9 +193,9 @@
* @return jSketch * @return jSketch
* @memberof jSketch * @memberof jSketch
*/ */
line: function(x1,y1, x2,y2) { line: function(x1, y1, x2, y2) {
this.context.moveTo(x1,y1); this.context.moveTo(x1, y1);
this.lineTo(x2,y2); this.lineTo(x2, y2);
return this; return this;
}, },
/** /**
@ -207,8 +207,8 @@
* @return jSketch * @return jSketch
* @memberof jSketch * @memberof jSketch
*/ */
curveTo: function(x,y, cpx,cpy) { curveTo: function(x, y, cpx, cpy) {
this.context.quadraticCurveTo(cpx,cpy, x,y); this.context.quadraticCurveTo(cpx, cpy, x, y);
return this; return this;
}, },
/** /**
@ -222,9 +222,9 @@
* @return jSketch * @return jSketch
* @memberof jSketch * @memberof jSketch
*/ */
curve: function(x1,y1, x2,y2, cpx,cpy) { curve: function(x1, y1, x2, y2, cpx, cpy) {
this.context.moveTo(x1,y1); this.context.moveTo(x1, y1);
this.curveTo(x2,y2, cpx,cpy); this.curveTo(x2, y2, cpx, cpy);
return this; return this;
}, },
/** /**
@ -245,9 +245,9 @@
* @return jSketch * @return jSketch
* @memberof jSketch * @memberof jSketch
*/ */
strokeRect: function(x,y, width,height) { strokeRect: function(x, y, width, height) {
this.context.beginPath(); this.context.beginPath();
this.context.strokeRect(x,y, width,height); this.context.strokeRect(x, y, width, height);
this.context.closePath(); this.context.closePath();
return this; return this;
}, },
@ -260,9 +260,9 @@
* @return jSketch * @return jSketch
* @memberof jSketch * @memberof jSketch
*/ */
fillRect: function(x,y, width,height) { fillRect: function(x, y, width, height) {
this.context.beginPath(); this.context.beginPath();
this.context.fillRect(x,y, width,height); this.context.fillRect(x, y, width, height);
this.context.closePath(); this.context.closePath();
return this; return this;
}, },
@ -274,9 +274,9 @@
* @return jSketch * @return jSketch
* @memberof jSketch * @memberof jSketch
*/ */
strokeCircle: function(x,y, radius) { strokeCircle: function(x, y, radius) {
this.context.beginPath(); this.context.beginPath();
this.context.arc(x,y, radius, 0, 2*Math.PI, false); this.context.arc(x, y, radius, 0, 2*Math.PI, false);
this.context.stroke(); this.context.stroke();
this.context.closePath(); this.context.closePath();
return this; return this;
@ -289,9 +289,9 @@
* @return jSketch * @return jSketch
* @memberof jSketch * @memberof jSketch
*/ */
fillCircle: function(x,y, radius) { fillCircle: function(x, y, radius) {
this.context.beginPath(); this.context.beginPath();
this.context.arc(x,y, radius, 0, 2*Math.PI, false); this.context.arc(x, y, radius, 0, 2*Math.PI, false);
this.context.fill(); this.context.fill();
this.context.closePath(); this.context.closePath();
return this; return this;
@ -300,8 +300,8 @@
* Experimental. * Experimental.
* @ignore * @ignore
*/ */
radialCircle: function(x,y, radius, glowSize, colors) { radialCircle: function(x, y, radius, glowSize, colors) {
var g = this.context.createRadialGradient(x,y, radius, x,y, glowSize || 5); var g = this.context.createRadialGradient(x, y, radius, x, y, glowSize || 5);
if (!colors || colors.constructor.name !== 'array') { if (!colors || colors.constructor.name !== 'array') {
colors = [this.context.fillStyle, 'white']; colors = [this.context.fillStyle, 'white'];
} }
@ -309,7 +309,7 @@
var color = colors[s]; var color = colors[s];
g.addColorStop(s, color); g.addColorStop(s, color);
} }
this.beginFill(g).fillCircle(x,y, radius).endFill(); this.beginFill(g).fillCircle(x, y, radius).endFill();
return this; return this;
}, },
/** /**
@ -357,7 +357,7 @@
*/ */
clear: function() { clear: function() {
// Note: using 'this.canvas.width = this.canvas.width' resets _all_ styles, so better use clearRect. // Note: using 'this.canvas.width = this.canvas.width' resets _all_ styles, so better use clearRect.
this.context.clearRect(0,0, this.stageWidth,this.stageHeight); this.context.clearRect(0, 0, this.stageWidth, this.stageHeight);
return this; return this;
}, },
/** /**
@ -409,16 +409,16 @@
* @return jSketch * @return jSketch
* @memberof jSketch * @memberof jSketch
*/ */
drawImage: function(src, x,y) { drawImage: function(src, x, y) {
if (typeof x === 'undefined') x = 0; if (typeof x === 'undefined') x = 0;
if (typeof y === 'undefined') y = 0; if (typeof y === 'undefined') y = 0;
var self = this, img = new Image(); var self = this, img = new Image();
img.src = src; img.src = src;
img.onload = function() { img.onload = function() {
self.context.drawImage(img, x,y); self.context.drawImage(img, x, y);
} };
return this; return this;
} },
}; };
// Expose. // Expose.

View File

@ -5,6 +5,7 @@
"scripts": { "scripts": {
"test": "echo \"Error: no test specified\" && exit 1", "test": "echo \"Error: no test specified\" && exit 1",
"dist": "grunt", "dist": "grunt",
"lint": "eslint *sketchable*.js || echo [sudo] npm i -g eslint",
"docs": "jsdoc --debug -c jsdoc.json && cp -rn figs/ docs/ || echo [sudo] npm i -g jsdoc" "docs": "jsdoc --debug -c jsdoc.json && cp -rn figs/ docs/ || echo [sudo] npm i -g jsdoc"
}, },
"repository": { "repository": {
@ -21,6 +22,7 @@
"dependencies": { "dependencies": {
}, },
"devDependencies": { "devDependencies": {
"minami": "^1.2.3",
"grunt": "^0.4.5", "grunt": "^0.4.5",
"grunt-contrib-concat": "^0.5.1", "grunt-contrib-concat": "^0.5.1",
"grunt-contrib-clean": "0.6.0", "grunt-contrib-clean": "0.6.0",

View File

@ -50,15 +50,15 @@
Sketchable.prototype = { Sketchable.prototype = {
/** /**
* Initialize the selected CANVAS elements. * Initialize the selected CANVAS elements.
* @param {Object} [options] - Configuration (default: {@link Sketchable#defaults}). * @param {Object} [opts] - Configuration (default: {@link Sketchable#defaults}).
* @return Sketchable * @return {Sketchable}
* @memberof Sketchable * @memberof Sketchable
* @protected * @protected
* @ignore * @ignore
*/ */
init: function(options) { init: function(opts) {
// Options will be available for all plugin methods. // Options will be available for all plugin methods.
var options = deepExtend({}, Sketchable.prototype.defaults, options || {}); var options = deepExtend({}, Sketchable.prototype.defaults, opts || {});
var elem = this.elem, data = dataBind(elem)[namespace]; var elem = this.elem, data = dataBind(elem)[namespace];
// Check if element is not initialized yet. // Check if element is not initialized yet.
if (!data) { if (!data) {
@ -73,7 +73,7 @@
postProcess(elem, options); postProcess(elem, options);
} }
var sketch = new jSketch(elem, options.graphics); var sketch = new jSketch(elem, options.graphics); // eslint-disable-line new-cap
// Reconfigure element data. // Reconfigure element data.
dataBind(elem)[namespace] = data = { dataBind(elem)[namespace] = data = {
// All strokes will be stored here. // All strokes will be stored here.
@ -89,34 +89,33 @@
// since we access the instance via `$('selector').sketchable('method')`. // since we access the instance via `$('selector').sketchable('method')`.
instance: this, instance: this,
// Save also a pointer to the given options. // Save also a pointer to the given options.
options: options options: options,
}; };
// Trigger init event. // Trigger init event.
if (typeof options.events.init === 'function') { if (typeof options.events.init === 'function')
options.events.init(elem, data); options.events.init(elem, data);
}
// Initialize plugins. // Initialize plugins.
for (var name in this.plugins) { for (var name in this.plugins) this.plugins[name](this);
this.plugins[name](this);
}
// Make methods chainable. // Make methods chainable.
return this; return this;
}, },
/** /**
* Change configuration of an existing Sketchable instance. * Change configuration of an existing Sketchable instance.
* @param {Object} [options] - Configuration (default: {@link Sketchable#defaults}). * @param {Object} [opts] - Configuration (default: {@link Sketchable#defaults}).
* @return Sketchable * @return {Sketchable}
* @memberof Sketchable * @memberof Sketchable
* @example * @example
* var sketcher = new Sketchable('canvas').config({ interactive: false }); * var sketcher = new Sketchable('canvas').config({ interactive: false });
* // Update later on: * // Update later on:
* sketcher.config({ interactive: true }); * sketcher.config({ interactive: true });
*/ */
config: function(options) { config: function(opts) {
var elem = this.elem, data = dataBind(elem)[namespace]; var elem = this.elem, data = dataBind(elem)[namespace];
if (options) { // setter
data.options = deepExtend({}, Sketchable.prototype.defaults, data.options, options); if (opts) { // setter
data.options = deepExtend({}, Sketchable.prototype.defaults, data.options, opts);
postProcess(elem); postProcess(elem);
return this; return this;
} else { // getter } else { // getter
@ -126,7 +125,7 @@
/** /**
* Get/Set drawing data strokes sequence. * Get/Set drawing data strokes sequence.
* @param {Array} [arr] - Multidimensional array of [x,y,time,status] tuples; status = 0 (pen down) or 1 (pen up). * @param {Array} [arr] - Multidimensional array of [x,y,time,status] tuples; status = 0 (pen down) or 1 (pen up).
* @return Strokes object on get, Sketchable instance on set (with the new data attached). * @return {Array|Sketchable} Strokes object on get, Sketchable instance on set (with the new data attached).
* @memberof Sketchable * @memberof Sketchable
* @example * @example
* // Getter: read associated strokes. * // Getter: read associated strokes.
@ -135,20 +134,19 @@
* new Sketchable('canvas').strokes([ [arr1], ..., [arrN] ]); * new Sketchable('canvas').strokes([ [arr1], ..., [arrN] ]);
*/ */
strokes: function(arr) { strokes: function(arr) {
var elem = this.elem; var elem = this.elem, data = dataBind(elem)[namespace];
if (arr) { // setter if (arr) { // setter
var data = dataBind(elem)[namespace];
data.strokes = arr; data.strokes = arr;
return this; return this;
} else { // getter } else { // getter
var data = dataBind(elem)[namespace];
return data.strokes; return data.strokes;
} }
}, },
/** /**
* Allows low-level manipulation of the sketchable canvas. * Allows low-level manipulation of the sketchable canvas.
* @param {Function} callback - Callback function, invoked with 2 arguments: elem (CANVAS element) and data (private element data). * @param {Function} callback - Callback function, invoked with 2 arguments: elem (CANVAS element) and data (private element data).
* @return Sketchable * @return {Sketchable}
* @memberof Sketchable * @memberof Sketchable
* @example * @example
* new Sketchable('canvas').handler(function(elem, data) { * new Sketchable('canvas').handler(function(elem, data) {
@ -159,12 +157,13 @@
var elem = this.elem, data = dataBind(elem)[namespace]; var elem = this.elem, data = dataBind(elem)[namespace];
callback(elem, data); callback(elem, data);
return this; return this;
}, },
/** /**
* Clears canvas <b>together with</b> associated strokes data. * Clears canvas <b>together with</b> associated strokes data.
* @see Sketchable.handler * @see Sketchable.handler
* @return Sketchable * @return {Sketchable}
* @memberof Sketchable * @memberof Sketchable
* @example * @example
* var sketcher = new Sketchable('canvas'); * var sketcher = new Sketchable('canvas');
@ -182,15 +181,15 @@
data.strokes = []; data.strokes = [];
data.coords = {}; data.coords = {};
if (typeof options.events.clear === 'function') { if (typeof options.events.clear === 'function')
options.events.clear(elem, data); options.events.clear(elem, data);
}
return this; return this;
}, },
/** /**
* Reinitializes a sketchable canvas with given configuration options. * Reinitializes a sketchable canvas with given configuration options.
* @param {Object} [options] - Configuration (default: {@link Sketchable#defaults}). * @param {Object} [opts] - Configuration (default: {@link Sketchable#defaults}).
* @return Sketchable * @return {Sketchable}
* @memberof Sketchable * @memberof Sketchable
* @example * @example
* // Reset default state. * // Reset default state.
@ -198,19 +197,19 @@
* // Reset with custom configuration. * // Reset with custom configuration.
* new Sketchable('canvas').reset({ interactive:false }); * new Sketchable('canvas').reset({ interactive:false });
*/ */
reset: function(options) { reset: function(opts) {
var elem = this.elem, data = dataBind(elem)[namespace], options = data.options; var elem = this.elem, data = dataBind(elem)[namespace], options = data.options;
this.destroy().init(options); this.destroy().init(opts);
if (typeof options.events.reset === 'function') { if (typeof options.events.reset === 'function')
options.events.reset(elem, data); options.events.reset(elem, data);
}
return this; return this;
}, },
/** /**
* Destroys sketchable canvas, together with strokes data and associated events. * Destroys sketchable canvas, together with strokes data and associated events.
* @return Sketchable * @return {Sketchable}
* @memberof Sketchable * @memberof Sketchable
* @example * @example
* // This will leave the canvas element intact. * // This will leave the canvas element intact.
@ -228,11 +227,11 @@
dataBind(elem)[namespace] = null; dataBind(elem)[namespace] = null;
if (typeof options.events.destroy === 'function') { if (typeof options.events.destroy === 'function')
options.events.destroy(elem, data); options.events.destroy(elem, data);
}
return this; return this;
} },
}; };
@ -333,12 +332,12 @@
fillStyle: '#F0F', fillStyle: '#F0F',
lineCap: 'round', lineCap: 'round',
lineJoin: 'round', lineJoin: 'round',
miterLimit: 10 miterLimit: 10,
} },
}; };
/** /**
* @private * @ignore
*/ */
function offset(el) { function offset(el) {
var box = el.getBoundingClientRect(); var box = el.getBoundingClientRect();
@ -352,12 +351,12 @@
var left = box.left + scrollLeft - clientLeft; var left = box.left + scrollLeft - clientLeft;
return { return {
top: Math.round(top), top: Math.round(top),
left: Math.round(left) left: Math.round(left),
} };
}; };
/** /**
* @private * @ignore
*/ */
function postProcess(elem, options) { function postProcess(elem, options) {
if (!options) options = dataBind(elem)[namespace].options; if (!options) options = dataBind(elem)[namespace].options;
@ -366,22 +365,24 @@
elem.style.cursor = options.interactive ? 'pointer' : 'not-allowed'; elem.style.cursor = options.interactive ? 'pointer' : 'not-allowed';
} }
// Fix unwanted highlight "bug". // Fix unwanted highlight "bug".
elem.onselectstart = function() { return false }; elem.onselectstart = function() {
return false;
};
}; };
/** /**
* @private * @ignore
*/ */
function getMousePos(e) { function getMousePos(e) {
var elem = e.target, pos = offset(elem); var elem = e.target, pos = offset(elem);
return { return {
x: Math.round(e.pageX - pos.left), x: Math.round(e.pageX - pos.left),
y: Math.round(e.pageY - pos.top) y: Math.round(e.pageY - pos.top),
} };
}; };
/** /**
* @private * @ignore
*/ */
function saveMousePos(idx, data, pt) { function saveMousePos(idx, data, pt) {
// Current coords are already initialized. // Current coords are already initialized.
@ -395,7 +396,7 @@
time -= data.timestamp; time -= data.timestamp;
} }
coords.push([ pt.x, pt.y, time, +data.sketch.isDrawing ]); coords.push([pt.x, pt.y, time, +data.sketch.isDrawing]);
// Check if consecutive points should be removed. // Check if consecutive points should be removed.
if (data.options.filterCoords && coords.length > 1) { if (data.options.filterCoords && coords.length > 1) {
@ -409,7 +410,7 @@
}; };
/** /**
* @private * @ignore
*/ */
function mousedownHandler(e) { function mousedownHandler(e) {
if (e.touches) return false; if (e.touches) return false;
@ -417,7 +418,7 @@
}; };
/** /**
* @private * @ignore
*/ */
function mousemoveHandler(e) { function mousemoveHandler(e) {
if (e.touches) return false; if (e.touches) return false;
@ -425,7 +426,7 @@
}; };
/** /**
* @private * @ignore
*/ */
function mouseupHandler(e) { function mouseupHandler(e) {
if (e.touches) return false; if (e.touches) return false;
@ -433,7 +434,7 @@
}; };
/** /**
* @private * @ignore
*/ */
function touchdownHandler(e) { function touchdownHandler(e) {
execTouchEvent(e, downHandler); execTouchEvent(e, downHandler);
@ -441,7 +442,7 @@
}; };
/** /**
* @private * @ignore
*/ */
function touchmoveHandler(e) { function touchmoveHandler(e) {
execTouchEvent(e, moveHandler); execTouchEvent(e, moveHandler);
@ -449,7 +450,7 @@
}; };
/** /**
* @private * @ignore
*/ */
function touchupHandler(e) { function touchupHandler(e) {
execTouchEvent(e, upHandler); execTouchEvent(e, upHandler);
@ -457,7 +458,7 @@
}; };
/** /**
* @private * @ignore
*/ */
function downHandler(e) { function downHandler(e) {
// Don't handle right clicks. // Don't handle right clicks.
@ -477,7 +478,10 @@
// Mark visually 1st point of stroke. // Mark visually 1st point of stroke.
if (options.graphics.firstPointSize > 0) { if (options.graphics.firstPointSize > 0) {
data.sketch.beginFill(options.graphics.fillStyle).fillCircle(p.x, p.y, options.graphics.firstPointSize).endFill(); data.sketch
.beginFill(options.graphics.fillStyle)
.fillCircle(p.x, p.y, options.graphics.firstPointSize)
.endFill();
} }
data.sketch.isDrawing = true; data.sketch.isDrawing = true;
@ -493,16 +497,15 @@
saveMousePos(idx, data, p); saveMousePos(idx, data, p);
if (typeof options.events.mousedown === 'function') { if (typeof options.events.mousedown === 'function')
options.events.mousedown(elem, data, e); options.events.mousedown(elem, data, e);
}
}; };
/** /**
* @private * @ignore
*/ */
function moveHandler(e) { function moveHandler(e) {
var idx = e.identifier || 0 var idx = e.identifier || 0,
elem = e.target, elem = e.target,
data = dataBind(elem)[namespace], data = dataBind(elem)[namespace],
options = data.options; options = data.options;
@ -532,16 +535,15 @@
saveMousePos(idx, data, p); saveMousePos(idx, data, p);
if (typeof options.events.mousemove === 'function') { if (typeof options.events.mousemove === 'function')
options.events.mousemove(elem, data, e); options.events.mousemove(elem, data, e);
}
}; };
/** /**
* @private * @ignore
*/ */
function upHandler(e) { function upHandler(e) {
var idx = e.identifier || 0 var idx = e.identifier || 0,
elem = e.target, elem = e.target,
data = dataBind(elem)[namespace], data = dataBind(elem)[namespace],
options = data.options; options = data.options;
@ -557,13 +559,12 @@
data.strokes.push(data.coords[idx]); data.strokes.push(data.coords[idx]);
data.coords[idx] = []; data.coords[idx] = [];
if (typeof options.events.mouseup === 'function') { if (typeof options.events.mouseup === 'function')
options.events.mouseup(elem, data, e); options.events.mouseup(elem, data, e);
}
}; };
/** /**
* @private * @ignore
*/ */
function execTouchEvent(e, callback) { function execTouchEvent(e, callback) {
var elem = e.target, data = dataBind(elem)[namespace], options = data.options; var elem = e.target, data = dataBind(elem)[namespace], options = data.options;

View File

@ -16,6 +16,7 @@
* and is part of the {@link Sketchable.plugins.memento} plugin. * and is part of the {@link Sketchable.plugins.memento} plugin.
* @class * @class
* @version 2.1 * @version 2.1
* @param {Sketchable} instance Sketchable element.
* @example * @example
* var sketcher = new Sketchable('canvas'); * var sketcher = new Sketchable('canvas');
* // This is internally done by the plugin, plus some checks: * // This is internally done by the plugin, plus some checks:
@ -40,7 +41,7 @@
// Note: jSketch.drawImage after clear creates some flickering, // Note: jSketch.drawImage after clear creates some flickering,
// so use the native HTMLCanvasElement.drawImage method instead. // so use the native HTMLCanvasElement.drawImage method instead.
data.sketch.clear(); data.sketch.clear();
data.sketch.context.drawImage(snapshot, 0,0); data.sketch.context.drawImage(snapshot, 0, 0);
// Update strokes. // Update strokes.
data.strokes = strokes.slice(); data.strokes = strokes.slice();
}); });
@ -112,7 +113,7 @@
if (evt && evt.identifier > 0) { if (evt && evt.identifier > 0) {
stack[stpos].strokes = data.strokes.slice(); stack[stpos].strokes = data.strokes.slice();
} else { } else {
stack.push({ image: elem.toDataURL(), strokes: data.strokes.slice() }); stack.push({image: elem.toDataURL(), strokes: data.strokes.slice()});
stpos++; stpos++;
} }
}); });
@ -163,7 +164,7 @@
/** /**
* Memento plugin constructor for Sketchable instances. * Memento plugin constructor for Sketchable instances.
* @param {Object} sketchable Sketchable instance. * @param {Sketchable} instance Sketchable element.
* @memberof Sketchable#plugins * @memberof Sketchable#plugins
*/ */
Sketchable.prototype.plugins.memento = function(instance) { Sketchable.prototype.plugins.memento = function(instance) {
@ -179,7 +180,7 @@
}, },
destroy: function(elem, data) { destroy: function(elem, data) {
data.memento.destroy(); data.memento.destroy();
} },
}; };
// A helper function to override user-defined event listeners. // A helper function to override user-defined event listeners.
@ -195,7 +196,7 @@
// Exec original function first, then exec our callback. // Exec original function first, then exec our callback.
fn.apply(instance, arguments); fn.apply(instance, arguments);
callbacks[evName].apply(instance, arguments); callbacks[evName].apply(instance, arguments);
} };
} else { } else {
// User has not defined this event, so attach our callback. // User has not defined this event, so attach our callback.
config.options.events[evName] = callbacks[evName]; config.options.events[evName] = callbacks[evName];
@ -265,8 +266,8 @@
restore: function(state) { restore: function(state) {
var data = dataBind(instance.elem)[namespace]; var data = dataBind(instance.elem)[namespace];
return data.memento.restore(state); return data.memento.restore(state);
} },
} },
}); });
// Initialize plugin here. // Initialize plugin here.

View File

@ -1,3 +1,5 @@
/* eslint-env browser */
(function() { (function() {
var cache = [0], expando = 'data' + Date.now(); var cache = [0], expando = 'data' + Date.now();
function data(elem) { function data(elem) {
@ -31,7 +33,7 @@
* @global * @global
* @module Event * @module Event
*/ */
var Event = { window.Event = {
/** /**
* Add event to DOM element. * Add event to DOM element.
* @memberof module:Event * @memberof module:Event
@ -48,9 +50,11 @@ var Event = {
if (elem.addEventListener) { // W3C standard if (elem.addEventListener) { // W3C standard
elem.addEventListener(type, fn, false); elem.addEventListener(type, fn, false);
} else if (elem.attachEvent) { // Old IE versions } else if (elem.attachEvent) { // Old IE versions
elem.attachEvent("on"+type, fn); elem.attachEvent('on'+type, fn);
} else { // Really old browser } else { // Really old browser
elem[type+fn] = function(){ fn(window.event); }; elem[type+fn] = function() {
fn(window.event);
};
} }
}, },
/** /**
@ -68,7 +72,7 @@ var Event = {
if (elem.removeEventListener) { // W3C standard if (elem.removeEventListener) { // W3C standard
elem.removeEventListener(type, fn, false); elem.removeEventListener(type, fn, false);
} else if (elem.detachEvent) { // Old IE versions } else if (elem.detachEvent) { // Old IE versions
elem.detachEvent("on"+type, fn); elem.detachEvent('on'+type, fn);
} else { // Really old browser } else { // Really old browser
elem[type+fn] = null; elem[type+fn] = null;
} }
@ -89,7 +93,7 @@ var Event = {
if (ev.which) return ev.which === 3; if (ev.which) return ev.which === 3;
else if (ev.button) return e.button === 2; else if (ev.button) return e.button === 2;
return false; return false;
} },
}; };
@ -109,7 +113,7 @@ var Event = {
* // Now `ext` is `{ foo:1, bar: { a:false, b:false } }` * // Now `ext` is `{ foo:1, bar: { a:false, b:false } }`
* // and `one` is left intact. * // and `one` is left intact.
*/ */
var deepExtend = function(myObj) { window.deepExtend = function(myObj) {
myObj = myObj || {}; myObj = myObj || {};
for (var i = 1; i < arguments.length; i++) { for (var i = 1; i < arguments.length; i++) {
var obj = arguments[i]; var obj = arguments[i];