<commit_before>/******************************************************************************
*       SOFA, Simulation Open-Framework Architecture, version 1.0 beta 4      *
*                (c) 2006-2009 MGH, INRIA, USTL, UJF, CNRS                    *
*                                                                             *
* This library is free software; you can redistribute it and/or modify it     *
* under the terms of the GNU Lesser General Public License as published by    *
* the Free Software Foundation; either version 2.1 of the License, or (at     *
* your option) any later version.                                             *
*                                                                             *
* This library is distributed in the hope that it will be useful, but WITHOUT *
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or       *
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License *
* for more details.                                                           *
*                                                                             *
* You should have received a copy of the GNU Lesser General Public License    *
* along with this library; if not, write to the Free Software Foundation,     *
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301 USA.          *
*******************************************************************************
*                               SOFA :: Modules                               *
*                                                                             *
* Authors: The SOFA Team and external contributors (see Authors.txt)          *
*                                                                             *
* Contact information: <EMAIL>                             *
******************************************************************************/
#include <sofa/simulation/common/Simulation.h>
#include <sofa/simulation/common/PrintVisitor.h>
#include <sofa/simulation/common/FindByTypeVisitor.h>
#include <sofa/simulation/common/ExportGnuplotVisitor.h>
#include <sofa/simulation/common/InitVisitor.h>
#include <sofa/simulation/common/InstrumentVisitor.h>
#include <sofa/simulation/common/AnimateVisitor.h>
#include <sofa/simulation/common/MechanicalVisitor.h>
#include <sofa/simulation/common/CollisionVisitor.h>
#include <sofa/simulation/common/UpdateContextVisitor.h>
#include <sofa/simulation/common/UpdateMappingVisitor.h>
#include <sofa/simulation/common/ResetVisitor.h>
#include <sofa/simulation/common/VisualVisitor.h>
#include <sofa/simulation/common/ExportOBJVisitor.h>
#include <sofa/simulation/common/WriteStateVisitor.h>
#include <sofa/simulation/common/XMLPrintVisitor.h>
#include <sofa/simulation/common/PropagateEventVisitor.h>
#include <sofa/simulation/common/BehaviorUpdatePositionVisitor.h>
#include <sofa/simulation/common/AnimateBeginEvent.h>
#include <sofa/simulation/common/AnimateEndEvent.h>
#include <sofa/simulation/common/UpdateMappingEndEvent.h>
#include <sofa/simulation/common/CleanupVisitor.h>
#include <sofa/simulation/common/DeleteVisitor.h>


#include <sofa/helper/system/SetDirectory.h>
#include <sofa/helper/system/PipeProcess.h>
#include <sofa/helper/AdvancedTimer.h>

#include <sofa/core/ObjectFactory.h>


#include <fstream>
#include <string.h>


// #include <sofa/simulation/common/FindByTypeVisitor.h>



// #include <sofa/helper/system/FileRepository.h>

// #include <fstream>
// #include <string.h>
// #ifndef WIN32
// #include <locale.h>
// #endif



