1 /**
  2 * Shape by Grant Skinner. Dec 5, 2010
  3 * Visit www.gskinner.com/blog for documentation, updates and more free code.
  4 *
  5 *
  6 * Copyright (c) 2010 Grant Skinner
  7 * 
  8 * Permission is hereby granted, free of charge, to any person
  9 * obtaining a copy of this software and associated documentation
 10 * files (the "Software"), to deal in the Software without
 11 * restriction, including without limitation the rights to use,
 12 * copy, modify, merge, publish, distribute, sublicense, and/or sell
 13 * copies of the Software, and to permit persons to whom the
 14 * Software is furnished to do so, subject to the following
 15 * conditions:
 16 * 
 17 * The above copyright notice and this permission notice shall be
 18 * included in all copies or substantial portions of the Software.
 19 * 
 20 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
 21 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
 22 * OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
 23 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
 24 * HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
 25 * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
 26 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
 27 * OTHER DEALINGS IN THE SOFTWARE.
 28 **/
 29 
 30 
 31 
 32 /**
 33 * Constructs a new Shape instance.
 34 * @param instructions Optional. The vector drawing instruction that this Shape will use. See the instructions property for information.
 35 * @class A Shape instance encapsulates a set of vector drawing instructions so they can be rendered to the stage. All of the current drawing methods map directly to canvas 2D context APIs.<br/> NOTE: This class is incomplete. I will be adding shortcut methods (ex. drawCircle, drawRoundRect, etc), and possibly changing the inner workings. It also doesn't clean up fill or stroke styles yet, so they can bleed into subsequent Shapes. You've been warned. :)
 36 * @augments DisplayObject
 37 **/
 38 function Shape(instructions) {
 39   this.init(instructions);
 40 this.prototype = new DisplayObject();
 41 
 42 // public properties:
 43 	/** A string containing all of the canvas drawing instructions encapsulated by this Shape. These will be evaluated using a ctx variable for the current canvas 2D context. For example instructions="ctx.fillStyle='#F00';ctx.fillRect(-75,-75,150,150);" would draw a 150x150 red square.  **/
 44 	this.instructions = null;
 45 	
 46 // constructor:
 47 	/** @private **/
 48 	this._init = this.init;
 49 	/** @private **/
 50 	this.init = function(instructions) {
 51 		this._init();
 52 		this.instructions = instructions || "";
 53 	}
 54 	
 55 // public methods:
 56 	this._draw = this.draw;
 57 	this.draw = function(ctx,ignoreCache) {
 58 		if (this.instructions == null || this.instructions.length < 1) { return false; }
 59 		if (!this._draw(ctx,ignoreCache)) { return false; }
 60 		var type = typeof(this.instructions);
 61 		if (type == "function") {
 62 			this.instructions(ctx);
 63 		} else if (type == "string") {
 64 			eval(this.instructions);
 65 		}
 66 	}
 67 	
 68 	/**
 69 	* Clears all drawing instructions.
 70 	**/
 71 	this.clear = function() {
 72 		this.instructions = "";
 73 	}
 74 	
 75 	this.beginPath = function() { this.instructions += "ctx.beginPath();"; }
 76 	this.closePath = function() { this.instructions += "ctx.closePath();"; }
 77 	this.moveTo = function(x,y) { this.instructions += "ctx.moveTo("+x+","+y+");"; }
 78 	this.lineTo = function(x,y) { this.instructions += "ctx.lineTo("+x+","+y+");"; }
 79 	this.quadraticCurveTo = function(cpx,cpy,x,y) { this.instructions += "ctx.quadraticCurveTo("+cpx+","+cpy+","+x+","+y+");"; }
 80 	this.bezierCurveTo = function(cpx1,cpy1,cpx2,cpy2,x,y) { this.instructions += "ctx.bezierCurveTo("+cpx1+","+cpy1+","+cpx2+","+cpy2+","+x+","+y+");"; }
 81 	this.arcTo = function(x1,y1,x2,y2,radius) { this.instructions += "ctx.arcTo("+x1+","+y1+","+x2+","+y2+","+radius+");"; }
 82 	this.rect = function(x,y,w,h) { this.instructions += "ctx.rect("+x+","+y+","+w+","+h+");"; }
 83 	this.arc = function(x,y,radius,startAngle,endAngle,anticlockwise) { this.instructions += "ctx.arc("+x+","+y+","+startAngle+","+endAngle+","+anticlockwise+");"; }
 84 	this.fill = function() { this.instructions += "ctx.fill();"; }
 85 	this.stroke = function() { this.instructions += "ctx.stroke();"; }
 86 	this.clip = function() { this.instructions += "ctx.clip();"; } // ?
 87 	this.fillRect = function(x,y,w,h) { this.instructions += "ctx.fillRect("+x+","+y+","+w+","+h+");"; }
 88 	this.strokeRect = function(x,y,w,h) { this.instructions += "ctx.strokeRect("+x+","+y+","+w+","+h+");"; }
 89 	this.setFillStyle = function(value) { this.instructions += "ctx.fillStyle='"+value+"';"; }
 90 	this.setStrokeStyle = function(value) { this.instructions += "ctx.strokeStyle='"+value+"';"; }
 91 	
 92 	this.clone = function() {
 93 		var o = new Shape(this.instructions);
 94 		this.cloneProps(o);
 95 		return o;
 96 	}
 97 		
 98 	this.toString = function() {
 99 		return "[Shape (name="+  this.name +")]";
100 	}
101 	
102 // TO ADD:
103 	// create gradient and radial gradient
104 	/*
105 	gradient . addColorStop(offset, color)
106 	
107 	gradient = context . createLinearGradient(x0, y0, x1, y1)
108 	
109 	gradient = context . createRadialGradient(x0, y0, r0, x1, y1, r1)
110 	*/
111 	// line styles
112 	/*
113 	context . lineWidth [ = value ]
114 	
115 	context . lineCap [ = value ]
116 	
117 	context . lineJoin [ = value ]
118 	
119 	context . miterLimit [ = value ]
120 	*/
121 	/*
122 	drawCircle
123 	drawElipse
124 	drawRect
125 	drawSquare
126 	drawRoundRect
127 	drawRoundRectComplex
128 	drawArc
129 	*/
130 }