From 499c702ffb6c697303b4f5a28461590c33bd9672 Mon Sep 17 00:00:00 2001 From: ehofman Date: Mon, 27 Dec 2004 13:21:18 +0000 Subject: [PATCH] =?utf8?q?Mathias=20Fr=F6hlich:?= MIME-Version: 1.0 Content-Type: text/plain; charset=utf8 Content-Transfer-Encoding: 8bit We should now be able to find wires or catapults when the ac3d model is loaded without the crease patch (caused by the much more unstructured scene graph emitted by the old loader). It should also emit more warnings if the carrier hardware configuration includes conflicting definitions. That code is the most intrusive one, it should not be used until you configure an aircraft carrier as a aimodel. So I think it should be save to apply that before the release too. --- src/AIModel/AICarrier.cxx | 142 +++++++++++++++++++++++++++----------- src/AIModel/AICarrier.hxx | 6 +- 2 files changed, 103 insertions(+), 45 deletions(-) diff --git a/src/AIModel/AICarrier.cxx b/src/AIModel/AICarrier.cxx index 6c33639e3..6d836d434 100644 --- a/src/AIModel/AICarrier.cxx +++ b/src/AIModel/AICarrier.cxx @@ -92,7 +92,7 @@ bool FGAICarrier::init() { // Attach a pointer to this carrier class to those objects. mark_wires(sel, wire_objects); mark_cat(sel, catapult_objects); - mark_solid(sel, solid_objects, false); + mark_solid(sel, solid_objects); return true; } @@ -129,14 +129,18 @@ void FGAICarrier::mark_nohot(ssgEntity* e) { } } -bool FGAICarrier::mark_wires(ssgEntity* e, const list& wire_objects) { +bool FGAICarrier::mark_wires(ssgEntity* e, const list& wire_objects, bool mark) { bool found = false; if (e->isAKindOf(ssgTypeBranch())) { - ssgBranch* br = (ssgBranch*)e; ssgEntity* kid; + + list::const_iterator it; + for (it = wire_objects.begin(); it != wire_objects.end(); ++it) + mark = mark || (e->getName() && (*it) == e->getName()); + for ( kid = br->getKid(0); kid != NULL ; kid = br->getNextKid() ) - found = mark_wires(kid, wire_objects) || found; + found = mark_wires(kid, wire_objects, mark) || found; if (found) br->setTraversalMaskBits(SSGTRAV_HOT); @@ -144,16 +148,31 @@ bool FGAICarrier::mark_wires(ssgEntity* e, const list& wire_objects) { } else if (e->isAKindOf(ssgTypeLeaf())) { list::const_iterator it; for (it = wire_objects.begin(); it != wire_objects.end(); ++it) { - if (e->getName() && (*it) == e->getName()) { + if (mark || (e->getName() && (*it) == e->getName())) { e->setTraversalMaskBits(SSGTRAV_HOT); - e->setUserData( FGAICarrierHardware::newWire( this ) ); - ssgLeaf *l = (ssgLeaf*)e; - if ( l->getNumLines() != 1 ) { - SG_LOG(SG_GENERAL, SG_ALERT, - "AICarrier: Found wires not modelled with exactly one line!"); + ssgBase* ud = e->getUserData(); + if (ud) { + FGAICarrierHardware* ch = dynamic_cast(ud); + if (ch) { + SG_LOG(SG_GENERAL, SG_WARN, + "AICarrier: Carrier hardware gets marked twice!\n" + " You have propably a whole branch marked as" + " a wire which also includes other carrier hardware." + ); + } else { + SG_LOG(SG_GENERAL, SG_ALERT, + "AICarrier: Found user data attached to a leaf node which " + "should be marked as a wire!\n ****Skipping!****"); + } + } else { + e->setUserData( FGAICarrierHardware::newWire( this ) ); + ssgLeaf *l = (ssgLeaf*)e; + if ( l->getNumLines() != 1 ) { + SG_LOG(SG_GENERAL, SG_ALERT, + "AICarrier: Found wires not modelled with exactly one line!"); + } + found = true; } - - found = true; } } } @@ -168,7 +187,7 @@ bool FGAICarrier::mark_solid(ssgEntity* e, const list& solid_objects, bo list::const_iterator it; for (it = solid_objects.begin(); it != solid_objects.end(); ++it) - mark = mark || e->getName() && (*it) == e->getName(); + mark = mark || (e->getName() && (*it) == e->getName()); for ( kid = br->getKid(0); kid != NULL ; kid = br->getNextKid() ) found = mark_solid(kid, solid_objects, mark) || found; @@ -181,21 +200,42 @@ bool FGAICarrier::mark_solid(ssgEntity* e, const list& solid_objects, bo for (it = solid_objects.begin(); it != solid_objects.end(); ++it) { if (mark || (e->getName() && (*it) == e->getName())) { e->setTraversalMaskBits(SSGTRAV_HOT); - e->setUserData( FGAICarrierHardware::newSolid( this ) ); - found = true; + ssgBase* ud = e->getUserData(); + if (ud) { + FGAICarrierHardware* ch = dynamic_cast(ud); + if (ch) { + SG_LOG(SG_GENERAL, SG_WARN, + "AICarrier: Carrier hardware gets marked twice!\n" + " You have propably a whole branch marked solid" + " which also includes other carrier hardware." + ); + } else { + SG_LOG(SG_GENERAL, SG_ALERT, + "AICarrier: Found user data attached to a leaf node which " + "should be marked solid!\n ****Skipping!****"); + } + } else { + e->setUserData( FGAICarrierHardware::newSolid( this ) ); + found = true; + } } } } return found; } -bool FGAICarrier::mark_cat(ssgEntity* e, const list& cat_objects) { +bool FGAICarrier::mark_cat(ssgEntity* e, const list& cat_objects, bool mark) { bool found = false; if (e->isAKindOf(ssgTypeBranch())) { ssgBranch* br = (ssgBranch*)e; ssgEntity* kid; + + list::const_iterator it; + for (it = cat_objects.begin(); it != cat_objects.end(); ++it) + mark = mark || (e->getName() && (*it) == e->getName()); + for ( kid = br->getKid(0); kid != NULL ; kid = br->getNextKid() ) - found = mark_cat(kid, cat_objects) || found; + found = mark_cat(kid, cat_objects, mark) || found; if (found) br->setTraversalMaskBits(SSGTRAV_HOT); @@ -203,33 +243,51 @@ bool FGAICarrier::mark_cat(ssgEntity* e, const list& cat_objects) { } else if (e->isAKindOf(ssgTypeLeaf())) { list::const_iterator it; for (it = cat_objects.begin(); it != cat_objects.end(); ++it) { - if (e->getName() && (*it) == e->getName()) { + if (mark || (e->getName() && (*it) == e->getName())) { e->setTraversalMaskBits(SSGTRAV_HOT); - e->setUserData( FGAICarrierHardware::newCatapult( this ) ); - ssgLeaf *l = (ssgLeaf*)e; - if ( l->getNumLines() != 1 ) { - SG_LOG(SG_GENERAL, SG_ALERT, - "AICarrier: Found a cat not modelled with exactly one line!"); - } - // Now some special code to make sure the cat points in the right - // direction. The 0 index must be the backward end, the 1 index - // the forward end. - // Forward is positive x-direction in our 3D model, also the model - // as such is flattened when it is loaded, so we do not need to care - // for transforms ... - short v[2]; - l->getLine(0, v, v+1 ); - sgVec3 ends[2]; - for (int k=0; k<2; ++k) - sgCopyVec3( ends[k], l->getVertex( v[k] ) ); - - // When the 1 end is behind the 0 end, swap the coordinates. - if (ends[0][0] < ends[1][0]) { - sgCopyVec3( l->getVertex( v[0] ), ends[1] ); - sgCopyVec3( l->getVertex( v[1] ), ends[0] ); + ssgBase* ud = e->getUserData(); + if (ud) { + FGAICarrierHardware* ch = dynamic_cast(ud); + if (ch) { + SG_LOG(SG_GENERAL, SG_WARN, + "AICarrier: Carrier hardware gets marked twice!\n" + " You have propably a whole branch marked as" + " a catapult which also includes other carrier hardware." + ); + } else { + SG_LOG(SG_GENERAL, SG_ALERT, + "AICarrier: Found user data attached to a leaf node which " + "should be marked as a catapult!\n ****Skipping!****"); + } + } else { + e->setUserData( FGAICarrierHardware::newCatapult( this ) ); + ssgLeaf *l = (ssgLeaf*)e; + if ( l->getNumLines() != 1 ) { + SG_LOG(SG_GENERAL, SG_ALERT, + "AICarrier: Found a cat not modelled with exactly " + "one line!"); + } else { + // Now some special code to make sure the cat points in the right + // direction. The 0 index must be the backward end, the 1 index + // the forward end. + // Forward is positive x-direction in our 3D model, also the model + // as such is flattened when it is loaded, so we do not need to + // care for transforms ... + short v[2]; + l->getLine(0, v, v+1 ); + sgVec3 ends[2]; + for (int k=0; k<2; ++k) + sgCopyVec3( ends[k], l->getVertex( v[k] ) ); + + // When the 1 end is behind the 0 end, swap the coordinates. + if (ends[0][0] < ends[1][0]) { + sgCopyVec3( l->getVertex( v[0] ), ends[1] ); + sgCopyVec3( l->getVertex( v[1] ), ends[0] ); + } + + found = true; + } } - - found = true; } } } diff --git a/src/AIModel/AICarrier.hxx b/src/AIModel/AICarrier.hxx index a9ae9e962..29f63f73b 100644 --- a/src/AIModel/AICarrier.hxx +++ b/src/AIModel/AICarrier.hxx @@ -90,9 +90,9 @@ private: void update(double dt); void mark_nohot(ssgEntity*); - bool mark_wires(ssgEntity*, const list&); - bool mark_cat(ssgEntity*, const list&); - bool mark_solid(ssgEntity*, const list&, bool); + bool mark_wires(ssgEntity*, const list&, bool = false); + bool mark_cat(ssgEntity*, const list&, bool = false); + bool mark_solid(ssgEntity*, const list&, bool = false); list solid_objects; // List of solid object names list wire_objects; // List of wire object names -- 2.39.5