git-svn-id: svn://svn.icms.temple.edu/lammps-ro/trunk@14440 f3b2605a-c512-4ea7-a41b-209d697bcdaa
This commit is contained in:
286
src/fix_move.cpp
286
src/fix_move.cpp
@ -26,7 +26,12 @@
|
||||
#include "respa.h"
|
||||
#include "input.h"
|
||||
#include "variable.h"
|
||||
#include "atom_vec_ellipsoid.h"
|
||||
#include "atom_vec_line.h"
|
||||
#include "atom_vec_tri.h"
|
||||
#include "atom_vec_body.h"
|
||||
#include "math_const.h"
|
||||
#include "math_extra.h"
|
||||
#include "memory.h"
|
||||
#include "error.h"
|
||||
|
||||
@ -37,6 +42,8 @@ using namespace MathConst;
|
||||
enum{LINEAR,WIGGLE,ROTATE,VARIABLE};
|
||||
enum{EQUAL,ATOM};
|
||||
|
||||
#define INERTIA 0.2 // moment of inertia prefactor for ellipsoid
|
||||
|
||||
/* ---------------------------------------------------------------------- */
|
||||
|
||||
FixMove::FixMove(LAMMPS *lmp, int narg, char **arg) :
|
||||
@ -216,7 +223,7 @@ FixMove::FixMove(LAMMPS *lmp, int narg, char **arg) :
|
||||
|
||||
// set omega_rotate from period
|
||||
|
||||
if (mstyle == WIGGLE || mstyle == ROTATE) omega_rotate = 2.0*MY_PI / period;
|
||||
if (mstyle == WIGGLE || mstyle == ROTATE) omega_rotate = MY_2PI / period;
|
||||
|
||||
// runit = unit vector along rotation axis
|
||||
|
||||
@ -229,24 +236,54 @@ FixMove::FixMove(LAMMPS *lmp, int narg, char **arg) :
|
||||
runit[2] = axis[2]/len;
|
||||
}
|
||||
|
||||
// set omega_flag if particles store omega
|
||||
|
||||
// set flags for extra attributes particles may store
|
||||
// relevant extra attributes = omega, angmom, theta, quat
|
||||
|
||||
omega_flag = atom->omega_flag;
|
||||
angmom_flag = atom->angmom_flag;
|
||||
|
||||
radius_flag = atom->radius_flag;
|
||||
ellipsoid_flag = atom->ellipsoid_flag;
|
||||
line_flag = atom->line_flag;
|
||||
tri_flag = atom->tri_flag;
|
||||
body_flag = atom->body_flag;
|
||||
|
||||
theta_flag = quat_flag = 0;
|
||||
if (line_flag) theta_flag = 1;
|
||||
if (ellipsoid_flag || tri_flag || body_flag) quat_flag = 1;
|
||||
|
||||
extra_flag = 0;
|
||||
if (omega_flag || angmom_flag || theta_flag || quat_flag) extra_flag = 1;
|
||||
|
||||
// perform initial allocation of atom-based array
|
||||
// register with Atom class
|
||||
|
||||
xoriginal = NULL;
|
||||
toriginal = NULL;
|
||||
qoriginal = NULL;
|
||||
grow_arrays(atom->nmax);
|
||||
atom->add_callback(0);
|
||||
atom->add_callback(1);
|
||||
|
||||
displace = velocity = NULL;
|
||||
|
||||
// AtomVec pointers to retrieve per-atom storage of extra quantities
|
||||
|
||||
avec_ellipsoid = (AtomVecEllipsoid *) atom->style_match("ellipsoid");
|
||||
avec_line = (AtomVecLine *) atom->style_match("line");
|
||||
avec_tri = (AtomVecTri *) atom->style_match("tri");
|
||||
avec_body = (AtomVecBody *) atom->style_match("body");
|
||||
|
||||
// xoriginal = initial unwrapped positions of atoms
|
||||
// toriginal = initial theta of lines
|
||||
// qoriginal = initial quat of extended particles
|
||||
|
||||
double **x = atom->x;
|
||||
imageint *image = atom->image;
|
||||
int *ellipsoid = atom->ellipsoid;
|
||||
int *line = atom->line;
|
||||
int *tri = atom->tri;
|
||||
int *body = atom->body;
|
||||
int *mask = atom->mask;
|
||||
int nlocal = atom->nlocal;
|
||||
|
||||
@ -255,6 +292,45 @@ FixMove::FixMove(LAMMPS *lmp, int narg, char **arg) :
|
||||
else xoriginal[i][0] = xoriginal[i][1] = xoriginal[i][2] = 0.0;
|
||||
}
|
||||
|
||||
if (theta_flag) {
|
||||
for (int i = 0; i < nlocal; i++) {
|
||||
if ((mask[i] & groupbit) && line[i] >= 0)
|
||||
toriginal[i] = avec_line->bonus[line[i]].theta;
|
||||
else toriginal[i] = 0.0;
|
||||
}
|
||||
}
|
||||
|
||||
if (quat_flag) {
|
||||
double *quat;
|
||||
for (int i = 0; i < nlocal; i++) {
|
||||
quat = NULL;
|
||||
if (mask[i] & groupbit) {
|
||||
if (ellipsoid_flag && ellipsoid[i] >= 0)
|
||||
quat = avec_ellipsoid->bonus[ellipsoid[i]].quat;
|
||||
else if (tri_flag && tri[i] >= 0)
|
||||
quat = avec_tri->bonus[tri[i]].quat;
|
||||
else if (body_flag && body[i] >= 0)
|
||||
quat = avec_body->bonus[body[i]].quat;
|
||||
}
|
||||
if (quat) {
|
||||
qoriginal[i][0] = quat[0];
|
||||
qoriginal[i][1] = quat[1];
|
||||
qoriginal[i][2] = quat[2];
|
||||
qoriginal[i][3] = quat[3];
|
||||
} else qoriginal[i][0] = qoriginal[i][1] =
|
||||
qoriginal[i][2] = qoriginal[i][3] = 0.0;
|
||||
}
|
||||
}
|
||||
|
||||
// nrestart = size of per-atom restart data
|
||||
// nrestart = 1 + xorig + torig + qorig
|
||||
|
||||
nrestart = 4;
|
||||
if (theta_flag) nrestart++;
|
||||
if (quat_flag) nrestart += 4;
|
||||
|
||||
// time origin for movement = current timestep
|
||||
|
||||
time_origin = update->ntimestep;
|
||||
}
|
||||
|
||||
@ -270,6 +346,8 @@ FixMove::~FixMove()
|
||||
// delete locally stored arrays
|
||||
|
||||
memory->destroy(xoriginal);
|
||||
memory->destroy(toriginal);
|
||||
memory->destroy(qoriginal);
|
||||
memory->destroy(displace);
|
||||
memory->destroy(velocity);
|
||||
|
||||
@ -381,9 +459,12 @@ void FixMove::init()
|
||||
|
||||
void FixMove::initial_integrate(int vflag)
|
||||
{
|
||||
double dtfm;
|
||||
double xold[3],a[3],b[3],c[3],d[3],disp[3];
|
||||
int flag;
|
||||
double ddotr,dx,dy,dz;
|
||||
double dtfm,theta_new;
|
||||
double xold[3],a[3],b[3],c[3],d[3],disp[3],w[3],ex[3],ey[3],ez[3];
|
||||
double inertia_ellipsoid[3],qrotate[4];
|
||||
double *quat,*inertia,*shape;
|
||||
|
||||
double delta = (update->ntimestep - time_origin) * dt;
|
||||
|
||||
@ -391,10 +472,17 @@ void FixMove::initial_integrate(int vflag)
|
||||
double **v = atom->v;
|
||||
double **f = atom->f;
|
||||
double **omega = atom->omega;
|
||||
double **angmom = atom->angmom;
|
||||
double *radius = atom->radius;
|
||||
double *rmass = atom->rmass;
|
||||
double *mass = atom->mass;
|
||||
int *type = atom->type;
|
||||
int *ellipsoid = atom->ellipsoid;
|
||||
int *line = atom->line;
|
||||
int *tri = atom->tri;
|
||||
int *body = atom->body;
|
||||
int *mask = atom->mask;
|
||||
|
||||
int nlocal = atom->nlocal;
|
||||
|
||||
// for linear: X = X0 + V*dt
|
||||
@ -553,17 +641,89 @@ void FixMove::initial_integrate(int vflag)
|
||||
v[i][0] = omega_rotate * (runit[1]*disp[2] - runit[2]*disp[1]);
|
||||
v[i][1] = omega_rotate * (runit[2]*disp[0] - runit[0]*disp[2]);
|
||||
v[i][2] = omega_rotate * (runit[0]*disp[1] - runit[1]*disp[0]);
|
||||
if (omega_flag) {
|
||||
omega[i][0] = omega_rotate*runit[0];
|
||||
omega[i][1] = omega_rotate*runit[1];
|
||||
omega[i][2] = omega_rotate*runit[2];
|
||||
}
|
||||
|
||||
// set any extra attributes affected by rotation
|
||||
|
||||
if (extra_flag) {
|
||||
|
||||
// omega for spheres and lines
|
||||
|
||||
if (omega_flag) {
|
||||
flag = 0;
|
||||
if (radius_flag && radius[i] > 0.0) flag = 1;
|
||||
if (line_flag && line[i] >= 0.0) flag = 1;
|
||||
if (flag) {
|
||||
omega[i][0] = omega_rotate*runit[0];
|
||||
omega[i][1] = omega_rotate*runit[1];
|
||||
omega[i][2] = omega_rotate*runit[2];
|
||||
}
|
||||
}
|
||||
|
||||
// angmom for ellipsoids, tris, and bodies
|
||||
|
||||
if (angmom_flag) {
|
||||
quat = inertia = NULL;
|
||||
if (ellipsoid_flag && ellipsoid[i] >= 0) {
|
||||
quat = avec_ellipsoid->bonus[ellipsoid[i]].quat;
|
||||
shape = avec_ellipsoid->bonus[ellipsoid[i]].shape;
|
||||
inertia_ellipsoid[0] =
|
||||
INERTIA*rmass[i] * (shape[1]*shape[1]+shape[2]*shape[2]);
|
||||
inertia_ellipsoid[1] =
|
||||
INERTIA*rmass[i] * (shape[0]*shape[0]+shape[2]*shape[2]);
|
||||
inertia_ellipsoid[2] =
|
||||
INERTIA*rmass[i] * (shape[0]*shape[0]+shape[1]*shape[1]);
|
||||
inertia = inertia_ellipsoid;
|
||||
} else if (tri_flag && tri[i] >= 0) {
|
||||
quat = avec_tri->bonus[tri[i]].quat;
|
||||
inertia = avec_tri->bonus[tri[i]].inertia;
|
||||
} else if (body_flag && body[i] >= 0) {
|
||||
quat = avec_body->bonus[body[i]].quat;
|
||||
inertia = avec_body->bonus[body[i]].inertia;
|
||||
}
|
||||
if (quat) {
|
||||
w[0] = omega_rotate*runit[0];
|
||||
w[1] = omega_rotate*runit[1];
|
||||
w[2] = omega_rotate*runit[2];
|
||||
MathExtra::q_to_exyz(quat,ex,ey,ez);
|
||||
MathExtra::omega_to_angmom(w,ex,ey,ez,inertia,angmom[i]);
|
||||
}
|
||||
}
|
||||
|
||||
// theta for lines
|
||||
|
||||
if (theta_flag && line[i] >= 0.0) {
|
||||
theta_new = fmod(toriginal[i]+arg,MY_2PI);
|
||||
avec_line->bonus[atom->line[i]].theta = theta_new;
|
||||
}
|
||||
|
||||
// quats for ellipsoids, tris, and bodies
|
||||
|
||||
if (quat_flag) {
|
||||
quat = NULL;
|
||||
if (ellipsoid_flag && ellipsoid[i] >= 0)
|
||||
quat = avec_ellipsoid->bonus[ellipsoid[i]].quat;
|
||||
else if (tri_flag && tri[i] >= 0)
|
||||
quat = avec_tri->bonus[tri[i]].quat;
|
||||
else if (body_flag && body[i] >= 0)
|
||||
quat = avec_body->bonus[body[i]].quat;
|
||||
if (quat) {
|
||||
qrotate[0] = cosine;
|
||||
qrotate[1] = runit[0]*sine;
|
||||
qrotate[2] = runit[1]*sine;
|
||||
qrotate[3] = runit[2]*sine;
|
||||
MathExtra::quatquat(qrotate,qoriginal[i],quat);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
domain->remap_near(x[i],xold);
|
||||
}
|
||||
}
|
||||
|
||||
// for variable: compute x,v from variables
|
||||
// NOTE: also allow for changes to extra attributes?
|
||||
// omega, angmom, theta, quat
|
||||
// only necessary if prescribed motion involves rotation
|
||||
|
||||
} else if (mstyle == VARIABLE) {
|
||||
|
||||
@ -809,6 +969,8 @@ void FixMove::final_integrate_respa(int ilevel, int iloop)
|
||||
double FixMove::memory_usage()
|
||||
{
|
||||
double bytes = atom->nmax*3 * sizeof(double);
|
||||
if (theta_flag) bytes += atom->nmax * sizeof(double);
|
||||
if (quat_flag) bytes += atom->nmax*4 * sizeof(double);
|
||||
if (displaceflag) bytes += atom->nmax*3 * sizeof(double);
|
||||
if (velocityflag) bytes += atom->nmax*3 * sizeof(double);
|
||||
return bytes;
|
||||
@ -850,6 +1012,8 @@ void FixMove::restart(char *buf)
|
||||
void FixMove::grow_arrays(int nmax)
|
||||
{
|
||||
memory->grow(xoriginal,nmax,3,"move:xoriginal");
|
||||
if (theta_flag) memory->grow(toriginal,nmax,"move:toriginal");
|
||||
if (quat_flag) memory->grow(qoriginal,nmax,4,"move:qoriginal");
|
||||
array_atom = xoriginal;
|
||||
}
|
||||
|
||||
@ -862,6 +1026,13 @@ void FixMove::copy_arrays(int i, int j, int delflag)
|
||||
xoriginal[j][0] = xoriginal[i][0];
|
||||
xoriginal[j][1] = xoriginal[i][1];
|
||||
xoriginal[j][2] = xoriginal[i][2];
|
||||
if (theta_flag) toriginal[j] = toriginal[i];
|
||||
if (quat_flag) {
|
||||
qoriginal[j][0] = qoriginal[i][0];
|
||||
qoriginal[j][1] = qoriginal[i][1];
|
||||
qoriginal[j][2] = qoriginal[i][2];
|
||||
qoriginal[j][3] = qoriginal[i][3];
|
||||
}
|
||||
}
|
||||
|
||||
/* ----------------------------------------------------------------------
|
||||
@ -870,8 +1041,15 @@ void FixMove::copy_arrays(int i, int j, int delflag)
|
||||
|
||||
void FixMove::set_arrays(int i)
|
||||
{
|
||||
double theta;
|
||||
double *quat;
|
||||
|
||||
double **x = atom->x;
|
||||
imageint *image = atom->image;
|
||||
int *ellipsoid = atom->ellipsoid;
|
||||
int *line = atom->line;
|
||||
int *tri = atom->tri;
|
||||
int *body = atom->body;
|
||||
int *mask = atom->mask;
|
||||
|
||||
// particle not in group
|
||||
@ -932,6 +1110,33 @@ void FixMove::set_arrays(int i)
|
||||
xoriginal[i][0] = point[0] + c[0] + disp[0];
|
||||
xoriginal[i][1] = point[1] + c[1] + disp[1];
|
||||
xoriginal[i][2] = point[2] + c[2] + disp[2];
|
||||
|
||||
// set theta and quat extra attributes affected by rotation
|
||||
|
||||
if (extra_flag) {
|
||||
|
||||
// theta for lines
|
||||
|
||||
if (theta_flag && line[i] >= 0.0) {
|
||||
theta = avec_line->bonus[atom->line[i]].theta;
|
||||
toriginal[i] = theta - 0.0; // NOTE: edit this line
|
||||
}
|
||||
|
||||
// quats for ellipsoids, tris, and bodies
|
||||
|
||||
if (quat_flag) {
|
||||
quat = NULL;
|
||||
if (ellipsoid_flag && ellipsoid[i] >= 0)
|
||||
quat = avec_ellipsoid->bonus[ellipsoid[i]].quat;
|
||||
else if (tri_flag && tri[i] >= 0)
|
||||
quat = avec_tri->bonus[tri[i]].quat;
|
||||
else if (body_flag && body[i] >= 0)
|
||||
quat = avec_body->bonus[body[i]].quat;
|
||||
if (quat) {
|
||||
// qoriginal = f(quat,-delta); // NOTE: edit this line
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@ -941,10 +1146,18 @@ void FixMove::set_arrays(int i)
|
||||
|
||||
int FixMove::pack_exchange(int i, double *buf)
|
||||
{
|
||||
buf[0] = xoriginal[i][0];
|
||||
buf[1] = xoriginal[i][1];
|
||||
buf[2] = xoriginal[i][2];
|
||||
return 3;
|
||||
int n = 0;
|
||||
buf[n++] = xoriginal[i][0];
|
||||
buf[n++] = xoriginal[i][1];
|
||||
buf[n++] = xoriginal[i][2];
|
||||
if (theta_flag) buf[n++] = toriginal[i];
|
||||
if (quat_flag) {
|
||||
buf[n++] = qoriginal[i][0];
|
||||
buf[n++] = qoriginal[i][1];
|
||||
buf[n++] = qoriginal[i][2];
|
||||
buf[n++] = qoriginal[i][3];
|
||||
}
|
||||
return n;
|
||||
}
|
||||
|
||||
/* ----------------------------------------------------------------------
|
||||
@ -953,10 +1166,18 @@ int FixMove::pack_exchange(int i, double *buf)
|
||||
|
||||
int FixMove::unpack_exchange(int nlocal, double *buf)
|
||||
{
|
||||
xoriginal[nlocal][0] = buf[0];
|
||||
xoriginal[nlocal][1] = buf[1];
|
||||
xoriginal[nlocal][2] = buf[2];
|
||||
return 3;
|
||||
int n = 0;
|
||||
xoriginal[nlocal][0] = buf[n++];
|
||||
xoriginal[nlocal][1] = buf[n++];
|
||||
xoriginal[nlocal][2] = buf[n++];
|
||||
if (theta_flag) toriginal[nlocal] = buf[n++];
|
||||
if (quat_flag) {
|
||||
qoriginal[nlocal][0] = buf[n++];
|
||||
qoriginal[nlocal][1] = buf[n++];
|
||||
qoriginal[nlocal][2] = buf[n++];
|
||||
qoriginal[nlocal][3] = buf[n++];
|
||||
}
|
||||
return n;
|
||||
}
|
||||
|
||||
/* ----------------------------------------------------------------------
|
||||
@ -965,11 +1186,19 @@ int FixMove::unpack_exchange(int nlocal, double *buf)
|
||||
|
||||
int FixMove::pack_restart(int i, double *buf)
|
||||
{
|
||||
buf[0] = 4;
|
||||
buf[1] = xoriginal[i][0];
|
||||
buf[2] = xoriginal[i][1];
|
||||
buf[3] = xoriginal[i][2];
|
||||
return 4;
|
||||
int n = 1;
|
||||
buf[n++] = xoriginal[i][0];
|
||||
buf[n++] = xoriginal[i][1];
|
||||
buf[n++] = xoriginal[i][2];
|
||||
if (theta_flag) buf[n++] = toriginal[i];
|
||||
if (quat_flag) {
|
||||
buf[n++] = qoriginal[i][0];
|
||||
buf[n++] = qoriginal[i][1];
|
||||
buf[n++] = qoriginal[i][2];
|
||||
buf[n++] = qoriginal[i][3];
|
||||
}
|
||||
buf[0] = n;
|
||||
return n;
|
||||
}
|
||||
|
||||
/* ----------------------------------------------------------------------
|
||||
@ -989,6 +1218,13 @@ void FixMove::unpack_restart(int nlocal, int nth)
|
||||
xoriginal[nlocal][0] = extra[nlocal][m++];
|
||||
xoriginal[nlocal][1] = extra[nlocal][m++];
|
||||
xoriginal[nlocal][2] = extra[nlocal][m++];
|
||||
if (theta_flag) toriginal[nlocal] = extra[nlocal][m++];
|
||||
if (quat_flag) {
|
||||
qoriginal[nlocal][0] = extra[nlocal][m++];
|
||||
qoriginal[nlocal][1] = extra[nlocal][m++];
|
||||
qoriginal[nlocal][2] = extra[nlocal][m++];
|
||||
qoriginal[nlocal][3] = extra[nlocal][m++];
|
||||
}
|
||||
}
|
||||
|
||||
/* ----------------------------------------------------------------------
|
||||
@ -997,7 +1233,7 @@ void FixMove::unpack_restart(int nlocal, int nth)
|
||||
|
||||
int FixMove::maxsize_restart()
|
||||
{
|
||||
return 4;
|
||||
return nrestart;
|
||||
}
|
||||
|
||||
/* ----------------------------------------------------------------------
|
||||
@ -1006,7 +1242,7 @@ int FixMove::maxsize_restart()
|
||||
|
||||
int FixMove::size_restart(int nlocal)
|
||||
{
|
||||
return 4;
|
||||
return nrestart;
|
||||
}
|
||||
|
||||
/* ---------------------------------------------------------------------- */
|
||||
|
||||
Reference in New Issue
Block a user