GraphicsPathで円・正多角形・星型正多角形
http://ferv.jp/blog/2009/10/29/graphicspath-circle-nthpolygon/
@langversion ActionScript 3.0
@playerversion Flash 10.0
@author dsk
@since 2009/10/28
/**
* Copyright minodisk ( http://wonderfl.net/user/minodisk )
* MIT License ( http://www.opensource.org/licenses/mit-license.php )
* Downloaded from: http://wonderfl.net/c/74QW
*/
package
{
import com.bit101.components.Slider;
import flash.display.GraphicsSolidFill;
import flash.display.GraphicsStroke;
import flash.display.IGraphicsData;
import flash.display.Sprite;
import flash.events.Event;
import flash.geom.Point;
/**
* http://ferv.jp/blog/2009/10/29/graphicspath-circle-nthpolygon/
*
* @langversion ActionScript 3.0
* @playerversion Flash 10.0
*
* @author dsk
* @since 2009/10/28
*/
public class SampleGraphicsPath extends Sprite
{
//--------------------------------------
// CLASS CONSTANTS
//--------------------------------------
//--------------------------------------
// PRIVATE VARIABLES
//--------------------------------------
private var _radius:Slider;
private var _length:Slider;
//--------------------------------------
// GETTER/SETTERS
//--------------------------------------
//--------------------------------------
// CONSTRUCTOR
//--------------------------------------
public function SampleGraphicsPath()
{
_radius = new Slider(Slider.HORIZONTAL, this, 0, 0, _onChange);
_length = new Slider(Slider.HORIZONTAL, this, 0, 12, _onChange);
_radius.maximum = 200;
_length.minimum = 5;
_length.maximum = 20;
_radius.value = 300;
_onChange();
}
//--------------------------------------
// PUBLIC METHODS
//--------------------------------------
//--------------------------------------
// PRIVATE METHODS
//--------------------------------------
private function _onChange(e:Event = null):void
{
var centerX:Number = stage.stageWidth / 2;
var centerY:Number = stage.stageHeight / 2;
var radius:Number = _radius.value;
var length:Number = _length.value;
graphics.clear();
graphics.drawGraphicsData(Vector.<IGraphicsData>([
new GraphicsStroke(2, false, 'normal', 'none', 'round', 3, new GraphicsSolidFill(0xFF3B9A)),
GraphicsPathUtil.createCircle(centerX, centerY, radius),
new GraphicsStroke(2, false, 'normal', 'none', 'round', 3, new GraphicsSolidFill(0xA6D810)),
GraphicsPathUtil.createRegularPolygon(centerX, centerY, radius, length),
new GraphicsStroke(2, false, 'normal', 'none', 'round', 3, new GraphicsSolidFill(0x4697CE)),
GraphicsPathUtil.createRegularStar(centerX, centerY, radius, length)
]));
}
}
}
import flash.display.GraphicsPath;
import flash.display.GraphicsPathCommand;
import flash.geom.Point;
internal class GraphicsPathUtil
{
private static const ELLIPSE_RATIO:Number = Math.SQRT2 - 1;
public static function createEllipse(x:Number, y:Number, width:Number, height:Number):GraphicsPath
{
width /= 2;
height /= 2;
x += width;
y += height;
var commands:Vector.<int> = new Vector.<int>();
var data:Vector.<Number> = new Vector.<Number>();
var i:int, signX:int, signY:int;
for (i = 0; i < 4; i ++) {
signX = (i == 0 || i == 3)? 1: -1;
signY = (i == 0 || i == 1)? 1: -1;
var points:Array = [
[x + width * signX, y],
[x + width * signX, y + height * ELLIPSE_RATIO * signY],
[x + width * Math.SQRT1_2 * signX, y + height * Math.SQRT1_2 * signY],
[x + width * ELLIPSE_RATIO * signX, y + height * signY],
[x, y + height * signY]
];
if (i % 2 != 0) points.reverse();
points.shift();
commands.push(GraphicsPathCommand.CURVE_TO, GraphicsPathCommand.CURVE_TO);
points = points[0].concat(points[1], points[2], points[3]);
data.push.apply(null, points);
}
commands.unshift(GraphicsPathCommand.MOVE_TO);
data.unshift(x + width, y);
return new GraphicsPath(commands, data);
}
public static function createCircle(x:Number, y:Number, radius:Number):GraphicsPath
{
return createEllipse(x - radius, y - radius, radius * 2, radius * 2);
}
public static function createRegularPolygon(x:Number, y:Number, radius:Number, length:uint):GraphicsPath
{
var vertices:Vector.<Point> = new Vector.<Point>();
var center:Point = new Point(x, y);
var top:Point = center.subtract(new Point(0, radius));
var i:int;
for (i = 0; i < length; i++) {
vertices[i] = PointUtil.rotateAround(top, center, (Math.PI * 2 / length) * i);
}
return createPolygon(vertices);
}
public static function createRegularStar(x:Number, y:Number, radius:Number, length:uint):GraphicsPath
{
var vertices:Vector.<Point> = new Vector.<Point>();
var center:Point = new Point(x, y);
var angle:Number = Math.PI / length;
var majorTop:Point = center.subtract(new Point(0, radius));
var minorTop:Point = PointUtil.rotateAround(center.subtract(new Point(0, radius * Math.cos(angle * 2) / Math.cos(angle))), center, angle);
angle *= 2;
var i:int;
for (i = 0; i < length; i++) {
vertices[i * 2] = PointUtil.rotateAround(majorTop, center, angle * i);
vertices[i * 2 + 1] = PointUtil.rotateAround(minorTop, center, angle * i);
}
return createPolygon(vertices);
}
public static function createPolygon(points:Vector.<Point>):GraphicsPath
{
var commands:Vector.<int> = new Vector.<int>();
var data:Vector.<Number> = new Vector.<Number>();
var i:int, point:Point;
var length:int = points.length;
for (i = 0; i < length + 1; i ++) {
point = points[i % length];
commands.push(GraphicsPathCommand.LINE_TO);
data.push(point.x, point.y);
}
commands[0] = GraphicsPathCommand.MOVE_TO;
return new GraphicsPath(commands, data);
}
}
internal class PointUtil
{
public static function rotateAround(pt:Point, center:Point, angle:Number):Point
{
return center.add(rotate(pt.subtract(center), angle));
}
public static function rotate(pt:Point, angle:Number):Point
{
return Point.polar(pt.length, getAngle(pt) + angle);
}
public static function getAngle(pt:Point):Number
{
return Math.atan2(pt.y, pt.x);
}
}