反重力ポイント
反重力ポイント
@author tkinjo
/**
* Copyright tkinjo ( http://wonderfl.net/user/tkinjo )
* MIT License ( http://www.opensource.org/licenses/mit-license.php )
* Downloaded from: http://wonderfl.net/c/s132
*/
// forked from tkinjo's 反重力ポイント(四方の壁)フォースマップ
// forked from tkinjo's forked from: カラーグリッド
// forked from tkinjo's カラーグリッド
// forked from tkinjo's ストライプ
// forked from tkinjo's minimalcomps を使ってコンポーネントを作ってみた
package
{
import flash.display.*;
import flash.events.*;
import flash.geom.*;
import com.bit101.components.*;
import flash.ui.Mouse;
[SWF(width="465", height="465", backgroundColor="0xffffff", frameRate="60")]
/**
* 反重力ポイント
*
* @author tkinjo
*/
public class Main extends Sprite
{
private const MAX_POWER:Number = 100;
private var stageWidth:Number = stage.stageWidth;
private var stageHeight:Number = stage.stageHeight;
/** --------------------------------------------------
* component
*/
private var configPanel:SlidePanel;
private var gridNumInputTextAndHSlider:InputTextAndHSlider;
private var wallPowerInputTextAndHSlider:InputTextAndHSlider;
private var wallDecreasingPowerInputTextAndHSlider:InputTextAndHSlider;
private var gravityPointPowerInputTextAndHSlider:InputTextAndHSlider;
private var gravityPointDecreasingPowerInputTextAndHSlider:InputTextAndHSlider;
private var selectPushButton:PushButton;
private var influencedPointPushButton:PushButton;
private var gravityPointPushButton:PushButton;
/** --------------------------------------------------
*
*/
private var gravitySprites:Vector.<GravitySprite>;
private var influencedPoints:Vector.<Particle>;
private var viewBitmapData:BitmapData;
private var viewBitmap:Bitmap;
private var view:Sprite;
private var movedSprite:Sprite;
public function Main()
{
setComponents();
influencedPoints = new Vector.<Particle>();
gravitySprites = new Vector.<GravitySprite>();
influencedPointPushButton.selected = true;
view.addEventListener(MouseEvent.MOUSE_DOWN, mouseDownHandler );
stage.addEventListener(MouseEvent.MOUSE_UP, mouseUpHandler );
stage.addEventListener(MouseEvent.MOUSE_MOVE, mouseMoveHandler );
addEventListener(Event.ENTER_FRAME, enterframeHandler );
draw();
}
private function setComponents():void {
viewBitmapData = new BitmapData( stageWidth, stageHeight, true, 0x0 );
viewBitmap = new Bitmap( viewBitmapData );
view = new Sprite();
view.addChild( viewBitmap );
addChild( view );
configPanel = new SlidePanel( 0, 0, stageWidth, 0, 1, 0xffffff, 0.9 );
addChild( configPanel );
// gridNumInputTextAndHSlider
gridNumInputTextAndHSlider = createInputTextAndHSlider( "resolution" );
gridNumInputTextAndHSlider.round = 0;
gridNumInputTextAndHSlider.value = 32;
gridNumInputTextAndHSlider.hSlider.maximum = 32;
gridNumInputTextAndHSlider.addEventListener(Event.CHANGE, function( event:Event ):void {
draw();
} );
// wall power
wallPowerInputTextAndHSlider = createInputTextAndHSlider( "wall power", gridNumInputTextAndHSlider );
wallPowerInputTextAndHSlider.round = 0;
wallPowerInputTextAndHSlider.hSlider.maximum = 100;
wallPowerInputTextAndHSlider.hSlider.minimum = -100;
wallPowerInputTextAndHSlider.value = 10;
wallPowerInputTextAndHSlider.addEventListener(Event.CHANGE, function( event:Event ):void {
draw();
} );
// wall dpower
wallDecreasingPowerInputTextAndHSlider = createInputTextAndHSlider( "wall dpower", wallPowerInputTextAndHSlider );
wallDecreasingPowerInputTextAndHSlider.round = 1;
wallDecreasingPowerInputTextAndHSlider.hSlider.maximum = 10;
wallDecreasingPowerInputTextAndHSlider.hSlider.minimum = -10;
wallDecreasingPowerInputTextAndHSlider.value = 2;
wallDecreasingPowerInputTextAndHSlider.addEventListener(Event.CHANGE, function( event:Event ):void {
draw();
} );
// gravityPoint power
gravityPointPowerInputTextAndHSlider = createInputTextAndHSlider( "gpoint power", wallDecreasingPowerInputTextAndHSlider );
gravityPointPowerInputTextAndHSlider.round = 0;
gravityPointPowerInputTextAndHSlider.hSlider.maximum = 100;
gravityPointPowerInputTextAndHSlider.hSlider.minimum = -100;
gravityPointPowerInputTextAndHSlider.value = 10;
gravityPointPowerInputTextAndHSlider.addEventListener(Event.CHANGE, function( event:Event ):void {
for ( var i:uint = 0; i < gravitySprites.length; i++ ) {
gravitySprites[i].gravityPoint.power = gravityPointPowerInputTextAndHSlider.value;
}
draw();
} );
// gravityPoint dpower
gravityPointDecreasingPowerInputTextAndHSlider = createInputTextAndHSlider( "gpoint dpower", gravityPointPowerInputTextAndHSlider );
gravityPointDecreasingPowerInputTextAndHSlider.round = 1;
gravityPointDecreasingPowerInputTextAndHSlider.hSlider.maximum = 10;
gravityPointDecreasingPowerInputTextAndHSlider.hSlider.minimum = -10;
gravityPointDecreasingPowerInputTextAndHSlider.value = 2;
gravityPointDecreasingPowerInputTextAndHSlider.addEventListener(Event.CHANGE, function( event:Event ):void {
for ( var i:uint = 0; i < gravitySprites.length; i++ ) {
gravitySprites[i].gravityPoint.decreasingPower = gravityPointDecreasingPowerInputTextAndHSlider.value;
}
draw();
} );
// select
selectPushButton = createPushButton( "select", gravityPointDecreasingPowerInputTextAndHSlider, true );
selectPushButton.toggle = true;
selectPushButton.addEventListener(MouseEvent.CLICK, function( event:MouseEvent ):void {
if ( selectPushButton.selected ) {
unselectedPushButton();
selectPushButton.selected = true;
} else
selectPushButton.selected = true;
} );
// influenced point
influencedPointPushButton = createPushButton( "influenced point", selectPushButton );
influencedPointPushButton.toggle = true;
influencedPointPushButton.addEventListener(MouseEvent.CLICK, function( event:MouseEvent ):void {
if ( influencedPointPushButton.selected ) {
unselectedPushButton();
influencedPointPushButton.selected = true;
} else
selectPushButton.selected = true;
} );
// gravity point
gravityPointPushButton = createPushButton( "gravity point", influencedPointPushButton );
gravityPointPushButton.toggle = true;
gravityPointPushButton.addEventListener(MouseEvent.CLICK, function( event:MouseEvent ):void {
if ( gravityPointPushButton.selected ) {
unselectedPushButton();
gravityPointPushButton.selected = true;
} else
selectPushButton.selected = true;
} );
configPanel.height = gravityPointPushButton.y + gravityPointPushButton.height + 15;
// hueCircle
var hueCircle:HueCircle = new HueCircle( 50, 30 );
hueCircle.x = hueCircle.radius + stageWidth - hueCircle.width;
hueCircle.y = hueCircle.radius + stageHeight - hueCircle.height;
hueCircle.graphics.beginFill( 0xffffff );
hueCircle.graphics.drawRect( -hueCircle.radius, -hueCircle.radius, hueCircle.width, hueCircle.height );
hueCircle.graphics.endFill();
addChild( hueCircle );
}
private function unselectedPushButton():void {
selectPushButton.selected = false;
influencedPointPushButton.selected = false;
gravityPointPushButton.selected = false;
}
private function createInputTextAndHSlider( text:String = "", component:DisplayObject = null ):InputTextAndHSlider {
var inputTextAndHSlider:InputTextAndHSlider = new InputTextAndHSlider( configPanel, 10, ( component != null ) ? component.y + component.height + 10 : 10, text );
inputTextAndHSlider.label.width = 70;
inputTextAndHSlider.inputText.width = 30;
inputTextAndHSlider.hSlider.width = 300;
return inputTextAndHSlider;
}
private function createPushButton( text:String = "", component:DisplayObject = null, newLine:Boolean = false ):PushButton {
var pushButton:PushButton = new PushButton( configPanel,
( component != null && !newLine ) ?
component.x + component.width + 10 :
10,
( component != null ) ?
( ( newLine ) ?
component.y + component.height + 10 :
component.y
) :
10,
text );
return pushButton;
}
private function force( point:Point ):Point {
var force:Point = new Point( 0, 0 );
for ( var i:uint = 0; i < gravitySprites.length; i++ ) {
var gravityPointForce:Point = gravitySprites[i].gravityPoint.force( point );
force.x += gravityPointForce.x;
force.y += gravityPointForce.y;
}
var wallPower:Number = wallPowerInputTextAndHSlider.value;
var wallDecreasingPower:Number = wallDecreasingPowerInputTextAndHSlider.value;
var topWallGravity:GravityPoint = new GravityPoint( point.x, 0, wallPower, wallDecreasingPower );
var rightWallGravity:GravityPoint = new GravityPoint( stageWidth, point.y, wallPower, wallDecreasingPower );
var bottomWallGravity:GravityPoint = new GravityPoint( point.x, stageHeight, wallPower, wallDecreasingPower );
var leftWallGravity:GravityPoint = new GravityPoint( 0, point.y, wallPower, wallDecreasingPower );
var topWallForce:Point = topWallGravity.force( point );
var rightWallForce:Point = rightWallGravity.force( point );
var bottomWallForce:Point = bottomWallGravity.force( point );
var leftWallForce:Point = leftWallGravity.force( point );
force.y += topWallForce.y;
force.x += rightWallForce.x;
force.y += bottomWallForce.y;
force.x += leftWallForce.x;
return force;
}
private function draw():void {
graphics.clear();
var i:int;
var j:int;
var gridNum:Number = gridNumInputTextAndHSlider.value;
var gridNumPower:Number = Math.pow( gridNum, 2 );
var gridWidth:Number = stageWidth / gridNum;
var gridHeight:Number = stageHeight / gridNum;
var forces:Vector.<Vector.<Point>> = new Vector.<Vector.<Point>>( gridNum );
var maxForceLength:Number = 0;
for ( i = 0; i < gridNum; i++ ) {
forces[i] = new Vector.<Point>( gridNum );
for ( j = 0; j < gridNum; j++ ) {
var point:Point = new Point( i * stageWidth / gridNum + gridWidth / 2, j * stageHeight / gridNum + gridHeight / 2 );
forces[i][j] = force( point );
var length:Number = forces[i][j].length;
if ( maxForceLength < length )
maxForceLength = length;
}
}
var centerPoint:Point = new Point();
for ( i = 0; i < gridNum; i++ ) {
for ( j = 0; j < gridNum; j++ ) {
//var color:int = HSVtoRGB( getHueCircleAngle( centerPoint, forces[i][j] ), forces[i][j].length / maxForceLength, 1 );
var color:int = HSVtoRGB( getHueCircleAngle( centerPoint, forces[i][j] ), 0.5, 1 );
graphics.beginFill( color, 1 );
graphics.drawRect( i * stageWidth / gridNum, j * stageHeight / gridNum, gridWidth, gridHeight );
graphics.endFill();
}
}
}
private function enterframeHandler( event:Event ):void {
var influencedPointPosition:Point = new Point();
for ( var i:uint = 0; i < influencedPoints.length; i++ ) {
var influencedPoint:Particle = influencedPoints[i];
influencedPointPosition.x = influencedPoint.x;
influencedPointPosition.y = influencedPoint.y;
influencedPoint.vx = influencedPoint.vx * 0.98 + force( influencedPointPosition ).x * 0.5;
influencedPoint.vy = influencedPoint.vy * 0.98 + force( influencedPointPosition ).y * 0.5;
influencedPoint.x += influencedPoint.vx;
influencedPoint.y += influencedPoint.vy;
if (influencedPoint.x < 1)
influencedPoint.x = 1;
else if ( influencedPoint.x > stageWidth - 1 )
influencedPoint.x = stageWidth - 1;
if ( influencedPoint.y < 1 )
influencedPoint.y = 1;
else if ( influencedPoint.y > stageHeight - 1 )
influencedPoint.y = stageHeight - 1;
}
}
private function mouseDownHandler( event:MouseEvent ):void {
if ( influencedPointPushButton.selected ) {
var particle:Particle = new Particle( event.stageX, event.stageY );
influencedPoints.push( particle );
view.addChild( particle );
particle.addEventListener(MouseEvent.MOUSE_DOWN, function( event:MouseEvent ):void {
if ( selectPushButton.selected && movedSprite == null )
movedSprite = event.currentTarget as Sprite;
} );
} else if ( gravityPointPushButton.selected ) {
var gravitySprite:GravitySprite = new GravitySprite( event.stageX, event.stageY,
gravityPointPowerInputTextAndHSlider.value, gravityPointDecreasingPowerInputTextAndHSlider.value );
gravitySprites.push( gravitySprite );
view.addChild( gravitySprite );
draw();
gravitySprite.addEventListener(MouseEvent.MOUSE_DOWN, function( event:MouseEvent ):void {
if ( selectPushButton.selected && movedSprite == null )
movedSprite = event.currentTarget as Sprite;
} );
}
}
private function mouseUpHandler( event:MouseEvent ):void {
movedSprite = null;
}
private function mouseMoveHandler( event:MouseEvent ):void {
if ( movedSprite == null )
return;
movedSprite.x = event.stageX;
movedSprite.y = event.stageY;
if( movedSprite is GravitySprite )
draw();
}
}
}
import com.bit101.components.*;
import flash.display.*;
import flash.events.*;
import flash.geom.*;
import flash.text.*;
import org.libspark.betweenas3.BetweenAS3;
import org.libspark.betweenas3.easing.Cubic;
class GravityPoint extends Point {
private var _power:Number;
public function get power():Number {
return _power;
}
public function set power(value:Number):void
{
_power = value;
}
private var _decreasingPower:Number;
public function get decreasingPower():Number {
return _decreasingPower;
}
public function set decreasingPower(value:Number):void
{
_decreasingPower = value;
}
public function force( point:Point ):Point {
var positionFromPoint:Point = subtract( point );
var forceLength:Number = power / Math.pow( positionFromPoint.length, decreasingPower );
var angle:Number = Angle.normalizeRadianM180toP180(Math.PI/2 - Math.atan2(point.y - y, point.x - x));
var forceX:Number = Math.sin(angle) * forceLength;
var forceY:Number = Math.cos(angle) * forceLength;
return new Point( forceX, forceY );
}
public function GravityPoint( x:Number, y:Number, power:Number = -1000, decreasingPower:Number = 2 ):void {
super(x,y);
_power = power;
_decreasingPower = decreasingPower;
}
}
class Angle {
public static const RADIAN_0_DEGREE:Number = 0;
public static const RADIAN_90_DEGREE:Number = Math.PI / 2;
public static const RADIAN_180_DEGREE:Number = Math.PI;
public static const RADIAN_270_DEGREE:Number = Math.PI / 2 * 3;
public static const RADIAN_360_DEGREE:Number = 2 * Math.PI;
public static function normalizeRadian0to360( value:Number ):Number {
value %= Angle.RADIAN_360_DEGREE;
if( value < RADIAN_0_DEGREE )
value += Angle.RADIAN_360_DEGREE;
return value;
}
public static function normalizeRadianM180toP180( value:Number ):Number {
value = normalizeRadian0to360( value );
if( value > RADIAN_180_DEGREE )
value -= Angle.RADIAN_360_DEGREE;
return value;
}
}
class Particle extends Sprite {
public var vx:Number;
public var vy:Number;
function Particle( x:Number = 0, y:Number = 0, vx:Number = 0, vy:Number = 0 ) {
this.x = x;
this.y = y;
this.vx = vx;
this.vy = vy;
graphics.beginFill( 0x0 );
graphics.drawCircle( 0, 0, 10 );
graphics.endFill();
}
}
class GravitySprite extends Sprite {
public function get gravityPoint():GravityPoint { return _gravityPoint; }
private var _gravityPoint:GravityPoint;
public override function set x(value:Number):void {
super.x = value;
_gravityPoint.x = value;
}
public override function set y(value:Number):void
{
super.y = value;
_gravityPoint.y = value;
}
public function GravitySprite( x:Number = 0, y:Number = 0, power:Number = -1000, decreasingPower:Number = 2 ) {
super.x = x;
super.y = y;
_gravityPoint = new GravityPoint( x, y, power, decreasingPower );
graphics.beginFill( 0x0 );
graphics.drawCircle( 0, 0, 10 );
graphics.drawCircle( 0, 0, 8 );
graphics.drawCircle( 0, 0, 6 );
graphics.endFill();
}
}
/* -----
* component
*/
class LabelEx extends Label {
/**
* Dispatched after a control value is modified, unlike the textInput event, which is dispatched before the value is modified.
* @eventType flash.events.Event.CHANGE
*/
[Event(name = "change", type = "flash.events.Event")]
/**
* ...
* @eventType com.bit101.components.Component.DRAW
*/
[Event(name = "draw", type = "com.bit101.components.Component")]
private var textField:TextField;
public function LabelEx(parent:DisplayObjectContainer = null, xpos:Number = 0, ypos:Number = 0, text:String = ""):void
{
super(parent, xpos, ypos, text);
}
/**
* Initializes the component.
*/
override protected function init():void
{
super.init();
setSize(100, 16);
}
/**
* Creates and adds the child display objects of this component.
*/
override protected function addChildren():void
{
super.addChildren();
for ( var i:uint = 0; i < numChildren; i++ ) {
var child:DisplayObject = getChildAt( i );
if ( child is TextField ) {
textField = child as TextField;
break;
}
}
}
}
class InputTextEx extends InputText {
/**
* Dispatched after a control value is modified, unlike the textInput event, which is dispatched before the value is modified.
* @eventType flash.events.Event.CHANGE
*/
[Event(name = "change", type = "flash.events.Event")]
/**
* ...
* @eventType com.bit101.components.Component.DRAW
*/
[Event(name = "draw", type = "com.bit101.components.Component")]
private var textField:TextField;
public function InputTextEx(parent:DisplayObjectContainer = null, xpos:Number = 0, ypos:Number = 0, text:String = "", defaultHandler:Function = null)
{
super( parent, xpos, ypos, text, defaultHandler );
}
/**
* Creates and adds child display objects.
*/
override protected function addChildren():void
{
super.addChildren();
for ( var i:uint = 0; i < numChildren; i++ ) {
var child:DisplayObject = getChildAt( i );
if ( child is TextField ) {
textField = child as TextField;
break;
}
}
textField.autoSize = TextFieldAutoSize.LEFT;
}
protected override function onChange(event:Event):void
{
super.onChange( event );
dispatchEvent( event );
}
}
class HSliderEx extends HSlider {
/**
* Dispatched after a control value is modified, unlike the textInput event, which is dispatched before the value is modified.
* @eventType flash.events.Event.CHANGE
*/
[Event(name = "change", type = "flash.events.Event")]
/**
* ...
* @eventType com.bit101.components.Component.DRAW
*/
[Event(name = "draw", type = "com.bit101.components.Component")]
public function HSliderEx(parent:DisplayObjectContainer = null, xpos:Number = 0, ypos:Number = 0, defaultHandler:Function = null):void
{
super(parent, xpos, ypos, defaultHandler);
}
}
class InputTextAndHSlider extends Sprite {
/**
* Dispatched after a control value is modified, unlike the textInput event, which is dispatched before the value is modified.
* @eventType flash.events.Event.CHANGE
*/
[Event(name = "change", type = "flash.events.Event")]
/**
* label
*/
public function get label():Label {
return _label;
}
private var _label:Label;
/**
* inputText
*/
public function get inputText():InputTextEx {
return _inputText;
}
private var _inputText:InputTextEx;
/**
* hSlider
*/
public function get hSlider():HSliderEx {
return _hSlider;
}
private var _hSlider:HSliderEx;
/**
* round
*/
public var round:int = 2;
/**
* value
*/
public function get value():Number {
return _value;
}
public function set value( tempValue:Number ):void {
hSlider.value = tempValue;
_value = Math.round( hSlider.value * Math.pow( 10, round ) ) / Math.pow( 10, round );
if ( !isNaN( value ) )
inputText.text = value.toString();
dispatchEvent( new Event( Event.CHANGE ) );
}
private var _value:Number;
/**
*
* @param parent
* @param xpos
* @param ypos
* @param text
*/
public function InputTextAndHSlider(parent:DisplayObjectContainer=null, xpos:Number=0, ypos:Number=0, text:String = ""):void
{
parent.addChild( this );
x = xpos;
y = ypos;
// label
_label = new LabelEx( this, 0, 0, text );
// inputText
_inputText = new InputTextEx( this );
inputText.restrict = "-0-9.";
updateInputTextPosition( label );
// hSlider
_hSlider = new HSliderEx( this );
hSlider.backClick = true;
updateHSliderPosition( inputText );
// hSlider eventlistener
label.addEventListener(Component.DRAW, function( event:Event ):void {
updateInputTextPosition( label );
} );
// inputText eventlistener
inputText.addEventListener(Event.CHANGE, function( event:Event ):void {
value = parseFloat( inputText.text );
} );
inputText.addEventListener(Component.DRAW, function( event:Event ):void {
updateHSliderPosition( inputText );
} );
inputText.addEventListener(FocusEvent.FOCUS_OUT, function( event:FocusEvent ):void {
if ( isNaN( value ) )
inputText.text = "0";
} );
// hSlider eventlistener
hSlider.addEventListener(Event.CHANGE, function( event:Event ):void {
value = hSlider.value;
} );
}
/**
*
* @param component
*/
private function updateInputTextPosition( component:DisplayObject ):void {
inputText.y = component.y + ( component.height - inputText.height ) / 2;
inputText.x = ( component.x + component.width ) + ( inputText.y - component.y );
}
/**
*
* @param component
*/
private function updateHSliderPosition( component:Component ):void {
hSlider.y = component.y + ( component.height - hSlider.height ) / 2;
hSlider.x = ( component.x + component.width ) + ( hSlider.y - component.y );
}
}
class ClearColorPanel extends Sprite {
private var _backgroundColor:Number;
public function get backgroundColor():Number { return _backgroundColor; }
public function set backgroundColor(value:Number):void
{
_backgroundColor = value;
draw();
}
private var _backgroundAlpha:Number;
public function get backgroundAlpha():Number { return _backgroundAlpha; }
public function set backgroundAlpha(value:Number):void
{
_backgroundAlpha = value;
draw();
}
private var _width:Number;
public override function get width():Number { return _width; }
public override function set width(value:Number):void
{
_width = value;
draw();
}
private var _height:Number;
public override function get height():Number { return _height; }
public override function set height(value:Number):void
{
_height = value;
draw();
}
public function ClearColorPanel( x:Number = 0, y:Number = 0, width:Number = 0, height:Number = 0, alpha:Number = 1, backgroundColor:int = 0, backgroundAlpha:Number = 0.1 ) {
this.x = x;
this.y = y;
_width = width;
_height = height;
this.alpha = alpha;
_backgroundColor = backgroundColor;
_backgroundAlpha = backgroundAlpha;
draw();
}
public function draw():void {
graphics.clear();
graphics.beginFill( backgroundColor, backgroundAlpha );
graphics.drawRect( 0, 0, width, height );
graphics.endFill();
}
}
class SlidePanel extends Sprite {
private var panel:ClearColorPanel;
private var openCloseSwitchButton:PushButton;
private var open:Boolean;
public override function set width(value:Number):void
{
super.width = value;
panel.width = value;
openCloseSwitchButton.x = width - 20;
}
public override function set height(value:Number):void
{
super.height = height;
panel.height = value;
}
public function SlidePanel( x:Number = 0, y:Number = 0, width:Number = 0, height:Number = 0, alpha:Number = 1, backgroundColor:int = 0, backgroundAlpha:Number = 0.1 ) {
this.x = x;
this.y = y;
panel = new ClearColorPanel( 0, 0, width, height, alpha, backgroundColor, backgroundAlpha );
super.addChild( panel );
openCloseSwitchButton = new PushButton(super, width - 20, 0);
super.addChild( openCloseSwitchButton );
openCloseSwitchButton.width = 20;
openCloseSwitchButton.addEventListener(MouseEvent.CLICK, openCloseSwitchButtonClickHandler );
openCloseSwitchButton.label = "-";
open = true;
}
private function openCloseSwitchButtonClickHandler( event:MouseEvent ):void {
// hide
if ( open )
show();
// show
else
hide();
}
private function show():void {
open = false;
openCloseSwitchButton.label = "+";
BetweenAS3.tween(panel, {y: -panel.height}, null, 0.5, Cubic.easeInOut ).play();
}
private function hide():void {
open = true;
openCloseSwitchButton.label = "-";
BetweenAS3.tween(panel, { y: 0 }, null, 0.5, Cubic.easeInOut ).play();
}
override public function addChild(child:DisplayObject):DisplayObject
{
return panel.addChild(child);
}
override public function addChildAt(child:DisplayObject, index:int):DisplayObject
{
return panel.addChildAt(child, index);
}
}
class HueCircle extends Sprite {
public function get radius():Number { return _radius; }
public function set radius(value:Number):void
{
_radius = value;
draw();
}
private var _radius:Number;
public function get innerRadius():Number { return _innerRadius; }
public function set innerRadius(value:Number):void
{
_innerRadius = value;
draw();
}
private var _innerRadius:Number;
private var bitmap:Bitmap;
private var circleMask:Sprite;
public function HueCircle( radius:Number, innerRadius:Number = 0 ) {
_radius = radius;
_innerRadius = innerRadius;
var diameter:Number = radius * 2;
if ( hueCircleBitmapData == null )
resizeHueCircleBitmapData( diameter );
bitmap = new Bitmap( hueCircleBitmapData );
bitmap.cacheAsBitmap = true;
addChild( bitmap );
circleMask = new Sprite();
circleMask.cacheAsBitmap = true;
addChild( circleMask );
bitmap.mask = circleMask;
draw();
}
private function draw():void {
circleMask.graphics.clear();
circleMask.graphics.beginFill( 0xffffff );
circleMask.graphics.drawCircle( radius, radius, radius);
if( innerRadius != 0 ) circleMask.graphics.drawCircle( radius, radius, innerRadius );
circleMask.graphics.endFill();
var largeRadius:Number = ( ( radius > innerRadius ) ? radius : innerRadius );
bitmap.x = -largeRadius;
bitmap.y = -largeRadius;
bitmap.scaleX = largeRadius / ( hueCircleBitmapData.width / 2 );
bitmap.scaleY = largeRadius / ( hueCircleBitmapData.width / 2 );
circleMask.x = -radius;
circleMask.y = -radius;
}
private static var hueCircleBitmapData:BitmapData;
public static function resizeHueCircleBitmapData( width:Number ):void {
var centerPoint:Point = new Point( width / 2, width / 2 );
var tempPoint:Point = new Point();
hueCircleBitmapData = new BitmapData( width, width, false );
hueCircleBitmapData.lock();
for ( var i:int = 0; i < width; i++ ) {
for ( var j:int = 0; j < width; j++ ) {
tempPoint.x = i;
tempPoint.y = j;
hueCircleBitmapData.setPixel( i, j, getHueCircleColor( centerPoint, tempPoint ) );
}
}
hueCircleBitmapData.unlock();
}
}
function getHueCircleColor( centerPoint:Point, point:Point ):uint {
return HSVtoRGB( getHueCircleAngle( centerPoint, point ), 1, 1 );
}
function getHueCircleAngle( centerPoint:Point, point:Point ):uint {
var pointFromCenterPoint:Point = point.subtract( centerPoint );
var pointBearingFromCenterPoint:Number = Math.atan2( pointFromCenterPoint.y, pointFromCenterPoint.x ) * 180 / Math.PI;
if ( pointBearingFromCenterPoint < 0 )
pointBearingFromCenterPoint = pointBearingFromCenterPoint + 360;
return pointBearingFromCenterPoint;
}
function HSVtoRGB( h:Number, s:Number, v:Number ):uint {
var Hi:uint = ( h / 60 ) % 6;
var f:Number = h / 60 - Hi;
var p:Number = v * ( 1 - s );
var q:Number = v * ( 1 - f * s );
var t:Number = v * ( 1 - ( 1 - f ) * s );
switch( Hi ) {
case 0:
return toRGB255( v, t, p );
case 1:
return toRGB255( q, v, p );
case 2:
return toRGB255( p, v, t );
case 3:
return toRGB255( p, q, v );
case 4:
return toRGB255( t, p, v );
case 5:
return toRGB255( v, p, q );
}
return 0;
}
function toRGB255( r:Number, g:Number, b:Number ):uint {
return ( r * 255 << 16 ) + ( g * 255 << 8 ) + b * 255;
}