Advanced Camera
by Thomas \"Man of Ice\" Lund · 04/03/2008 (11:57 am) · 480 comments
Download Code File
Description
Over time a lot of people have released camera resources, but some do not work anymore, others are hard to implement etc.
I've tried to assemble a single class to add to the engine that implements them all in one go using the same basic architecture. This enables minimum code bloat and makes it way easier to keep the code up to date.
Change log
March 3rd, 2005
Manoel made some changes to the orbit camera. Works in multiplayer now and is much nicer by using console variables
February 3rd, 2005
Fixed small big in interpolation.
February 2nd, 2005
Major changes in this one with various contributors.
* Static camera mode
* Smooth interpolation and transition between modes
* Smooth orbit camera!!!
* Vertical freedom mode when in 3rd person
* Better collision check with terrain and interiors
* Mouse control of orbit camera
* Totally reworked codebase and lots of cleanups. Much more readable now
Manoel Neto contributed the new orbit camera and the interpolation
Zik Saleeba contributed the vertical freedom mode and better collision check
Thanks a lot!!!!
I have marked changes with a New in the text below for those who upgrade
January 23rd, 2005
Minor changes. Larger update soon with new functionality
* Now takes GameBase objects as target + player
* Removed debug message in orbit camera
* Added getters for player and target object
June 25th, 2004
Updated the bindings for orbit camera. Switched left+right.
June 23rd, 2004
A big thanks to Stephen Zepp for contributing with an orbit camera mode. Its added to the resource, and is perfect for RTS games and action adventures. It allows for a camera to rotate around a user as if placed on a sphere. The user can zoom in/out, rotate and tilt the camera.
June 9th, 2004
Added getter/setter for the 3 offset values accessible from script
Added a "follow terrain" mode for the third person camera, so the camera follows the terrain slope - doesnt work perfectly
April 5th, 2004
All camera modes now use a raycast to not get hidden behind terrain or interiors
April 3rd, 2004
This release is the first release, and might not be as "advanced" as the author would like, but its time to release it and get some feedback to further enhance it down the road.
Camera Modes Implemented
The resource currently implements the following camera systems:
* Track Mode
This is the same as the tracking camera resource posted by Cory Osborn. A stationary camera tracks the player and keeps him in focus.
* New Static Mode
Camera stays in its position and rotation. Useful for e.g. scene based adventures where the camera doesnt move with the players
* Third Person Mode
The camera is placed at an offset behind the player and rotates with the player. The camera itself is not controllable
* Third Person Track Mode
The camera is placed in third person mode but rotated so it always looks at a specified object, but with the player in full view
* God View
Camera is placed at an offset from the player and does not rotate with the player. This is your typical "Diablo" kind of camera.
* New Orbit Mode
Camera is placed on a sphere looking at the player, and can rotate/tilt and zoom controlled by the player. There are bindings to the mouse when in single player game (server and client on same machine)
Movie
Here is a small movie displaying the different camera modes (3 MB)
www.codejar.com/advancedcamerademo.wmv
How to Add
First off all you need to take the attached advancedCamera.cc/h files and add to engine\game and add them to the project.
Then you need to expose the camera object in GameConnection as described in Cory's resource www.garagegames.com/index.php?sec=mg&mod=resource&page=view&qid=4720
I took the liberty to paste the relevant parts in here too
Exposing mCameraObject
The first thing you want to do is add console method's to access the GameConnection setCameraObject/getCameraObject methods. I added these to GameConnection.cc right after the console method for getControlObject:
After playing around with it, I also found you need some adjustments to the setCameraObject and setControlObject methods - otherwise the client connection can screw things up if you bounce the same object from your connection's control to camera or vice versa. Here is my GameConnection::setControlObject:
and here is my GameConnection::setCameraObject:
Camera read/write packets
None of this will work unless the client copy of the camera object gets packets updated. Here we're going to modify GameConnection::readPacket and GameConnection::writePacket.
In GameConnection::readPacket, find this block of code:
and change it to
In GameConnection::writePacket, find this block of code:
and change it to:
Recompile it all and the engine is ready to go.
Script
To use the camera you need to follow some of Corys resource, but with some modifications. Datablock and naming has changed
First, add a datablock for the tracking camera to /fps/server/scripts/camera.cs:
Next, add it to the connection just like is currently done with the base camera class. Add this inside GameConnection::onClientEnterGame (/fps/server/scripts/game.cs), right after %this.camera is set up:
We'll need to clean it up after the client leaves the game, so add this to GameConnection::onClientLeaveGame
We need to tell it what to do when added and assign the connection's camera object, so add this to the end of GameConnection::createPlayer:
And we'll want to unhook it when the player dies. Insert this at the beginning of GameConnection::onDeath:
The last thing to know, is if you're in first-person mode, GameConnection automatically uses the control object to render the engine rather than the camera object. So if you don't see this working when you first enter a mission, toggle out of first-person.
Orbit mode
To use the orbit camera, one needs to add some key binds to manipulating the camera.
All you need to do, is add the following to your client\config.cs or better to your client\scripts\default.bind.cs
Remember to comment out the mouse commands for the player movement, as these are overwritten by the orbit camera controls
Script API
To use the different camera modes you can use the following API
Selecting the camera mode is done with e.g.:
Prior to calling the above modes you have to set the PlayerObject using
To use the 3rd person target mode you also need to set a TargetObject using
To use the static or tracking camera you need to set the position the camera should be placed suing
To use the follow terrain mode in 3rd person you give a bool to
To use the vertical freedom mode in 3rd person you give a bool to
The offset values in the datablock can be changed for the camera object via script using
The orbit camera can be manipulated from script using
You can also manipulate the orbit camera directly by assigning values to the following variables
[code]
$advCamera::Yaw
$advCamera::Pitch
$advCamera::Zoom
$advCamera::azimuth
$advCamera::declination
$advCamera::zoomDistance
[code]
All camera modes coexist, so you can set the position, player object and target object once and then switch camera modes around as you see fit. Switching mode will not clear the old objects/positions.
Description
Over time a lot of people have released camera resources, but some do not work anymore, others are hard to implement etc.
I've tried to assemble a single class to add to the engine that implements them all in one go using the same basic architecture. This enables minimum code bloat and makes it way easier to keep the code up to date.
Change log
March 3rd, 2005
Manoel made some changes to the orbit camera. Works in multiplayer now and is much nicer by using console variables
February 3rd, 2005
Fixed small big in interpolation.
February 2nd, 2005
Major changes in this one with various contributors.
* Static camera mode
* Smooth interpolation and transition between modes
* Smooth orbit camera!!!
* Vertical freedom mode when in 3rd person
* Better collision check with terrain and interiors
* Mouse control of orbit camera
* Totally reworked codebase and lots of cleanups. Much more readable now
Manoel Neto contributed the new orbit camera and the interpolation
Zik Saleeba contributed the vertical freedom mode and better collision check
Thanks a lot!!!!
I have marked changes with a New in the text below for those who upgrade
January 23rd, 2005
Minor changes. Larger update soon with new functionality
* Now takes GameBase objects as target + player
* Removed debug message in orbit camera
* Added getters for player and target object
June 25th, 2004
Updated the bindings for orbit camera. Switched left+right.
June 23rd, 2004
A big thanks to Stephen Zepp for contributing with an orbit camera mode. Its added to the resource, and is perfect for RTS games and action adventures. It allows for a camera to rotate around a user as if placed on a sphere. The user can zoom in/out, rotate and tilt the camera.
June 9th, 2004
Added getter/setter for the 3 offset values accessible from script
Added a "follow terrain" mode for the third person camera, so the camera follows the terrain slope - doesnt work perfectly
April 5th, 2004
All camera modes now use a raycast to not get hidden behind terrain or interiors
April 3rd, 2004
This release is the first release, and might not be as "advanced" as the author would like, but its time to release it and get some feedback to further enhance it down the road.
Camera Modes Implemented
The resource currently implements the following camera systems:
* Track Mode
This is the same as the tracking camera resource posted by Cory Osborn. A stationary camera tracks the player and keeps him in focus.
* New Static Mode
Camera stays in its position and rotation. Useful for e.g. scene based adventures where the camera doesnt move with the players
* Third Person Mode
The camera is placed at an offset behind the player and rotates with the player. The camera itself is not controllable
* Third Person Track Mode
The camera is placed in third person mode but rotated so it always looks at a specified object, but with the player in full view
* God View
Camera is placed at an offset from the player and does not rotate with the player. This is your typical "Diablo" kind of camera.
* New Orbit Mode
Camera is placed on a sphere looking at the player, and can rotate/tilt and zoom controlled by the player. There are bindings to the mouse when in single player game (server and client on same machine)
Movie
Here is a small movie displaying the different camera modes (3 MB)
www.codejar.com/advancedcamerademo.wmv
How to Add
First off all you need to take the attached advancedCamera.cc/h files and add to engine\game and add them to the project.
Then you need to expose the camera object in GameConnection as described in Cory's resource www.garagegames.com/index.php?sec=mg&mod=resource&page=view&qid=4720
I took the liberty to paste the relevant parts in here too
Exposing mCameraObject
The first thing you want to do is add console method's to access the GameConnection setCameraObject/getCameraObject methods. I added these to GameConnection.cc right after the console method for getControlObject:
ConsoleMethod( GameConnection, setCameraObject, bool, 3, 3, "(ShapeBase object)")
{
ShapeBase *gb;
if(!Sim::findObject(argv[2], gb))
return false;
object->setCameraObject(gb);
return true;
}
ConsoleMethod( GameConnection, getCameraObject, S32, 2, 2, "")
{
argv;
SimObject* cp = object->getCameraObject();
return cp ? cp->getId(): 0;
}
ConsoleMethod( GameConnection, clearCameraObject, void, 2, 2, "")
{
object->setCameraObject(NULL);
}After playing around with it, I also found you need some adjustments to the setCameraObject and setControlObject methods - otherwise the client connection can screw things up if you bounce the same object from your connection's control to camera or vice versa. Here is my GameConnection::setControlObject:
void GameConnection::setControlObject(ShapeBase *obj)
{
if(mControlObject == obj)
return;
if(mControlObject && mControlObject != mCameraObject)
mControlObject->setControllingClient(0);
if(obj)
{
// Nothing else is permitted to control this object.
if (ShapeBase* coo = obj->getControllingObject())
coo->setControlObject(0);
if (GameConnection *con = obj->getControllingClient())
{
if (this != con)
{
// was it controlled via camera or control?
if (con->getControlObject() == obj)
con->setControlObject(0);
else
con->setCameraObject(0);
}
}
// We are now the controlling client of this object.
obj->setControllingClient(this);
}
// Okay, set our control object.
mControlObject = obj;
if (mCameraObject.isNull())
setScopeObject(mControlObject);
}and here is my GameConnection::setCameraObject:
void GameConnection::setCameraObject(ShapeBase *obj)
{
if(mCameraObject == obj)
return;
if(mCameraObject && mCameraObject != mControlObject)
mCameraObject->setControllingClient(0);
if (obj) {
// Nothing else is permitted to control this object.
if (ShapeBase* coo = obj->getControllingObject())
coo->setControlObject(0);
if (GameConnection *con = obj->getControllingClient())
{
if (this != con)
{
// was it controlled via camera or control?
if (con->getControlObject() == obj)
con->setControlObject(0);
else
con->setCameraObject(0);
}
}
// We are now the controlling client of this object.
obj->setControllingClient(this);
}
// Okay, set our camera object.
mCameraObject = obj;
if (mCameraObject.isNull()) {
setScopeObject(mControlObject);
} else {
setScopeObject(mCameraObject);
// if this is a client then set the fov and active image
if(isServerConnection())
{
F32 fov = mCameraObject->getDefaultCameraFov();
GameSetCameraFov(fov);
}
}
}Camera read/write packets
None of this will work unless the client copy of the camera object gets packets updated. Here we're going to modify GameConnection::readPacket and GameConnection::writePacket.
In GameConnection::readPacket, find this block of code:
if (bstream->readFlag())
{
S32 gIndex = bstream->readInt(10);
ShapeBase* obj = static_cast<ShapeBase*>(resolveGhost(gIndex));
setCameraObject(obj);
}
else
setCameraObject(0);and change it to
if (bstream->readFlag())
{
S32 gIndex = bstream->readInt(NetConnection::GhostIdBitSize);
ShapeBase* obj = static_cast<ShapeBase*>(resolveGhost(gIndex));
setCameraObject(obj);
obj->readPacketData(this, bstream);
}
else
setCameraObject(0);In GameConnection::writePacket, find this block of code:
if (!mCameraObject.isNull() && mCameraObject != mControlObject)
{
gIndex = getGhostIndex(mCameraObject);
if (bstream->writeFlag(gIndex != -1))
bstream->writeInt(gIndex, 10);
}
else
bstream->writeFlag( false );and change it to:
if (!mCameraObject.isNull() && mCameraObject != mControlObject)
{
gIndex = getGhostIndex(mCameraObject);
if (bstream->writeFlag(gIndex != -1)) {
bstream->writeInt(gIndex, NetConnection::GhostIdBitSize);
mCameraObject->writePacketData(this, bstream);
}
}
else
bstream->writeFlag( false );Recompile it all and the engine is ready to go.
Script
To use the camera you need to follow some of Corys resource, but with some modifications. Datablock and naming has changed
First, add a datablock for the tracking camera to /fps/server/scripts/camera.cs:
...
datablock AdvancedCameraData(AdvCameraData)
{
lookAtOffset = "0 0 2";
thirdPersonOffset = "0 -3 3";
godViewOffset = "0 -20 20";
maxTerrainDiff = 2;
orbitMinMaxZoom = "5 100";
orbitMinMaxDeclination = "10 80";
damping = 0.25;
};
...Next, add it to the connection just like is currently done with the base camera class. Add this inside GameConnection::onClientEnterGame (/fps/server/scripts/game.cs), right after %this.camera is set up:
...
// create advanced camera
%this.advCamera = new AdvancedCamera() {
dataBlock = AdvCameraData;
};
MissionCleanup.add(%this.advCamera);
%this.advCamera.scopeToClient(%this);
...We'll need to clean it up after the client leaves the game, so add this to GameConnection::onClientLeaveGame
...
if (isObject(%this.advCamera))
%this.advCamera.delete();
...We need to tell it what to do when added and assign the connection's camera object, so add this to the end of GameConnection::createPlayer:
... // We set the camera system to run in 3rd person mode around the %player %this.advCamera.setPlayerObject(%player); %this.advCamera.setThirdPersonMode(); %this.advCamera.setFollowTerrainMode(false); %this.advCamera.setVerticalFreedomMode(false); %this.setCameraObject(%this.advCamera); ...
And we'll want to unhook it when the player dies. Insert this at the beginning of GameConnection::onDeath:
... // clear connections camera %this.advCamera.clearPlayerObject(); %this.advCamera.clearTargetObject(); %this.clearCameraObject(); ...
The last thing to know, is if you're in first-person mode, GameConnection automatically uses the control object to render the engine rather than the camera object. So if you don't see this working when you first enter a mission, toggle out of first-person.
Orbit mode
To use the orbit camera, one needs to add some key binds to manipulating the camera.
All you need to do, is add the following to your client\config.cs or better to your client\scripts\default.bind.cs
//------------------------------------------------------------------------------
// Advanced Camera Movement
//------------------------------------------------------------------------------
$cameraYawSpeed = -100.0;
$cameraPitchSpeed = -50.0;
$cameraZoomSpeed = -5.0;
function rotateCameraHorizontal(%val)
{
$advCamera::Yaw = getMouseAdjustAmount(%val)*$cameraYawSpeed ;
}
function rotateCameraVertical(%val)
{
$advCamera::Pitch = getMouseAdjustAmount(%val)*$cameraPitchSpeed;
}
function zoomCamera(%val)
{
$advCamera::Zoom = getMouseAdjustAmount(%val)*$cameraZoomSpeed;
}
moveMap.bind( mouse, xaxis, rotateCameraHorizontal);
moveMap.bind( mouse, yaxis, rotateCameraVertical );
moveMap.bind( mouse, zaxis, zoomCamera );Remember to comment out the mouse commands for the player movement, as these are overwritten by the orbit camera controls
//moveMap.bind( mouse, xaxis, yaw ); //moveMap.bind( mouse, yaxis, pitch );
Script API
To use the different camera modes you can use the following API
Selecting the camera mode is done with e.g.:
%this.advCamera.setTrackMode(); %this.advCamera.setThirdPersonMode(); %this.advCamera.setThirdPersonTargetMode(); %this.advCamera.setGodViewMode(); %this.advCamera.setOrbitMode(); %this.advCamera.setStaticMode();
Prior to calling the above modes you have to set the PlayerObject using
setPlayerObject();
To use the 3rd person target mode you also need to set a TargetObject using
setTargetObject();
To use the static or tracking camera you need to set the position the camera should be placed suing
setCameraPosition(Point3F pos);
To use the follow terrain mode in 3rd person you give a bool to
setFollowTerrainMode(true/false);
To use the vertical freedom mode in 3rd person you give a bool to
setVerticalFreedomMode(true/false);This only works if the player object is a Player, because it uses the head movement.
The offset values in the datablock can be changed for the camera object via script using
get/setLookAtOffset(); get/setThirdPersonOffset(); get/setGodViewOffset();The setters take a Point3F as argument.
The orbit camera can be manipulated from script using
get/setOrbitMinMaxZoom() get/setOrbitMinMaxDeclination()The min/max take a Point2F
You can also manipulate the orbit camera directly by assigning values to the following variables
[code]
$advCamera::Yaw
$advCamera::Pitch
$advCamera::Zoom
$advCamera::azimuth
$advCamera::declination
$advCamera::zoomDistance
[code]
All camera modes coexist, so you can set the position, player object and target object once and then switch camera modes around as you see fit. Switching mode will not clear the old objects/positions.
#282
moveMap.bind(mouse0, "xaxis", rotateCameraHorizontal);
moveMap.bind(mouse0, "yaxis", rotateCameraVertical);
moveMap.bind(mouse0, "zaxis", zoomCamera);
08/10/2006 (8:44 pm)
I use this to bind the keys, its exactly like the resource says to do. moveMap.bind(mouse0, "xaxis", rotateCameraHorizontal);
moveMap.bind(mouse0, "yaxis", rotateCameraVertical);
moveMap.bind(mouse0, "zaxis", zoomCamera);
#283
I'm trying to get the God View working but I cannot get it to restrict the pitch on the mouse (Kork still aims up and down). I'd assume it was something in the createPlayer section of game.cs but I don't know what much else there is. Any help on this would be greatly appreciated!
08/14/2006 (11:17 pm)
Argh,I'm trying to get the God View working but I cannot get it to restrict the pitch on the mouse (Kork still aims up and down). I'd assume it was something in the createPlayer section of game.cs but I don't know what much else there is. Any help on this would be greatly appreciated!
// We set the camera system to run in 3rd person mode around the %player %this.advCamera.setPlayerObject(%player); %this.advCamera.setFollowTerrainMode(false); %this.advCamera.setVerticalFreedomMode(false); %this.setCameraObject(%this.advCamera); %this.advCamera.setGodViewMode();
#284
//moveMap.bind( mouse, xaxis, yaw );
//moveMap.bind( mouse, yaxis, pitch );
08/15/2006 (4:36 am)
You have to remove the 2 binds that let kork look up and down in default.bind.cs. And then run the delete config .bat file.//moveMap.bind( mouse, xaxis, yaw );
//moveMap.bind( mouse, yaxis, pitch );
#285
08/15/2006 (8:12 am)
Thanks Robin, I assumed that was the direct issue and obvious before posting and forgot to mention that I tried that first thing. I have discovered though that it's not the the pitch restritctions that art totally giving me the problem, it's something with the view. Sometimes my character will just shoot blank missiles and no explosion animation will occur but I can still get hurt from it by shooting my feet. If I try to push the mouse's pitch in anyway quickly it does this. Anyone have this problem before?
#286
is it possible to has a switch between the advanced camera and the standart camera?
what i mean is like changine the camera object through script on the fly
i use the player movement by cory osborn and its a little problematic with vehicles, however i found that if i could switch the camera object in script, then thye would work,
any iodeas? i have no idea what that type of code would look like:S
08/18/2006 (9:37 am)
hi , i was jsut wodnering,is it possible to has a switch between the advanced camera and the standart camera?
what i mean is like changine the camera object through script on the fly
i use the player movement by cory osborn and its a little problematic with vehicles, however i found that if i could switch the camera object in script, then thye would work,
any iodeas? i have no idea what that type of code would look like:S
#287
function serverCmdClearCamera(%client) {
//%client.clearCameraObject();
echo("restoring default cam");
%client.clearCameraObject();
}
function serverCmdUseAdvCamera(%client) {
//%client.setCameraObject(%client.advanced);
echo("setting advCam");
/// We set the camera system to run in 3rd person mode around the %player
%client.advCamera.setPlayerObject(%client.player);
//%this.advCamera.setThirdPersonMode();
//%this.advCamera.setGodViewMode();
%client.advCamera.setOrbitMode();
//%this.advCamera.setThirdPersonMode();
%client.advCamera.setFollowTerrainMode(false);
%client.advCamera.setVerticalFreedomMode(false);
%client.setCameraObject(%client.advCamera);
}
call clearcamera on mount, and useadvcamera on unmount and ur set:) for vehicles, the new player movement, and the advanced camera resource:)
08/18/2006 (10:59 am)
ok here it is!function serverCmdClearCamera(%client) {
//%client.clearCameraObject();
echo("restoring default cam");
%client.clearCameraObject();
}
function serverCmdUseAdvCamera(%client) {
//%client.setCameraObject(%client.advanced);
echo("setting advCam");
/// We set the camera system to run in 3rd person mode around the %player
%client.advCamera.setPlayerObject(%client.player);
//%this.advCamera.setThirdPersonMode();
//%this.advCamera.setGodViewMode();
%client.advCamera.setOrbitMode();
//%this.advCamera.setThirdPersonMode();
%client.advCamera.setFollowTerrainMode(false);
%client.advCamera.setVerticalFreedomMode(false);
%client.setCameraObject(%client.advCamera);
}
call clearcamera on mount, and useadvcamera on unmount and ur set:) for vehicles, the new player movement, and the advanced camera resource:)
#288
Thanks in advance.
08/20/2006 (1:24 pm)
Thanks to all for such a wonderful resource. I've spent the morning and most of the afternoon going over all of the posts trying to answer somthing that is probably pretty simple. Overall it is working. Thanks to Darrel Cusey's post on (Mar 26, 2006 at 20:45) the camera toggles between orbit and third. Is there a way to get the camera setting from the orbit and assign it to the third? Apologies if this is really simple, noob to Torque.Thanks in advance.
#289
1. Add some attributes to AdvancedCameraData struct
2. Add one attribute to AdvancedCamera class
3. In AdvancedCamera, change declaration and definition (.h and .cc, respectively) of
to
4. Define default values to the new attributes in AdvancedCameraData::AdvancedCameraData()
5. Define initial value to velocity attribute in AdvancedCamera::AdvancedCamera()
6. Expose the new attributes in AdvancedCameraData::initPersistFields()
7. Pack the new attributes in AdvancedCameraData::packData(BitStream* stream)
8. Unpack the new attributes in AdvancedCameraData::unpackData(BitStream* stream)
9. In AdvancedCamera::advanceTime(F32 dt), change
to
10. In AdvancedCamera::setPosition(const Point3F& pos, F32 dt), change
to
11. In AdvancedCamera::writePacketData(GameConnection *connection, BitStream *bstream), add
12. At last, in AdvancedCamera::readPacketData(GameConnection *connection, BitStream *bstream), add
Finished!
Just more one advice, in GameConnection::createPlayer(), I prefer to set camera position before setting the player as control object to avoid seeing some frames in (0, 0, 0) position.
Note 1: I took spring model from Game Programming Gems 4, chapter 4.1, "Third-Person Camera Navigation". There are information about setting "spring" and "damping" parameters. If you don't know nothing about that, just keep "spring = ( damping^2 )/4" constraints.
Note 2: I'd like to know how to post code blocks with that nice grey box :-(
Edit: Added a forgotten change (transmit mVelocity through network). Sorry.
08/23/2006 (1:55 pm)
I was also sick of my camera coming from (0,0,0) and delaying when the game slowed down (due to the frame rate dependent interpolation). So I solved both problems by modifying that interpolation, turning it to a spring model. Try this out...1. Add some attributes to AdvancedCameraData struct
//---------------------------------------------------------------- // Declare attributes F32 mMaxDistance; F32 mSpringMove; F32 mDampingMove; //----------------------------------------------------------------
2. Add one attribute to AdvancedCamera class
//---------------------------------------------------------------- // Declare velocity attribute Point3F mVelocity; //----------------------------------------------------------------
3. In AdvancedCamera, change declaration and definition (.h and .cc, respectively) of
//---------------------------------------------------------------- void setPosition(const Point3F& pos) //----------------------------------------------------------------
to
//---------------------------------------------------------------- // Dt specifies if there should interpolation. // If dt > 0, interpolate using dt itself // If dt == 0, do not interpolate // If dt < 0, ??? void setPosition(const Point3F& pos, F32 dt = 0.0f) //----------------------------------------------------------------
4. Define default values to the new attributes in AdvancedCameraData::AdvancedCameraData()
//---------------------------------------------------------------- // Define default values mMaxDistance = 2.0f; mSpringMove = 6.25f; mDampingMove = 5.0f; //----------------------------------------------------------------
5. Define initial value to velocity attribute in AdvancedCamera::AdvancedCamera()
//---------------------------------------------------------------- // Define initial value to velocity mVelocity.zero(); //----------------------------------------------------------------
6. Expose the new attributes in AdvancedCameraData::initPersistFields()
//----------------------------------------------------------------
// Expose new attributes
addField("maxDistance", TypeF32, Offset(mMaxDistance, AdvancedCameraData));
addField("springMove", TypeF32, Offset(mSpringMove, AdvancedCameraData));
addField("dampingMove", TypeF32, Offset(mDampingMove, AdvancedCameraData));
//----------------------------------------------------------------7. Pack the new attributes in AdvancedCameraData::packData(BitStream* stream)
// after write thirdPersonOffset.z stream->write(thirdPersonOffset.z); //---------------------------------------------------------------- // Write new attributes stream->write(mMaxDistance); stream->write(mSpringMove); stream->write(mDampingMove); //----------------------------------------------------------------
8. Unpack the new attributes in AdvancedCameraData::unpackData(BitStream* stream)
// after read thirdPersonOffset.z stream->read(&thirdPersonOffset.z); //---------------------------------------------------------------- // Read new attributes stream->read(&mMaxDistance); stream->read(&mSpringMove); stream->read(&mDampingMove); //----------------------------------------------------------------
9. In AdvancedCamera::advanceTime(F32 dt), change
// Note: To make your search easer, next change is after this if statement
if (mMode && mMode != TrackMode && playerObj != NULL) {
cameraPosWorld = runCameraCollisionCheck(playerObj->getRenderPosition(), cameraPosWorld);
}
//----------------------------------------------------------------
setPosition(cameraPosWorld);
//----------------------------------------------------------------to
//----------------------------------------------------------------
setPosition(cameraPosWorld, dt);
if (playerObj != NULL) {
// Actual camera position, not ideal position
Point3F cameraPosBefore( getPosition() );
cameraPosWorld = runCameraCollisionCheck(playerObj->getRenderPosition(), cameraPosBefore);
// If camera position before collision check is not equals after
if (cameraPosBefore != cameraPosWorld)
{
// Place camera into its final position without interpolation (dt = 0.0f)
setPosition(cameraPosWorld, 0.0f);
}
}
//----------------------------------------------------------------10. In AdvancedCamera::setPosition(const Point3F& pos, F32 dt), change
//---------------------------------------------------------------- F32 tInterpolation = 0.333333333; tPos = pos*tInterpolation + tPos*(1.0-tInterpolation); //----------------------------------------------------------------
to
//----------------------------------------------------------------
// If interpolation is not time dependant (dt = 0)
if ( dt == 0.0f )
{
tPos = pos;
}
else if (mPlayerObject != NULL)
{
GameBase *castObj = mPlayerObject;
ShapeBase* playerObj = dynamic_cast<ShapeBase*>(castObj);
Player* playerObjAsPlayer = dynamic_cast<Player*>(playerObj);
Point3F displace(tPos - pos);
F32 displaceLen = displace.len();
// If tPos is not far away from pos
if ( (displaceLen > mDataBlock->mMaxDistance) )
{
// Resize displace to have max distance size
// Multiply by 0.99f to avoid floating point approaching error
displace *= (0.99f*mDataBlock->mMaxDistance)/displaceLen;
tPos = pos + displace;
}
else
{
Point3F velocity(playerObjAsPlayer->getVelocity());
Point3F accel( -mDataBlock->mSpringMove*displace
- mDataBlock->mDampingMove*velocity );
if (mDot(accel, velocity) < 0)
{
accel = accel - (mDot(accel,velocity)/velocity.lenSquared())*velocity;
}
mVelocity += accel*dt;
tPos += mVelocity*dt;
}
}
//----------------------------------------------------------------11. In AdvancedCamera::writePacketData(GameConnection *connection, BitStream *bstream), add
//---------------------------------------------------------------- // Write mVelocity attribute mathWrite(*bstream, mVelocity); // Write mVelocity attribute //---------------------------------------------------------------- // Before write mCameraPos mathWrite(*bstream, mCameraPos);
12. At last, in AdvancedCamera::readPacketData(GameConnection *connection, BitStream *bstream), add
//---------------------------------------------------------------- // Read mVelocity attribute mathRead(*bstream, &mVelocity); // Read mVelocity attribute //---------------------------------------------------------------- // Before read mCameraPos mathRead(*bstream, &mCameraPos);
Finished!
Just more one advice, in GameConnection::createPlayer(), I prefer to set camera position before setting the player as control object to avoid seeing some frames in (0, 0, 0) position.
// Right after set original Torque camera position %this.camera.setTransform(%spawnPoint); //---------------------------------------------------------------- // Set advanced camera position %this.advCamera.setPlayerObject(%player); %this.advCamera.setCameraPosition(%spawnPoint); //---------------------------------------------------------------- // before give the client control of the player %this.player = %player; %this.setControlObject(%player);
Note 1: I took spring model from Game Programming Gems 4, chapter 4.1, "Third-Person Camera Navigation". There are information about setting "spring" and "damping" parameters. If you don't know nothing about that, just keep "spring = ( damping^2 )/4" constraints.
Note 2: I'd like to know how to post code blocks with that nice grey box :-(
Edit: Added a forgotten change (transmit mVelocity through network). Sorry.
#290
Oh yeah... And thanx...
08/24/2006 (2:00 am)
[code]Text goes here[/ code] without the space in the tags
Oh yeah... And thanx...
#291
Should read?
And there's a missing semi-colon at the end of
08/27/2006 (8:24 pm)
In advancedCamera.cc//---------------------------------------------------------------- // Dt specifies if there should interpolation. // If dt > 0, interpolate using dt itself // If dt == 0, do not interpolate // If dt < 0, ??? void setPosition(const Point3F& pos, F32 dt = 0.0f) //----------------------------------------------------------------
Should read?
//---------------------------------------------------------------- // Dt specifies if there should interpolation. // If dt > 0, interpolate using dt itself // If dt == 0, do not interpolate // If dt < 0, ??? void setPosition(const Point3F& pos, F32 dt) // removed second declaration of dt //----------------------------------------------------------------
And there's a missing semi-colon at the end of
void setPosition(const Point3F& pos, F32 dt = 0.0f)
#292
Ok, ok. I was a lazy explaining this part. What you exactly have to do in step 3 is...
3. In AdvancedCamera class (in AdvancedCamera.h file), change declaration of
And in AdvancedCamera class (in AdvancedCamera.cc file), change definition of
I hope I have explained clearly now.
08/28/2006 (8:21 am)
@DionOk, ok. I was a lazy explaining this part. What you exactly have to do in step 3 is...
3. In AdvancedCamera class (in AdvancedCamera.h file), change declaration of
//---------------------------------------------------------------- void setPosition(const Point3F& pos); //----------------------------------------------------------------for
//---------------------------------------------------------------- // Dt specifies if there should interpolation. // If dt > 0, interpolate using dt itself // If dt == 0, do not interpolate // If dt < 0, ??? void setPosition(const Point3F& pos, F32 dt = 0.0f); //----------------------------------------------------------------
And in AdvancedCamera class (in AdvancedCamera.cc file), change definition of
//---------------------------------------------------------------- void AdvancedCamera::setPosition(const Point3F& pos) //----------------------------------------------------------------for
//---------------------------------------------------------------- void AdvancedCamera::setPosition(const Point3F& pos, F32 dt) //----------------------------------------------------------------Don't remove the "F32 dt = 0.0f" default argument definition. It's necessary to keep compatibility with earlier calls of this method.
I hope I have explained clearly now.
#293
I have:
executable Revision of TGE 1.4 (At the time of writing 9-2-06)
Windows XP
Added: advancedCamera.cc/.h Files to my project
NOTE: The only difference between the Source Code of the self extracting .exe and the version I have with the problem is the addition of the two above files. The rest of the code changes were already in stock 1.4
NOTE 2: The only script Changes I have are what was needed to get the camera in game
If anyone has any suggestions please let me know.
EDIT: OK... I guess I was wrong about the problem with the issue... It appears to be what was discussed on this page about the (0,0,0) server camera position and scope issue. I am not sure which fix I should try first but here goes :P
09/02/2006 (1:33 pm)
I have been trying to track down a strange issue that I have not seen anyone post about yet with this resource. Currently Everything seems to work correctly except the standard AI player is not visible. I can see his ID moving around in the Editor but no shape. the only difference I could see with the pref.cs files being generated from stock 1.4 is $pref::Editor::visibleDistance = "0"; rather then the default 2100.I have:
executable Revision of TGE 1.4 (At the time of writing 9-2-06)
Windows XP
Added: advancedCamera.cc/.h Files to my project
NOTE: The only difference between the Source Code of the self extracting .exe and the version I have with the problem is the addition of the two above files. The rest of the code changes were already in stock 1.4
NOTE 2: The only script Changes I have are what was needed to get the camera in game
If anyone has any suggestions please let me know.
EDIT: OK... I guess I was wrong about the problem with the issue... It appears to be what was discussed on this page about the (0,0,0) server camera position and scope issue. I am not sure which fix I should try first but here goes :P
#294
09/03/2006 (3:49 pm)
The Fix post by Manoel Neto, dated Mar 07, 2005. Seems to fix the problem and works fine for my needs :D.
#295
The fix from Manoel worked but it made everything shaking strangely, we had to take it off. The only way we found to fix our problem was to increase the visible area to 1400 in order to cover almost the whole mission area (my mission area is 1024 square, so 1448 was the cercle to cover everything).
Did you have the same problem ?
09/04/2006 (3:24 am)
Hello Matt, we had the same problem.The fix from Manoel worked but it made everything shaking strangely, we had to take it off. The only way we found to fix our problem was to increase the visible area to 1400 in order to cover almost the whole mission area (my mission area is 1024 square, so 1448 was the cercle to cover everything).
Did you have the same problem ?
#296
This resource is a lifesaver. I have the engine updated, which was minimal with 1.4, and I have my mission starting off with this camera set in static mode.
But how do i set where the camera is pointing in static mode? I dont see any functions that allow you to specify this. I have tried making an object in the mission editor, a spawn object, and setting the transform of the static camera to it but it doesnt seem to work. Its like calling setStaticMode() completely resets its information.
any help is greatly appreciated.
09/13/2006 (6:03 pm)
Hello everyoneThis resource is a lifesaver. I have the engine updated, which was minimal with 1.4, and I have my mission starting off with this camera set in static mode.
But how do i set where the camera is pointing in static mode? I dont see any functions that allow you to specify this. I have tried making an object in the mission editor, a spawn object, and setting the transform of the static camera to it but it doesnt seem to work. Its like calling setStaticMode() completely resets its information.
any help is greatly appreciated.
#297
09/21/2006 (7:16 am)
Did anybody get it to work with TSE?
#298
I just had to add the advancedCamera.cpp and .h to the project and make the Script changes. All other code changes were already in the codebase.
09/21/2006 (7:55 am)
I got it working with TSE yesterday. My code is up to date with what is in CVS. I just had to add the advancedCamera.cpp and .h to the project and make the Script changes. All other code changes were already in the codebase.
#299
09/25/2006 (2:06 pm)
Anyone know if I can make it so that when the camera collides into the player's collision, it'll switch to First Person mode? Any suggestions on how to accomplish this or if there is a resource on doing this would be great?
#300
Any help would be great.
10/01/2006 (5:00 pm)
Has anyone got this working with 3rd person zoom? I am using 1.4 CVS and would like to get the 3rd person distance zoom and tried the suggestion by Chris Birmingham (Sep 11, 2004 at 23:35) but for some reason it won't zoom in and out.Any help would be great.

Torque 3D Owner Thanhda Tie
Digital Shock Inc.