PhCirclingCamera.cpp

Go to the documentation of this file.
00001 #include "PhCirclingCamera.hpp"
00002 #include "sim/area/Area.hpp"
00003 #include "../area/NavMeshArea.hpp"
00004 #include "sim/physics/PhysicsComponent.hpp"
00005 
00006 using namespace se_basic;
00007 using namespace se_client;
00008 using namespace se_core;
00009 
00010 namespace se_basic {
00011 
00012     const PhCirclingCamera physicsCirclingCamera;   
00013 
00014 
00015     void PhCirclingCamera
00016     ::calcNext(const PhysicsComponent& physics
00017             , const Pos& pos
00018             , Pos& nextPos
00019             , const Move& move
00020             , Move& nextMove
00021             ) const {
00022     
00023         // If the camera is not inside an area, physics are meaningless
00024         if(!pos.hasArea()) {
00025             return;
00026         }
00027 
00028         if(!nextPos.hasParent()) {
00029             return;
00030         }
00031 
00032         // Player has already been updated, because it is set as
00033         // the parent by the "T" option in the data/logic/start/start.txt
00034         PosComponent::Ptr target(*nextPos.parent());
00035         const Pos& targetPos = target->nextPos();
00036 
00037         // As this camera dangles behind the player, the player should
00038         // be inside an area as well
00039         if(!targetPos.hasArea()) {
00040             return;
00041         }
00042 
00043         // If they are on the same position, move camera
00044         // to the players spawn coordinate 0
00045         //SpawnComponent::Ptr targetSpawn(*target);
00046         //ViewPoint lookAt(*playerSpawn->spawnPoint(4));
00047         //lookAt.add(playerPos.world_);
00048         ViewPoint lookAt(targetPos.world_);
00049 
00050         // Keep the camera inside the same area as the player.
00051         // (This camera cannot collide, so it doesn't matter if the 
00052         // camera coordinate is outside area bounds.)
00053         PosComponent* a = target->nextPos().area();
00054         if(a != 0 && a != nextPos.area()) {
00055             nextPos.setArea(*a);
00056         }
00057 
00058         NavMeshArea::Ptr area(ClientSchema::player->nextPos().area());
00059         Point3 dest(0, 6 * COOR_RES, 0);
00060         Vector3 tmp;
00061         tmp.sub(lookAt.coor_, pos.worldCoor());
00062         tmp.y_ = 0;
00063         coor_t dist = tmp.length();
00064         bray_t yaw = BrayT::invert(pos.worldFace().yaw_);
00065         yaw = BrayT::invert(tmp.yaw());
00066 
00067         coor_t MAX_TRAIL_DISTANCE = 16 * COOR_RES;
00068         coor_t MIN_TRAIL_DISTANCE = 1 * COOR_RES;
00069         coor_t MOVE_SPEED = 0.3f;
00070         coor_t TRAIL_DISTANCE = dist + MOVE_SPEED;
00071         if(MOVE_SPEED < 0)
00072             MOVE_SPEED = 1;
00073 
00074         if(TRAIL_DISTANCE > MAX_TRAIL_DISTANCE) {
00075             TRAIL_DISTANCE = MAX_TRAIL_DISTANCE;
00076         }
00077         coor_t legalDist = area->farthestLineOfSight(targetPos, yaw, TRAIL_DISTANCE, 1 * COOR_RES, dest);
00078         if(dist > legalDist || dist < MIN_TRAIL_DISTANCE || true) {
00079             if(TRAIL_DISTANCE > legalDist) {
00080                 TRAIL_DISTANCE -= 2 * MOVE_SPEED;
00081                 if(TRAIL_DISTANCE < legalDist) {
00082                     TRAIL_DISTANCE = legalDist;
00083                 }
00084             }
00085             //dest.add(areaPos->nextPos().worldCoor());
00086             dest.setForward(TRAIL_DISTANCE, yaw);
00087             dest.add(lookAt.coor_);
00088             dest.y_ = 6 + 2 * (1 - (TRAIL_DISTANCE / MAX_TRAIL_DISTANCE));
00089 
00090             nextPos.worldCoor().set(dest);
00091         }
00092         nextPos.worldCoor().eulerTowards(lookAt.coor_, nextPos.worldFace());
00093         //nextPos.worldFace().yaw_ = BrayT::towards(pos.worldFace().yaw_, targetPos.worldFace().yaw_, BRAY_RES >> 2);
00094 
00095         // Look at the player
00096         nextPos.updateLocalViewPoint();
00097     }
00098 
00099 
00100     void PhCirclingCamera
00101     ::affect(PhysicsComponent& physics) const {
00102         if(!PosComponent::Ptr(physics)->nextPos().hasArea()) {
00103             // Camera has left all areas - which means
00104             // it should be destroyed
00105             //physics.owner()->scheduleForDestruction();
00106         }
00107     }
00108 
00109 }

Home Page | SagaEngine trunk (updated nightly) reference generated Sun Dec 2 20:06:03 2007 by Doxygen version 1.3.9.1.

SourceForge.net Logo