git-svn-id: svn://svn.icms.temple.edu/lammps-ro/trunk@12612 f3b2605a-c512-4ea7-a41b-209d697bcdaa
This commit is contained in:
@ -1,3 +1,5 @@
|
||||
/// -*- c++ -*-
|
||||
|
||||
#include "colvarmodule.h"
|
||||
#include "colvarparse.h"
|
||||
#include "colvaratoms.h"
|
||||
@ -44,8 +46,8 @@ cvm::atom_group::atom_group (std::vector<cvm::atom> const &atoms)
|
||||
|
||||
cvm::atom_group::atom_group()
|
||||
: b_dummy (false), b_center (false), b_rotate (false),
|
||||
b_fit_gradients (false), ref_pos_group (NULL),
|
||||
noforce (false)
|
||||
b_user_defined_fit (false), b_fit_gradients (false),
|
||||
ref_pos_group (NULL), noforce (false)
|
||||
{
|
||||
total_mass = 0.0;
|
||||
}
|
||||
@ -63,7 +65,7 @@ cvm::atom_group::~atom_group()
|
||||
void cvm::atom_group::add_atom (cvm::atom const &a)
|
||||
{
|
||||
if (b_dummy) {
|
||||
cvm::fatal_error ("Error: cannot add atoms to a dummy group.\n");
|
||||
cvm::error ("Error: cannot add atoms to a dummy group.\n", INPUT_ERROR);
|
||||
} else {
|
||||
this->push_back (a);
|
||||
total_mass += a.mass;
|
||||
@ -83,7 +85,7 @@ void cvm::atom_group::reset_mass(std::string &name, int i, int j)
|
||||
" atoms: total mass = "+cvm::to_str (this->total_mass)+".\n");
|
||||
}
|
||||
|
||||
void cvm::atom_group::parse (std::string const &conf,
|
||||
int cvm::atom_group::parse (std::string const &conf,
|
||||
char const *key)
|
||||
{
|
||||
std::string group_conf;
|
||||
@ -98,9 +100,10 @@ void cvm::atom_group::parse (std::string const &conf,
|
||||
save_delimiters = true;
|
||||
|
||||
if (group_conf.size() == 0) {
|
||||
cvm::fatal_error ("Error: atom group \""+
|
||||
std::string (key)+"\" is set, but "
|
||||
"has no definition.\n");
|
||||
cvm::error ("Error: atom group \""+std::string (key)+
|
||||
"\" is set, but has no definition.\n",
|
||||
INPUT_ERROR);
|
||||
return COLVARS_ERROR;
|
||||
}
|
||||
|
||||
cvm::increase_depth();
|
||||
@ -135,9 +138,11 @@ void cvm::atom_group::parse (std::string const &conf,
|
||||
for (size_t i = 0; i < atom_indexes.size(); i++) {
|
||||
this->push_back (cvm::atom (atom_indexes[i]));
|
||||
}
|
||||
} else
|
||||
cvm::fatal_error ("Error: no numbers provided for \""
|
||||
"atomNumbers\".\n");
|
||||
} else {
|
||||
cvm::error ("Error: no numbers provided for \""
|
||||
"atomNumbers\".\n", INPUT_ERROR);
|
||||
return COLVARS_ERROR;
|
||||
}
|
||||
|
||||
atom_indexes.clear();
|
||||
}
|
||||
@ -147,13 +152,15 @@ void cvm::atom_group::parse (std::string const &conf,
|
||||
// use an index group from the index file read globally
|
||||
std::list<std::string>::iterator names_i = cvm::index_group_names.begin();
|
||||
std::list<std::vector<int> >::iterator index_groups_i = cvm::index_groups.begin();
|
||||
for ( ; names_i != cvm::index_group_names.end() ; names_i++, index_groups_i++) {
|
||||
for ( ; names_i != cvm::index_group_names.end() ; ++names_i, ++index_groups_i) {
|
||||
if (*names_i == index_group_name)
|
||||
break;
|
||||
}
|
||||
if (names_i == cvm::index_group_names.end()) {
|
||||
cvm::fatal_error ("Error: could not find index group "+
|
||||
index_group_name+" among those provided by the index file.\n");
|
||||
cvm::error ("Error: could not find index group "+
|
||||
index_group_name+" among those provided by the index file.\n",
|
||||
INPUT_ERROR);
|
||||
return COLVARS_ERROR;
|
||||
}
|
||||
this->reserve (index_groups_i->size());
|
||||
for (size_t i = 0; i < index_groups_i->size(); i++) {
|
||||
@ -183,20 +190,19 @@ void cvm::atom_group::parse (std::string const &conf,
|
||||
}
|
||||
}
|
||||
|
||||
cvm::fatal_error ("Error: no valid definition for \""
|
||||
"atomNumbersRange\", \""+
|
||||
range_conf+"\".\n");
|
||||
cvm::error ("Error: no valid definition for \"atomNumbersRange\", \""+
|
||||
range_conf+"\".\n", INPUT_ERROR);
|
||||
}
|
||||
}
|
||||
|
||||
std::vector<std::string> psf_segids;
|
||||
get_keyval (group_conf, "psfSegID", psf_segids, std::vector<std::string> (), mode);
|
||||
for (std::vector<std::string>::iterator psii = psf_segids.begin();
|
||||
psii < psf_segids.end(); psii++) {
|
||||
psii < psf_segids.end(); ++psii) {
|
||||
|
||||
if ( (psii->size() == 0) || (psii->size() > 4) ) {
|
||||
cvm::fatal_error ("Error: invalid segmend identifier provided, \""+
|
||||
(*psii)+"\".\n");
|
||||
cvm::error ("Error: invalid segmend identifier provided, \""+
|
||||
(*psii)+"\".\n", INPUT_ERROR);
|
||||
}
|
||||
}
|
||||
|
||||
@ -210,8 +216,8 @@ void cvm::atom_group::parse (std::string const &conf,
|
||||
range_count++;
|
||||
|
||||
if (range_count > psf_segids.size()) {
|
||||
cvm::fatal_error ("Error: more instances of \"atomNameResidueRange\" than "
|
||||
"values of \"psfSegID\".\n");
|
||||
cvm::error ("Error: more instances of \"atomNameResidueRange\" than "
|
||||
"values of \"psfSegID\".\n", INPUT_ERROR);
|
||||
}
|
||||
|
||||
std::string const &psf_segid = psf_segids.size() ? *psii : std::string ("");
|
||||
@ -231,17 +237,17 @@ void cvm::atom_group::parse (std::string const &conf,
|
||||
}
|
||||
range_conf = "";
|
||||
} else {
|
||||
cvm::fatal_error ("Error: cannot parse definition for \""
|
||||
"atomNameResidueRange\", \""+
|
||||
range_conf+"\".\n");
|
||||
cvm::error ("Error: cannot parse definition for \""
|
||||
"atomNameResidueRange\", \""+
|
||||
range_conf+"\".\n");
|
||||
}
|
||||
|
||||
} else {
|
||||
cvm::fatal_error ("Error: atomNameResidueRange with empty definition.\n");
|
||||
cvm::error ("Error: atomNameResidueRange with empty definition.\n");
|
||||
}
|
||||
|
||||
if (psf_segid.size())
|
||||
psii++;
|
||||
++psii;
|
||||
}
|
||||
}
|
||||
|
||||
@ -252,24 +258,25 @@ void cvm::atom_group::parse (std::string const &conf,
|
||||
|
||||
std::string atoms_col;
|
||||
if (!get_keyval (group_conf, "atomsCol", atoms_col, std::string (""), mode)) {
|
||||
cvm::fatal_error ("Error: parameter atomsCol is required if atomsFile is set.\n");
|
||||
cvm::error ("Error: parameter atomsCol is required if atomsFile is set.\n",
|
||||
INPUT_ERROR);
|
||||
}
|
||||
|
||||
double atoms_col_value;
|
||||
bool const atoms_col_value_defined = get_keyval (group_conf, "atomsColValue", atoms_col_value, 0.0, mode);
|
||||
if (atoms_col_value_defined && (!atoms_col_value))
|
||||
cvm::fatal_error ("Error: atomsColValue, "
|
||||
"if provided, must be non-zero.\n");
|
||||
if (atoms_col_value_defined && (!atoms_col_value)) {
|
||||
cvm::error ("Error: atomsColValue, if provided, must be non-zero.\n", INPUT_ERROR);
|
||||
}
|
||||
|
||||
cvm::load_atoms (atoms_file_name.c_str(), *this, atoms_col, atoms_col_value);
|
||||
}
|
||||
}
|
||||
|
||||
for (std::vector<cvm::atom>::iterator a1 = this->begin();
|
||||
a1 != this->end(); a1++) {
|
||||
a1 != this->end(); ++a1) {
|
||||
std::vector<cvm::atom>::iterator a2 = a1;
|
||||
++a2;
|
||||
for ( ; a2 != this->end(); a2++) {
|
||||
for ( ; a2 != this->end(); ++a2) {
|
||||
if (a1->id == a2->id) {
|
||||
if (cvm::debug())
|
||||
cvm::log ("Discarding doubly counted atom with number "+
|
||||
@ -287,14 +294,15 @@ void cvm::atom_group::parse (std::string const &conf,
|
||||
} else
|
||||
b_dummy = false;
|
||||
|
||||
if (b_dummy && (this->size()))
|
||||
cvm::fatal_error ("Error: cannot set up group \""+
|
||||
std::string (key)+"\" as a dummy atom "
|
||||
"and provide it with atom definitions.\n");
|
||||
if (b_dummy && (this->size())) {
|
||||
cvm::error ("Error: cannot set up group \""+
|
||||
std::string (key)+"\" as a dummy atom "
|
||||
"and provide it with atom definitions.\n", INPUT_ERROR);
|
||||
}
|
||||
|
||||
#if (! defined (COLVARS_STANDALONE))
|
||||
if ( (!b_dummy) && (!cvm::b_analysis) && (!(this->size())) ) {
|
||||
cvm::fatal_error ("Error: no atoms defined for atom group \""+
|
||||
cvm::error ("Error: no atoms defined for atom group \""+
|
||||
std::string (key)+"\".\n");
|
||||
}
|
||||
#endif
|
||||
@ -329,17 +337,17 @@ void cvm::atom_group::parse (std::string const &conf,
|
||||
if (b_center || b_rotate) {
|
||||
|
||||
if (b_dummy)
|
||||
cvm::fatal_error ("Error: centerReference or rotateReference "
|
||||
"cannot be defined for a dummy atom.\n");
|
||||
cvm::error ("Error: centerReference or rotateReference "
|
||||
"cannot be defined for a dummy atom.\n");
|
||||
|
||||
if (key_lookup (group_conf, "refPositionsGroup")) {
|
||||
// instead of this group, define another group to compute the fit
|
||||
if (ref_pos_group) {
|
||||
cvm::fatal_error ("Error: the atom group \""+
|
||||
std::string (key)+"\" has already a reference group "
|
||||
"for the rototranslational fit, which was communicated by the "
|
||||
"colvar component. You should not use refPositionsGroup "
|
||||
"in this case.\n");
|
||||
cvm::error ("Error: the atom group \""+
|
||||
std::string (key)+"\" has already a reference group "
|
||||
"for the rototranslational fit, which was communicated by the "
|
||||
"colvar component. You should not use refPositionsGroup "
|
||||
"in this case.\n");
|
||||
}
|
||||
cvm::log ("Within atom group \""+std::string (key)+"\":\n");
|
||||
ref_pos_group = new atom_group (group_conf, "refPositionsGroup");
|
||||
@ -357,8 +365,8 @@ void cvm::atom_group::parse (std::string const &conf,
|
||||
if (get_keyval (group_conf, "refPositionsFile", ref_pos_file, std::string (""), mode)) {
|
||||
|
||||
if (ref_pos.size()) {
|
||||
cvm::fatal_error ("Error: cannot specify \"refPositionsFile\" and "
|
||||
"\"refPositions\" at the same time.\n");
|
||||
cvm::error ("Error: cannot specify \"refPositionsFile\" and "
|
||||
"\"refPositions\" at the same time.\n");
|
||||
}
|
||||
|
||||
std::string ref_pos_col;
|
||||
@ -368,8 +376,8 @@ void cvm::atom_group::parse (std::string const &conf,
|
||||
// if provided, use PDB column to select coordinates
|
||||
bool found = get_keyval (group_conf, "refPositionsColValue", ref_pos_col_value, 0.0, mode);
|
||||
if (found && !ref_pos_col_value)
|
||||
cvm::fatal_error ("Error: refPositionsColValue, "
|
||||
"if provided, must be non-zero.\n");
|
||||
cvm::error ("Error: refPositionsColValue, "
|
||||
"if provided, must be non-zero.\n");
|
||||
} else {
|
||||
// if not, rely on existing atom indices for the group
|
||||
group_for_fit->create_sorted_ids();
|
||||
@ -384,13 +392,13 @@ void cvm::atom_group::parse (std::string const &conf,
|
||||
|
||||
if (b_rotate) {
|
||||
if (ref_pos.size() != group_for_fit->size())
|
||||
cvm::fatal_error ("Error: the number of reference positions provided ("+
|
||||
cvm::to_str (ref_pos.size())+
|
||||
") does not match the number of atoms within \""+
|
||||
std::string (key)+
|
||||
"\" ("+cvm::to_str (group_for_fit->size())+
|
||||
"): to perform a rotational fit, "+
|
||||
"these numbers should be equal.\n");
|
||||
cvm::error ("Error: the number of reference positions provided ("+
|
||||
cvm::to_str (ref_pos.size())+
|
||||
") does not match the number of atoms within \""+
|
||||
std::string (key)+
|
||||
"\" ("+cvm::to_str (group_for_fit->size())+
|
||||
"): to perform a rotational fit, "+
|
||||
"these numbers should be equal.\n", INPUT_ERROR);
|
||||
}
|
||||
|
||||
// save the center of geometry of ref_pos and subtract it
|
||||
@ -398,7 +406,7 @@ void cvm::atom_group::parse (std::string const &conf,
|
||||
|
||||
} else {
|
||||
#if (! defined (COLVARS_STANDALONE))
|
||||
cvm::fatal_error ("Error: no reference positions provided.\n");
|
||||
cvm::error ("Error: no reference positions provided.\n");
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -431,29 +439,39 @@ void cvm::atom_group::parse (std::string const &conf,
|
||||
cvm::to_str (this->total_mass)+".\n");
|
||||
|
||||
cvm::decrease_depth();
|
||||
|
||||
return (cvm::get_error() ? COLVARS_ERROR : COLVARS_OK);
|
||||
}
|
||||
|
||||
|
||||
void cvm::atom_group::create_sorted_ids (void)
|
||||
int cvm::atom_group::create_sorted_ids (void)
|
||||
{
|
||||
// Only do the work if the vector is not yet populated
|
||||
if (sorted_ids.size())
|
||||
return;
|
||||
return COLVARS_OK;
|
||||
|
||||
std::list<int> temp_id_list;
|
||||
for (cvm::atom_iter ai = this->begin(); ai != this->end(); ai++) {
|
||||
cvm::atom_iter ai;
|
||||
for (ai = this->begin(); ai != this->end(); ai++) {
|
||||
temp_id_list.push_back (ai->id);
|
||||
}
|
||||
temp_id_list.sort();
|
||||
temp_id_list.unique();
|
||||
if (temp_id_list.size() != this->size()) {
|
||||
cvm::fatal_error ("Error: duplicate atom IDs in atom group? (found " +
|
||||
cvm::to_str(temp_id_list.size()) +
|
||||
" unique atom IDs instead of" +
|
||||
cvm::to_str(this->size()) + ").\n");
|
||||
cvm::error ("Error: duplicate atom IDs in atom group? (found " +
|
||||
cvm::to_str(temp_id_list.size()) +
|
||||
" unique atom IDs instead of" +
|
||||
cvm::to_str(this->size()) + ").\n");
|
||||
return COLVARS_ERROR;
|
||||
}
|
||||
sorted_ids = std::vector<int> (temp_id_list.begin(), temp_id_list.end());
|
||||
return;
|
||||
sorted_ids = std::vector<int> (temp_id_list.size());
|
||||
unsigned int id_i = 0;
|
||||
std::list<int>::iterator li;
|
||||
for (li = temp_id_list.begin(); li != temp_id_list.end(); ++li) {
|
||||
sorted_ids[id_i] = *li;
|
||||
id_i++;
|
||||
}
|
||||
return (cvm::get_error() ? COLVARS_ERROR : COLVARS_OK);
|
||||
}
|
||||
|
||||
void cvm::atom_group::center_ref_pos()
|
||||
@ -464,13 +482,12 @@ void cvm::atom_group::center_ref_pos()
|
||||
// This is called either by atom_group::parse or by CVCs that set
|
||||
// reference positions (eg. RMSD, eigenvector)
|
||||
ref_pos_cog = cvm::atom_pos (0.0, 0.0, 0.0);
|
||||
std::vector<cvm::atom_pos>::iterator pi = ref_pos.begin();
|
||||
for ( ; pi != ref_pos.end(); pi++) {
|
||||
std::vector<cvm::atom_pos>::iterator pi;
|
||||
for (pi = ref_pos.begin(); pi != ref_pos.end(); ++pi) {
|
||||
ref_pos_cog += *pi;
|
||||
}
|
||||
ref_pos_cog /= (cvm::real) ref_pos.size();
|
||||
for (std::vector<cvm::atom_pos>::iterator pi = ref_pos.begin();
|
||||
pi != ref_pos.end(); pi++) {
|
||||
for (pi = ref_pos.begin(); pi != ref_pos.end(); ++pi) {
|
||||
(*pi) -= ref_pos_cog;
|
||||
}
|
||||
}
|
||||
@ -679,14 +696,15 @@ void cvm::atom_group::calc_fit_gradients()
|
||||
|
||||
std::vector<cvm::atom_pos> cvm::atom_group::positions() const
|
||||
{
|
||||
if (b_dummy)
|
||||
cvm::fatal_error ("Error: positions are not available "
|
||||
if (b_dummy) {
|
||||
cvm::error ("Error: positions are not available "
|
||||
"from a dummy atom group.\n");
|
||||
}
|
||||
|
||||
std::vector<cvm::atom_pos> x (this->size(), 0.0);
|
||||
cvm::atom_const_iter ai = this->begin();
|
||||
std::vector<cvm::atom_pos>::iterator xi = x.begin();
|
||||
for ( ; ai != this->end(); xi++, ai++) {
|
||||
for ( ; ai != this->end(); ++xi, ++ai) {
|
||||
*xi = ai->pos;
|
||||
}
|
||||
return x;
|
||||
@ -694,14 +712,15 @@ std::vector<cvm::atom_pos> cvm::atom_group::positions() const
|
||||
|
||||
std::vector<cvm::atom_pos> cvm::atom_group::positions_shifted (cvm::rvector const &shift) const
|
||||
{
|
||||
if (b_dummy)
|
||||
cvm::fatal_error ("Error: positions are not available "
|
||||
"from a dummy atom group.\n");
|
||||
if (b_dummy) {
|
||||
cvm::error ("Error: positions are not available "
|
||||
"from a dummy atom group.\n");
|
||||
}
|
||||
|
||||
std::vector<cvm::atom_pos> x (this->size(), 0.0);
|
||||
cvm::atom_const_iter ai = this->begin();
|
||||
std::vector<cvm::atom_pos>::iterator xi = x.begin();
|
||||
for ( ; ai != this->end(); xi++, ai++) {
|
||||
for ( ; ai != this->end(); ++xi, ++ai) {
|
||||
*xi = (ai->pos + shift);
|
||||
}
|
||||
return x;
|
||||
@ -709,9 +728,10 @@ std::vector<cvm::atom_pos> cvm::atom_group::positions_shifted (cvm::rvector cons
|
||||
|
||||
std::vector<cvm::rvector> cvm::atom_group::velocities() const
|
||||
{
|
||||
if (b_dummy)
|
||||
cvm::fatal_error ("Error: velocities are not available "
|
||||
"from a dummy atom group.\n");
|
||||
if (b_dummy) {
|
||||
cvm::error ("Error: velocities are not available "
|
||||
"from a dummy atom group.\n");
|
||||
}
|
||||
|
||||
std::vector<cvm::rvector> v (this->size(), 0.0);
|
||||
cvm::atom_const_iter ai = this->begin();
|
||||
@ -724,14 +744,15 @@ std::vector<cvm::rvector> cvm::atom_group::velocities() const
|
||||
|
||||
std::vector<cvm::rvector> cvm::atom_group::system_forces() const
|
||||
{
|
||||
if (b_dummy)
|
||||
cvm::fatal_error ("Error: system forces are not available "
|
||||
"from a dummy atom group.\n");
|
||||
if (b_dummy) {
|
||||
cvm::error ("Error: system forces are not available "
|
||||
"from a dummy atom group.\n");
|
||||
}
|
||||
|
||||
std::vector<cvm::rvector> f (this->size(), 0.0);
|
||||
cvm::atom_const_iter ai = this->begin();
|
||||
std::vector<cvm::atom_pos>::iterator fi = f.begin();
|
||||
for ( ; ai != this->end(); fi++, ai++) {
|
||||
for ( ; ai != this->end(); ++fi, ++ai) {
|
||||
*fi = ai->system_force;
|
||||
}
|
||||
return f;
|
||||
@ -739,9 +760,10 @@ std::vector<cvm::rvector> cvm::atom_group::system_forces() const
|
||||
|
||||
cvm::rvector cvm::atom_group::system_force() const
|
||||
{
|
||||
if (b_dummy)
|
||||
cvm::fatal_error ("Error: system forces are not available "
|
||||
"from a dummy atom group.\n");
|
||||
if (b_dummy) {
|
||||
cvm::error ("Error: system forces are not available "
|
||||
"from a dummy atom group.\n");
|
||||
}
|
||||
|
||||
cvm::rvector f (0.0);
|
||||
for (cvm::atom_const_iter ai = this->begin(); ai != this->end(); ai++) {
|
||||
@ -756,9 +778,11 @@ void cvm::atom_group::apply_colvar_force (cvm::real const &force)
|
||||
if (b_dummy)
|
||||
return;
|
||||
|
||||
if (noforce)
|
||||
cvm::fatal_error ("Error: sending a force to a group that has "
|
||||
"\"enableForces\" set to off.\n");
|
||||
if (noforce) {
|
||||
cvm::error ("Error: sending a force to a group that has "
|
||||
"\"enableForces\" set to off.\n");
|
||||
return;
|
||||
}
|
||||
|
||||
if (b_rotate) {
|
||||
|
||||
@ -803,9 +827,11 @@ void cvm::atom_group::apply_force (cvm::rvector const &force)
|
||||
if (b_dummy)
|
||||
return;
|
||||
|
||||
if (noforce)
|
||||
cvm::fatal_error ("Error: sending a force to a group that has "
|
||||
"\"disableForces\" defined.\n");
|
||||
if (noforce) {
|
||||
cvm::error ("Error: sending a force to a group that has "
|
||||
"\"disableForces\" defined.\n");
|
||||
return;
|
||||
}
|
||||
|
||||
if (b_rotate) {
|
||||
|
||||
@ -831,12 +857,12 @@ void cvm::atom_group::apply_forces (std::vector<cvm::rvector> const &forces)
|
||||
return;
|
||||
|
||||
if (noforce)
|
||||
cvm::fatal_error ("Error: sending a force to a group that has "
|
||||
"\"disableForces\" defined.\n");
|
||||
cvm::error ("Error: sending a force to a group that has "
|
||||
"\"disableForces\" defined.\n");
|
||||
|
||||
if (forces.size() != this->size()) {
|
||||
cvm::fatal_error ("Error: trying to apply an array of forces to an atom "
|
||||
"group which does not have the same length.\n");
|
||||
cvm::error ("Error: trying to apply an array of forces to an atom "
|
||||
"group which does not have the same length.\n");
|
||||
}
|
||||
|
||||
if (b_rotate) {
|
||||
@ -844,7 +870,7 @@ void cvm::atom_group::apply_forces (std::vector<cvm::rvector> const &forces)
|
||||
cvm::rotation const rot_inv = rot.inverse();
|
||||
cvm::atom_iter ai = this->begin();
|
||||
std::vector<cvm::rvector>::const_iterator fi = forces.begin();
|
||||
for ( ; ai != this->end(); fi++, ai++) {
|
||||
for ( ; ai != this->end(); ++fi, ++ai) {
|
||||
ai->apply_force (rot_inv.rotate (*fi));
|
||||
}
|
||||
|
||||
@ -852,7 +878,7 @@ void cvm::atom_group::apply_forces (std::vector<cvm::rvector> const &forces)
|
||||
|
||||
cvm::atom_iter ai = this->begin();
|
||||
std::vector<cvm::rvector>::const_iterator fi = forces.begin();
|
||||
for ( ; ai != this->end(); fi++, ai++) {
|
||||
for ( ; ai != this->end(); ++fi, ++ai) {
|
||||
ai->apply_force (*fi);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user