Bond4
You can copy Bond2 example, substitute Bond2 with Bond4 in every part of the code,
add int index_k and int index_w to the computables functions arguments and create your
generic Bond4 Potential. But most of the times, bond interactions between four particles
only deppend on the dihedral angle between them, see Bond4. So UAMMD-structured offer the option
of create AngularBond4 potentials.
The template is similar, but now computable() functions receive as arguments
\(sin(\phi)\) and \(cos(\phi)\) where \(\phi\) is the dihedral angle
and ComputationalData. The decision to use the angle projections instead
of the angle value itself is because obtaining the projections requires
one less operation, and in many cases, the potentials depend on the projections.
You always can obtain the dihedral angle using \(\phi = atan2(sin(\phi),cos(\phi))\)
Also, force() and hessian() are not defined. Instead you must define energyDerivate() and energySecondDerivate().
#include "System/ExtendedSystem.cuh"
#include "GlobalData/GlobalData.cuh"
#include "ParticleData/ExtendedParticleData.cuh"
#include "ParticleData/ParticleGroup.cuh"
#include "Interactor/Bonds/BondsInteractor.cuh"
#include "Interactor/Bonds/Bond3/Bond3.cuh"
#include "Interactor/InteractorFactory.cuh"
namespace uammd{
namespace structured{
namespace Potentials{
namespace Bond3{
struct MyAngularPotential_{
//Potential parameters
struct ComputationalData{
// Add necessary fields foor computational data
};
struct StorageData{
// Add fields to store potential-related data
};
struct BondParameters{
real3 parameter1; //Example, replace with actual parameters
};
//Computational data getter
static __host__ ComputationalData getComputationalData(std::shared_ptr<GlobalData> gd,
std::shared_ptr<ParticleGroup> pg,
const StorageData& storage,
const Computables& computables,
const cudaStream_t&est){
ComputationalData computational;
return computational;
}
//Storage data reader
static __host__ StorageData getStorageData(std::shared_ptr<GlobalData> gd,
std::shared_ptr<ParticleGroup> pg,
DataEntry& data){
StorageData storage;
return storage;
}
//Bond parameters reader
template<typename T>
static __host__ BondParameters processBondParameters(std::shared_ptr<GlobalData> gd,
std::map<std::string,T>& bondParametersMap){
BondParameters param;
param.parameter1 = bondParametersMap.at("parameter1");
return param;
}
//Energy and force definition
static inline __device__ real energy(const real& cos_dih, const real& sin_dih,
const ComputationalData &computational,
const BondParameters &bondParam){
const real energyValue = real(0.0);
return energyValue;
}
static inline __device__ real energyDerivate(const real& cos_dih, const real& sin_dih,
const ComputationalData &computational,
const BondParameters &bondParam){
const real energyDerivateValue = real(0.0);
return energyDerivateValue;
}
static inline __device__ real energySecondDerivate(const real& cos_dih, const real& sin_dih,
const ComputationalData &computational,
const BondParameters &bondParam){
const real energySecondDerivateValue = real(0.0);
return energySecondDerivateValue;
}
};
// Alias the struct with AngularBond3 !!!
using MyAngularPotential = AngularBond4_<MyAngularPotential_>;
}}}}
REGISTER_BOND_INTERACTOR(
Bond4,MyAngularPotential,
uammd::structured::Interactor::BondsInteractor<uammd::structured::Potentials::Bond4::MyAngularPotential>
)
To register your own Bond4 potential create the file
src/Interactor/Bonds/Bond4/myPotential.cu and add to
the Components.json.
{
"Interactor":
"Bonds":[
["..."],
["Bond4","myPotential","myPotential.cu"]
]
}