3 #include "potentials_base.h" 23 return a - b * a.dot(b);
54 const double half_length,
55 const Point& separation)
57 const auto c = segment_direction.dot(separation);
59 if (c > half_length) {
63 d = (c > -half_length) ? c : -half_length;
65 return -separation + (segment_direction * d);
73 const Point& w_vec,
double cutoff_squared,
double cospatch,
74 std::array<double, 5>& intersections);
80 std::array<double, 5>& intersections);
89 const Point& w_vec,
double rcut2,
double cospatch,
90 std::array<double, 5>& intersections);
97 std::array<double, 5>& intersections,
double cutoff_squared);
103 std::array<double, 5>& intersections,
double rcut2);
105 inline double fanglscale(
const double a,
const Cigar& cigar)
128 [[maybe_unused]]
double d,
129 const Point& center_to_center_distance)
const override 132 auto minimum_distance_squared =
134 particle1.
ext->scdir, particle1.
ext->half_length, particle2.
ext->scdir,
135 particle1.
ext->half_length, center_to_center_distance)
137 const auto contact_distance = 0.5 * (particle1.
traits().sigma + particle2.
traits().sigma);
138 if (minimum_distance_squared < contact_distance * contact_distance) {
145 void to_json(
json& j)
const override;
146 void from_json(
const json& j)
override;
160 PatchPotential patch_potential;
161 CylinderPotential cylinder_potential;
165 void to_json(
json& j)
const override;
166 void from_json(
const json& j)
override;
169 [[maybe_unused]]
double distance_squared,
170 const Point& center_separation)
const override 173 const auto c = cigar.
getExt().scdir.dot(center_separation);
175 if (c > cigar.
ext->half_length) {
176 contt = cigar.
ext->half_length;
179 if (c > -cigar.
ext->half_length) {
183 contt = -cigar.
ext->half_length;
186 const Point distvec = -center_separation + (cigar.
ext->scdir * contt);
189 return cylinder_potential(cigar, sphere, distvec.squaredNorm(), Point::Zero());
193 const auto cutoff_squared = patch_potential.cutOffSquared(cigar.
id, sphere.
id);
196 const auto s = vec1.dot(cigar.
ext->patchdir);
197 const auto f1 = SpheroCylinder::fanglscale(s, cigar.
getExt());
200 const auto ndist_squared = distvec.dot(distvec);
201 const auto t = sqrt(cutoff_squared - ndist_squared);
203 if (contt + t > cigar.
ext->half_length) {
204 f0 = cigar.
ext->half_length;
209 if (contt - t < -cigar.ext->half_length) {
210 f0 -= -cigar.
ext->half_length;
215 return f1 * (f0 + 1.0) * patch_potential(cigar, sphere, ndist_squared, Point::Zero()) +
216 cylinder_potential(cigar, sphere, ndist_squared, Point::Zero());
238 PatchPotential patch_potential;
239 CylinderPotential cylinder_potential;
241 [[nodiscard]]
double patchyPatchyEnergy(
const Particle& particle1,
const Particle& particle2,
242 const Point& center_separation)
const;
244 [[nodiscard]]
double isotropicIsotropicEnergy(
const Particle& particle1,
246 const Point& center_separation)
const;
250 void to_json(
json& j)
const override;
251 void from_json(
const json& j)
override;
253 inline double operator()(
const Particle& particle1,
const Particle& particle2,
254 [[maybe_unused]]
double center_separation_squared,
255 const Point& center_separation)
const override 260 return patchyPatchyEnergy(particle1, particle2, center_separation);
262 return isotropicIsotropicEnergy(particle1, particle2, center_separation);
283 SphereWithSphere sphere_sphere;
290 [[maybe_unused]]
double distance_squared,
293 const double small_number = 1e-6;
294 const auto a_is_sphere = !a.
hasExtension() || a.
ext->half_length < small_number;
295 const auto b_is_sphere = !a.
hasExtension() || b.
ext->half_length < small_number;
297 if (!a_is_sphere && !b_is_sphere) {
298 return cigar_cigar(a, b, distance_squared, distance);
300 if (a_is_sphere && b_is_sphere) {
301 return sphere_sphere(a, b, distance_squared, distance);
304 return cigar_sphere(a, b, distance_squared, distance);
306 return cigar_sphere(b, a, distance_squared, distance);
309 void to_json([[maybe_unused]]
json& j)
const override;
310 void from_json(
const json& j)
override;
Point mindist_segment2point(const Point &segment_direction, const double half_length, const Point &separation)
Definition: spherocylinder.h:53
Point mindist_segment2segment(const Point &dir1, const double half_length1, const Point &dir2, const double half_length2, const Point &r_cm)
Calculate minimum distance between two line segments.
Definition: spherocylinder.cpp:15
nlohmann::json json
JSON object.
Definition: json_support.h:10
double pcangl
Cosine of AtomData::patch_angle (speed optimization)
Definition: particle.h:132
Eigen::Vector3d Point
3D vector used for positions, velocities, forces etc.
Definition: coordinates.h:7
int cpsc_intersect(const Cigar &cigar1, const Cigar &cigar2, const Point &r_cm, std::array< double, 5 > &intersections, const double cutoff_squared)
Intersection of PSC2 with cylindrical patch of PSC1 and return them (CPSC)
Definition: spherocylinder.cpp:429
int find_intersect_plane(const Cigar &part1, const Cigar &part2, const Point &r_cm, const Point &w_vec, const double cutoff_squared, const double cospatch, std::array< double, 5 > &intersections)
Finds intersections of spherocylinder and plane defined by vector "w_vec" and if they are in all-way ...
Definition: spherocylinder.cpp:102
Hard-sphere pair potential for spherocylinders.
Definition: spherocylinder.h:124
int find_intersect_planec(const Cigar &part1, const Cigar &part2, const Point &r_cm, const Point &w_vec, double rcut2, double cospatch, std::array< double, 5 > &intersections)
Intersect of plane.
Definition: spherocylinder.cpp:182
Template for interactions between patchy sphero-cylinders (PSCs) interactions.
Definition: spherocylinder.h:235
ParticleExtension & getExt()
get/create extension
Definition: particle.h:240
double operator()(const Particle &particle1, const Particle &particle2, [[maybe_unused]] double d, const Point ¢er_to_center_distance) const override
Pair energy in units of kT.
Definition: spherocylinder.h:127
Point vec_perpproject(const Point &a, const Point &b)
Calculate perpendicular projection of the first vector versus the second vector.
Definition: spherocylinder.h:21
double pcanglsw
Cosine of switch angle from AtomData (speed optimization)
Definition: particle.h:131
Set pair potential between cigar-cigar, sphere-sphere, cigar-sphere.
Definition: spherocylinder.h:280
Patchy sphero cylinder a.k.a.Sphero-cylinder properties.
Definition: particle.h:122
The algorithms found here are mainly direct conversions from Robert Vacha's spherocylinder C code (~2...
Definition: spherocylinder.cpp:5
std::unique_ptr< ParticleExtension > ext
Point to extended properties.
Definition: particle.h:224
int id
Particle id/type.
Definition: particle.h:225
Particle class for storing positions, id, and other properties.
Definition: particle.h:220
const AtomData & traits() const
get properties from AtomData
Definition: particle.cpp:183
bool hasExtension() const
check if particle has extensions (dipole etc.)
Definition: particle.cpp:249
int test_intrpatch(const Cigar &part1, Point &vec, double cospatch, double ti, std::array< double, 5 > &intersections)
Finds if vector "vec" has angular intersection w.
Definition: spherocylinder.cpp:147
concept RequirePairPotential
Concept matching a particle pair potential derived from Potential::PairPotentialBase ...
Definition: potentials_base.h:180
auto distance(T1 first, T2 last)
Distance between two arbitrary contiguous iterators.
Definition: iteratorsupport.h:7
Namespace for particle pair-potentials.
Definition: analysis.h:18
Base for all pair-potentials.
Definition: potentials_base.h:131
Pair potential between a patchy sphero-cylinder (first particle) and a sphere (second particle) ...
Definition: spherocylinder.h:157
int psc_intersect(const Cigar &particle1, const Cigar &particle2, const Point &r_cm, std::array< double, 5 > &intersections, const double cutoff_squared)
Intersections of spherocylinder2 with a all-way patch of spherocylinder1 and return them (PSC) ...
Definition: spherocylinder.cpp:231