string PhysicsController::run(string myState, float time_since_last_tick) { string game_state_request = " "; for(vector<Entity*>::size_type i = 0; i != controlled_entities.size(); i++) { if(controlled_entities[i]->getGameState()==myState) { if(controlled_entities[i]->getActive()) { //PULL THE MOVING OBJECTS INFORMATION PhysicsComponent* physics = (PhysicsComponent*)controlled_entities[i]->getComponent("Physics"); PositionComponent* position = (PositionComponent*)controlled_entities[i]->getComponent("Position"); //PULLING ALL THE MASS AND FORCE INFORMATION float total_mass = 0 + physics->getMass(); float total_translation [2] = {0,0}; float moment_of_inertia = 0 + physics->getMass(); float total_torque = 0; if( controlled_entities[i]->checkIfHasComponent("Collection")) { CollectionComponent* collection = (CollectionComponent*) controlled_entities[i]->getComponent("Collection"); vector<Entity*> attached_entities = collection->getAttachedEntities(); //Cycling through attached entities for(vector<Entity*>::size_type p = 0; p != attached_entities.size(); p++) { Entity* attached_entity = attached_entities[p]; TetheredComponent* tethered = (TetheredComponent*) attached_entity->getComponent("Tethered"); PhysicsComponent* attached_physics = (PhysicsComponent*) attached_entity->getComponent("Physics"); PositionComponent* attached_position = (PositionComponent*) attached_entity->getComponent("Position"); RocketComponent* rocket = (RocketComponent*) attached_entity->getComponent("Rocket"); float radian_from_center_mass = tethered->getDirectionRadian(); float radian_to_center_mass = radian_from_center_mass + 3.1415926; float t = attached_position->getAngle() - radian_to_center_mass ; tethered->setT(t); //Translational vector<float> attached_vector_forces = attached_physics->getNetTranslationalForce(); total_translation[0] += attached_vector_forces[0]; total_translation[1] += attached_vector_forces[1]; total_mass+= attached_physics->getMass(); //Angular float attached_net_angular_force = attached_physics->getNetAngularForce(); total_torque += attached_net_angular_force; float distance = tethered->getDistance(); moment_of_inertia += attached_physics->getMass()*(distance*distance); } } //Apparently on forces that have a distance can spin it //So after we've pulled all the angular forces we can find the angular acceleration //and then you use torque = I*a physics->setAngularAcceleration(total_torque/moment_of_inertia); //PLANAR MOVEMENT //We already have the tethered objects' forces so now we need the forces affectin the main object itself vector<float> vector_forces = physics->getNetTranslationalForce(); total_translation[0] += vector_forces[0]; total_translation[1] += vector_forces[1]; //Calculating the net acceleration net forces and net mass physics->setAccelerationX(total_translation[0]/total_mass); physics->setAccelerationY(total_translation[1]/total_mass); //Determine its new velocity physics->setVelocityX(physics->getVelocity()[0]+physics->getAcceleration()[0]*time_since_last_tick); physics->setVelocityY(physics->getVelocity()[1]+physics->getAcceleration()[1]*time_since_last_tick); //Determine its new position if its not tethered to something if( !controlled_entities[i]->checkIfHasComponent("Tethered")) { position->setX(position->getPosition()[0]+physics->getVelocity()[0]*time_since_last_tick); position->setY(position->getPosition()[1]+physics->getVelocity()[1]*time_since_last_tick); } //ANGULAR MOVEMENT // Both tethered and collected entities get this because a tethered can be rotating on its own // on top of being rotated by the collectors movement. // On it's own, a tethered object cannot have an angular acceleration, it must be machine assisted. physics->setAngularVelocity(physics->getAngularVelocity()+physics->getAngularAcceleration()*time_since_last_tick); position->setAngle(position->getAngle()+physics->getAngularVelocity()*time_since_last_tick); //To make sure the tethered objects get moved we make sure the collector handles them we he is passed into this controller if( controlled_entities[i]->checkIfHasComponent("Collection")) { CollectionComponent* collection = (CollectionComponent*) controlled_entities[i]->getComponent("Collection"); vector<Entity*> attached_entities = collection->getAttachedEntities(); //Go throuhg all the attached entities and update their tethered position wiht the new positon of the collector for(vector<Entity*>::size_type p = 0; p != attached_entities.size(); p++) { Entity* attached_entity = attached_entities[p]; TetheredComponent* tethered = (TetheredComponent*) attached_entity->getComponent("Tethered"); PhysicsComponent* attached_physics = (PhysicsComponent*) attached_entity->getComponent("Physics"); PositionComponent* attached_position = (PositionComponent*) attached_entity->getComponent("Position"); ////Determine its new position //As the object spins so will all the tethered objects tethered->setDirectionRadian( tethered->getDirectionRadian() + physics->getAngularVelocity()*time_since_last_tick); float radian_from_center_mass = tethered->getDirectionRadian(); float radian_to_center_mass = radian_from_center_mass + 3.1415926; attached_position->setAngle(radian_to_center_mass + tethered->getT()); //Need to update the angle of the rocket as the main ship spins //Set the tethered object to the new position in the new direction attached_position->setX( position->getPosition()[0] + cos(tethered->getDirectionRadian())*tethered->getDistance()); attached_position->setY( position->getPosition()[1] + sin(tethered->getDirectionRadian())*tethered->getDistance()); } } position->calculateBucketPosition(BUCKET_WIDTH); } } } return game_state_request; }
string RocketController::run(string myState) { string game_state_request; for(vector<Entity*>::size_type i = 0; i != controlled_entities.size(); i++) { Entity* ent = controlled_entities[i]; if(ent->getGameState() == myState) { if(ent->getActive()) { //SUBTRACT FUEL SpaceshipComponent* spaceship = (SpaceshipComponent*) ent->getComponent("Spaceship"); float current_fuel = spaceship->getCurrentFuel(); CollectionComponent* collection = (CollectionComponent*) ent->getComponent("Collection"); vector<Entity*> attached_entities = collection->getAttachedEntities(); //Cycling through attached entities for(vector<Entity*>::size_type p = 0; p != attached_entities.size(); p++) { Entity* attached_entity = attached_entities[p]; attached_entity->setActive(true); if(attached_entity->checkIfHasComponent("Rocket")) { RocketComponent* rocket = (RocketComponent*) attached_entity->getComponent("Rocket"); TetheredComponent* tethered = (TetheredComponent*) attached_entity->getComponent("Tethered"); PositionComponent* position = (PositionComponent*) attached_entity->getComponent("Position"); PhysicsComponent* physics = (PhysicsComponent*) attached_entity->getComponent("Physics"); physics->clearForces(); if(rocket->getOnOrOff()) { if(spaceship->getCurrentFuel() - rocket->getFuelConsumption() >= 0) { //The rocket is on float force_exerted = rocket->getForceExerted(); float angle = position->getAngle(); float x = rocket->getForceExerted()*cos(angle); float y = rocket->getForceExerted()*sin(angle); physics->addTranslationalForce(x,y); //Angular Forces float distance = tethered->getDistance(); float angular_force = distance * rocket->getForceExerted() * -sin(tethered->getT()); physics->addAngularForce(angular_force); //Burning fuel spaceship->subtractCurrentFuel(rocket->getFuelConsumption()); } } } } } else { CollectionComponent* collection = (CollectionComponent*) ent->getComponent("Collection"); vector<Entity*> attached_entities = collection->getAttachedEntities(); //Cycling through attached entities for(vector<Entity*>::size_type p = 0; p != attached_entities.size(); p++) { attached_entities[p]->setActive(false); } } } } return game_state_request; }