# Understanding pixels and meters with Box2D and how to select an object with mouse – part 1

This will be the longest post title in blogging history… anyway I am about to explain you two things that seem to be still unclear about AS3 version of Box2D.

The first one is Box2D measuring units that may seem weird until you realize Box2D works with meters where 1mt = 30 pixels.

The second one is the capability of selecting single objects with the mouse thanks to the custom GetBodyAtMouse. There are even people willing to pay for those information in the official forum.

So I modified the HelloWorld example in my own way in order to have some 90×90 ox sided crates (texture by http://www.reallyreallygoodthings.com/) I can make “jump” and “torque” clicking the mouse on them.

This is the uncommented actionscript, I will post the step-by-step explaination tomorrow.

package {
import flash.display.Sprite;
import flash.events.Event;
import flash.events.MouseEvent;
import Box2D.Dynamics.*;
import Box2D.Collision.*;
import Box2D.Collision.Shapes.*;
import Box2D.Common.Math.*;
public class cratetest extends Sprite {
public var m_world:b2World;
public var m_iterations:int = 10;
public var m_timeStep:Number = 1/30;
public var mousePVec:b2Vec2 = new b2Vec2();
public var real_x_mouse:Number;
public var real_y_mouse:Number;
public var pixels_in_a_meter = 30;
public var worldAABB:b2AABB = new b2AABB()
public var gravity:b2Vec2 = new b2Vec2(0.0, 10.0);
public function cratetest() {
worldAABB.lowerBound.Set(-100.0, -100.0);
worldAABB.upperBound.Set(100.0, 100.0);
m_world = new b2World(worldAABB, gravity, true);
var body:b2Body;
var bodyDef:b2BodyDef;
var boxDef:b2PolygonDef;
bodyDef = new b2BodyDef();
bodyDef.position.Set(8.5, 13.5);
boxDef = new b2PolygonDef();
var ground_width = 8.5;
var ground_height = 0.5;
boxDef.SetAsBox(ground_width, ground_height);
boxDef.friction = 0.3;
boxDef.density = 0;
bodyDef.userData = new floor();
bodyDef.userData.width = ground_width * 2 * pixels_in_a_meter;
bodyDef.userData.height = ground_height * 2 * pixels_in_a_meter;
body = m_world.CreateBody(bodyDef);
body.CreateShape(boxDef);
body.SetMassFromShapes();
for (var i:int = 1; i <=5; i++) {
bodyDef = new b2BodyDef();
bodyDef.position.x = Math.random() * 15 + 1;
bodyDef.position.y = Math.random();
var crate_width:Number = 1.5;
var crate_height:Number = 1.5;
boxDef = new b2PolygonDef();
boxDef.SetAsBox(crate_width, crate_height);
boxDef.density = 1.0;
boxDef.friction = 0.5;
boxDef.restitution = 0.2;
bodyDef.userData = new crate();
bodyDef.userData.width = crate_width * 2 * pixels_in_a_meter;
bodyDef.userData.height = crate_height * 2* pixels_in_a_meter;
body = m_world.CreateBody(bodyDef);
body.CreateShape(boxDef);
body.SetMassFromShapes();
}
}
public function Update(e:Event):void {
m_world.Step(m_timeStep, m_iterations);
for (var bb:b2Body = m_world.m_bodyList; bb; bb = bb.m_next) {
if (bb.m_userData is Sprite) {
bb.m_userData.x = bb.GetPosition().x * pixels_in_a_meter;
bb.m_userData.y = bb.GetPosition().y * pixels_in_a_meter;
bb.m_userData.rotation = bb.GetAngle() * (180/Math.PI);
}
}
}
public function on_mouse_down(e:MouseEvent) {
var body:b2Body = GetBodyAtMouse();
if (body) {
body.ApplyImpulse(new b2Vec2(0.0, -80.0), body.GetWorldCenter());
body.ApplyTorque(450);
}
}
public function GetBodyAtMouse(includeStatic:Boolean=false):b2Body {
real_x_mouse = (stage.mouseX)/pixels_in_a_meter;
real_y_mouse = (stage.mouseY)/pixels_in_a_meter;
mousePVec.Set(real_x_mouse, real_y_mouse);
var aabb:b2AABB = new b2AABB();
aabb.lowerBound.Set(real_x_mouse - 0.001, real_y_mouse - 0.001);
aabb.upperBound.Set(real_x_mouse + 0.001, real_y_mouse + 0.001);
var k_maxCount:int = 10;
var shapes:Array = new Array();
var count:int = m_world.Query(aabb, shapes, k_maxCount);
var body:b2Body = null;
for (var i:int = 0; i < count; ++i) {
if (shapes[i].m_body.IsStatic() == false || includeStatic) {
var tShape:b2Shape = shapes[i] as b2Shape;
var inside:Boolean = tShape.TestPoint(tShape.m_body.GetXForm(), mousePVec);
if (inside) {
body = tShape.m_body;
break;
}
}
}
return body;
}
}
}

and this is the result:

Click on a crate to make it jump and torque. Download the source code and wait for the step-by-step tutorial.

215 GAME PROTOTYPES EXPLAINED WITH SOURCE CODE
// 1+2=3
// 10000000
// 2 Cars
// 2048
// Avoider
// Ballz
// Block it
// Blockage
// Bloons
// Boids
// Bombuzal
// Breakout
// Bricks
// Columns
// CubesOut
// Dots
// DROP'd
// Dudeski
// Eskiv
// Filler
// Fling
// Globe
// HookPod
// Hundreds
// InkTd
// Iromeku
// Lumines
// Magick
// MagOrMin
// Maze
// Memdot
// Nano War
// Nodes
// o:anquan
// Ononmin
// Pacco
// Phyballs
// Platform
// Poker
// Pool
// Poux
// Pudi
// qomp
// Racing
// Renju
// SameGame
// Security
// Sling
// Slingy
// Sokoban
// Splitter
// Sproing
// Stack
// Stairs
// Stringy
// Sudoku
// Tetris
// Threes
// Toony
// Turn
// TwinSpin
// vvvvvv
// Wordle
// Worms
// Yanga
// Zhed
// zNumbers