flash on 2010-3-31 2010年3月31日 二つの円の接触・包含関係を判定 tenasaku forked:0favorite:1lines:86license : MIT License modified : 2010-03-31 09:21:10 Embed Tweet // 2010年3月31日 // 二つの円の接触・包含関係を判定 package { import flash.display.*; import flash.events.*; import flash.geom.*; import flash.text.*; public class FlashTest extends Sprite { private const STROKE:Number = 3; private var tf:TextField; private var ring1:Sprite,ring2:Sprite; private var radius1:Number,radius2:Number; private var velo1:Point,velo2:Point; private function initialize(e:Event):void { radius1 = 100; ring1 = new Sprite(); ring1.graphics.lineStyle(STROKE,0xff0000); ring1.graphics.beginFill(0x00ff00,0.5); ring1.graphics.drawCircle(0,0,radius1); ring1.graphics.endFill(); radius2 = 60; ring2 = new Sprite(); ring2.graphics.lineStyle(STROKE,0xff0000); ring2.graphics.beginFill(0x0000ff,0.5); ring2.graphics.drawCircle(0,0,radius2); ring2.graphics.endFill(); ring1.x = 232.5; ring1.y = 232.5; ring2.x = 300; ring2.y = 110; this.addChild(ring1); this.addChild(ring2); tf = new TextField(); tf.background = true; tf.backgroundColor = 0xffff00; tf.alpha = 0.5; tf.width = 200; tf.height = 32; tf.text = "小さいほうの円をドラッグしてください"; this.addChild(tf); ring2.addEventListener(MouseEvent.MOUSE_DOWN, onMouseDown); } private function onMouseDown(e:MouseEvent):void { ring2.startDrag(); stage.addEventListener(MouseEvent.MOUSE_MOVE, onMouseMove); stage.addEventListener(MouseEvent.MOUSE_UP, onMouseUp); } private function onMouseMove(e:MouseEvent):void { e.updateAfterEvent(); switch (howCirclesMeet()) { case 0: tf.text = "離れている"; break; case 1: tf.text = "接している"; break; case 2: tf.text = "部分的に重なっている"; break; case 3: tf.text = "接している"; break; case 4: tf.text = "完全に重なっている"; break; default: tf.text = ""; } } private function onMouseUp(e:MouseEvent):void { ring2.stopDrag(); stage.removeEventListener(MouseEvent.MOUSE_UP, onMouseUp); stage.removeEventListener(MouseEvent.MOUSE_MOVE,onMouseMove); } // 二円の接触状態を返す // 0: 接触していない // 1: 外接している // 2: 部分的に重なっている // 3: 内接している // 4: 完全に重なっている // 「接している」判定には描画の線幅程度に「余裕」を持たせる private function howCirclesMeet():int { var dx:Number = ring1.x - ring2.x; var dy:Number = ring1.y - ring2.y; var distance:Number = Math.sqrt(dx*dx+dy*dy); if ( distance > radius1+radius2+STROKE ) { return 0; // 離れている } else if ( distance > radius1+radius2-STROKE ) { return 1; // 外接している } else if ( distance > Math.abs(radius1-radius2)+STROKE ) { return 2; // 部分的に重なっている } else if ( distance > Math.abs(radius1-radius2)-STROKE ) { return 3; // 内接している } else { return 4; // 完全に重なっている } } public function FlashTest() { if ( stage != null ) { initialize(null); } else { this.addEventListener(Event.ADDED_TO_STAGE, initialize); } } } } Code Fullscreen Preview Fullscreen bradsedito 初等幾何 接触判定 Point.distance text MouseEvent.MOUSE_MOVE removeEventListener stopDrag startDrag updateAfterEvent MouseEvent.MOUSE_UP addEventListener MouseEvent Math.abs backgroundColor stage background addChild drawCircle Event.ADDED_TO_STAGE MouseEvent.MOUSE_DOWN alpha Math.sqrt