Chap06 PointクラスとRectangleクラス: 2009年7月アーカイブ

(section06-03 衝突判定から抜粋)

 intersects()とcontainsRect()は矩形と矩形の衝突判定を行う関数です。intersects()は比較する矩形と矩形が少しでも重なっているときにtrueになり、containsRect()は矩形の中に比較する矩形が完全に入っているときにtrueになります。
 次の例はcontainsRect()のサンプルです。写真のphoto_mcインスタンスを写真枠のphotoFrame_mcインスタンスにドラッグ&ドロップしたとき、photo_mcがphotoFrame_mcの領域の中に完全に入っているかどうかを判定しています。photo_mcがphotoFrame_mcの領域の中に完全に入っているときはphoto_mcをphotoFrame_mcの中央に位置揃えし、領域内に完全に入っていないときはphotoFrame_mcの外に出してしまいます。

fig06-03-03a.jpgswfを試す

[:script:]photo_mcをphotoFrame_mcの矩形の中に入るようにドロップしたか判定する
//マウスダウンでドラッグ開始
photo_mc.addEventListener(MouseEvent.MOUSE_DOWN, onStartDrag);
//ドラッグ開始
function onStartDrag(eventObj:MouseEvent):void {
	photo_mc.startDrag(false);
	photo_mc.alpha=0.5;
	stage.addEventListener(MouseEvent.MOUSE_UP, onStopDrag);
}
//ドラッグ終了
function onStopDrag(eventObj:MouseEvent):void {
	photo_mc.stopDrag();
	photo_mc.alpha=1;
	containsCheck();
}
//photo_mcの矩形がphotoFrame_mcの矩形に完全に入っているかどうかチェックする
function containsCheck():void {
	//photoFrame_mcの矩形
	var frameBounds:Rectangle=photoFrame_mc.getBounds(stage);
	//photo_mcの矩形
	var photoBounds:Rectangle=photo_mc.getBounds(stage);
	//photo_mcの矩形がphotoFrame_mcの矩形に完全に入っているかどうか
	if (frameBounds.containsRect(photoBounds)) {
		//入っていれば中央に表示する
		var center_x:Number=frameBounds.left+photoFrame_mc.width/2;
		var center_y:Number=frameBounds.top+photoFrame_mc.height/2;
		photo_mc.x=center_x-photoBounds.width/2;
		photo_mc.y=center_y-photoBounds.height/2;
	} else {
		//photoFrame_mcの外に出してしまう
		photo_mc.x=frameBounds.right+photoBounds.width/2;
		photo_mc.y=frameBounds.top+photoBounds.height/2;
	}
}
(section06-03 衝突判定から抜粋)

 containsPoint()は点と領域を比較します。引数で指定した点が矩形領域の中に入っているときにtureになります。
 次のサンプルは写真の3つの部分を示すrect_1、rect_2、rect_3の矩形を作っておき、その領域にカーソルが入ったらその部分をインスタンスで囲んで示します。
 マウスカーソルが矩形の中に入っているかどうかをチェックするのは24行目です。矩形のrect_1、rect_2、rect_3は写真の左上角を座標の基準としているので、マウス座標と比較するために、20行目ではステージでの写真の左上角の頂点に合わせて座標をオフセットしています。このとき、矩形に対してoffset()を実行すると元の矩形が変化するので18行目のようにclone()で複製した矩形を使って比較を行います。
 ステージにはあらかじめ矩形を囲むインスタンスselectBox_mcを作っておきます。処理を簡単にするためにselectBox_mcは左上角に基準点があるように作ります。

fig06-03-01b.jpgswfを試す

