Attenzione: il tutorial pubblicato sul sito è stato suddiviso in 5 parti. Linee di codice troppo lunghe potrebbero essere tagliate dal browser. Per la completezza e l'affidabilità del codice fate riferimento al tutorial completo in pdf.
scarica il seguente tutorial in formato pdf (161 kb)
scarica il codice completo in formato testo (.cpp, 10.6 Kb)
UNA TELECAMERA PER LA NOSTRA STAR:
Vi posto il codice di questa “following camera”.
Non è codice mio (si trova sul forum ufficiale del progetto irrlicht, postato da keless), ma è comunque (a parte qualche lieve imperfezione) sufficiente per dare un minimo di senso al nostro esempio.
Naturalmente, siete liberi di prendere spunto e modificare il codice come meglio credete (salvo che keless non si incazzi e dica di no… di norma però non penso che lo avrebbe postato su di un forum).
Scherzi a parte,cito per correttezza il topic dal quale ho preso il codice:
http://irrlicht.sourceforge.net/phpBB2/viewtopic.php?t=1140
Ed ecco il codice vero e proprio:
class followingCamera
{
irr::scene::ISceneNode* m_pTargetNode;
irr::scene::ICameraSceneNode* m_cam;
irr::core::vector3df lastTargetPos;
irr::f32 m_height; //distance above object camera tries to float at
irr::f32 m_leash; //max distance object can be from camera before it moves
irr::f32 m_speed; //rate at which camera moves per Update()
public:
// class constructor
followingCamera(irr::scene::ISceneNode* targetNode, irr::scene::ISceneManager* smgr,
irr::f32 height = 80.0f, irr::f32 leash = 100.0f, irr::f32 speed = 1.0f, irr::s32 id = -1);
// class destructor
~followingCamera();
irr::scene::ICameraSceneNode* getCam() { return m_cam; }
void Update();
};
// class constructor
followingCamera::followingCamera(irr::scene::ISceneNode* targetNode, irr::scene::ISceneManager* smgr,
irr::f32 height /*30.0f*/, irr::f32 leash /*100.0f*/, irr::f32 speed /*5.0f*/, irr::s32 id /*-1*/)
{
m_speed = speed;
m_height = height;
m_leash = leash;
//create a camera
lastTargetPos = targetNode->getPosition();
m_cam = smgr->addCameraSceneNode(0, lastTargetPos + irr::core::vector3df(0, 20, 20), lastTargetPos, id );
m_pTargetNode = targetNode;
m_pTargetNode->grab(); //make sure the node wont dissappear on us
}
// class destructor
followingCamera::~followingCamera()
{
m_pTargetNode->drop(); //make sure we let go of the node resource
}
void followingCamera::Update() {
if(!m_cam || !m_pTargetNode) return;
irr::core::vector3df currTargetPos = m_pTargetNode->getPosition();
//if too far away, move camera closer
irr::core::vector3df camToTarg = currTargetPos - m_cam->getPosition() ;
//leash is only in the X-Z plane, so only count distance using X and Z
irr::core::vector2df xzDist( camToTarg.X, camToTarg.Z );
if(xzDist.getLength() > m_leash) { //need to move closer
camToTarg = irr::core::vector3df( xzDist.X, 0, xzDist.Y);
camToTarg = camToTarg.normalize() * m_speed;
//set X-Z position
m_cam->setPosition( m_cam->getPosition() + camToTarg ); //move closer
//set Y position
//Commentata e modificata da hammeronthenet, solo per renderla meno "traballante"
/* irr::f32 h_tolerance = m_height / 10 ; //the ammount of leway given to how close we need to be to the right height
irr::f32 h_delta = m_cam->getPosition().Y - currTargetPos.Y + m_height; //distance from prefered height position
if( m_cam->getPosition().Y < ( currTargetPos.Y + m_height) - h_tolerance) {
m_cam->setPosition( irr::core::vector3df( m_cam->getPosition().X, m_cam->getPosition().Y + h_delta, m_cam->getPosition().Z) );
}else if( m_cam->getPosition().Y > ( currTargetPos.Y + m_height) + h_tolerance ) {
m_cam->setPosition( irr::core::vector3df( m_cam->getPosition().X, m_cam->getPosition().Y - h_delta/200, m_cam->getPosition().Z) );
}
*/
}
m_cam->setPosition( irr::core::vector3df( m_cam->getPosition().X, currTargetPos.Y+20, m_cam->getPosition().Z) );
m_cam->setTarget( currTargetPos ); //look at Target position
lastTargetPos = currTargetPos;
}
Vi faccio notare che ne ho modificato una parte (commentando il codice originale) solo per adattarlo meglio all’esempio.
Per dubbi, incomprensioni, suggerimenti e problemi vi invito a visitare il link che vi ho indicato poco prima