00001 /************************************************************************/ 00002 /* This file is part of openMask(c) INRIA, CNRS, Universite de Rennes 1 */ 00003 /* 1993-2002, thereinafter the Software */ 00004 /* */ 00005 /* The Software has been developped within the Siames Project. */ 00006 /* INRIA, the University of Rennes 1 and CNRS jointly hold intellectual */ 00007 /* property rights */ 00008 /* */ 00009 /* The Software has been registered with the Agence pour la Protection */ 00010 /* des Programmes (APP) under registration number */ 00011 /* IDDN.FR.001.510008.00.S.P.2001.000.41200 */ 00012 /* */ 00013 /* This file may be distributed under the terms of the Q Public License */ 00014 /* version 1.0 as defined by Trolltech AS of Norway and appearing in */ 00015 /* the file LICENSE.QPL included in the packaging of this file. */ 00016 /* */ 00017 /* Licensees holding valid specific licenses issued by INRIA, CNRS or */ 00018 /* Universite Rennes 1 for the software may use this file in */ 00019 /* acordance with that specific license */ 00020 /************************************************************************/ 00021 00022 #include "OMKJointExtension.h" 00023 #include "OMKJoint.h" 00024 #include "OMKExtensibleSimulatedObject.h" 00025 #include "OMKInteractorExtension.h" 00026 #include "OMKParametersAccessor.inl" 00027 #include "OMKInputNT.h" 00028 #include "OMKSessionPrm.h" 00029 #include "OMKTransformType.h" 00030 00031 namespace OMK 00032 { 00033 namespace Iii 00034 { 00035 //================================================================= 00036 // JointInteractorExtension 00037 //================================================================= 00046 class JointInteractorExtension : public InteractorExtension 00047 { 00048 friend class JointExtension ; 00050 00051 public: 00053 virtual ~JointInteractorExtension() ; 00054 protected: 00056 JointInteractorExtension( JointExtension* jointExtension ) ; 00058 00059 virtual bool loadObjectParameters( const ConfigurationParameterDescriptor * node ) ; 00060 virtual bool loadExtensionParameters( const ConfigurationParameterDescriptor * node ) ; 00062 virtual void postComputeParameters() ; 00063 void startRetroPropagation() ; 00064 void stopRetroPropagation() ; 00065 Name _referenceId ; 00066 Name _positionId ; 00067 bool _connected ; 00068 JointExtension* _jointExtension ; 00069 } ; 00070 00071 //----------------------------------------------------------------- 00072 JointInteractorExtension::JointInteractorExtension( JointExtension* jointExtension ) 00073 : InteractorExtension( jointExtension->_owner, std::string( jointExtension->_id.getCString() ) + "Interactor", false ), 00074 _connected( false ), 00075 _jointExtension( jointExtension ) 00076 { 00077 _access._level = 0 ; 00078 } 00079 //----------------------------------------------------------------- 00080 JointInteractorExtension::~JointInteractorExtension() 00081 { 00082 } 00083 //----------------------------------------------------------------- 00084 bool JointInteractorExtension::loadObjectParameters( const ConfigurationParameterDescriptor * node ) 00085 { 00086 bool ok = true ; 00087 00088 std::pair< Name, Name > connection ; 00089 ok = ok && ParametersAccessor::get( node, "refPositionConnect", connection, _owner ) ; 00090 if( ok ) 00091 { 00092 _referenceId = connection.first ; 00093 _positionId = connection.second ; 00094 } 00095 00096 return ok ; 00097 } 00098 //----------------------------------------------------------------- 00099 bool JointInteractorExtension::loadExtensionParameters( const ConfigurationParameterDescriptor * node ) 00100 { 00101 ParametersAccessor::get( node, "Level", _access._level ); 00102 OMTRACEID( OMK_DEBUG_III, "The interactor " << OMK::debugMsg( this, _owner ) << " has the level " << _access._level ) ; 00103 startInteractor() ; 00104 00105 // Try to read the category in the configuration of the reference object 00106 bool found = false ; // flag to know if the search is ok 00107 std::string category( "absolute" ) ; // The default value 00108 // 1/ Search in the current configuration the category 00109 if( ParametersAccessor::get( node, "Category", category ) ) 00110 { 00111 OMTRACEID( OMK_DEBUG_III, "The category for the reference is \"" << category << "\" and it " << ( found ? "was found in configuration" : "is the default value" ) ) ; 00112 } 00113 else 00114 { 00115 // 2/ search the extensions configuration of the reference object 00116 const ConfigurationParameterDescriptor *extNodeForRef = _owner->getController().getObjectDescriptorOfObject( _referenceId ).getExtensionsParameters() ; 00117 int nbItems = extNodeForRef ? extNodeForRef->getNumberOfSubItems() : 0 ; 00118 for( int i = 0 ; i < nbItems && !found ; ++i ) 00119 { 00120 // Retrieves configuration for each extension 00121 const ConfigurationParameterDescriptor * extNode = extNodeForRef->getSubDescriptorByPosition( i ) ; 00122 // Try to found "Connectors" in it 00123 const ConfigurationParameterDescriptor * connectorsNode = extNode->getSubDescriptorByName( "Connectors" ) ; 00124 // Try to found the connector with the same id than the output which is the reference for the joint 00125 const ConfigurationParameterDescriptor * connectorNode = connectorsNode ? connectorsNode->getSubDescriptorByName( _positionId.getCString() ) : 0 ; 00126 if( connectorNode ) 00127 { // Ok, so try to read the "Category" field 00128 ParametersAccessor::get( connectorNode, "Category", category ) ; 00129 found = true ; 00130 break ; 00131 } 00132 else 00133 { // Not ok, no connectors has this id 00134 int nbItems2 = connectorsNode ? connectorsNode->getNumberOfSubItems() : 0 ; 00135 for( int j = 0 ; j < nbItems2 ; ++j ) 00136 { // Look for connector which has the "Attribute" field equals to the id 00137 std::string id ; 00138 const ConfigurationParameterDescriptor * connectorNode = connectorsNode->getSubDescriptorByPosition( j ) ; 00139 if( ParametersAccessor::get( connectorNode, "Attribute", id ) && id == _positionId ) 00140 { // The "Attribute" field is ok => try to read the "Category" field 00141 ParametersAccessor::get( connectorNode, "Category", category ) ; 00142 found = true ; 00143 break ; 00144 } 00145 } 00146 } 00147 } 00148 OMTRACEID( OMK_DEBUG_III, "The category for the reference is \"" << category << "\" and it " << ( found ? "was found in configuration" : "is the default value" ) ) ; 00149 } 00150 00151 // Creates the interactor output 00152 InteractorOutput::create( _jointExtension->_referencePosition.getId(), _jointExtension->_referencePosition.getId(), this, category, OMK::Type::AccessGroupLevel(), false ) ; 00153 00154 return true ; 00155 } 00156 //----------------------------------------------------------------- 00157 void JointInteractorExtension::postComputeParameters() 00158 { 00159 } 00160 //----------------------------------------------------------------- 00161 void JointInteractorExtension::startRetroPropagation() 00162 { 00163 if( !getSessionWith( _referenceId ) ) 00164 { 00165 startSessionWith( _referenceId ) ; 00166 OMMESSAGE( "start session" ) ; 00167 } 00168 else if( !_connected ) 00169 { 00170 (*getSessionWith( _referenceId )).c( _jointExtension->_referencePosition.getId() ).c( OMK::Iii::controlTakeOverAndGetCurrentValues ) ; 00171 _connected = true ; 00172 OMMESSAGE( "start retro propagation" ) ; 00173 } 00174 } 00175 //----------------------------------------------------------------- 00176 void JointInteractorExtension::stopRetroPropagation() 00177 { 00178 if( _connected ) 00179 { 00180 (*getSessionWith( _referenceId )).c( _jointExtension->_referencePosition.getId() ).c( OMK::Iii::controlRelease ) ; 00181 _connected = false ; 00182 OMMESSAGE( "stop retro propagation" ) ; 00183 } 00184 } 00185 //----------------------------------------------------------------- 00186 00187 //================================================================= 00188 // JointExtension 00189 //================================================================= 00190 00191 REGISTER_EXTENSION_FACTORY( JointExtension, "Joint" ) ; 00192 //----------------------------------------------------------------- 00193 00194 // Default constructor 00195 JointExtension::JointExtension( ExtensibleSimulatedObject* owner, const Name& id, bool registerExtension ) 00196 : ExtensionT< ExtensibleSimulatedObject >( owner, id, registerExtension ), 00197 _objectPosition( 0 ), 00198 _referencePosition( "refPosition", OMK::Type::Transform::sk_identity ), 00199 _jointPosition( "jointPosition", OMK::Type::Transform::sk_identity ), 00200 _connected( false ), 00201 _interactor( 0 ), 00202 _joint( 0 ) 00203 { 00204 // add the attributes to the object 00205 _owner->addAttribute( _referencePosition ) ; 00206 _owner->addAttribute( _jointPosition ) ; 00207 // Look for the retrto propagation flag 00208 const ConfigurationParameterDescriptor * node = _owner->getObjectDescriptor().getExtensionsParameters() ; 00209 const ConfigurationParameterDescriptor * extNode = node ? node->getSubDescriptorByName( _id.getCString() ) : 0 ; 00210 bool retroAction = false ; // Default is false 00211 ParametersAccessor::get( extNode, "Retro", retroAction ) ; 00212 if( retroAction ) 00213 { 00214 // For retro-propagation the extension must declare the output for the reference position 00215 _referencePosition.createOutput() ; 00216 // And create the interactor to update the reference position 00217 _interactor = new JointInteractorExtension( this ) ; 00218 } 00219 } 00220 00221 //----------------------------------------------------------------- 00222 00223 // Destructor 00224 JointExtension::~JointExtension() 00225 { 00226 // delete the associated interactor 00227 delete _interactor ; 00228 } 00229 //----------------------------------------------------------------- 00230 00231 bool JointExtension::loadObjectParameters( const ConfigurationParameterDescriptor * node ) 00232 { 00233 // Calls the interactor loader if neccessary 00234 return !_interactor || _interactor->loadObjectParameters( node ) ; 00235 } 00236 //----------------------------------------------------------------- 00237 00238 bool JointExtension::loadExtensionParameters( const ConfigurationParameterDescriptor * node ) 00239 { 00240 // Gets the name of the position attribute of the object 00241 Name attributeName( "Position" ) ; // by default "Position" 00242 ParametersAccessor::get( node, "PositionName", attributeName ) ; 00243 // Gets the attribute accessor 00244 _objectPosition = _owner->getBaseAttribute< OMK::Type::Transform >( attributeName ) ; 00245 bool ok = _objectPosition != 0 ; 00246 00247 // Calls the interactor loader if neccessary 00248 ok = ok && ( !_interactor || _interactor->loadExtensionParameters( node ) ) ; 00249 00250 // The joint 00251 std::string jointClass( "Lock" ) ; 00252 00253 ok = ok && ParametersAccessor::get( node, "Joint", jointClass ) ; 00254 _joint = OMK::Iii::JointFactory::getInstance().create( jointClass )( this, node ) ; 00255 OMASSERTM( _joint, "Joint [" << jointClass << "] cannot be created, may be not registered in the main !" ) ; 00256 00257 return ok ; 00258 } 00259 //----------------------------------------------------------------- 00260 00261 void JointExtension::postComputeParameters() 00262 { 00263 OMASSERTM( _joint, "The joint must be created" ) ; 00264 // To be linked the joint must found the position, see if the reference position declares an input and if this one is connected 00265 bool updatedLinkstate = _objectPosition 00266 && _referencePosition.getInput() 00267 && _referencePosition.getInput()->getConnectedOutput() ; 00268 if( _connected ) 00269 { 00270 if( !updatedLinkstate ) 00271 { // Change the state => no more connected 00272 _connected = false ; 00273 // Nothing else to do 00274 OMMESSAGE( "release" ) ; 00275 } 00276 else 00277 { // Connected and still connected 00278 // Calculates the new joint position based on the reference position 00279 _joint->currentJointPosition() ; 00280 // Does the object move ? 00281 00282 // Retro propagation is activated 00283 // the object moves itself (by an interactor, its own behavior,...) 00284 // => calculates the the ideal position for the reference position 00285 if( _objectPosition->isUpdated() && _joint->retroPropagation() ) 00286 { 00287 // Starts retro-propagation 00288 if( _interactor ) _interactor->startRetroPropagation() ; 00289 } 00290 else 00291 { 00292 // The object doesn't move itself => it follows the reference, no more retro-propagation 00293 if( _interactor ) _interactor->stopRetroPropagation() ; 00294 } 00295 // Calculates the new joint position based on the joint position 00296 _joint->currentObjectPosition() ; 00297 } 00298 } 00299 else 00300 { 00301 if( updatedLinkstate ) 00302 { // Change the state => The connection has just been connected 00303 OMMESSAGE( "linked" ) ; 00304 _connected = true ; 00305 _joint->establishLink() ; 00306 } 00307 // else unconnected and still unconnected => nothing to do 00308 } 00309 } 00310 00311 }// namespace Iii 00312 }// namespace OMK
Documentation generated on Mon Jun 9 11:45:56 2008 |
Generated with doxygen by Dimitri van Heesch , 1997-2007 |