add polylight support to NodePath; prevent compiler warnings; minor style changes to polylightEffect to be consistent with panda conventions

This commit is contained in:
David Rose 2004-08-04 22:41:10 +00:00
parent f0a204b084
commit c23792f1dc
9 changed files with 138 additions and 38 deletions

View File

@ -19,7 +19,7 @@
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
// Function: LightAttrib::Constructor // Function: LightAttrib::Constructor
// Access: Private // Access: Protected
// Description: Use LightAttrib::make() to construct a new // Description: Use LightAttrib::make() to construct a new
// LightAttrib object. // LightAttrib object.
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -30,7 +30,7 @@ LightAttrib() {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
// Function: LightAttrib::Copy Constructor // Function: LightAttrib::Copy Constructor
// Access: Private // Access: Protected
// Description: Use LightAttrib::make() to construct a new // Description: Use LightAttrib::make() to construct a new
// LightAttrib object. The copy constructor is only // LightAttrib object. The copy constructor is only
// defined to facilitate methods like add_on_light(). // defined to facilitate methods like add_on_light().

View File

@ -34,7 +34,7 @@
// from the total set of "on" lights. // from the total set of "on" lights.
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
class EXPCL_PANDA LightAttrib : public RenderAttrib { class EXPCL_PANDA LightAttrib : public RenderAttrib {
private: protected:
INLINE LightAttrib(); INLINE LightAttrib();
INLINE LightAttrib(const LightAttrib &copy); INLINE LightAttrib(const LightAttrib &copy);

View File

@ -2095,6 +2095,7 @@ set_light(const NodePath &light, int priority) {
if (!light.is_empty()) { if (!light.is_empty()) {
Light *light_obj = light.node()->as_light(); Light *light_obj = light.node()->as_light();
if (light_obj != (Light *)NULL) { if (light_obj != (Light *)NULL) {
// It's an actual Light object.
const RenderAttrib *attrib = const RenderAttrib *attrib =
node()->get_attrib(LightAttrib::get_class_type()); node()->get_attrib(LightAttrib::get_class_type());
if (attrib != (const RenderAttrib *)NULL) { if (attrib != (const RenderAttrib *)NULL) {
@ -2112,6 +2113,31 @@ set_light(const NodePath &light, int priority) {
node()->set_attrib(la->add_on_light(light), priority); node()->set_attrib(la->add_on_light(light), priority);
} }
return; return;
} else if (light.node()->is_of_type(PolylightNode::get_class_type())) {
// It's a Polylight object.
if (priority != 0) {
// PolylightEffects can't have a priority, since they're just
// an effect to be applied immediately.
pgraph_cat.warning()
<< "Ignoring priority on set_light(" << light << ")\n";
}
const RenderEffect *effect =
node()->get_effect(PolylightEffect::get_class_type());
if (effect != (const RenderEffect *)NULL) {
const PolylightEffect *ple = DCAST(PolylightEffect, effect);
// Modify the existing PolylightEffect to add the indicated
// light.
node()->set_effect(ple->add_light(light));
} else {
// Create a new PolylightEffect for this node.
CPT(PolylightEffect) ple = DCAST(PolylightEffect, PolylightEffect::make());
node()->set_effect(ple->add_light(light));
}
return;
} }
} }
nassert_raise("Not a Light object."); nassert_raise("Not a Light object.");
@ -2135,6 +2161,7 @@ void NodePath::
set_light_off(int priority) { set_light_off(int priority) {
nassertv_always(!is_empty()); nassertv_always(!is_empty());
node()->set_attrib(LightAttrib::make_all_off(), priority); node()->set_attrib(LightAttrib::make_all_off(), priority);
node()->clear_effect(PolylightEffect::get_class_type());
} }
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -2224,6 +2251,16 @@ clear_light(const NodePath &light) {
} }
} }
return; return;
} else if (light.node()->is_of_type(PolylightNode::get_class_type())) {
const RenderEffect *effect =
node()->get_effect(PolylightEffect::get_class_type());
if (effect != (const RenderEffect *)NULL) {
CPT(PolylightEffect) ple = DCAST(PolylightEffect, effect);
ple = DCAST(PolylightEffect, ple->remove_light(light));
node()->set_effect(ple);
}
return;
} }
} }
nassert_raise("Not a Light object."); nassert_raise("Not a Light object.");
@ -2250,6 +2287,16 @@ has_light(const NodePath &light) const {
const LightAttrib *la = DCAST(LightAttrib, attrib); const LightAttrib *la = DCAST(LightAttrib, attrib);
return la->has_on_light(light); return la->has_on_light(light);
} }
return false;
} else if (light.node()->is_of_type(PolylightNode::get_class_type())) {
const RenderEffect *effect =
node()->get_effect(PolylightEffect::get_class_type());
if (effect != (const RenderEffect *)NULL) {
const PolylightEffect *ple = DCAST(PolylightEffect, effect);
return ple->has_light(light);
}
return false;
} }
} }
nassert_raise("Not a Light object."); nassert_raise("Not a Light object.");

