問答収集 カテゴリ:Flashプログラミング
現在のスレッド一覧 / 新規に質問を投稿
レス数:10 / 状態:未解決 / No:59 / ATOM
1 名前:pupu 日付:2010/09/10(金)10:42:43 ID:4aboKz05wQBP
flash8, AS2.0です。

初歩的な質問で恐縮です。
以下の条件の動きを設定したいと思っています。

[1].mcはスタート地点から設定した目的地点へ向かって動く
[2].最高速度を設定できる
[3].加速し減速する
[4].目的地点へは直線で動く

http://hakuhin.jp/as/move.html#MOVE_02
こちらをベースにスクリプトを書きました。
大分理想的な動きを得ることができましたが、
これでは縦横が独立し放物線を描いて動くので[4]を実現できません。

flaファイルを上げました、
どなたかアドバイスをいただけると幸いです。

moveto_100910.fla(2つとも同じ)
http://sharedfile.jp/r/dKV9Xlu0Xh8LGBju/
2 名前:(1/2) 日付:2010/09/13(月)13:40:07 ID:qPr0YUEfJmUW
目的地への移動は奥が深いと思います。

二次元座標上を移動するのでベクトルを使って計算してみます。


// --------------------------------------------
// パラメータ
// --------------------------------------------
var SPEED_ADD = 1;// 加速度
var SPEED_MAX =50;// 最高速度
var SPEED_FRI = 0.7;// 摩擦係数(0.0~1.0)
var SPEED_FRI_SIDE = 0.7;// 目的地と垂直な方向の摩擦係数(0.0~1.0)

var POS_START_x = 200;// 開始座標
var POS_START_y = 200;// 開始座標
var POS_END_x   =300;// 終了座標
var POS_END_y   = 0;// 終了座標


// --------------------------------------------
// 初期化
// --------------------------------------------
var px = POS_START_x;// x 座標
var py = POS_START_y;// y 座標
var dx = 0.0;// x 方向の速度
var dy = 0.0;// y 方向の速度
3 名前:(2/3) 日付:2010/09/13(月)13:41:55 ID:qPr0YUEfJmUW

// --------------------------------------------
// 毎フレーム実行されるイベント
// --------------------------------------------
mc.onEnterFrame = function(){

// マウスの座標を目的地に
POS_END_x   = _root._xmouse;// 終了座標
POS_END_y   = _root._ymouse;// 終了座標

// 現在位置から目的地までのベクトル
var sub_x = POS_END_x - px;
var sub_y = POS_END_y - py;

// ベクトルの長さ
var len = Math.sqrt((sub_x * sub_x) + (sub_y * sub_y));

// ベクトルを正規化
var nor_x = sub_x * (1 / len);
var nor_y = sub_y * (1 / len);

// 0.1px以下まで近づいたら終了
if ( len  <= 0.1){
this._x = POS_END_x;
this._y = POS_END_y;
delete(this.onEnterFrame);
}
4 名前:(3/3) 日付:2010/09/13(月)13:42:21 ID:qPr0YUEfJmUW

// 目的地までの距離に(1.0 - 摩擦係数)を乗算
len = len * (1.0 - SPEED_FRI);

// 加速度ベクトルを速度ベクトルに加算
dx += nor_x * SPEED_ADD;
dy += nor_y * SPEED_ADD;

// 現在の速度ベクトルの長さを取得
var spd = Math.sqrt((dx * dx) + (dy * dy));

// 速度ベクトルを正規化
nor_x = dx * (1 / spd);
nor_y = dy * (1 / spd);

// 最高速度を超えていないかチェック
if(spd > SPEED_MAX)spd = SPEED_MAX;

// 減速すべきかチェック
if(spd > len)spd = len;

// 丸めたスカラ値を速度ベクトルに反映
dx = nor_x * spd;
dy = nor_y * spd;

// 速度を座標に加算する
px += dx;
py += dy;

// 座標をインスタンスの座標に反映
this._x = px;
this._y = py;
}
5 日付:2010/09/13(月)13:44:24 ID:qPr0YUEfJmUW

>>2>>4のソースを動作させてみると
目的地の周りをグルグルと回り続け、目的地にたどり着けない事があります。


