103 lines
2.5 KiB
Plaintext
103 lines
2.5 KiB
Plaintext
// Copyright (C) 2010, Guy Barrand. All rights reserved.
|
|
// See the file tools.license for terms.
|
|
|
|
#ifndef tools_sg_perspective
|
|
#define tools_sg_perspective
|
|
|
|
#include "base_camera"
|
|
|
|
#include "../mathf"
|
|
|
|
namespace tools {
|
|
namespace sg {
|
|
|
|
class perspective : public base_camera {
|
|
TOOLS_NODE(perspective,tools::sg::perspective,base_camera)
|
|
public:
|
|
virtual float near_height() const {
|
|
return 2.0f*znear.value()*ftan(height_angle.value()*0.5f);
|
|
}
|
|
virtual void zoom(float a_fac) {
|
|
//for exa :
|
|
// a_fac = 0.99f is a zoom in
|
|
// a_fac = 1.01f is a zoom out
|
|
height_angle.value(height_angle.value()*a_fac);
|
|
}
|
|
virtual camera_type type() const {return camera_perspective;}
|
|
public:
|
|
sf<float> height_angle;
|
|
public:
|
|
virtual const desc_fields& node_desc_fields() const {
|
|
TOOLS_FIELD_DESC_NODE_CLASS(tools::sg::perspective)
|
|
static const desc_fields s_v(parent::node_desc_fields(),1, //WARNING : take care of count.
|
|
TOOLS_ARG_FIELD_DESC(height_angle)
|
|
);
|
|
return s_v;
|
|
}
|
|
private:
|
|
void add_fields(){
|
|
add_field(&height_angle);
|
|
}
|
|
public:
|
|
perspective()
|
|
:parent()
|
|
,height_angle(fpi()/4.0f) //45 degrees.
|
|
{
|
|
#ifdef TOOLS_MEM
|
|
mem::increment(s_class().c_str());
|
|
#endif
|
|
add_fields();
|
|
}
|
|
virtual ~perspective(){
|
|
#ifdef TOOLS_MEM
|
|
mem::decrement(s_class().c_str());
|
|
#endif
|
|
}
|
|
public:
|
|
perspective(const perspective& a_from)
|
|
:parent(a_from)
|
|
,height_angle(a_from.height_angle)
|
|
{
|
|
#ifdef TOOLS_MEM
|
|
mem::increment(s_class().c_str());
|
|
#endif
|
|
add_fields();
|
|
}
|
|
perspective& operator=(const perspective& a_from){
|
|
parent::operator=(a_from);
|
|
height_angle = a_from.height_angle;
|
|
return *this;
|
|
}
|
|
public: //operators:
|
|
bool operator==(const perspective& a_from) const{
|
|
if(!parent::operator==(a_from)) return false;
|
|
if(height_angle!=a_from.height_angle) return false;
|
|
return true;
|
|
}
|
|
bool operator!=(const perspective& a_from) const {
|
|
return !operator==(a_from);
|
|
}
|
|
public:
|
|
void dump(std::ostream& a_out) {
|
|
parent::dump(a_out);
|
|
a_out << " height_angle " << height_angle.value() << std::endl;
|
|
}
|
|
|
|
protected:
|
|
virtual void get_lrbt(unsigned int a_ww,unsigned int a_wh,
|
|
float& a_l,float& a_r,float& a_b,float& a_t) {
|
|
float aspect = float(a_ww)/float(a_wh);
|
|
float hh = near_height()*0.5f;
|
|
a_l = -aspect*hh;
|
|
a_r = aspect*hh;
|
|
a_b = -hh;
|
|
a_t = hh;
|
|
}
|
|
};
|
|
|
|
inline perspective* cast_perspective(base_camera& a_bcam) {return safe_cast<base_camera,perspective>(a_bcam);}
|
|
|
|
}}
|
|
|
|
#endif
|