Box2D joints: Revolute Joint

After introducing Distance Joints, it’s time to learn something about Revolute Joints.

A Revolute Joint attaches two objects by “pinning” them together at an anchor point which they may revolve around.

The most interesting thing, that I will cover in another post, is the capibility of making motors out of Revolute Joints. Yes… motors… engines… easy to do and ecologic since they don’t need fuel, just some code.

But at the moment let’s see the basic Revolute Joint.

Here it is:

Now let’s see how to make this possible:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
package {
	import flash.display.Sprite;
	import flash.events.Event;
	import Box2D.Dynamics.*;
	import Box2D.Collision.*;
	import Box2D.Collision.Shapes.*;
	import Box2D.Common.Math.*;
	import Box2D.Dynamics.Joints.*;
	import flash.events.MouseEvent;
	public class revolute_joint extends Sprite {
		var mouseJoint:b2MouseJoint;
		var mousePVec:b2Vec2 = new b2Vec2();
		var bd:b2BodyDef;
		var the_box:b2PolygonDef = new b2PolygonDef();
		var the_pivot:b2CircleDef = new b2CircleDef();
		var the_rev_joint:b2RevoluteJointDef = new b2RevoluteJointDef();
		public function revolute_joint() {
			// world setup
			var worldAABB:b2AABB = new b2AABB();
			worldAABB.lowerBound.Set(-100.0, -100.0);
			worldAABB.upperBound.Set(100.0, 100.0);
			var gravity:b2Vec2=new b2Vec2(0.0,10.0);
			var doSleep:Boolean=true;
			m_world=new b2World(worldAABB,gravity,doSleep);
			// debug draw
			var m_sprite:Sprite;
			m_sprite = new Sprite();
			addChild(m_sprite);
			var dbgDraw:b2DebugDraw = new b2DebugDraw();
			var dbgSprite:Sprite = new Sprite();
			m_sprite.addChild(dbgSprite);
			dbgDraw.m_sprite=m_sprite;
			dbgDraw.m_drawScale=30;
			dbgDraw.m_alpha = 1;
			dbgDraw.m_fillAlpha=0.5;
			dbgDraw.m_lineThickness=1;
			dbgDraw.m_drawFlags=b2DebugDraw.e_shapeBit|b2DebugDraw.e_jointBit;
			m_world.SetDebugDraw(dbgDraw);
			// pivot for revolute joint
			the_pivot.radius = 0.5;
			the_pivot.density = 0;
			bd = new b2BodyDef();
			bd.position.Set(8.5,6.5);
			var rev_joint:b2Body = m_world.CreateBody(bd);
			rev_joint.CreateShape(the_pivot)
			rev_joint.SetMassFromShapes();
			// box for the revolute joint
			the_box.SetAsBox(4,0.5);
			the_box.density = 0.01;
			the_box.friction = 1;
			the_box.restitution = 0.1;
			bd = new b2BodyDef();
			bd.position.Set(6.5,6.5);
			var rev_box:b2Body = m_world.CreateBody(bd);
			rev_box.CreateShape(the_box)
			rev_box.SetMassFromShapes();
			the_rev_joint.Initialize(rev_joint, rev_box, new b2Vec2(8.5,6.5));
			var joint_added:b2RevoluteJoint = m_world.CreateJoint(the_rev_joint) as b2RevoluteJoint;
			// listeners
			stage.addEventListener(MouseEvent.MOUSE_DOWN, createMouse);
			stage.addEventListener(MouseEvent.MOUSE_UP, destroyMouse);
			addEventListener(Event.ENTER_FRAME, Update, false, 0, true);
		}
		public function createMouse(evt:MouseEvent):void {
			var body:b2Body=GetBodyAtMouse();
			if (body) {
				var mouseJointDef:b2MouseJointDef=new b2MouseJointDef;
				mouseJointDef.body1=m_world.GetGroundBody();
				mouseJointDef.body2=body;
				mouseJointDef.target.Set(mouseX/30, mouseY/30);
				mouseJointDef.maxForce=30000;
				mouseJointDef.timeStep=m_timeStep;
				mouseJoint=m_world.CreateJoint(mouseJointDef) as b2MouseJoint;
			}
		}
		public function destroyMouse(evt:MouseEvent):void {
			if (mouseJoint) {
				m_world.DestroyJoint(mouseJoint);
				mouseJoint=null;
			}
		}
		public function GetBodyAtMouse(includeStatic:Boolean=false):b2Body {
			var mouseXWorldPhys = (mouseX)/30;
			var mouseYWorldPhys = (mouseY)/30;
			mousePVec.Set(mouseXWorldPhys, mouseYWorldPhys);
			var aabb:b2AABB = new b2AABB();
			aabb.lowerBound.Set(mouseXWorldPhys - 0.001, mouseYWorldPhys - 0.001);
			aabb.upperBound.Set(mouseXWorldPhys + 0.001, mouseYWorldPhys + 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].GetBody().IsStatic()==false||includeStatic) {
					var tShape:b2Shape=shapes[i] as b2Shape;
					var inside:Boolean=tShape.TestPoint(tShape.GetBody().GetXForm(),mousePVec);
					if (inside) {
						body=tShape.GetBody();
						break;
					}
				}
			}
			return body;
		}
		public function Update(e:Event):void {
			m_world.Step(m_timeStep, m_iterations);
			if (mouseJoint) {
				var mouseXWorldPhys=mouseX/30;
				var mouseYWorldPhys=mouseY/30;
				var p2:b2Vec2=new b2Vec2(mouseXWorldPhys,mouseYWorldPhys);
				mouseJoint.SetTarget(p2);
			}
		}
		public var m_world:b2World;
		public var m_iterations:int=10;
		public var m_timeStep:Number=1.0/30.0;
	}
}