View File

@ -19,7 +19,7 @@
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
// Function: PolylightEffect::Constructor // Function: PolylightEffect::Constructor
// Access: Private // Access: Protected
// Description: Use PolylightEffect::make() to construct a new // Description: Use PolylightEffect::make() to construct a new
// PolylightEffect object. // PolylightEffect object.
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -29,7 +29,7 @@ PolylightEffect() {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
// Function: PolylightEffect::Constructor // Function: PolylightEffect::Constructor
// Access: Private // Access: Protected
// Description: Copy Constructor used by the const methods // Description: Copy Constructor used by the const methods
// to modify data on a copy and return a new one // to modify data on a copy and return a new one
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -55,9 +55,9 @@ get_weight() const {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
// Function: PolylightEffect::get_contrib // Function: PolylightEffect::get_contrib
// Access: Published // Access: Published
// Description: Returns CALL or CPROXIMAL // Description: Returns CT_all or CT_proximal
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
INLINE PolylightEffect::Contrib_Type PolylightEffect:: INLINE PolylightEffect::ContribType PolylightEffect::
get_contrib() const { get_contrib() const {
return _contribution_type; return _contribution_type;
} }

View File

@ -36,7 +36,7 @@ TypeHandle PolylightEffect::_type_handle;
CPT(RenderEffect) PolylightEffect:: CPT(RenderEffect) PolylightEffect::
make() { make() {
PolylightEffect *effect = new PolylightEffect; PolylightEffect *effect = new PolylightEffect;
effect->_contribution_type = CPROXIMAL; effect->_contribution_type = CT_proximal;
effect->_weight = 0.9; effect->_weight = 0.9;
effect->_effect_center = LPoint3f(0.0,0.0,0.0); effect->_effect_center = LPoint3f(0.0,0.0,0.0);
return return_new(effect); return return_new(effect);
@ -48,7 +48,7 @@ make() {
// Description: Constructs a new PolylightEffect object. // Description: Constructs a new PolylightEffect object.
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
CPT(RenderEffect) PolylightEffect:: CPT(RenderEffect) PolylightEffect::
make(float weight, Contrib_Type contrib, LPoint3f effect_center) { make(float weight, ContribType contrib, LPoint3f effect_center) {
PolylightEffect *effect = new PolylightEffect; PolylightEffect *effect = new PolylightEffect;
effect->_contribution_type = contrib; effect->_contribution_type = contrib;
effect->_weight = weight; effect->_weight = weight;
@ -62,7 +62,8 @@ make(float weight, Contrib_Type contrib, LPoint3f effect_center) {
// Description: Constructs a new PolylightEffect object. // Description: Constructs a new PolylightEffect object.
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
CPT(RenderEffect) PolylightEffect:: CPT(RenderEffect) PolylightEffect::
make(float weight, Contrib_Type contrib, LPoint3f effect_center, LIGHTGROUP lights) { make(float weight, ContribType contrib, LPoint3f effect_center,
const LightGroup &lights) {
PolylightEffect *effect = new PolylightEffect; PolylightEffect *effect = new PolylightEffect;
effect->_contribution_type = contrib; effect->_contribution_type = contrib;
effect->_weight = weight; effect->_weight = weight;
@ -82,7 +83,7 @@ make(float weight, Contrib_Type contrib, LPoint3f effect_center, LIGHTGROUP ligh
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
bool PolylightEffect:: bool PolylightEffect::
has_cull_callback() const { has_cull_callback() const {
return true; return !_lightgroup.empty();
} }
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -129,7 +130,7 @@ do_poly_light(const CullTraverserData *data, const TransformState *node_transfor
r = 1.0; r = 1.0;
g = 1.0; g = 1.0;
b = 1.0; b = 1.0;
LIGHTGROUP::const_iterator light_iter; LightGroup::const_iterator light_iter;
// Cycle through all the lights in this effect's lightgroup // Cycle through all the lights in this effect's lightgroup
for (light_iter = _lightgroup.begin(); light_iter != _lightgroup.end(); light_iter++){ for (light_iter = _lightgroup.begin(); light_iter != _lightgroup.end(); light_iter++){
const PolylightNode *light = DCAST(PolylightNode, (*light_iter).node()); const PolylightNode *light = DCAST(PolylightNode, (*light_iter).node());
@ -179,7 +180,7 @@ do_poly_light(const CullTraverserData *data, const TransformState *node_transfor
} // for all lights } // for all lights
if ( _contribution_type == CALL) { if ( _contribution_type == CT_all) {
// Sometimes to prevent snapping of color at light volume boundaries // Sometimes to prevent snapping of color at light volume boundaries
// just divide total contribution by all the lights in the effect // just divide total contribution by all the lights in the effect
// whether or not they contribute color // whether or not they contribute color
@ -204,6 +205,24 @@ do_poly_light(const CullTraverserData *data, const TransformState *node_transfor
return ColorScaleAttrib::make(LVecBase4f(r, g, b, 1.0)); return ColorScaleAttrib::make(LVecBase4f(r, g, b, 1.0));
} }
////////////////////////////////////////////////////////////////////
// Function: PolylightEffect::output
// Access: Public
// Description:
////////////////////////////////////////////////////////////////////
void PolylightEffect::
output(ostream &out) const {
out << get_type() << ":";
LightGroup::const_iterator li;
for (li = _lightgroup.begin(); li != _lightgroup.end(); ++li) {
NodePath light = (*li);
out << " " << light;
}
out << " weight " << _weight << " contrib " << _contribution_type
<< " center " << _effect_center;
}
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
// Function: PolylightEffect::compare_to_impl // Function: PolylightEffect::compare_to_impl
@ -265,10 +284,11 @@ add_light(const NodePath &newlight) const {
CPT(RenderEffect) PolylightEffect:: CPT(RenderEffect) PolylightEffect::
remove_light(const NodePath &newlight) const { remove_light(const NodePath &newlight) const {
PolylightEffect *effect = new PolylightEffect(*this); PolylightEffect *effect = new PolylightEffect(*this);
LIGHTGROUP::iterator light_iter; LightGroup::iterator light_iter;
light_iter = find(effect->_lightgroup.begin(),effect->_lightgroup.end(), newlight); light_iter = find(effect->_lightgroup.begin(),effect->_lightgroup.end(), newlight);
if(light_iter == effect->_lightgroup.end()) { if (light_iter == effect->_lightgroup.end()) {
cerr << "Light Not Found!\n"; pgraph_cat.debug()
<< "Attempt to remove Polylight " << newlight << "; not found.\n";
} else { } else {
// Remove light // Remove light
effect->_lightgroup.erase(light_iter); effect->_lightgroup.erase(light_iter);
@ -303,7 +323,7 @@ set_weight(float w) const {
// Here, we just pass that to the make // Here, we just pass that to the make
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
CPT(RenderEffect) PolylightEffect:: CPT(RenderEffect) PolylightEffect::
set_contrib(Contrib_Type ct) const { set_contrib(ContribType ct) const {
PolylightEffect *effect = new PolylightEffect(*this); PolylightEffect *effect = new PolylightEffect(*this);
effect->_contribution_type = ct; effect->_contribution_type = ct;
return return_new(effect); return return_new(effect);
@ -325,3 +345,28 @@ set_effect_center(LPoint3f ec) const{
return return_new(effect); return return_new(effect);
} }
////////////////////////////////////////////////////////////////////
// Function: PolylightEffect::has_light
// Access: Published
// Description: Returns true if the indicated light is listed in the
// PolylightEffect, false otherwise.
////////////////////////////////////////////////////////////////////
bool PolylightEffect::
has_light(const NodePath &light) const {
LightGroup::const_iterator li;
li = find(_lightgroup.begin(), _lightgroup.end(), light);
return (li != _lightgroup.end());
}
ostream &
operator << (ostream &out, PolylightEffect::ContribType ct) {
switch (ct) {
case PolylightEffect::CT_proximal:
return out << "proximal";
case PolylightEffect::CT_all:
return out << "all";
}
return out << "**Invalid ContribType(" << (int)ct << ")**";
}

View File

@ -40,36 +40,33 @@
// specially for night scenes // specially for night scenes
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
class EXPCL_PANDA PolylightEffect : public RenderEffect { class EXPCL_PANDA PolylightEffect : public RenderEffect {
PUBLISHED: PUBLISHED:
enum Contrib_Type { enum ContribType {
CPROXIMAL, CT_proximal,
CALL, CT_all,
}; };
private: typedef pvector< NodePath > LightGroup;
protected:
INLINE PolylightEffect(); INLINE PolylightEffect();
INLINE PolylightEffect(const PolylightEffect &copy); INLINE PolylightEffect(const PolylightEffect &copy);
Contrib_Type _contribution_type;
float _weight;
typedef pvector< NodePath > LIGHTGROUP;
LIGHTGROUP _lightgroup;
LPoint3f _effect_center;
PUBLISHED: PUBLISHED:
static CPT(RenderEffect) make(); static CPT(RenderEffect) make();
static CPT(RenderEffect) make(float weight, Contrib_Type contrib, LPoint3f effect_center); static CPT(RenderEffect) make(float weight, ContribType contrib, LPoint3f effect_center);
static CPT(RenderEffect) make(float weight, Contrib_Type contrib, LPoint3f effect_center, LIGHTGROUP lights); static CPT(RenderEffect) make(float weight, ContribType contrib, LPoint3f effect_center, const LightGroup &lights);
CPT(RenderEffect) add_light(const NodePath &newlight) const; CPT(RenderEffect) add_light(const NodePath &newlight) const;
CPT(RenderEffect) remove_light(const NodePath &newlight) const; CPT(RenderEffect) remove_light(const NodePath &newlight) const;
CPT(RenderEffect) set_weight(float w) const; CPT(RenderEffect) set_weight(float w) const;
CPT(RenderEffect) set_contrib(Contrib_Type c) const; CPT(RenderEffect) set_contrib(ContribType c) const;
CPT(RenderEffect) set_effect_center(LPoint3f ec) const; CPT(RenderEffect) set_effect_center(LPoint3f ec) const;
INLINE float get_weight() const; INLINE float get_weight() const;
INLINE Contrib_Type get_contrib() const; INLINE ContribType get_contrib() const;
INLINE LPoint3f get_effect_center()const; INLINE LPoint3f get_effect_center()const;
bool has_light(const NodePath &light) const;
public: public:
virtual bool has_cull_callback() const; virtual bool has_cull_callback() const;
virtual void cull_callback(CullTraverser *trav, CullTraverserData &data, virtual void cull_callback(CullTraverser *trav, CullTraverserData &data,
@ -78,6 +75,14 @@ public:
CPT(RenderAttrib) do_poly_light(const CullTraverserData *data, const TransformState *node_transform) const; CPT(RenderAttrib) do_poly_light(const CullTraverserData *data, const TransformState *node_transform) const;
virtual void output(ostream &out) const;
private:
ContribType _contribution_type;
float _weight;
LightGroup _lightgroup;
LPoint3f _effect_center;
protected: protected:
virtual int compare_to_impl(const RenderEffect *other) const; virtual int compare_to_impl(const RenderEffect *other) const;
@ -101,6 +106,8 @@ private:
#include "polylightEffect.I" #include "polylightEffect.I"
ostream &operator << (ostream &out, PolylightEffect::ContribType ct);
#endif #endif

View File

@ -19,7 +19,7 @@
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
// Function: TextureAttrib::Constructor // Function: TextureAttrib::Constructor
// Access: Private // Access: Protected
// Description: Use TextureAttrib::make() to construct a new // Description: Use TextureAttrib::make() to construct a new
// TextureAttrib object. // TextureAttrib object.
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
@ -31,7 +31,7 @@ TextureAttrib() {
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
// Function: TextureAttrib::Copy Constructor // Function: TextureAttrib::Copy Constructor
// Access: Private // Access: Protected
// Description: Use TextureAttrib::make() to construct a new // Description: Use TextureAttrib::make() to construct a new
// TextureAttrib object. The copy constructor is only // TextureAttrib object. The copy constructor is only
// defined to facilitate methods like add_on_stage(). // defined to facilitate methods like add_on_stage().

View File

@ -780,8 +780,9 @@ fillin(DatagramIterator &scan, BamReader *manager) {
// Push back a NULL pointer for each off TextureStage for now, until // Push back a NULL pointer for each off TextureStage for now, until
// we get the actual list of pointers later in complete_pointers(). // we get the actual list of pointers later in complete_pointers().
//_off_stages.reserve(num_off_stages); int i;
for (int i = 0; i < num_off_stages; i++) { _off_stages.reserve(num_off_stages);
for (i = 0; i < num_off_stages; i++) {
manager->read_pointer(scan); manager->read_pointer(scan);
_off_stages.push_back(NULL); _off_stages.push_back(NULL);
} }
@ -790,7 +791,7 @@ fillin(DatagramIterator &scan, BamReader *manager) {
// just read the pointers, all allocation will happen from // just read the pointers, all allocation will happen from
// complete_pointers because, it is a map template we get the // complete_pointers because, it is a map template we get the
// actual list of pointers later in complete_pointers(). // actual list of pointers later in complete_pointers().
for (int i = 0; i < _num_on_textures; i++) { for (i = 0; i < _num_on_textures; i++) {
manager->read_pointer(scan); manager->read_pointer(scan);
manager->read_pointer(scan); manager->read_pointer(scan);
} }

View File

@ -36,7 +36,7 @@
// secondary texture. // secondary texture.
//////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////
class EXPCL_PANDA TextureAttrib : public RenderAttrib { class EXPCL_PANDA TextureAttrib : public RenderAttrib {
private: protected:
INLINE TextureAttrib(); INLINE TextureAttrib();
INLINE TextureAttrib(const TextureAttrib &copy); INLINE TextureAttrib(const TextureAttrib &copy);