namespace sofa
{

namespace simulation
{


using namespace sofa::defaulttype;
Simulation::Simulation()
    : numMechSteps( initData(&numMechSteps,(unsigned) 1,"numMechSteps","Number of mechanical steps within one update step. If the update time step is dt, the mechanical time step is dt/numMechSteps.") ),
      nbSteps( initData(&nbSteps, (unsigned)0, "nbSteps", "Steps number of computation", true, false)),
      needToPrefetch(false),
      gnuplotDirectory( initData(&gnuplotDirectory,std::string(""),"gnuplotDirectory","Directory where the gnuplot files will be saved")),
      instrumentInUse( initData( &instrumentInUse, -1, "instrumentinuse", "Numero of the instrument currently used"))
{}

Simulation::~Simulation()
{
    if (Simulation::theSimulation == this) setSimulation( NULL );
}

/// The (unique) simulation which controls the scene
Simulation* Simulation::theSimulation = NULL;

void setSimulation ( Simulation* s )
{
    Simulation::theSimulation = s;
}

Simulation* getSimulation()
{
    return Simulation::theSimulation;
}

/// Print all object in the graph
void Simulation::print ( Node* root )
{
    if ( !root ) return;
    root->execute<PrintVisitor>();
}

/// Print all object in the graph
void Simulation::exportXML ( Node* root, const char* fileName, bool compact )
{
    if ( !root ) return;
    if ( fileName!=NULL )
    {
        std::ofstream out ( fileName );
        XMLPrintVisitor print ( out,compact );
        root->execute ( print );
    }
    else
    {
        XMLPrintVisitor print ( std::cout,compact );
        root->execute ( print );
    }
}

/// Initialize the scene.
void Simulation::init ( Node* root )
{
    //cerr<<"Simulation::init"<<endl;
    setContext( root->getContext());
    if ( !root ) return;
    needToPrefetch = false;
    root->execute<InitVisitor>();
    // Save reset state for later uses in reset()
    root->execute<MechanicalPropagatePositionAndVelocityVisitor>();
    root->execute<MechanicalPropagateFreePositionVisitor>();
    root->execute<StoreResetStateVisitor>();

    //Get the list of instruments present in the scene graph
    getInstruments(root);
}

void Simulation::getInstruments( Node *node)
{
    InstrumentVisitor fetchInstrument;
    fetchInstrument.execute(node);
    instruments = fetchInstrument.getInstruments();
}

/// Execute one timestep. If dt is 0, the dt parameter in the graph will be used
void Simulation::animate ( Node* root, double dt )
{
    if ( !root ) return;
    if ( root->getMultiThreadSimulation() )
        return;

#ifdef SOFA_DUMP_VISITOR_INFO
    simulation::Visitor::printNode(std::string("Step"));
#endif

    sofa::helper::AdvancedTimer::begin("Animate");

    {
        AnimateBeginEvent ev ( dt );
        PropagateEventVisitor act ( &ev );
        root->execute ( act );
    }

    //std::cout << "animate\n";
    double startTime = root->getTime();
    double mechanicalDt = dt/numMechSteps.getValue();
    //double nextTime = root->getTime() + root->getDt();

    // CHANGE to support MasterSolvers : CollisionVisitor is now activated within AnimateVisitor
    //root->execute<CollisionVisitor>();


    AnimateVisitor act;
    act.setDt ( mechanicalDt );
    BehaviorUpdatePositionVisitor beh(root->getDt());
    for( unsigned i=0; i<numMechSteps.getValue(); i++ )
    {
        root->execute ( beh );
        root->execute ( act );
        root->setTime ( startTime + (i+1)* act.getDt() );
        root->execute<UpdateSimulationContextVisitor>();
    }

    {
        AnimateEndEvent ev ( dt );
        PropagateEventVisitor act ( &ev );
        root->execute ( act );
    }

    sofa::helper::AdvancedTimer::stepBegin("UpdateMapping");
    //Visual Information update: Ray Pick add a MechanicalMapping used as VisualMapping
    root->execute<UpdateMappingVisitor>();
    sofa::helper::AdvancedTimer::step("UpdateMappingEndEvent");
    {
        UpdateMappingEndEvent ev ( dt );
        PropagateEventVisitor act ( &ev );
        root->execute ( act );
    }
    sofa::helper::AdvancedTimer::stepEnd("UpdateMapping");
#ifdef SOFA_DUMP_VISITOR_INFO
    simulation::Visitor::printCloseNode(std::string("Step"));<commit_msg>r6398/sofa-dev : BUGFIX: time was not propagated to the nodes of the visual graph<commit_after>/******************************************************************************
*       SOFA, Simulation Open-Framework Architecture, version 1.0 beta 4      *
*                (c) 2006-2009 MGH, INRIA, USTL, UJF, CNRS                    *
*                                                                             *
* This library is free software; you can redistribute it and/or modify it     *
* under the terms of the GNU Lesser General Public License as published by    *
* the Free Software Foundation; either version 2.1 of the License, or (at     *
* your option) any later version.                                             *
*                                                                             *
* This library is distributed in the hope that it will be useful, but WITHOUT *
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or       *
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License *
* for more details.                                                           *
*                                                                             *
* You should have received a copy of the GNU Lesser General Public License    *
* along with this library; if not, write to the Free Software Foundation,     *
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301 USA.          *
*******************************************************************************
*                               SOFA :: Modules                               *
*                                                                             *
* Authors: The SOFA Team and external contributors (see Authors.txt)          *
*                                                                             *
* Contact information: <EMAIL>                             *
******************************************************************************/
#include <sofa/simulation/common/Simulation.h>
#include <sofa/simulation/common/PrintVisitor.h>
#include <sofa/simulation/common/FindByTypeVisitor.h>
#include <sofa/simulation/common/ExportGnuplotVisitor.h>
#include <sofa/simulation/common/InitVisitor.h>
#include <sofa/simulation/common/InstrumentVisitor.h>
#include <sofa/simulation/common/AnimateVisitor.h>
#include <sofa/simulation/common/MechanicalVisitor.h>
#include <sofa/simulation/common/CollisionVisitor.h>
#include <sofa/simulation/common/UpdateContextVisitor.h>
#include <sofa/simulation/common/UpdateMappingVisitor.h>
#include <sofa/simulation/common/ResetVisitor.h>
#include <sofa/simulation/common/VisualVisitor.h>
#include <sofa/simulation/common/ExportOBJVisitor.h>
#include <sofa/simulation/common/WriteStateVisitor.h>
#include <sofa/simulation/common/XMLPrintVisitor.h>
#include <sofa/simulation/common/PropagateEventVisitor.h>
#include <sofa/simulation/common/BehaviorUpdatePositionVisitor.h>
#include <sofa/simulation/common/AnimateBeginEvent.h>
#include <sofa/simulation/common/AnimateEndEvent.h>
#include <sofa/simulation/common/UpdateMappingEndEvent.h>
#include <sofa/simulation/common/CleanupVisitor.h>
#include <sofa/simulation/common/DeleteVisitor.h>


#include <sofa/helper/system/SetDirectory.h>
#include <sofa/helper/system/PipeProcess.h>
#include <sofa/helper/AdvancedTimer.h>

#include <sofa/core/ObjectFactory.h>


#include <fstream>
#include <string.h>


// #include <sofa/simulation/common/FindByTypeVisitor.h>



// #include <sofa/helper/system/FileRepository.h>

// #include <fstream>
// #include <string.h>
// #ifndef WIN32
// #include <locale.h>
// #endif



namespace sofa
{

namespace simulation
{


using namespace sofa::defaulttype;
Simulation::Simulation()
    : numMechSteps( initData(&numMechSteps,(unsigned) 1,"numMechSteps","Number of mechanical steps within one update step. If the update time step is dt, the mechanical time step is dt/numMechSteps.") ),
      nbSteps( initData(&nbSteps, (unsigned)0, "nbSteps", "Steps number of computation", true, false)),
      needToPrefetch(false),
      gnuplotDirectory( initData(&gnuplotDirectory,std::string(""),"gnuplotDirectory","Directory where the gnuplot files will be saved")),
      instrumentInUse( initData( &instrumentInUse, -1, "instrumentinuse", "Numero of the instrument currently used"))
{}

Simulation::~Simulation()
{
    if (Simulation::theSimulation == this) setSimulation( NULL );
}

/// The (unique) simulation which controls the scene
Simulation* Simulation::theSimulation = NULL;

void setSimulation ( Simulation* s )
{
    Simulation::theSimulation = s;
}

Simulation* getSimulation()
{
    return Simulation::theSimulation;
}

/// Print all object in the graph
void Simulation::print ( Node* root )
{
    if ( !root ) return;
    root->execute<PrintVisitor>();
}

/// Print all object in the graph
void Simulation::exportXML ( Node* root, const char* fileName, bool compact )
{
    if ( !root ) return;
    if ( fileName!=NULL )
    {
        std::ofstream out ( fileName );
        XMLPrintVisitor print ( out,compact );
        root->execute ( print );
    }
    else
    {
        XMLPrintVisitor print ( std::cout,compact );
        root->execute ( print );
    }
}

/// Initialize the scene.
void Simulation::init ( Node* root )
{
    //cerr<<"Simulation::init"<<endl;
    setContext( root->getContext());
    if ( !root ) return;
    needToPrefetch = false;
    root->execute<InitVisitor>();
    // Save reset state for later uses in reset()
    root->execute<MechanicalPropagatePositionAndVelocityVisitor>();
    root->execute<MechanicalPropagateFreePositionVisitor>();
    root->execute<StoreResetStateVisitor>();

    //Get the list of instruments present in the scene graph
    getInstruments(root);
}

void Simulation::getInstruments( Node *node)
{
    InstrumentVisitor fetchInstrument;
    fetchInstrument.execute(node);
    instruments = fetchInstrument.getInstruments();
}

/// Execute one timestep. If dt is 0, the dt parameter in the graph will be used
void Simulation::animate ( Node* root, double dt )
{
    if ( !root ) return;
    if ( root->getMultiThreadSimulation() )
        return;

#ifdef SOFA_DUMP_VISITOR_INFO
    simulation::Visitor::printNode(std::string("Step"));
#endif

    sofa::helper::AdvancedTimer::begin("Animate");

    {
        AnimateBeginEvent ev ( dt );
        PropagateEventVisitor act ( &ev );
        root->execute ( act );
    }

    //std::cout << "animate\n";
    double startTime = root->getTime();
    double mechanicalDt = dt/numMechSteps.getValue();
    //double nextTime = root->getTime() + root->getDt();

    // CHANGE to support MasterSolvers : CollisionVisitor is now activated within AnimateVisitor
    //root->execute<CollisionVisitor>();


    AnimateVisitor act;
    act.setDt ( mechanicalDt );
    BehaviorUpdatePositionVisitor beh(root->getDt());
    for( unsigned i=0; i<numMechSteps.getValue(); i++ )
    {
        root->execute ( beh );
        root->execute ( act );
        root->setTime ( startTime + (i+1)* act.getDt() );
        getVisualRoot()->setTime ( root->getTime() );
        root->execute<UpdateSimulationContextVisitor>();
        getVisualRoot()->execute<UpdateSimulationContextVisitor>();
    }

    {
        AnimateEndEvent ev ( dt );
        PropagateEventVisitor act ( &ev );
        root->execute ( act );
    }

    sofa::helper::AdvancedTimer::stepBegin("UpdateMapping");
    //Visual Information update: Ray Pick add a MechanicalMapping used as VisualMapping
    root->execute<UpdateMappingVisitor>();
    sofa::helper::AdvancedTimer::step("UpdateMappingEndEvent");
    {
        UpdateMappingEndEvent ev ( dt );
        PropagateEventVisitor act ( &ev );
        root->execute ( act );
    }
    sofa::helper::AdvancedTimer::stepEnd("UpdateMapping");
#ifdef SOFA_DUMP_VISITOR_INFO
    simulation::Visitor::printCloseNode(std::string("Step"));
{'fraction_non_alphanumeric': 0.14183215887251763, 'fraction_numerical': 0.004356181934657271, 'mean_word_length': 2.898851148851149, 'pattern_counts': {'":': 0, '<': 104, '<?xml version=': 0, '>': 137, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 38, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '361418', 'n_tokens_mistral': 4336, 'n_tokens_neox': 4208, 'n_words': 1050}