LCOV - code coverage report
Current view: top level - crystallization - MoleculePlane.cpp (source / functions) Hit Total Coverage
Test: plumed test coverage Lines: 40 56 71.4 %
Date: 2026-03-30 13:16:06 Functions: 6 8 75.0 %

          Line data    Source code
       1             : /* +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
       2             :    Copyright (c) 2014-2023 The plumed team
       3             :    (see the PEOPLE file at the root of the distribution for a list of names)
       4             : 
       5             :    See http://www.plumed.org for more information.
       6             : 
       7             :    This file is part of plumed, version 2.
       8             : 
       9             :    plumed is free software: you can redistribute it and/or modify
      10             :    it under the terms of the GNU Lesser General Public License as published by
      11             :    the Free Software Foundation, either version 3 of the License, or
      12             :    (at your option) any later version.
      13             : 
      14             :    plumed is distributed in the hope that it will be useful,
      15             :    but WITHOUT ANY WARRANTY; without even the implied warranty of
      16             :    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      17             :    GNU Lesser General Public License for more details.
      18             : 
      19             :    You should have received a copy of the GNU Lesser General Public License
      20             :    along with plumed.  If not, see <http://www.gnu.org/licenses/>.
      21             : +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ */
      22             : #include "core/ActionRegister.h"
      23             : #include "VectorMultiColvar.h"
      24             : 
      25             : namespace PLMD {
      26             : namespace crystallization {
      27             : 
      28             : //+PLUMEDOC MCOLVAR PLANES
      29             : /*
      30             : Calculate the plane perpendicular to two vectors in order to represent the orientation of a planar molecule.
      31             : 
      32             : \par Examples
      33             : 
      34             : 
      35             : */
      36             : //+ENDPLUMEDOC
      37             : 
      38             : 
      39             : class MoleculePlane : public VectorMultiColvar {
      40             : private:
      41             : public:
      42             :   static void registerKeywords( Keywords& keys );
      43             :   explicit MoleculePlane( const ActionOptions& ao );
      44             :   AtomNumber getAbsoluteIndexOfCentralAtom( const unsigned& iatom ) const override;
      45             :   void calculateVector( multicolvar::AtomValuePack& myatoms ) const override;
      46             : };
      47             : 
      48       13789 : PLUMED_REGISTER_ACTION(MoleculePlane,"PLANES")
      49             : 
      50           6 : void MoleculePlane::registerKeywords( Keywords& keys ) {
      51           6 :   VectorMultiColvar::registerKeywords( keys );
      52           6 :   keys.use("VMEAN");
      53          12 :   keys.add("numbered","MOL","The numerical indices of the atoms in the molecule. If three atoms are specified the orientation "
      54             :            "of the molecule is taken as the normal to the plane containing the vector connecting the first and "
      55             :            "second atoms and the vector connecting the second and third atoms.  If four atoms are specified the "
      56             :            "orientation of the molecule is taken as the normal to the plane containing the vector connecting the "
      57             :            "first and second atoms and the vector connecting the third and fourth atoms. The molecule is always "
      58             :            "assumed to lie at the geometric center for the three/four atoms.");
      59          12 :   keys.reset_style("MOL","atoms");
      60           6 : }
      61             : 
      62           2 : MoleculePlane::MoleculePlane( const ActionOptions& ao ):
      63             :   Action(ao),
      64           2 :   VectorMultiColvar(ao) {
      65             :   std::vector<AtomNumber> all_atoms;
      66           4 :   readAtomsLikeKeyword("MOL",-1,all_atoms);
      67           2 :   if( ablocks.size()!=3 && ablocks.size()!=4 ) {
      68           0 :     error("number of atoms in molecule specification is wrong.  Should be three or four.");
      69             :   }
      70             : 
      71           2 :   if( all_atoms.size()==0 ) {
      72           0 :     error("No atoms were specified");
      73             :   }
      74           2 :   setVectorDimensionality( 3 );
      75           2 :   setupMultiColvarBase( all_atoms );
      76           2 : }
      77             : 
      78           0 : AtomNumber MoleculePlane::getAbsoluteIndexOfCentralAtom( const unsigned& iatom ) const {
      79             :   plumed_dbg_assert( iatom<atom_lab.size() );
      80           0 :   plumed_assert( atom_lab[iatom].first==0 );
      81           0 :   return ActionAtomistic::getAbsoluteIndex( ablocks[0][atom_lab[iatom].second] );
      82             : }
      83             : 
      84        8888 : void MoleculePlane::calculateVector( multicolvar::AtomValuePack& myatoms ) const {
      85        8888 :   Vector d1, d2, cp;
      86        8888 :   if( myatoms.getNumberOfAtoms()==3 ) {
      87        8888 :     d1=getSeparation( myatoms.getPosition(1), myatoms.getPosition(0) );
      88        8888 :     d2=getSeparation( myatoms.getPosition(1), myatoms.getPosition(2) );
      89             :   } else {
      90           0 :     d1=getSeparation( myatoms.getPosition(1), myatoms.getPosition(0) );
      91           0 :     d2=getSeparation( myatoms.getPosition(2), myatoms.getPosition(3) );
      92             :   }
      93        8888 :   cp = crossProduct( d1, d2 );
      94             : 
      95        8888 :   addAtomDerivatives( 2, 0, crossProduct( Vector(-1.0,0,0), d2 ), myatoms );
      96        8888 :   if( myatoms.getNumberOfAtoms()==3 ) {
      97        8888 :     addAtomDerivatives( 2, 1, crossProduct( Vector(+1.0,0,0), d2 ) + crossProduct( Vector(-1.0,0,0), d1 ), myatoms );
      98        8888 :     addAtomDerivatives( 2, 2, crossProduct( Vector(+1.0,0,0), d1 ), myatoms );
      99             :   } else {
     100           0 :     addAtomDerivatives( 2, 1, crossProduct( Vector(+1.0,0,0), d2 ), myatoms );
     101           0 :     addAtomDerivatives( 2, 2, crossProduct( Vector(-1.0,0,0), d1 ), myatoms );
     102           0 :     addAtomDerivatives( 2, 3, crossProduct( Vector(+1.0,0,0), d1 ), myatoms );
     103             :   }
     104        8888 :   myatoms.addBoxDerivatives( 2, Tensor(d1,crossProduct(Vector(+1.0,0,0), d2)) + Tensor( d2, crossProduct(Vector(-1.0,0,0), d1)) );
     105        8888 :   myatoms.addValue( 2, cp[0] );
     106             : 
     107        8888 :   addAtomDerivatives( 3, 0, crossProduct( Vector(0,-1.0,0), d2 ), myatoms );
     108        8888 :   if( myatoms.getNumberOfAtoms()==3 ) {
     109        8888 :     addAtomDerivatives( 3, 1, crossProduct( Vector(0,+1.0,0), d2 ) + crossProduct( Vector(0,-1.0,0), d1 ), myatoms );
     110        8888 :     addAtomDerivatives( 3, 2, crossProduct( Vector(0,+1.0,0), d1 ), myatoms );
     111             :   } else {
     112           0 :     addAtomDerivatives( 3, 1, crossProduct( Vector(0,+1.0,0), d2 ), myatoms );
     113           0 :     addAtomDerivatives( 3, 2, crossProduct( Vector(0,-1.0,0), d1 ), myatoms );
     114           0 :     addAtomDerivatives( 3, 3, crossProduct( Vector(0,+1.0,0), d1 ), myatoms );
     115             :   }
     116        8888 :   myatoms.addBoxDerivatives( 3, Tensor(d1,crossProduct(Vector(0,+1.0,0), d2)) + Tensor( d2, crossProduct(Vector(0,-1.0,0), d1)) );
     117        8888 :   myatoms.addValue( 3, cp[1] );
     118             : 
     119        8888 :   addAtomDerivatives( 4, 0, crossProduct( Vector(0,0,-1.0), d2 ), myatoms );
     120        8888 :   if( myatoms.getNumberOfAtoms()==3 ) {
     121        8888 :     addAtomDerivatives( 4, 1, crossProduct( Vector(0,0,+1.0), d2 ) + crossProduct( Vector(0,0,-1.0), d1 ), myatoms );
     122        8888 :     addAtomDerivatives( 4, 2, crossProduct( Vector(0,0,+1.0), d1 ), myatoms);
     123             :   } else {
     124           0 :     addAtomDerivatives( 4, 1, crossProduct( Vector(0,0,-1.0), d2 ), myatoms);
     125           0 :     addAtomDerivatives( 4, 2, crossProduct( Vector(0,0,-1.0), d1 ), myatoms);
     126           0 :     addAtomDerivatives( 4, 3, crossProduct( Vector(0,0,+1.0), d1 ), myatoms);
     127             :   }
     128        8888 :   myatoms.addBoxDerivatives( 4, Tensor(d1,crossProduct(Vector(0,0,+1.0), d2)) + Tensor( d2, crossProduct(Vector(0,0,-1.0), d1)) );
     129        8888 :   myatoms.addValue( 4, cp[2] );
     130        8888 : }
     131             : 
     132             : // Vector MoleculePlane::getCentralAtom(){
     133             : //   Vector com; com.zero();
     134             : //   if( getNAtoms()==3 ){
     135             : //       com+=(1.0/3.0)*getPosition(0);
     136             : //       com+=(1.0/3.0)*getPosition(1);
     137             : //       com+=(1.0/3.0)*getPosition(2);
     138             : //       addCentralAtomDerivatives( 0, (1.0/3.0)*Tensor::identity() );
     139             : //       addCentralAtomDerivatives( 1, (1.0/3.0)*Tensor::identity() );
     140             : //       addCentralAtomDerivatives( 2, (1.0/3.0)*Tensor::identity() );
     141             : //       return com;
     142             : //   }
     143             : //   com+=0.25*getPosition(0);
     144             : //   com+=0.25*getPosition(1);
     145             : //   com+=0.25*getPosition(2);
     146             : //   com+=0.25*getPosition(3);
     147             : //   addCentralAtomDerivatives( 0, 0.25*Tensor::identity() );
     148             : //   addCentralAtomDerivatives( 1, 0.25*Tensor::identity() );
     149             : //   addCentralAtomDerivatives( 2, 0.25*Tensor::identity() );
     150             : //   addCentralAtomDerivatives( 3, 0.25*Tensor::identity() );
     151             : //   return com;
     152             : // }
     153             : 
     154             : }
     155             : }

Generated by: LCOV version 1.16