Permalink
Browse files

Add wet feather tool. Remove obsolete tool.

  • Loading branch information...
1 parent 9c5db0d commit 065d168189035f112b163ed608258ca65d7839c6 @tadast committed May 6, 2012
View
6 index.html
@@ -36,10 +36,10 @@
</div>
<div class='separator'></div>
<div id='tools'>
- <div class='tool active' data-toolname='feather'>〻</div>
+ <div class='tool active' data-toolname='pencil'>✎</div>
+ <div class='tool' data-toolname='wetFeather'>✒</div>
<div class='tool' data-toolname='dot'>⠿</div>
- <!--<div class='tool' data-toolname='finger'>☛</div>
- <div class='tool' data-toolname='pencil'>✎</div>-->
+ <!--<div class='tool' data-toolname='finger'>☛</div>-->
</div>
<div class='separator'></div>
<div id='reset'>↻</div>
View
6 scripts/objects/canver.coffee
@@ -38,8 +38,10 @@ class Canver
true
applyColor: ->
- @ctx.fillStyle = @colorizer.nextColour()
- @ctx.strokeStyle = @colorizer.nextColour()
+ colour = @colorizer.nextColour()
+ @ctx.fillStyle = colour
+ @ctx.shadowColor = colour
+ @ctx.strokeStyle = colour
resizeCanvas: ->
@canvas.width = window.innerWidth
View
7 scripts/objects/canver.js
@@ -43,8 +43,11 @@ Canver = (function() {
}, this));
};
Canver.prototype.applyColor = function() {
- this.ctx.fillStyle = this.colorizer.nextColour();
- return this.ctx.strokeStyle = this.colorizer.nextColour();
+ var colour;
+ colour = this.colorizer.nextColour();
+ this.ctx.fillStyle = colour;
+ this.ctx.shadowColor = colour;
+ return this.ctx.strokeStyle = colour;
};
Canver.prototype.resizeCanvas = function() {
this.canvas.width = window.innerWidth;
View
96 scripts/objects/draw_tools.coffee
@@ -1,7 +1,7 @@
# contains info about all available tools
class ToolRegister
constructor: ->
- @tools = [DotTool, FingerTool, FeatherTool]
+ @tools = [DotTool, WetFeather, PencilTool]
# gives a tool class given a tool name
toolFor: (toolName) ->
@@ -23,7 +23,7 @@ class DrawTool
@drawRadius = 10
init: ->
- true
+ @ctx.shadowBlur = 0
setSize: (size) ->
@drawRadius = size
@@ -49,45 +49,19 @@ class DotTool extends DrawTool
@ctx.closePath();
@ctx.fill();
-# Finger tool draws like a pencil yo!
-# Currently doesn't work as expected with multitouch
-class FingerTool extends DrawTool
- @toolName = 'finger'
-
- init: ->
- @touchlog ||= new TouchLog
- @ctx.setLineJoin('round')
- @ctx.setLineCap('round')
-
- start: (e) ->
- @touchlog.logEvent e
-
- move: (e) ->
- @touchlog.logEvent e
- for touch in e.changedTouches # migth be buggy, because logger does not know when to use changed vs all touches
- previous = @touchlog.forTouch(touch).previous
- @ctx.beginPath()
- @ctx.lineWidth = @drawRadius
- @ctx.moveTo previous.x, previous.y
- @ctx.lineTo touch.clientX, touch.clientY
- @ctx.stroke();
- @ctx.closePath()
-
- end: (e) ->
- true
- #@touchlog.clearFromEvent e # does not work, removes all touches, we need to remove only ended touches
-
-class FeatherTool extends DrawTool
- @toolName = 'feather'
+# Feather tool uses bezier curves to smooth out user input
+class PencilTool extends DrawTool
+ @toolName = 'pencil'
init: ->
+ super()
@touchlog ||= new TouchLog
- @ctx.setLineJoin('round')
- @ctx.setLineCap('round')
start: (e) ->
@touchlog.logEvent e
move: (e) ->
+ @ctx.setLineCap 'round'
+ @ctx.setLineJoin 'round'
for touch in e.changedTouches
log = @touchlog.forTouch(touch)
continue unless log && log.previous
@@ -110,4 +84,56 @@ class FeatherTool extends DrawTool
@touchlog.logEvent e
end: (e) ->
- true
+ true
+
+class WetFeather extends PencilTool
+ @toolName = 'wetFeather'
+ init: ->
+ super()
+ @defaultAlpha = 1.0
+ @maxDribbleLength = 120 # how long is a drop
+ @probability = 0.5 # how likely is it to drip for each touch event?
+ @dropFactor = 1.3 # how much bigger is the dropplet at the end of the line?
+ @ctx.shadowBlur = 4
+
+ move: (e) ->
+ super e
+ @ctx.setLineCap 'square'
+ @ctx.globalAlpha = Math.random()
+
+ for touch in e.changedTouches
+ @dribble(touch)
+
+ @ctx.globalAlpha = @defaultAlpha
+
+ dribble: (touch) ->
+ log = @touchlog.forTouch(touch)
+ return false unless log && log.previous
+ return false if Math.random() > @probability
+ @ctx.lineWidth = @drawRadius / (@ctx.globalAlpha * 2 + 1) # the thicker the more transparent
+ @ctx.beginPath()
+
+ startX = log.current.x
+ startY = log.current.y
+ dropEndY = startY + Math.random() * @maxDribbleLength
+ @ctx.moveTo startX, startY
+ @ctx.lineTo startX, dropEndY
+ @ctx.closePath()
+ @ctx.stroke();
+
+ @dropletEnd(startX, dropEndY, @ctx.lineWidth)
+
+ dropletEnd: (x, y, width) ->
+ @ctx.beginPath()
+ radius = @dropFactor * width / 2
+
+ # Trapeze
+ @ctx.moveTo x - width/2, y
+ @ctx.lineTo x + width/2, y
+ @ctx.lineTo x + radius, y + radius*2
+ @ctx.lineTo x - radius, y + radius*2
+
+ # half circle
+ @ctx.arc x, y + radius*2, radius, 0, Math.PI, false
+ @ctx.closePath();
+ @ctx.fill();
View
129 scripts/objects/draw_tools.js
@@ -1,4 +1,4 @@
-var DotTool, DrawTool, FeatherTool, FingerTool, ToolRegister;
+var DotTool, DrawTool, PencilTool, ToolRegister, WetFeather;
var __hasProp = Object.prototype.hasOwnProperty, __extends = function(child, parent) {
for (var key in parent) { if (__hasProp.call(parent, key)) child[key] = parent[key]; }
function ctor() { this.constructor = child; }
@@ -9,7 +9,7 @@ var __hasProp = Object.prototype.hasOwnProperty, __extends = function(child, par
};
ToolRegister = (function() {
function ToolRegister() {
- this.tools = [DotTool, FingerTool, FeatherTool];
+ this.tools = [DotTool, WetFeather, PencilTool];
}
ToolRegister.prototype.toolFor = function(toolName) {
var tool, _i, _len, _ref;
@@ -35,7 +35,7 @@ DrawTool = (function() {
this.drawRadius = 10;
}
DrawTool.prototype.init = function() {
- return true;
+ return this.ctx.shadowBlur = 0;
};
DrawTool.prototype.setSize = function(size) {
return this.drawRadius = size;
@@ -79,58 +79,23 @@ DotTool = (function() {
};
return DotTool;
})();
-FingerTool = (function() {
- __extends(FingerTool, DrawTool);
- function FingerTool() {
- FingerTool.__super__.constructor.apply(this, arguments);
+PencilTool = (function() {
+ __extends(PencilTool, DrawTool);
+ function PencilTool() {
+ PencilTool.__super__.constructor.apply(this, arguments);
}
- FingerTool.toolName = 'finger';
- FingerTool.prototype.init = function() {
- this.touchlog || (this.touchlog = new TouchLog);
- this.ctx.setLineJoin('round');
- return this.ctx.setLineCap('round');
+ PencilTool.toolName = 'pencil';
+ PencilTool.prototype.init = function() {
+ PencilTool.__super__.init.call(this);
+ return this.touchlog || (this.touchlog = new TouchLog);
};
- FingerTool.prototype.start = function(e) {
+ PencilTool.prototype.start = function(e) {
return this.touchlog.logEvent(e);
};
- FingerTool.prototype.move = function(e) {
- var previous, touch, _i, _len, _ref, _results;
- this.touchlog.logEvent(e);
- _ref = e.changedTouches;
- _results = [];
- for (_i = 0, _len = _ref.length; _i < _len; _i++) {
- touch = _ref[_i];
- previous = this.touchlog.forTouch(touch).previous;
- this.ctx.beginPath();
- this.ctx.lineWidth = this.drawRadius;
- this.ctx.moveTo(previous.x, previous.y);
- this.ctx.lineTo(touch.clientX, touch.clientY);
- this.ctx.stroke();
- _results.push(this.ctx.closePath());
- }
- return _results;
- };
- FingerTool.prototype.end = function(e) {
- return true;
- };
- return FingerTool;
-})();
-FeatherTool = (function() {
- __extends(FeatherTool, DrawTool);
- function FeatherTool() {
- FeatherTool.__super__.constructor.apply(this, arguments);
- }
- FeatherTool.toolName = 'feather';
- FeatherTool.prototype.init = function() {
- this.touchlog || (this.touchlog = new TouchLog);
- this.ctx.setLineJoin('round');
- return this.ctx.setLineCap('round');
- };
- FeatherTool.prototype.start = function(e) {
- return this.touchlog.logEvent(e);
- };
- FeatherTool.prototype.move = function(e) {
+ PencilTool.prototype.move = function(e) {
var endX, endY, log, startX, startY, touch, _i, _len, _ref;
+ this.ctx.setLineCap('round');
+ this.ctx.setLineJoin('round');
_ref = e.changedTouches;
for (_i = 0, _len = _ref.length; _i < _len; _i++) {
touch = _ref[_i];
@@ -151,8 +116,68 @@ FeatherTool = (function() {
}
return this.touchlog.logEvent(e);
};
- FeatherTool.prototype.end = function(e) {
+ PencilTool.prototype.end = function(e) {
return true;
};
- return FeatherTool;
+ return PencilTool;
+})();
+WetFeather = (function() {
+ __extends(WetFeather, PencilTool);
+ function WetFeather() {
+ WetFeather.__super__.constructor.apply(this, arguments);
+ }
+ WetFeather.toolName = 'wetFeather';
+ WetFeather.prototype.init = function() {
+ WetFeather.__super__.init.call(this);
+ this.defaultAlpha = 1.0;
+ this.maxDribbleLength = 120;
+ this.probability = 0.5;
+ this.dropFactor = 1.3;
+ return this.ctx.shadowBlur = 4;
+ };
+ WetFeather.prototype.move = function(e) {
+ var touch, _i, _len, _ref;
+ WetFeather.__super__.move.call(this, e);
+ this.ctx.setLineCap('square');
+ this.ctx.globalAlpha = Math.random();
+ _ref = e.changedTouches;
+ for (_i = 0, _len = _ref.length; _i < _len; _i++) {
+ touch = _ref[_i];
+ this.dribble(touch);
+ }
+ return this.ctx.globalAlpha = this.defaultAlpha;
+ };
+ WetFeather.prototype.dribble = function(touch) {
+ var dropEndY, log, startX, startY;
+ log = this.touchlog.forTouch(touch);
+ if (!(log && log.previous)) {
+ return false;
+ }
+ if (Math.random() > this.probability) {
+ return false;
+ }
+ this.ctx.lineWidth = this.drawRadius / (this.ctx.globalAlpha * 2 + 1);
+ this.ctx.beginPath();
+ startX = log.current.x;
+ startY = log.current.y;
+ dropEndY = startY + Math.random() * this.maxDribbleLength;
+ this.ctx.moveTo(startX, startY);
+ this.ctx.lineTo(startX, dropEndY);
+ this.ctx.closePath();
+ this.ctx.stroke();
+ return this.dropletEnd(startX, dropEndY, this.ctx.lineWidth);
+ };
+ WetFeather.prototype.dropletEnd = function(x, y, width) {
+ var radius;
+ this.ctx.beginPath();
+ radius = this.dropFactor * width / 2;
+ this.ctx.moveTo(x - width / 2, y);
+ this.ctx.lineTo(x + width / 2, y);
+ this.ctx.lineTo(x + radius, y + radius * 2);
+ this.ctx.lineTo(x - radius, y + radius * 2);
+ this.ctx.arc(x, y + radius * 2, radius, 0, Math.PI, false);
+ this.ctx.closePath();
+ return this.ctx.fill();
+ };
+ return WetFeather;
})();
View
8 spec/javascripts/DrawToolsSpec.coffee
@@ -21,9 +21,9 @@ describe "DotTool", ->
it "does not respond to line", ->
expect(DotTool.respondsTo('line')).toBeFalsy()
-describe "FeatherTool", ->
- it "responds to feather", ->
- expect(FeatherTool.respondsTo('feather')).toBeTruthy()
+describe "PencilTool", ->
+ it "responds to pencil", ->
+ expect(PencilTool.respondsTo('pencil')).toBeTruthy()
it "does not respond to zomg", ->
- expect(FeatherTool.respondsTo('zomg')).toBeFalsy()
+ expect(PencilTool.respondsTo('zomg')).toBeFalsy()
View
8 spec/javascripts/DrawToolsSpec.js
@@ -24,11 +24,11 @@ describe("DotTool", function() {
return expect(DotTool.respondsTo('line')).toBeFalsy();
});
});
-describe("FeatherTool", function() {
- it("responds to feather", function() {
- return expect(FeatherTool.respondsTo('feather')).toBeTruthy();
+describe("PencilTool", function() {
+ it("responds to pencil", function() {
+ return expect(PencilTool.respondsTo('pencil')).toBeTruthy();
});
return it("does not respond to zomg", function() {
- return expect(FeatherTool.respondsTo('zomg')).toBeFalsy();
+ return expect(PencilTool.respondsTo('zomg')).toBeFalsy();
});
});

0 comments on commit 065d168

Please sign in to comment.