[:script:]カーソルが領域に入ったならば領域を囲むインスタンスを表示する
//選択枠の初期化
selectBox_mc.visible=false;
selectBox_mc.alpha=0.5;
//ホット領域の矩形
var rect_1:Rectangle=new Rectangle(120,10,35,20);//江ノ島
var rect_2:Rectangle=new Rectangle(230,30,120,25);//サーファー
var rect_3:Rectangle=new Rectangle(170,75,120,70);//ボードキャリア
var rectList:Array=[rect_1,rect_2,rect_3];
//写真の矩形
var photoRect:Rectangle=photo_mc.getRect(stage);
//ロールオーバーのチェック
stage.addEventListener(MouseEvent.MOUSE_MOVE, rollCheck);
function rollCheck(eventObj:MouseEvent):void {
	for (var i:int=0; i<rectList.length; i++) {
		//チェックする矩形を取り出す
		var rect:Rectangle=rectList[i];
		//offset処理で変化しないように矩形の複製を作る
		var chkRect:Rectangle=rect.clone();
		//矩形をステージのグローバル座標に合わせる
		chkRect.offset(photoRect.left,photoRect.top);
		//マウス座標
		var mousePt:Point=new Point(stage.mouseX,stage.mouseY);
		//マウス座標がホット領域に入っているかチェックする
		if (chkRect.containsPoint(mousePt)) {
			//選択枠を表示する
			selectBox_mc.x=chkRect.x;
			selectBox_mc.y=chkRect.y;
			selectBox_mc.width=chkRect.width;
			selectBox_mc.height=chkRect.height;
			selectBox_mc.visible=true;
			//forによる無駄な繰り返しを抜ける
			break;
		} else {
			//選択枠を消す
			selectBox_mc.visible=false;
		}
	}
}
(section06-02 Rectangleクラスから抜粋)

 次のサンプルは回転しながら水平移動するインスタンスbox_mcがステージの両端で跳ね返ります。box_mcが回転しているので変化する領域をgetBounds()で取得し、box_mcの左右の辺の座標をleft、rightのプロパティで取り出しています。

fig06-02-06_shiji.jpgswfを試す

[:script:]回転しながら移動し、ステージの両端で跳ね返る
var dx:int=5;
var dd:int=15;
box_mc.addEventListener(Event.ENTER_FRAME, onEnterframe);
function onEnterframe(eventObj:Event):void {
	//box_mcの領域を調べる
	var bounds:Rectangle=box_mc.getBounds(stage);
	//左右の辺がステージからはみ出たら動作を反転する
	if (bounds.left<0) {
		dx*=-1;
		dd*=-1;
	} else if (bounds.right>stage.stageWidth) {
		dx*=-1;
		dd*=-1;
	}
	//移動と回転
	box_mc.x+=dx;
	box_mc.rotation+=dd;
}
(section06-01 Pointクラスから抜粋)

 次のサンプルではインスタンスball_mcとマウスカーソルの距離を測り、距離が200ピクセル以内になったとき、マウスが近づくほどball_mcが速く回転するというものです。ball_mcとマウスカーソルの距離は8行目のPoint.distance(ballPt,mousePt)で計算しています。ball_mcとマウスカーソルの距離はマウスカーソルがball_mcの左右上下のどの方向にあっても正の値になります。また、11行目では回転速度が大きく成りすぎないように距離が10ピクセルより近づいたときには、計算では10ピクセルを最低値として使用しています。

fig06-01-06.jpgswfを試す

[:script:]マウスが近づくほど回転が速くなる
addEventListener(Event.ENTER_FRAME, onEnterframe);
function onEnterframe(eventObj:Event):void {
	//インスタンスの座標
	var ballPt:Point=new Point(ball_mc.x,ball_mc.y);
	//マウスの座標
	var mousePt:Point=new Point(stage.mouseX,stage.mouseY);
	//インスタンスとマウスの距離
	var distance:Number=Point.distance(ballPt,mousePt);
	//距離が200以下の時に回転する
	if(distance<200){
		ball_mc.rotation+=2000/Math.max(10,distance);
	}
}
まったく新しいAS3の世界!
694a.jpg
Adobe Flash CS4
詳細!ActionScript3.0入門ノート[完全改訂版](CD-ROM付)

楽しいActionScript。
新たなる1歩へと踏み出しましょう。
■内容は?→ 目次を見る
■評判は?→ 書評を読む
この本を書いたわけ

このアーカイブについて

このページには、2009年7月以降に書かれたブログ記事のうちChap06 PointクラスとRectangleクラスカテゴリに属しているものが含まれています。

最近のコンテンツはインデックスページで見られます。過去に書かれたものはアーカイブのページで見られます。

あわせて読みたいブログパーツ