今回もbox2dwebやります
キーでオブジェクトをいろいろ制御します。
今回のスクリーンショットです。
全ソースコードです。
キー操作をするためにjQueryも使ってます。
test.html
<canvas id="canvas" width="600px" height="420px" style="background-color:#333333;"></canvas>
<pre>
fキー:力をかける
iキー:衝撃を与える
vキー:一定速度を与える
tキー:瞬間移動させる
</pre>
<script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1.8.0/jquery.min.js"></script>
<script type="text/javascript" src="Box2dWeb-2.1.a.3.min.js"></script>
<script type="text/javascript">
// Box2Dオブジェクトを取得
var b2Vec2 = Box2D.Common.Math.b2Vec2 // 2Dベクトル
, b2BodyDef = Box2D.Dynamics.b2BodyDef // Body定義
, b2Body = Box2D.Dynamics.b2Body // Body
, b2FixtureDef = Box2D.Dynamics.b2FixtureDef // Fixture定義
, b2Fixture = Box2D.Dynamics.b2Fixture // Fixture
, b2World = Box2D.Dynamics.b2World // 物理世界
, b2PolygonShape = Box2D.Collision.Shapes.b2PolygonShape // 衝突オブジェクトの形状(ポリゴン)
, b2CircleShape = Box2D.Collision.Shapes.b2CircleShape // 衝突オブジェクトの形状(円)
, b2DebugDraw = Box2D.Dynamics.b2DebugDraw // デバッグ描画
// 世界を作る
var world = new b2World(new b2Vec2(0,10), true);
////////////////////////////////////
//box
var bodyDef = new b2BodyDef;
bodyDef.type = b2Body.b2_dynamicBody;
bodyDef.position.Set(2,1);
bodyDef.fixedRotation = true;
var fixDef = new b2FixtureDef;
fixDef.density = 1.0;
fixDef.friction = 0.4;
fixDef.restitution = .5;
fixDef.shape = new b2PolygonShape;
fixDef.shape.SetAsBox(.5,1);
var box = world.CreateBody(bodyDef);
box.CreateFixture(fixDef);
//地面
var holderDef = new b2BodyDef;
holderDef.type = b2Body.b2_staticBody;
holderDef.position.Set(8, 14);
var fd = new b2FixtureDef;
fd.shape = new b2PolygonShape;
fd.shape.SetAsBox(8,1);
var ground = world.CreateBody(holderDef);
ground.CreateFixture(fd);
var keydown = 0;
// 力
function push(c) {
if(c==1)
box.ApplyForce(new b2Vec2(0,-300), box.GetWorldCenter());
}
// 衝撃
function hit(c) {
if(c==1)
box.ApplyImpulse(new b2Vec2(5,0), box.GetWorldCenter());
}
// 速度
function speed(c) {
if(c==1){
box.SetAwake(true);
box.SetLinearVelocity(new b2Vec2(4,0));
}
}
// テレポート
function teleport(c) {
if(c==1){
box.SetAwake(true);
box.SetPositionAndAngle(new b2Vec2(10,0),Math.PI/3);
}
}
$(window).keydown(function(key) {
keydown++;
var code = key.keyCode;
if(code == 102 || code == 70) push(keydown); // fキー
if(code == 105 || code == 73) hit(keydown); // iキー
if(code == 118 || code == 86) speed(keydown); // vキー
if(code == 116 || code == 84) teleport(keydown); // tキー
});
$(window).keyup(function(e) {
keydown=0;
});
////////////////////////////////////
// デバッグ描画の設定
var debugDraw = new b2DebugDraw();
debugDraw.SetSprite ( document.getElementById ("canvas").getContext ("2d"));
debugDraw.SetDrawScale(30); //描画スケール
debugDraw.SetFillAlpha(0.3); //半透明値
debugDraw.SetLineThickness(1.0);//線の太さ
debugDraw.SetFlags(b2DebugDraw.e_shapeBit | b2DebugDraw.e_jointBit);// 何をデバッグ描画するか
world.SetDebugDraw(debugDraw);
window.setInterval(update,1000/60);
function update() {
world.Step(1 / 60, 10, 10); // 物理世界を更新する
world.DrawDebugData(); // デバック描画
world.ClearForces(); // 物理世界上の力をリセットする
}
</script>
今回はBodyが回転しないように
fixedRotationフラグをtrueにして
向きを固定します
bodyDef.fixedRotation = true;
このフラグを入れないとボックスが転んでしまうので
アクションゲームのキャラクターとかだと必須です。
今回は次の4つの制御を行ってみます
①オブジェクトに力を加える
②オブジェクトに衝撃を加える
③オブジェクトの速度を指定する
④オブジェクトの位置、向きを指定する
①ApplyForceメソッドでオブジェクトに力を加えることが出来ます。
第1引数には力ベクトル
第2引数には力を加える位置を指定します
box.ApplyForce(new b2Vec2(0,-300), box.GetWorldCenter());
②ApplyImpulseメソッドでオブジェクトに衝撃を加えることが出来ます。
ApplyForceメソッドと引数は同じですが、
計算式が違います。
こちらは瞬間的な力を加えます
box.ApplyImpulse(new b2Vec2(5,0), box.GetWorldCenter());
③SetLinearVelocityメソッドで平行移動速度を指定します。
力を加えている訳ではないのでスリープ状態で
判定されずにめり込んだりする場合があるので
SetAwakeでアクティブにしておいた方がよいです
box.SetAwake(true);
box.SetLinearVelocity(new b2Vec2(4,0));
④SetPositionAndAngleメソッドで位置と向きの指定が出来ます。
こちらもSetAwakeしておいた方がよいです
box.SetAwake(true);
box.SetPositionAndAngle(new b2Vec2(10,0),Math.PI/3);
次回は衝突判定の取得をやります。