// Ray-cast output data. The ray hits at p1 + fraction * (p2 - p1), where p1 and p2// come from b2RayCastInput.structb2RayCastOutput{b2Vec2normal;float32fraction;};
FooTest(){//a static bodyb2BodyDefmyBodyDef;myBodyDef.type=b2_staticBody;myBodyDef.position.Set(0,0);b2Body*staticBody=m_world->CreateBody(&myBodyDef);//shape definitionb2PolygonShapepolygonShape;//fixture definitionb2FixtureDefmyFixtureDef;myFixtureDef.shape=&polygonShape;//add four walls to the static bodyb2Vec2bl(-20,0);b2Vec2br(20,0);b2Vec2tl(-20,40);b2Vec2tr(20,40);polygonShape.SetAsEdge(bl,br);//groundstaticBody->CreateFixture(&myFixtureDef);polygonShape.SetAsEdge(tl,tr);//ceilingstaticBody->CreateFixture(&myFixtureDef);polygonShape.SetAsEdge(bl,tl);//left wallstaticBody->CreateFixture(&myFixtureDef);polygonShape.SetAsEdge(br,tr);//right wallstaticBody->CreateFixture(&myFixtureDef);myBodyDef.type=b2_dynamicBody;myBodyDef.position.Set(0,20);polygonShape.SetAsBox(2,2);myFixtureDef.density=1;for(inti=0;i<5;i++)m_world->CreateBody(&myBodyDef)->CreateFixture(&myFixtureDef);//circlesb2CircleShapecircleShape;circleShape.m_radius=2;myFixtureDef.shape=&circleShape;for(inti=0;i<5;i++)m_world->CreateBody(&myBodyDef)->CreateFixture(&myFixtureDef);//turn gravity offm_world->SetGravity(b2Vec2(0,0));}
//at global scopefloatcurrentRayAngle=0;//in Step() functioncurrentRayAngle+=360/20.0/60.0*DEGTORAD;//one revolution every 20 seconds//calculate points of rayfloatrayLength=25;//long enough to hit the wallsb2Vec2p1(0,20);//center of sceneb2Vec2p2=p1+rayLength*b2Vec2(sinf(currentRayAngle),cosf(currentRayAngle));//draw a lineglColor3f(1,1,1);//whiteglBegin(GL_LINES);glVertex2f(p1.x,p1.y);glVertex2f(p2.x,p2.y);glEnd();
//in Step() function, continuing on from section above//set up inputb2RayCastInputinput;input.p1=p1;input.p2=p2;input.maxFraction=1;//check every fixture of every body to find closestfloatclosestFraction=1;//start with end of line as p2b2Vec2intersectionNormal(0,0);for(b2Body*b=m_world->GetBodyList();b;b=b->GetNext()){for(b2Fixture*f=b->GetFixtureList();f;f=f->GetNext()){b2RayCastOutputoutput;if(!f->RayCast(&output,input))continue;if(output.fraction<closestFraction){closestFraction=output.fraction;intersectionNormal=output.normal;}}}b2Vec2intersectionPoint=p1+closestFraction*(p2-p1);//draw a lineglColor3f(1,1,1);//whiteglBegin(GL_LINES);glVertex2f(p1.x,p1.y);glVertex2f(intersectionPoint.x,intersectionPoint.y);glEnd();//draw a point at the intersection pointglPointSize(5);glBegin(GL_POINTS);glVertex2f(intersectionPoint.x,intersectionPoint.y);glEnd();
//new function for FooTest classvoiddrawReflectedRay(b2Vec2p1,b2Vec2p2){//set up inputb2RayCastInputinput;input.p1=p1;input.p2=p2;input.maxFraction=1;//check every fixture of every body to find closestfloatclosestFraction=1;//start with end of line as p2b2Vec2intersectionNormal(0,0);for(b2Body*b=m_world->GetBodyList();b;b=b->GetNext()){for(b2Fixture*f=b->GetFixtureList();f;f=f->GetNext()){b2RayCastOutputoutput;if(!f->RayCast(&output,input))continue;if(output.fraction<closestFraction){closestFraction=output.fraction;intersectionNormal=output.normal;}}}b2Vec2intersectionPoint=p1+closestFraction*(p2-p1);//draw this part of the rayglBegin(GL_LINES);glVertex2f(p1.x,p1.y);glVertex2f(intersectionPoint.x,intersectionPoint.y);glEnd();if(closestFraction==1)return;//ray hit nothing so we can finish hereif(closestFraction==0)return;//still some ray left to reflectb2Vec2remainingRay=(p2-intersectionPoint);b2Vec2projectedOntoNormal=b2Dot(remainingRay,intersectionNormal)*intersectionNormal;b2Vec2nextp2=p2-2*projectedOntoNormal;//recursedrawReflectedRay(intersectionPoint,nextp2);}
…然后在Step()方法中天假下面几行代码:
1234567
//calculate points of rayfloatrayLength=25;b2Vec2p1(0,20);//center of sceneb2Vec2p2=p1+rayLength*b2Vec2(sinf(currentRayAngle),cosf(currentRayAngle));glColor3f(1,1,1);//whitedrawReflectedRay(p1,p2);