Created
December 10, 2010 05:41
-
-
Save threeve/735832 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#import "BoxTestViewController.h" | |
#import <Box2D/Box2D.h> | |
#define PTM_RATIO 16 | |
@interface BoxTestViewController () | |
@property (assign) b2World *world; | |
@property (retain) CADisplayLink *displayLink; | |
@end | |
@implementation BoxTestViewController | |
@synthesize world, displayLink; | |
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation | |
{ | |
return YES; | |
} | |
- (void)dealloc { | |
[super dealloc]; | |
} | |
-(void)createPhysicsWorld | |
{ | |
CGSize screenSize = self.view.bounds.size; | |
NSLog(@"screenSize: %@", NSStringFromCGSize(screenSize)); | |
// Define the gravity vector. | |
b2Vec2 gravity; | |
gravity.Set(0.0f, -9.81f); | |
// Do we want to let bodies sleep? | |
// This will speed up the physics simulation | |
bool doSleep = true; | |
// Construct a world object, which will hold and simulate the rigid bodies. | |
world = new b2World(gravity, doSleep); | |
world->SetContinuousPhysics(true); | |
// Define the ground body. | |
b2BodyDef groundBodyDef; | |
groundBodyDef.position.Set(0, 0); // bottom-left corner | |
// Call the body factory which allocates memory for the ground body | |
// from a pool and creates the ground box shape (also from a pool). | |
// The body is also added to the world. | |
b2Body* groundBody = world->CreateBody(&groundBodyDef); | |
// Define the ground box shape. | |
// b2PolygonShape groundBox; | |
// // bottom | |
// groundBox.SetAsEdge(b2Vec2(0,0), b2Vec2(screenSize.width/PTM_RATIO,0)); | |
// groundBody->CreateFixture(&groundBox, 0); | |
// | |
// // top | |
// groundBox.SetAsEdge(b2Vec2(0,screenSize.height/PTM_RATIO), b2Vec2(screenSize.width/PTM_RATIO,screenSize.height/PTM_RATIO)); | |
// groundBody->CreateFixture(&groundBox, 0); | |
// | |
// // left | |
// groundBox.SetAsEdge(b2Vec2(0,screenSize.height/PTM_RATIO), b2Vec2(0,0)); | |
// groundBody->CreateFixture(&groundBox, 0); | |
// | |
// // right | |
// groundBox.SetAsEdge(b2Vec2(screenSize.width/PTM_RATIO,screenSize.height/PTM_RATIO), b2Vec2(screenSize.width/PTM_RATIO,0)); | |
// groundBody->CreateFixture(&groundBox, 0); | |
b2EdgeShape groundBox; | |
// bottom | |
groundBox.Set(b2Vec2(0,0), b2Vec2(screenSize.width/PTM_RATIO,0)); | |
groundBody->CreateFixture(&groundBox, 0); | |
// top | |
groundBox.Set(b2Vec2(0,screenSize.height/PTM_RATIO), b2Vec2(screenSize.width/PTM_RATIO,screenSize.height/PTM_RATIO)); | |
groundBody->CreateFixture(&groundBox, 0); | |
// left | |
groundBox.Set(b2Vec2(0,screenSize.height/PTM_RATIO), b2Vec2(0,0)); | |
groundBody->CreateFixture(&groundBox, 0); | |
// right | |
groundBox.Set(b2Vec2(screenSize.width/PTM_RATIO,screenSize.height/PTM_RATIO), b2Vec2(screenSize.width/PTM_RATIO,0)); | |
groundBody->CreateFixture(&groundBox, 0); | |
} | |
-(void)addPhysicalBodyForView:(UIView *)physicalView | |
{ | |
// Define the dynamic body. | |
b2BodyDef bodyDef; | |
bodyDef.type = b2_dynamicBody; | |
CGPoint p = physicalView.center; | |
CGPoint boxDimensions = CGPointMake(physicalView.bounds.size.width/PTM_RATIO/2.0,physicalView.bounds.size.height/PTM_RATIO/2.0); | |
bodyDef.position.Set(p.x/PTM_RATIO, (self.view.bounds.size.height - p.y)/PTM_RATIO); | |
bodyDef.userData = physicalView; | |
// Tell the physics world to create the body | |
b2Body *body = world->CreateBody(&bodyDef); | |
// Define another box shape for our dynamic body. | |
b2PolygonShape dynamicBox; | |
dynamicBox.SetAsBox(boxDimensions.x, boxDimensions.y); | |
// Define the dynamic body fixture. | |
b2FixtureDef fixtureDef; | |
fixtureDef.shape = &dynamicBox; | |
fixtureDef.density = 3.0f; | |
fixtureDef.friction = 0.3f; | |
fixtureDef.restitution = 0.5f; // 0 is a lead ball, 1 is a super bouncy ball | |
body->CreateFixture(&fixtureDef); | |
// a dynamic body reacts to forces right away | |
body->SetType(b2_dynamicBody); | |
// we abuse the tag property as pointer to the physical body | |
physicalView.tag = (int)body; | |
} | |
- (void)viewDidLoad | |
{ | |
[super viewDidLoad]; | |
} | |
- (void) didRotateFromInterfaceOrientation:(UIInterfaceOrientation)fromInterfaceOrientation; | |
{ | |
NSLog(@"blarg"); | |
[self createPhysicsWorld]; | |
for (UIView *oneView in self.view.subviews) | |
{ | |
[self addPhysicalBodyForView:oneView]; | |
} | |
// tickTimer = [NSTimer scheduledTimerWithTimeInterval:1.0/60.0 target:self selector:@selector(tick:) userInfo:nil repeats:YES]; | |
[self.displayLink invalidate]; | |
self.displayLink = [CADisplayLink displayLinkWithTarget:self selector:@selector(tick:)]; | |
[self.displayLink addToRunLoop:[NSRunLoop mainRunLoop] forMode:NSDefaultRunLoopMode]; | |
} | |
//- (void)viewWillAppear:(BOOL)animated; | |
//{ | |
//} | |
-(void) tick:(CADisplayLink *)displayLink | |
{ | |
//It is recommended that a fixed time step is used with Box2D for stability | |
//of the simulation, however, we are using a variable time step here. | |
//You need to make an informed choice, the following URL is useful | |
//http://gafferongames.com/game-physics/fix-your-timestep/ | |
int32 velocityIterations = 8; | |
int32 positionIterations = 1; | |
// Instruct the world to perform a single step of simulation. It is | |
// generally best to keep the time step and iterations fixed. | |
world->Step(1.0f/60.0f, velocityIterations, positionIterations); | |
//Iterate over the bodies in the physics world | |
for (b2Body* b = world->GetBodyList(); b; b = b->GetNext()) | |
{ | |
if (b->GetUserData() != NULL) | |
{ | |
UIView *oneView = (UIView *)b->GetUserData(); | |
// y Position subtracted because of flipped coordinate system | |
CGPoint newCenter = CGPointMake(b->GetPosition().x * PTM_RATIO, | |
self.view.bounds.size.height - b->GetPosition().y * PTM_RATIO); | |
oneView.center = newCenter; | |
CGAffineTransform transform = CGAffineTransformMakeRotation(- b->GetAngle()); | |
oneView.transform = transform; | |
} | |
} | |
} | |
@end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment