Skip to content

mmp22squ@uea.ac.uk

Due to recent bot attacks we have changed the sign-up process. If you want to participate in our forum please send a message via our contact form.

Forum Replies Created

Viewing 5 posts - 1 through 5 (of 5 total)
  • Author
    Posts
  • in reply to: Issue with Implementing New Features in .h and .hh Files #9832

    Hi Adrian

    I truly appreciate your help.
    I am working on modifying the wetting boundary conditions in my free energy model by replacing the linear potentials (Eq. 24/25/26 from PhysRevE.93.033305) with cubic and quartic potential. the cubic quartic potential include c1 and c2 concentration fractions of fluids 1, 2 ,and 3 .

    so C1 and C2 are defined in the file olb-1.7r0/examples/multiComponent/contactAngle3d/contactAngle3d.cpp as follows:

    SuperLatticeVelocity3D<T, DESCRIPTOR> velocity(sLattice1);
    SuperLatticeDensity3D<T, DESCRIPTOR> rho(sLattice1);
    rho.getName() = “rho”;
    SuperLatticeDensity3D<T, DESCRIPTOR> phi(sLattice2);
    phi.getName() = “phi”;
    SuperIdentity3D<T,T> c1 (half*(rho+phi));
    c1.getName() = “density-fluid-1”;
    SuperIdentity3D<T,T> c2 (half*(rho-phi));
    c2.getName() = “density-fluid-2”;

    I need to use C1 and C2 inside the : olb-1.7r0/src/boundary/setFreeEnergyWallBoundary3D.hh file, but I’m unsure how to properly set them up there. Do you have any suggestions on how to structure this so I can access them correctly in the .hh?

    For the Duplicate issue:
    in the src/boundary/setFreeEnergyWallBoundary3D.hh

    I noticed some duplicate code, and out of curiosity, I tried deleting one of the identical parts. Surprisingly, this caused an error. I understand it’s not a major issue, but it triggered my curiosity—why would removing an exact duplicate make a difference?

    namespace olb {

    /// Implementation of a wetting boundary condition for the ternary free energy model, consisting of a BounceBack
    /// dynamics and an FreeEnergyWall PostProcessor.
    /// \param[in] alpha_ – Parameter related to the interface width. [lattice units]
    /// \param[in] kappa1_ – Parameter related to surface tension. [lattice units]
    /// \param[in] kappa2_ – Parameter related to surface tension. [lattice units]
    /// \param[in] h1_ – Parameter related to resulting contact angle of the boundary. [lattice units]
    /// \param[in] h2_ – Parameter related to resulting contact angle of the boundary. [lattice units]
    /// \param[in] latticeNumber – determines the number of the free energy lattice to set the boundary accordingly
    /// \param[in] modelNumber
    ////////// SuperLattice Domain /////////////////////////////////////////

    ///Initialising the Free Energy Wall Boundary on the superLattice domain
    template<typename T, typename DESCRIPTOR>
    void setFreeEnergyWallBoundary(SuperLattice<T, DESCRIPTOR>& sLattice, SuperGeometry<T,3>& superGeometry, int material,
    T alpha, T kappa1, T kappa2, T h1, T h2, int latticeNumber, int modelNumber)
    {
    setFreeEnergyWallBoundary<T,DESCRIPTOR>(sLattice, superGeometry.getMaterialIndicator(material),
    alpha, kappa1, kappa2, h1, h2, latticeNumber,modelNumber);

    }

    //////////////
    ///Initialising the Free Energy Wall Boundary on the superLattice domain
    template<typename T, typename DESCRIPTOR>
    void setFreeEnergyWallBoundary(SuperLattice<T, DESCRIPTOR>& sLattice, FunctorPtr<SuperIndicatorF3D<T>>&& indicator,
    T alpha, T kappa1, T kappa2, T h1, T h2, int latticeNumber,int modelNumber)
    {
    OstreamManager clout(std::cout, “setFreeEnergyWallBoundary”);
    bool includeOuterCells = false;
    int _overlap = 1;
    if (indicator->getSuperGeometry().getOverlap() == 1) {
    includeOuterCells = true;
    clout << “WARNING: overlap == 1, boundary conditions set on overlap despite unknown neighbor materials” << std::endl;
    }
    T addend = 0;
    if (latticeNumber==1) {
    if (modelNumber==1) {

    addend = 1./(alpha*alpha) *( (h1/kappa1) + (h2/kappa2));
    }
    }
    else if (latticeNumber==2) {
    if (modelNumber==1) {
    addend = 1./(alpha*alpha) * ( (h1/kappa1) + (-h2/kappa2) );
    }
    }
    else if (latticeNumber==3) {
    if (modelNumber==1) {
    addend = 1./(alpha*alpha) * ( (h1/kappa1) + (h2/kappa2) );
    }
    }
    for (int iCloc = 0; iCloc < sLattice.getLoadBalancer().size(); ++iCloc) {
    setFreeEnergyWallBoundary<T,DESCRIPTOR>(sLattice.getBlock(iCloc),
    indicator->getBlockIndicatorF(iCloc), addend, latticeNumber,modelNumber ,includeOuterCells);
    }
    /// Adds needed Cells to the Communicator _commBC in SuperLattice
    addPoints2CommBC(sLattice, std::forward<decltype(indicator)>(indicator), _overlap);
    }

    /// Implementation of a wetting boundary condition for the ternary free energy model, consisting of a BounceBack
    /// dynamics and an FreeEnergyWall PostProcessor.
    /// \param[in] alpha_ – Parameter related to the interface width. [lattice units]
    /// \param[in] kappa1_ – Parameter related to surface tension. [lattice units]
    /// \param[in] kappa2_ – Parameter related to surface tension. [lattice units]
    /// \param[in] kappa3_ – Parameter related to surface tension. [lattice units]
    /// \param[in] h1_ – Parameter related to resulting contact angle of the boundary. [lattice units]
    /// \param[in] h2_ – Parameter related to resulting contact angle of the boundary. [lattice units]
    /// \param[in] h3_ – Parameter related to resulting contact angle of the boundary. [lattice units]
    /// \param[in] latticeNumber – determines the number of the free energy lattice to set the boundary accordingly

    ////////// SuperLattice Domain /////////////////////////////////////////

    ///Initialising the Free Energy Wall Boundary on the superLattice domain
    template<typename T, typename DESCRIPTOR>
    void setFreeEnergyWallBoundary(SuperLattice<T, DESCRIPTOR>& sLattice, SuperGeometry<T,3>& superGeometry, int material,
    T alpha, T kappa1, T kappa2, T kappa3, T h1, T h2,T h3, int latticeNumber,int modelNumber)
    {
    setFreeEnergyWallBoundary<T,DESCRIPTOR>(sLattice, superGeometry.getMaterialIndicator(material),
    alpha, kappa1, kappa2, kappa3, h1, h2, h3, latticeNumber,modelNumber);
    }

    ///Initialising the Free Energy Wall Boundary on the superLattice domain
    template<typename T, typename DESCRIPTOR>
    void setFreeEnergyWallBoundary(SuperLattice<T, DESCRIPTOR>& sLattice, FunctorPtr<SuperIndicatorF3D<T>>&& indicator,
    T alpha, T kappa1, T kappa2, T kappa3, T h1, T h2, T h3, int latticeNumber,int modelNumber)
    {
    OstreamManager clout(std::cout, “setFreeEnergyWallBoundary”);
    bool includeOuterCells = false;
    int _overlap = indicator->getSuperGeometry().getOverlap();
    if (indicator->getSuperGeometry().getOverlap() == 1) {
    includeOuterCells = true;
    clout << “WARNING: overlap == 1, boundary conditions set on overlap despite unknown neighbor materials” << std::endl;
    }
    T addend = 0;
    if (latticeNumber==1) {
    if (modelNumber==1) {
    addend = 1./(alpha*alpha) * ( (h1/kappa1) + (h2/kappa2) );
    }
    }
    else if (latticeNumber==2) {
    if (modelNumber==1) {
    addend = 1./(alpha*alpha) * ( (h1/kappa1) + (-h2/kappa2) );
    }
    }
    else if (latticeNumber==3) {
    if (modelNumber==1) {
    addend = 1./(alpha*alpha) * ( (h1/kappa1) + (h2/kappa2) );
    }
    }
    for (int iCloc = 0; iCloc < sLattice.getLoadBalancer().size(); ++iCloc) {
    setFreeEnergyWallBoundary<T,DESCRIPTOR>(sLattice.getBlock(iCloc),
    indicator->getBlockIndicatorF(iCloc), addend, latticeNumber, modelNumber, includeOuterCells);
    }
    /// Adds needed Cells to the Communicator _commBC in SuperLattice
    addPoints2CommBC(sLattice, std::forward<decltype(indicator)>(indicator), _overlap);
    }

    ////////// BlockLattice Domain /////////////////////////////////////////

    in reply to: Issue with Implementing New Features in .h and .hh Files #9828

    Dear Adrian

    I totally agree with you We are learn and we will be learning fron birth to death.
    However, I meant in same.hh addend along other parts are declared twice . I was not the develloper to know why and how the code works . But it seems declared twice .

    FYI I use c++ since 2010 .

    Kind regards
    MOKHTARI Ahlem

    in reply to: Issue with Implementing New Features in .h and .hh Files #9824

    Hi Adrian, I think the mistake was deleting the parts that occur twice. I can do it now, it has no error. However, I cannot see why parts of the code are repeated. Can you help me understand why?

    in reply to: Issue with Implementing New Features in .h and .hh Files #9823

    Hi Adrian
    Thanks alot for replying
    I’m working on modifying the Free Energy Wall Boundary implementation, and I want to introduce an indicator to distinguish between three different boundary condition models. My idea is to add an integer or an enumeration to specify which model is being used and then apply the corresponding boundary condition logic accordingly.

    Here is the Error

    rm -f tmp/*.* tmp/vtkData/*.* tmp/vtkData/data/*.* tmp/imageData/*.* tmp/imageData/data/*.* tmp/gnuplotData/*.* tmp/gnuplotData/data/*.*
    rm -f contactAngle3d.o contactAngle3d.d contactAngle3d
    make -C ../../../external
    make[1]: Entering directory ‘/local/mmp22squ/Downloads/olb-1.7r0/olb-1.7r0/external’
    make -C zlib
    make[2]: Entering directory ‘/local/mmp22squ/Downloads/olb-1.7r0/olb-1.7r0/external/zlib’
    make[2]: Nothing to be done for ‘all’.
    make[2]: Leaving directory ‘/local/mmp22squ/Downloads/olb-1.7r0/olb-1.7r0/external/zlib’
    cp zlib/build/libz.a lib/
    make -C tinyxml
    make[2]: Entering directory ‘/local/mmp22squ/Downloads/olb-1.7r0/olb-1.7r0/external/tinyxml’
    make[2]: Nothing to be done for ‘all’.
    make[2]: Leaving directory ‘/local/mmp22squ/Downloads/olb-1.7r0/olb-1.7r0/external/tinyxml’
    cp tinyxml/build/libtinyxml.a lib/
    make[1]: Leaving directory ‘/local/mmp22squ/Downloads/olb-1.7r0/olb-1.7r0/external’
    make -C ../../.. core
    make[1]: Entering directory ‘/local/mmp22squ/Downloads/olb-1.7r0/olb-1.7r0’
    make[1]: Nothing to be done for ‘core’.
    make[1]: Leaving directory ‘/local/mmp22squ/Downloads/olb-1.7r0/olb-1.7r0′
    g++ -O3 -Wall -march=native -mtune=native -std=c++17 -pthread -DPLATFORM_CPU_SISD -DDEFAULT_FLOATING_POINT_TYPE=double -I../../../src -I../../../external/zlib -I../../../external/tinyxml -c -o contactAngle3d.o contactAngle3d.cpp
    In file included from ../../../src/dynamics/dynamics3D.h:35,
    from ../../../src/olb3D.h:5,
    from contactAngle3d.cpp:36:
    ../../../src/dynamics/freeEnergyCoupling3D.h: In instantiation of ‘void olb::ChemicalPotentialCoupling3D::apply(CELLS&, PARAMETERS&) [with CELLS = olb::utilities::TypeIndexedTuple<olb::meta::plain_map<olb::meta::list<olb::names::A, olb::names::B>, olb::meta::list<olb::cpu::Cell<double, olb::descriptors::D3Q19<olb::descriptors::CHEM_POTENTIAL, olb::descriptors::FORCE>, olb::Platform::CPU_SISD>, olb::cpu::Cell<double, olb::descriptors::D3Q19<olb::descriptors::CHEM_POTENTIAL, olb::descriptors::FORCE>, olb::Platform::CPU_SISD> > > >; PARAMETERS = olb::ParametersD<double, olb::descriptors::D3Q19<olb::descriptors::CHEM_POTENTIAL, olb::descriptors::FORCE>, olb::ChemicalPotentialCoupling3D::ALPHA, olb::ChemicalPotentialCoupling3D::KAPPA1, olb::ChemicalPotentialCoupling3D::KAPPA2, olb::ChemicalPotentialCoupling3D::KAPPA3>]’:
    ../../../src/core/superLatticeCoupling.h:158:5: required from ‘void olb::ConcreteBlockCouplingO<COUPLEES, PLATFORM, COUPLER, olb::OperatorScope::PerCellWithParameters>::execute(typename olb::AbstractCouplingO<COUPLEES>::LatticeR) [with COUPLER = olb::ChemicalPotentialCoupling3D; COUPLEES = olb::meta::plain_map<olb::meta::list<olb::names::A, olb::names::B>, olb::meta::list<olb::descriptors::VALUED_DESCRIPTOR<double, olb::descriptors::D3Q19<olb::descriptors::CHEM_POTENTIAL, olb::descriptors::FORCE> >, olb::descriptors::VALUED_DESCRIPTOR<double, olb::descriptors::D3Q19<olb::descriptors::CHEM_POTENTIAL, olb::descriptors::FORCE> > > >; olb::Platform PLATFORM = olb::Platform::CPU_SISD; typename olb::AbstractCouplingO<COUPLEES>::LatticeR = olb::Vector<int, 3>]’
    ../../../src/core/superLatticeCoupling.h:199:17: required from ‘void olb::ConcreteBlockCouplingO<COUPLEES, PLATFORM, COUPLER, olb::OperatorScope::PerCellWithParameters>::execute() [with COUPLER = olb::ChemicalPotentialCoupling3D; COUPLEES = olb::meta::plain_map<olb::meta::list<olb::names::A, olb::names::B>, olb::meta::list<olb::descriptors::VALUED_DESCRIPTOR<double, olb::descriptors::D3Q19<olb::descriptors::CHEM_POTENTIAL, olb::descriptors::FORCE> >, olb::descriptors::VALUED_DESCRIPTOR<double, olb::descriptors::D3Q19<olb::descriptors::CHEM_POTENTIAL, olb::descriptors::FORCE> > > >; olb::Platform PLATFORM = olb::Platform::CPU_SISD]’
    ../../../src/core/superLatticeCoupling.h:186:8: required from here
    ../../../src/dynamics/freeEnergyCoupling3D.h:69:7: warning: unused variable ‘term3’ [-Wunused-variable]
    69 | V term3 = 0.;
    | ^~~~~
    g++ contactAngle3d.o -o contactAngle3d -lolbcore -L../../../external/lib -lpthread -lz -ltinyxml -L../../../build/lib
    /usr/bin/ld: contactAngle3d.o: in function `prepareLattice(olb::SuperLattice<double, olb::descriptors::D3Q19<olb::descriptors::CHEM_POTENTIAL, olb::descriptors::FORCE> >&, olb::SuperLattice<double, olb::descriptors::D3Q19<olb::descriptors::CHEM_POTENTIAL, olb::descriptors::FORCE> >&, olb::UnitConverter<double, olb::descriptors::D3Q19<olb::descriptors::CHEM_POTENTIAL, olb::descriptors::FORCE> >&, olb::SuperGeometry<double, 3u>&)’:
    contactAngle3d.cpp:(.text+0x154d1): undefined reference to `void olb::setFreeEnergyWallBoundary<double, olb::descriptors::D3Q19<olb::descriptors::CHEM_POTENTIAL, olb::descriptors::FORCE> >(olb::SuperLattice<double, olb::descriptors::D3Q19<olb::descriptors::CHEM_POTENTIAL, olb::descriptors::FORCE> >&, olb::SuperGeometry<double, 3u>&, int, double, double, double, double, double, int, int)’
    /usr/bin/ld: contactAngle3d.cpp:(.text+0x15521): undefined reference to `void olb::setFreeEnergyWallBoundary<double, olb::descriptors::D3Q19<olb::descriptors::CHEM_POTENTIAL, olb::descriptors::FORCE> >(olb::SuperLattice<double, olb::descriptors::D3Q19<olb::descriptors::CHEM_POTENTIAL, olb::descriptors::FORCE> >&, olb::SuperGeometry<double, 3u>&, int, double, double, double, double, double, int, int)’
    collect2: error: ld returned 1 exit status
    make: *** [../../../default.single.mk:38: contactAngle3d] Error 1

    Here is .h

    namespace olb {

    /// Implementation of a wetting boundary condition for the ternary free energy model, consisting of a BounceBack
    /// dynamics and an FreeEnergyWall PostProcessor.
    /// \param[in] alpha_ – Parameter related to the interface width. [lattice units]
    /// \param[in] kappa1_ – Parameter related to surface tension. [lattice units]
    /// \param[in] kappa2_ – Parameter related to surface tension. [lattice units]
    /// \param[in] h1_ – Parameter related to resulting contact angle of the boundary. [lattice units]
    /// \param[in] h2_ – Parameter related to resulting contact angle of the boundary. [lattice units]
    /// \param[in] latticeNumber – determines the number of the free energy lattice to set the boundary accordingly
    /// \param[in] ModelNumber

    ///Initialising the Free Energy Wall Boundary on the superLattice domain
    template<typename T, typename DESCRIPTOR>
    void setFreeEnergyWallBoundary(SuperLattice<T, DESCRIPTOR>& sLattice, SuperGeometry<T,3>& superGeometry, int material,
    T alpha, T kappa1, T kappa2, T h1, T h2, int latticeNumber,int ModelNumber);

    ///Initialising the Free Energy Wall Boundary on the superLattice domain
    template<typename T, typename DESCRIPTOR>
    void setFreeEnergyWallBoundary(SuperLattice<T, DESCRIPTOR>& sLattice, FunctorPtr<SuperIndicatorF3D<T>>&& indicator,
    T alpha, T kappa1, T kappa2, T h1, T h2, int latticeNumber, int ModelNumber);

    /// Implementation of a wetting boundary condition for the ternary free energy model, consisting of a BounceBack
    /// dynamics and an FreeEnergyWall PostProcessor.
    /// \param[in] alpha_ – Parameter related to the interface width. [lattice units]
    /// \param[in] kappa1_ – Parameter related to surface tension. [lattice units]
    /// \param[in] kappa2_ – Parameter related to surface tension. [lattice units]
    /// \param[in] kappa3_ – Parameter related to surface tension. [lattice units]
    /// \param[in] h1_ – Parameter related to resulting contact angle of the boundary. [lattice units]
    /// \param[in] h2_ – Parameter related to resulting contact angle of the boundary. [lattice units]
    /// \param[in] h3_ – Parameter related to resulting contact angle of the boundary. [lattice units]
    /// \param[in] latticeNumber – determines the number of the free energy lattice to set the boundary accordingly
    /// \param[in] ModelNumber
    ///Initialising the Free Energy Wall Boundary on the superLattice domain
    template<typename T, typename DESCRIPTOR>
    void setFreeEnergyWallBoundary(SuperLattice<T, DESCRIPTOR>& sLattice, SuperGeometry<T,3>& superGeometry, int material,
    T alpha, T kappa1, T kappa2, T kappa3, T h1, T h2,T h3, int latticeNumber, int ModelNumber);

    ///Initialising the Free Energy Wall Boundary on the superLattice domain
    template<typename T, typename DESCRIPTOR>
    void setFreeEnergyWallBoundary(SuperLattice<T, DESCRIPTOR>& sLattice, FunctorPtr<SuperIndicatorF3D<T>>&& indicator,
    T alpha, T kappa1, T kappa2, T kappa3, T h1, T h2, T h3, int latticeNumber, int ModelNumber);

    //set FreeEnergyWallBoundary on block domain.
    //This function works for the setFreeEnergyWallBoundary with h1,h2,h3 Parameters and h1,h2 Parameters
    template<typename T, typename DESCRIPTOR>
    void setFreeEnergyWallBoundary(BlockLattice<T,DESCRIPTOR>& _block, BlockIndicatorF3D<T>& indicator,
    T addend, int latticeNumber,int ModelNumber,bool includeOuterCells=false);

    }//namespace olb

    #endif

    Here is .hh
    namespace olb {

    /// Implementation of a wetting boundary condition for the ternary free energy model, consisting of a BounceBack
    /// dynamics and an FreeEnergyWall PostProcessor.
    /// \param[in] alpha_ – Parameter related to the interface width. [lattice units]
    /// \param[in] kappa1_ – Parameter related to surface tension. [lattice units]
    /// \param[in] kappa2_ – Parameter related to surface tension. [lattice units]
    /// \param[in] kappa3_ – Parameter related to surface tension. [lattice units]
    /// \param[in] h1_ – Parameter related to resulting contact angle of the boundary. [lattice units]
    /// \param[in] h2_ – Parameter related to resulting contact angle of the boundary. [lattice units]
    /// \param[in] h3_ – Parameter related to resulting contact angle of the boundary. [lattice units]
    /// \param[in] latticeNumber – determines the number of the free energy lattice to set the boundary accordingly
    /// \param[in] ModelNumber
    ////////// SuperLattice Domain /////////////////////////////////////////

    ///Initialising the Free Energy Wall Boundary on the superLattice domain
    template<typename T, typename DESCRIPTOR>
    void setFreeEnergyWallBoundary(SuperLattice<T, DESCRIPTOR>& sLattice, SuperGeometry<T,3>& superGeometry, int material,
    T alpha, T kappa1, T kappa2, T kappa3, T h1, T h2,T h3, int latticeNumber,int ModelNumber)
    {
    setFreeEnergyWallBoundary<T,DESCRIPTOR>(sLattice, superGeometry.getMaterialIndicator(material),
    alpha, kappa1, kappa2, kappa3, h1, h2, h3, latticeNumber,ModelNumber);
    }

    ///Initialising the Free Energy Wall Boundary on the superLattice domain
    template<typename T, typename DESCRIPTOR>
    void setFreeEnergyWallBoundary(SuperLattice<T, DESCRIPTOR>& sLattice, FunctorPtr<SuperIndicatorF3D<T>>&& indicator,
    T alpha, T kappa1, T kappa2, T kappa3, T h1, T h2, T h3, int latticeNumber,int ModelNumber)
    {
    OstreamManager clout(std::cout, “setFreeEnergyWallBoundary”);
    bool includeOuterCells = false;
    int _overlap = indicator->getSuperGeometry().getOverlap();
    if (indicator->getSuperGeometry().getOverlap() == 1) {
    includeOuterCells = true;
    clout << “WARNING: overlap == 1, boundary conditions set on overlap despite unknown neighbor materials” << std::endl;
    }
    T addend = 0;
    if (latticeNumber==1) {
    if (ModelNumber==1){
    addend = 1./(alpha*alpha) * ( (h1/kappa1) + (h2/kappa2) + (h3/kappa3) );
    }
    }
    else if (latticeNumber==2) {
    if (ModelNumber==1){
    addend = 1./(alpha*alpha) * ( (h1/kappa1) + (-h2/kappa2) );
    }
    }
    else if (latticeNumber==3) {
    if (ModelNumber==1){
    addend = 1./(alpha*alpha) * ( (h3/kappa3) );
    }
    }
    for (int iCloc = 0; iCloc < sLattice.getLoadBalancer().size(); ++iCloc) {
    setFreeEnergyWallBoundary<T,DESCRIPTOR>(sLattice.getBlock(iCloc),
    indicator->getBlockIndicatorF(iCloc), addend, latticeNumber,includeOuterCells,ModelNumber);
    }
    /// Adds needed Cells to the Communicator _commBC in SuperLattice
    addPoints2CommBC(sLattice, std::forward<decltype(indicator)>(indicator), _overlap);
    }

    ////////// BlockLattice Domain /////////////////////////////////////////

    //set FreeEnergyWallBoundary on block domain.
    //This function works for the setFreeEnergyWallBoundary with h1,h2,h3 Parameters and h1,h2 Parameters
    template<typename T, typename DESCRIPTOR>
    void setFreeEnergyWallBoundary(BlockLattice<T,DESCRIPTOR>& _block, BlockIndicatorF3D<T>& indicator,
    T addend, int latticeNumber, bool includeOuterCells,int ModelNumber)
    {
    using namespace boundaryhelper;
    OstreamManager clout(std::cout, “setFreeEnergyWallBoundary”);
    const auto& blockGeometryStructure = indicator.getBlockGeometry();
    const int margin = includeOuterCells ? 0 : 1;
    std::vector<int> discreteNormal(4, 0);
    blockGeometryStructure.forSpatialLocations([&](auto iX, auto iY, auto iZ) {
    if (blockGeometryStructure.getNeighborhoodRadius({iX, iY, iZ}) >= margin
    && indicator(iX, iY, iZ)) {
    discreteNormal = blockGeometryStructure.getStatistics().getType(iX, iY, iZ, true);
    if (discreteNormal[1]!=0 || discreteNormal[2]!=0 || discreteNormal[3]!=0) {
    if (latticeNumber == 1) {
    _block.template defineDynamics<BounceBackBulkDensity>({iX,iY,iZ});
    }
    else {
    _block.template defineDynamics<FreeEnergyWallDynamics>({iX,iY,iZ});
    }

    _block.addPostProcessor(
    typeid(stage::PostStream), {iX, iY, iZ},
    olb::boundaryhelper::promisePostProcessorForNormal<T,DESCRIPTOR,FreeEnergyWallProcessor3D>(
    Vector<int,3>(discreteNormal.data() + 1)));
    _block.get(iX, iY, iZ).template setField<olb::descriptors::ADDEND>(addend);

    if(latticeNumber == 1){
    _block.addPostProcessor(
    typeid(stage::PostStream), {iX, iY, iZ},
    promisePostProcessorForNormal<T,DESCRIPTOR,FreeEnergyChemPotBoundaryProcessor3DA>(
    Vector<int,3>(discreteNormal.data() + 1)));
    } else {
    _block.addPostProcessor(
    typeid(stage::PostStream), {iX, iY, iZ},
    promisePostProcessorForNormal<T,DESCRIPTOR,FreeEnergyChemPotBoundaryProcessor3DB>(
    Vector<int,3>(discreteNormal.data() + 1)));
    }

    }
    }
    });
    }
    }//namespace olb

    #endif

    Here is the main

    // Add wall boundary
    setFreeEnergyWallBoundary<T,DESCRIPTOR>(sLattice1, superGeometry, 2, alpha, kappa1, kappa2, h1, h2, 1,1);
    setFreeEnergyWallBoundary<T,DESCRIPTOR>(sLattice2, superGeometry, 2, alpha, kappa1, kappa2, h1, h2, 2,1);

    in reply to: Help on creating simulation of a solid falling into water? #9535

    Dear Stephan,

    I hope you are doing fine .

    I am reaching out to seek your guidance regarding coupling particle models to the free-energy approach within the lattice Boltzmann framework. Over time, my understanding and experience with lattice Boltzmann methods have improved significantly, and I am now confident in understanding the individual implementation of different models.

    However, I am currently facing challenges in achieving a proper coupling of models. Would you be able to recommend a tutorial or any reference material that provides clear guidance on coupling different models in the lattice Boltzmann method? Any resources, examples, or advice on this topic would be highly appreciated.

Viewing 5 posts - 1 through 5 (of 5 total)