そこで、「現在の位置から目的地の方向」と垂直な方向に摩擦運動を発生させて
目的地にいずれたどり着くように補正してみます。
6 名前:(1/3) 日付:2010/09/13(月)13:44:38 ID:qPr0YUEfJmUW
// --------------------------------------------
// パラメータ
// --------------------------------------------
var SPEED_ADD = 1;// 加速度
var SPEED_MAX =50;// 最高速度
var SPEED_FRI = 0.7;// 摩擦係数(0.0~1.0)
var SPEED_FRI_SIDE = 0.7;// 目的地と垂直な方向の摩擦係数(0.0~1.0)

var POS_START_x = 200;// 開始座標
var POS_START_y = 200;// 開始座標
var POS_END_x   =300;// 終了座標
var POS_END_y   = 0;// 終了座標


// --------------------------------------------
// 初期化
// --------------------------------------------
var px = POS_START_x;// x 座標
var py = POS_START_y;// y 座標
var dx = 0.0;// x 方向の速度
var dy = 0.0;// y 方向の速度
7 名前:(2/3) 日付:2010/09/13(月)13:45:04 ID:qPr0YUEfJmUW
// --------------------------------------------
// 毎フレーム実行されるイベント
// --------------------------------------------
mc.onEnterFrame = function(){

// マウスの座標を目的地に
POS_END_x   = _root._xmouse;// 終了座標
POS_END_y   = _root._ymouse;// 終了座標

// 現在位置から目的地までのベクトル
var sub_x = POS_END_x - px;
var sub_y = POS_END_y - py;

// ベクトルの長さ
var len = Math.sqrt((sub_x * sub_x) + (sub_y * sub_y));

// ベクトルを正規化
var nor_x = sub_x * (1 / len);
var nor_y = sub_y * (1 / len);

// 0.1px以下まで近づいたら終了
if ( len  <= 0.1){
this._x = POS_END_x;
this._y = POS_END_y;
delete(this.onEnterFrame);
}
8 名前:(3/3) 日付:2010/09/13(月)13:45:31 ID:qPr0YUEfJmUW
// 目的地までの距離に(1.0 - 摩擦係数)を乗算
len = len * (1.0 - SPEED_FRI);

// 加速度ベクトルを速度ベクトルに加算
dx += nor_x * SPEED_ADD;
dy += nor_y * SPEED_ADD;

// 現在の速度ベクトルから「現在位置から目的地までのベクトルと垂直な方向」なベクトルを抽出
var t = -(nor_x * dx + nor_y * dy)/(nor_x * nor_x + nor_y * nor_y);
var fx = dx + t * nor_x;
var fy = dy + t * nor_y;

// 摩擦係数を乗算して速度ベクトルに減算
dx -= fx * (1.0 - SPEED_FRI_SIDE);
dy -= fy * (1.0 - SPEED_FRI_SIDE); 

// 現在の速度ベクトルの長さを取得
var spd = Math.sqrt((dx * dx) + (dy * dy));

// 速度ベクトルを正規化
nor_x = dx * (1 / spd);
nor_y = dy * (1 / spd);

// 最高速度を超えていないかチェック
if(spd > SPEED_MAX)spd = SPEED_MAX;

// 減速すべきかチェック
if(spd > len)spd = len;

// 丸めたスカラ値を速度ベクトルに反映
dx = nor_x * spd;
dy = nor_y * spd;

// 速度を座標に加算する
px += dx;
py += dy;

// 座標をインスタンスの座標に反映
this._x = px;
this._y = py;
}
9 日付:2010/09/13(月)13:51:42 ID:qPr0YUEfJmUW
目的地への補正が弱すぎると、目的地にたどり着けなくなる恐れがあり
逆に目的地への補正が強すぎると、カクカクとした直線的な動きになります。

パラメータの調整が重要になりそうです。
10 日付:2010/09/14(火)16:50:08 ID:xr5yYD7zgFJJ
y=axみたいにy座標に加算する速度を
(yの直線距離÷xの直線距離)×(xの速度)にしたらどうでしょうか?


67// 速度を座標に加算する
68px += dx;
69py += dy;



// 速度を座標に加算する
px += dx;
py += ((POS_START_y - POS_END_y) / (POS_START_x - POS_END_x))*dx;
このスレッドについて
質問の状態 :
未解決
投稿開始日 :
2010/09/10(金)10:42:43
投稿終了日 :
2010/09/14(火)16:50:08
投稿者 :
pupu
レス総数 :
10
スレッド番号 :
59
MondoCollectionSystem ver.0x00020000 by Hakuhin