Line 16: Declaration of the_rev_joint variable, a b2RevoluteJointDef type

Lines 40-46: Creating a circle in the middle of the stage that will act as a pivot point. In most examples around the web you will find pivot points as tiny, almost invisible boxes. I am making a big one because I think it will be easier to skin it once I will need to do it. Notice at line 41 that the object is static because it has density at zero.

Lines 48-56: Creation of the box that will be tied to the joint. You can virtually place it anywhere, but for an interesting result, it should be in a position where the joint can act as a fulcrum.

Line 57: Initializing the joint: I am passing the joint pivot, the body tied to the joint and the point of intersection. You can see the (8.5,6.5) is the same as pivot’s origin (line 43).

Line 58: Adding the joint to the world.

And that’s it. Believe me, Box2D is very easy once you know the basics.

And this is the source code for you to download.

Rate this post: 1 Star2 Stars3 Stars4 Stars5 Stars (9 votes, average: 4.78 out of 5)
Loading ... Loading ...
Flash Templates provided by Template Monster are pre-made web design products developed using Flash technology.
They can be easily customized to meet the unique requirements of your project.
Be my fan on Facebook and follow me on Twitter! Exclusive content for my Facebook fans and Twitter followers

This post has 14 comments

  1. Niall Lavigne

    on January 13, 2009 at 8:32 pm

    PLEASE make the colours a bit darker, I could hardly see the last few box2d tutorials you’ve made. It looks pretty cool but I can’t really tell D:

  2. Shival

    on January 14, 2009 at 6:36 am

    “Once you know the basics…”

    Where do we learn the basics?

  3. X-Tender

    on January 14, 2009 at 11:04 am

    Nice. Could you do something with Sensors? I have problems to understnad ist :)

  4. thivy

    on January 14, 2009 at 1:24 pm

    Hey man thanks heaps for you tuts
    i am just getting into box2d this is my new work with box2d
    http://www.thivy.com

  5. Box2D joints: Revolute Joint - Building motors : Emanuele Feronato

    on January 19, 2009 at 2:11 pm

    [...] seeing how to create a revolute joint, it’s time to use them to create [...]

  6. Creating a sling with Box2D using joints : Emanuele Feronato

    on February 7, 2009 at 10:43 pm

    [...] used a distance joint, a revolute joint and a motor. The code does not need to be commented because there is nothing new, just look how I [...]

  7. Box2D joints: Gear Joints : Emanuele Feronato

    on February 14, 2009 at 12:56 am

    [...] other kinds of joint, the gear joint requires you have two bodies connected to ground by a revolute or prismatic [...]

  8. Manjil Pote

    on March 17, 2009 at 7:27 am

    I got it so hard and complicated, very hard to understand.

  9. Two ways to make Box2D cars : Emanuele Feronato

    on April 6, 2009 at 12:45 pm

    [...] truck is made using various joints, such as revolute joints and prismatic [...]

  10. Basic Box2D rope : Emanuele Feronato

    on October 5, 2009 at 11:07 pm

    [...] link is (guess what?) linked to the previous one with a revolute joint. Refer to Box2D joints: Revolute Joint if you need more information about revolute [...]

  11. Zas

    on January 12, 2010 at 1:57 am

    Hello,

    how did you make it that the objects rotation slows down after a while?

    http://www.box2d.org/forum/viewtopic.php?f=4&t=4264&p=20404

  12. Box2DFlash 2.1a released – what changed : Emanuele Feronato - italian geek and PROgrammer

    on January 27, 2010 at 5:21 pm

    [...] words, so I created a simple vehicle you can control with left and right arrow keys. It uses revolute joints and [...]

  13. Emanuele Feronato - italian geek and PROgrammer

    on April 11, 2010 at 2:25 pm

    [...] and uncommented code, but a lot of useful information about compound objects, revolute joints and [...]

  14. jaydn

    on December 8, 2011 at 6:05 am

    Emanuele, it would be nice to see how to implement a rubber band with box2d