From 72d20758284a87a19b734037513f08051ff3b962 Mon Sep 17 00:00:00 2001 From: frohlich Date: Sun, 11 Jun 2006 13:30:59 +0000 Subject: [PATCH] Modified Files: simgear/scene/material/mat.cxx simgear/scene/material/mat.hxx simgear/scene/material/matlib.cxx simgear/scene/material/matlib.hxx simgear/scene/tgdb/leaf.cxx simgear/scene/tgdb/obj.cxx Attach userdata to groundtile scenegraph leafs that contains a SGMaterial reference to the material of that leaf. Add (physical) material properties to the material definitions. Plug a memory leak with GlyphSigns. --- simgear/scene/material/mat.cxx | 14 +++ simgear/scene/material/mat.hxx | 97 ++++++++++++++++---- simgear/scene/material/matlib.cxx | 141 ++++++++++++++++++++---------- simgear/scene/material/matlib.hxx | 1 + simgear/scene/tgdb/leaf.cxx | 1 + simgear/scene/tgdb/obj.cxx | 1 + 6 files changed, 192 insertions(+), 63 deletions(-) diff --git a/simgear/scene/material/mat.cxx b/simgear/scene/material/mat.cxx index 8d197ede..48ba922a 100644 --- a/simgear/scene/material/mat.cxx +++ b/simgear/scene/material/mat.cxx @@ -136,6 +136,13 @@ SGMaterial::read_properties( const string &fg_root, const SGPropertyNode * props mipmap = props->getBoolValue("mipmap", true); light_coverage = props->getDoubleValue("light-coverage", 0.0); + // surface values for use with ground reactions + solid = props->getBoolValue("solid", true); + friction_factor = props->getDoubleValue("friction-factor", 1.0); + rolling_friction = props->getDoubleValue("rolling-friction", 0.02); + bumpiness = props->getDoubleValue("bumpiness", 0.0); + load_resistence = props->getDoubleValue("load-resistence", 1e30); + // Taken from default values as used in ac3d ambient[0] = props->getDoubleValue("ambient/r", 0.2); ambient[1] = props->getDoubleValue("ambient/g", 0.2); @@ -191,6 +198,13 @@ SGMaterial::init () mipmap = true; light_coverage = 0.0; + + solid = true; + friction_factor = 1; + rolling_friction = 0.02; + bumpiness = 0; + load_resistence = 1e30; + shininess = 1.0; for (int i = 0; i < 4; i++) { ambient[i] = (i < 3) ? 0.2 : 1.0; diff --git a/simgear/scene/material/mat.hxx b/simgear/scene/material/mat.hxx index c7534e70..62df39ec 100644 --- a/simgear/scene/material/mat.hxx +++ b/simgear/scene/material/mat.hxx @@ -36,6 +36,8 @@ #include #include +#include + #include #include @@ -104,7 +106,7 @@ public: /** * Destructor. */ - virtual ~SGMaterial( void ); + ~SGMaterial( void ); @@ -118,31 +120,31 @@ public: * @return true if the texture loaded, false if it was loaded * already. */ - virtual bool load_texture (int n = -1); + bool load_texture (int n = -1); /** * Get the textured state. */ - virtual ssgSimpleState *get_state (int n = -1) const; + ssgSimpleState *get_state (int n = -1) const; /** * Get the number of textures assigned to this material. */ - virtual inline int get_num() const { return _status.size(); } + inline int get_num() const { return _status.size(); } /** * Get the xsize of the texture, in meters. */ - virtual inline double get_xsize() const { return xsize; } + inline double get_xsize() const { return xsize; } /** * Get the ysize of the texture, in meters. */ - virtual inline double get_ysize() const { return ysize; } + inline double get_ysize() const { return ysize; } /** @@ -152,27 +154,61 @@ public: * * @return The area (m^2?) covered by each light. */ - virtual inline double get_light_coverage () const { return light_coverage; } + inline double get_light_coverage () const { return light_coverage; } + /** + * Return if the surface material is solid, if it is not solid, a fluid + * can be assumed, that is usually water. + */ + bool get_solid () const { return solid; } /** - * Get the number of randomly-placed objects defined for this material. + * Get the friction factor for that material + */ + double get_friction_factor () const { return friction_factor; } + + /** + * Get the rolling friction for that material + */ + double get_rolling_friction () const { return rolling_friction; } + + /** + * Get the bumpines for that material + */ + double get_bumpiness () const { return bumpiness; } + + /** + * Get the load resistence + */ + double get_load_resistence () const { return load_resistence; } + + /** + * Get the list of names for this material */ - virtual int get_object_group_count () const { return object_groups.size(); } + const vector& get_names() const { return _names; } + /** + * add the given name to the list of names this material is known + */ + void add_name(const string& name) { _names.push_back(name); } + + /** + * Get the number of randomly-placed objects defined for this material. + */ + int get_object_group_count () const { return object_groups.size(); } /** * Get a randomly-placed object for this material. */ - virtual SGMatModelGroup * get_object_group (int index) const { + SGMatModelGroup * get_object_group (int index) const { return object_groups[index]; } /** * Return pointer to glyph class, or 0 if it doesn't exist. */ - virtual SGMaterialGlyph * get_glyph (const string& name) const { - map::const_iterator it = glyphs.find(name); + SGMaterialGlyph * get_glyph (const string& name) const { + map >::const_iterator it = glyphs.find(name); return it != glyphs.end() ? it->second : 0; } @@ -186,7 +222,7 @@ protected: /** * Initialization method, invoked by all public constructors. */ - virtual void init(); + void init(); protected: @@ -223,14 +259,32 @@ private: // coverage of night lighting. double light_coverage; + // True if the material is solid, false if it is a fluid + bool solid; + + // the friction factor of that surface material + double friction_factor; + + // the rolling friction of that surface material + double rolling_friction; + + // the bumpiness of that surface material + double bumpiness; + + // the load resistence of that surface material + double load_resistence; + // material properties - sgVec4 ambient, diffuse, specular, emission; + SGVec4f ambient, diffuse, specular, emission; double shininess; + // the list of names for this material. May be empty. + vector _names; + vector > object_groups; // taxiway-/runway-sign texture elements - map glyphs; + map > glyphs; //////////////////////////////////////////////////////////////////// @@ -248,7 +302,7 @@ private: }; -class SGMaterialGlyph { +class SGMaterialGlyph : public SGReferenced { public: SGMaterialGlyph(SGPropertyNode *); inline double get_left() const { return _left; } @@ -260,4 +314,15 @@ protected: double _right; }; +class SGMaterialUserData : public ssgBase { +public: + SGMaterialUserData(const SGMaterial* material) : + mMaterial(material) + {} + const SGMaterial* getMaterial() const + { return mMaterial; } +private: + SGSharedPtr mMaterial; +}; + #endif // _SG_MAT_HXX diff --git a/simgear/scene/material/matlib.cxx b/simgear/scene/material/matlib.cxx index d3bd72c5..e4975831 100644 --- a/simgear/scene/material/matlib.cxx +++ b/simgear/scene/material/matlib.cxx @@ -33,6 +33,8 @@ # include #endif +#include + #include #include #include @@ -46,6 +48,7 @@ #include #include #include +#include #include "mat.hxx" @@ -188,17 +191,20 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char throw; } + SGSharedPtr m; + int nMaterials = materials.nChildren(); for (int i = 0; i < nMaterials; i++) { const SGPropertyNode * node = materials.getChild(i); if (!strcmp(node->getName(), "material")) { - SGSharedPtr m = new SGMaterial( fg_root, node, season ); + m = new SGMaterial( fg_root, node, season ); vectornames = node->getChildren("name"); for ( unsigned int j = 0; j < names.size(); j++ ) { string name = names[j]->getStringValue(); // cerr << "Material " << name << endl; matlib[name] = m; + m->add_name(name); SG_LOG( SG_TERRAIN, SG_INFO, " Loading material " << names[j]->getStringValue() ); } @@ -219,7 +225,9 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char gnd_lights->enable( GL_BLEND ); gnd_lights->disable( GL_ALPHA_TEST ); gnd_lights->disable( GL_LIGHTING ); - matlib["GROUND_LIGHTS"] = new SGMaterial( gnd_lights ); + m = new SGMaterial( gnd_lights ); + m->add_name("GROUND_LIGHTS"); + matlib["GROUND_LIGHTS"] = m; GLuint tex_name; @@ -237,10 +245,14 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char rwy_white_lights->setMaterial ( GL_SPECULAR, 0.0, 0.0, 0.0, 0.0 ); rwy_white_lights->setMaterial ( GL_EMISSION, 0.0, 0.0, 0.0, 0.0 ); rwy_white_lights->setTexture( tex_name ); - matlib["RWY_WHITE_LIGHTS"] = new SGMaterial( rwy_white_lights ); + m = new SGMaterial( rwy_white_lights ); + m->add_name("RWY_WHITE_LIGHTS"); + matlib["RWY_WHITE_LIGHTS"] = m; // For backwards compatibility ... remove someday - matlib["RUNWAY_LIGHTS"] = new SGMaterial( rwy_white_lights ); - matlib["RWY_LIGHTS"] = new SGMaterial( rwy_white_lights ); + m->add_name("RUNWAY_LIGHTS"); + matlib["RUNWAY_LIGHTS"] = m; + m->add_name("RWY_LIGHTS"); + matlib["RWY_LIGHTS"] = m; // end of backwards compatitibilty // hard coded runway medium intensity white light state @@ -257,8 +269,9 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char rwy_white_medium_lights->setMaterial ( GL_SPECULAR, 0.0, 0.0, 0.0, 0.0 ); rwy_white_medium_lights->setMaterial ( GL_EMISSION, 0.0, 0.0, 0.0, 0.0 ); rwy_white_medium_lights->setTexture( tex_name ); - matlib["RWY_WHITE_MEDIUM_LIGHTS"] - = new SGMaterial( rwy_white_medium_lights ); + m = new SGMaterial( rwy_white_medium_lights ); + m->add_name("RWY_WHITE_MEDIUM_LIGHTS"); + matlib["RWY_WHITE_MEDIUM_LIGHTS"] = m; // hard coded runway low intensity white light state tex_name = gen_standard_dir_light_map( 235, 235, 195, 155 ); @@ -274,8 +287,9 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char rwy_white_low_lights->setMaterial ( GL_SPECULAR, 0.0, 0.0, 0.0, 0.0 ); rwy_white_low_lights->setMaterial ( GL_EMISSION, 0.0, 0.0, 0.0, 0.0 ); rwy_white_low_lights->setTexture( tex_name ); - matlib["RWY_WHITE_LOW_LIGHTS"] - = new SGMaterial( rwy_white_low_lights ); + m = new SGMaterial( rwy_white_low_lights ); + m->add_name("RWY_WHITE_LOW_LIGHTS"); + matlib["RWY_WHITE_LOW_LIGHTS"] = m; // hard coded runway yellow light state tex_name = gen_standard_dir_light_map( 235, 215, 20, 255 ); @@ -291,7 +305,9 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char rwy_yellow_lights->setMaterial ( GL_SPECULAR, 0.0, 0.0, 0.0, 0.0 ); rwy_yellow_lights->setMaterial ( GL_EMISSION, 0.0, 0.0, 0.0, 0.0 ); rwy_yellow_lights->setTexture( tex_name ); - matlib["RWY_YELLOW_LIGHTS"] = new SGMaterial( rwy_yellow_lights ); + m = new SGMaterial( rwy_yellow_lights ); + m->add_name("RWY_YELLOW_LIGHTS"); + matlib["RWY_YELLOW_LIGHTS"] = m; // hard coded runway medium intensity yellow light state tex_name = gen_standard_dir_light_map( 235, 215, 20, 205 ); @@ -307,8 +323,9 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char rwy_yellow_medium_lights->setMaterial ( GL_SPECULAR, 0.0, 0.0, 0.0, 0.0 ); rwy_yellow_medium_lights->setMaterial ( GL_EMISSION, 0.0, 0.0, 0.0, 0.0 ); rwy_yellow_medium_lights->setTexture( tex_name ); - matlib["RWY_YELLOW_MEDIUM_LIGHTS"] - = new SGMaterial( rwy_yellow_medium_lights ); + m = new SGMaterial( rwy_yellow_medium_lights ); + m->add_name("RWY_YELLOW_MEDIUM_LIGHTS"); + matlib["RWY_YELLOW_MEDIUM_LIGHTS"] = m; // hard coded runway low intensity yellow light state tex_name = gen_standard_dir_light_map( 235, 215, 20, 155 ); @@ -324,8 +341,9 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char rwy_yellow_low_lights->setMaterial ( GL_SPECULAR, 0.0, 0.0, 0.0, 0.0 ); rwy_yellow_low_lights->setMaterial ( GL_EMISSION, 0.0, 0.0, 0.0, 0.0 ); rwy_yellow_low_lights->setTexture( tex_name ); - matlib["RWY_YELLOW_LOW_LIGHTS"] - = new SGMaterial( rwy_yellow_low_lights ); + m = new SGMaterial( rwy_yellow_low_lights ); + m->add_name("RWY_YELLOW_LOW_LIGHTS"); + matlib["RWY_YELLOW_LOW_LIGHTS"] = m; // hard coded runway red light state tex_name = gen_standard_dir_light_map( 235, 90, 90, 255 ); @@ -341,8 +359,9 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char rwy_red_lights->setMaterial ( GL_SPECULAR, 0.0, 0.0, 0.0, 0.0 ); rwy_red_lights->setMaterial ( GL_EMISSION, 0.0, 0.0, 0.0, 0.0 ); rwy_red_lights->setTexture( tex_name ); - matlib["RWY_RED_LIGHTS"] - = new SGMaterial( rwy_red_lights ); + m = new SGMaterial( rwy_red_lights ); + m->add_name("RWY_RED_LIGHTS"); + matlib["RWY_RED_LIGHTS"] = m; // hard coded medium intensity runway red light state tex_name = gen_standard_dir_light_map( 235, 90, 90, 205 ); @@ -358,8 +377,9 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char rwy_red_medium_lights->setMaterial ( GL_SPECULAR, 0.0, 0.0, 0.0, 0.0 ); rwy_red_medium_lights->setMaterial ( GL_EMISSION, 0.0, 0.0, 0.0, 0.0 ); rwy_red_medium_lights->setTexture( tex_name ); - matlib["RWY_RED_MEDIUM_LIGHTS"] - = new SGMaterial( rwy_red_medium_lights ); + m = new SGMaterial( rwy_red_medium_lights ); + m->add_name("RWY_RED_MEDIUM_LIGHTS"); + matlib["RWY_RED_MEDIUM_LIGHTS"] = m; // hard coded low intensity runway red light state tex_name = gen_standard_dir_light_map( 235, 90, 90, 155 ); @@ -375,8 +395,9 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char rwy_red_low_lights->setMaterial ( GL_SPECULAR, 0.0, 0.0, 0.0, 0.0 ); rwy_red_low_lights->setMaterial ( GL_EMISSION, 0.0, 0.0, 0.0, 0.0 ); rwy_red_low_lights->setTexture( tex_name ); - matlib["RWY_RED_LOW_LIGHTS"] - = new SGMaterial( rwy_red_low_lights ); + m = new SGMaterial( rwy_red_low_lights ); + m->add_name("RWY_RED_LOW_LIGHTS"); + matlib["RWY_RED_LOW_LIGHTS"] = m; // hard coded runway green light state tex_name = gen_standard_dir_light_map( 20, 235, 20, 255 ); @@ -392,8 +413,9 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char rwy_green_lights->setMaterial ( GL_SPECULAR, 0.0, 0.0, 0.0, 0.0 ); rwy_green_lights->setMaterial ( GL_EMISSION, 0.0, 0.0, 0.0, 0.0 ); rwy_green_lights->setTexture( tex_name ); - matlib["RWY_GREEN_LIGHTS"] - = new SGMaterial( rwy_green_lights ); + m = new SGMaterial( rwy_green_lights ); + m->add_name("RWY_GREEN_LIGHTS"); + matlib["RWY_GREEN_LIGHTS"] = m; // hard coded medium intensity runway green light state tex_name = gen_standard_dir_light_map( 20, 235, 20, 205 ); @@ -409,8 +431,9 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char rwy_green_medium_lights->setMaterial ( GL_SPECULAR, 0.0, 0.0, 0.0, 0.0 ); rwy_green_medium_lights->setMaterial ( GL_EMISSION, 0.0, 0.0, 0.0, 0.0 ); rwy_green_medium_lights->setTexture( tex_name ); - matlib["RWY_GREEN_MEDIUM_LIGHTS"] - = new SGMaterial( rwy_green_medium_lights ); + m = new SGMaterial( rwy_green_medium_lights ); + m->add_name("RWY_GREEN_MEDIUM_LIGHTS"); + matlib["RWY_GREEN_MEDIUM_LIGHTS"] = m; // hard coded low intensity runway green light state tex_name = gen_standard_dir_light_map( 20, 235, 20, 155 ); @@ -426,10 +449,11 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char rwy_green_low_lights->setMaterial ( GL_SPECULAR, 0.0, 0.0, 0.0, 0.0 ); rwy_green_low_lights->setMaterial ( GL_EMISSION, 0.0, 0.0, 0.0, 0.0 ); rwy_green_low_lights->setTexture( tex_name ); - matlib["RWY_GREEN_LOW_LIGHTS"] - = new SGMaterial( rwy_green_low_lights ); - matlib["RWY_GREEN_TAXIWAY_LIGHTS"] - = new SGMaterial( rwy_green_low_lights ); + m = new SGMaterial( rwy_green_low_lights ); + m->add_name("RWY_GREEN_LOW_LIGHTS"); + matlib["RWY_GREEN_LOW_LIGHTS"] = m; + m->add_name("RWY_GREEN_TAXIWAY_LIGHTS"); + matlib["RWY_GREEN_TAXIWAY_LIGHTS"] = m; // hard coded low intensity taxiway blue light state tex_name = gen_taxiway_dir_light_map( 90, 90, 235, 205 ); @@ -445,8 +469,9 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char taxiway_blue_low_lights->setMaterial ( GL_SPECULAR, 0.0, 0.0, 0.0, 0.0 ); taxiway_blue_low_lights->setMaterial ( GL_EMISSION, 0.0, 0.0, 0.0, 0.0 ); taxiway_blue_low_lights->setTexture( tex_name ); - matlib["RWY_BLUE_TAXIWAY_LIGHTS"] - = new SGMaterial( taxiway_blue_low_lights ); + m = new SGMaterial( taxiway_blue_low_lights ); + m->add_name("RWY_BLUE_TAXIWAY_LIGHTS"); + matlib["RWY_BLUE_TAXIWAY_LIGHTS"] = m; // hard coded runway vasi light state tex_name = gen_standard_dir_light_map( 235, 235, 195, 255 ); @@ -463,7 +488,9 @@ bool SGMaterialLib::load( const string &fg_root, const string& mpath, const char rwy_vasi_lights->setMaterial ( GL_EMISSION, 0.0, 0.0, 0.0, 0.0 ); // rwy_vasi_lights->setTexture( gen_vasi_light_map_old() ); rwy_vasi_lights->setTexture( tex_name ); - matlib["RWY_VASI_LIGHTS"] = new SGMaterial( rwy_vasi_lights ); + m = new SGMaterial( rwy_vasi_lights ); + m->add_name("RWY_VASI_LIGHTS"); + matlib["RWY_VASI_LIGHTS"] = m; return true; } @@ -491,6 +518,7 @@ bool SGMaterialLib::add_item ( const string &mat_name, const string &full_path ) << mat_name << " (" << full_path << ")"); matlib[mat_name] = new SGMaterial( full_path ); + matlib[mat_name]->add_name(mat_name); return true; } @@ -500,6 +528,7 @@ bool SGMaterialLib::add_item ( const string &mat_name, const string &full_path ) bool SGMaterialLib::add_item ( const string &mat_name, ssgSimpleState *state ) { matlib[mat_name] = new SGMaterial( state ); + matlib[mat_name]->add_name(mat_name); SG_LOG( SG_TERRAIN, SG_INFO, " Loading material given a premade " << "ssgSimpleState = " << mat_name ); @@ -539,8 +568,27 @@ void SGMaterialLib::load_next_deferred() { } } -bool SGMaterialLib::find( ssgSimpleState *state, string & material ) const +// Return the material from that given leaf +const SGMaterial* SGMaterialLib::findMaterial(/*const*/ssgLeaf* leaf) const { + if (!leaf) + return 0; + + ssgBase* base = leaf->getUserData(); + if (!base) + return 0; + + SGMaterialUserData* matUserData = dynamic_cast(base); + if (!matUserData) + return 0; + + return matUserData->getMaterial(); +} + +bool SGMaterialLib::find( ssgSimpleState* state, string & material ) const +{ + // is obsolete, just kept here to avoid a race condition with + // SimGear/flightgear cvs checkouts ... bool found = false; ssgSimpleState *state_mat; @@ -548,26 +596,25 @@ bool SGMaterialLib::find( ssgSimpleState *state, string & material ) const for( const_material_map_iterator iter = begin(); iter != end(); iter++ ) { - int nb_tex = (*iter).second->get_num(); + int nb_tex = (*iter).second->get_num(); - // many textures per material - for( int i = 0; i < nb_tex; i++ ) - { - // material state - state_mat = (*iter).second->get_state( i ); + // many textures per material + for( int i = 0; i < nb_tex; i++ ) + { + // material state + state_mat = (*iter).second->get_state( i ); - if( state_mat == state ) - { + if( state_mat == state ) + { material = (*iter).first.c_str(); - found = true; - break; - } - } + found = true; + break; + } + } - if( found ) - break; + if( found ) + break; } return found; } - diff --git a/simgear/scene/material/matlib.hxx b/simgear/scene/material/matlib.hxx index 269a3fa2..c5aaed7c 100644 --- a/simgear/scene/material/matlib.hxx +++ b/simgear/scene/material/matlib.hxx @@ -87,6 +87,7 @@ public: material_map_iterator end() { return matlib.end(); } const_material_map_iterator end() const { return matlib.end(); } + const SGMaterial* findMaterial(/*const*/ssgLeaf* leaf) const; bool find( ssgSimpleState*, string & material ) const; // Destructor diff --git a/simgear/scene/tgdb/leaf.cxx b/simgear/scene/tgdb/leaf.cxx index 9fbb4236..77e0ed9e 100644 --- a/simgear/scene/tgdb/leaf.cxx +++ b/simgear/scene/tgdb/leaf.cxx @@ -250,6 +250,7 @@ ssgLeaf *sgMakeLeaf( const string& path, // lookup the state record + leaf->setUserData( new SGMaterialUserData(mat) ); leaf->setState( state ); if ( calc_lights ) { diff --git a/simgear/scene/tgdb/obj.cxx b/simgear/scene/tgdb/obj.cxx index 9fdcd871..c0bf8d0f 100644 --- a/simgear/scene/tgdb/obj.cxx +++ b/simgear/scene/tgdb/obj.cxx @@ -176,6 +176,7 @@ bool sgGenTile( const string& path, SGBucket b, ssgLeaf *leaf = new ssgVtxTable ( GL_TRIANGLE_FAN, vl, nl, tl, cl ); + leaf->setUserData( new SGMaterialUserData(mat) ); leaf->setState( state ); geometry->addKid( leaf ); -- 2.39.5