Line data Source code
1 : /* +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 2 : Copyright (c) 2016-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/ActionShortcut.h" 23 : #include "core/ActionRegister.h" 24 : #include "MultiColvarShortcuts.h" 25 : 26 : //+PLUMEDOC COLVAR XANGLES 27 : /* 28 : Calculate the angle between an arbitrary vector and the positive x direction 29 : 30 : \par Examples 31 : 32 : */ 33 : //+ENDPLUMEDOC 34 : 35 : //+PLUMEDOC COLVAR YANGLES 36 : /* 37 : Calculate the angle between an arbitrary vector and the positive y direction 38 : 39 : \par Examples 40 : 41 : */ 42 : //+ENDPLUMEDOC 43 : 44 : //+PLUMEDOC COLVAR ZANGLES 45 : /* 46 : Calculate the angle between an arbitrary vector and the positive z direction 47 : 48 : \par Examples 49 : 50 : */ 51 : //+ENDPLUMEDOC 52 : 53 : 54 : namespace PLMD { 55 : namespace multicolvar { 56 : 57 : class XAngle : public ActionShortcut { 58 : public: 59 : static void registerKeywords(Keywords& keys); 60 : explicit XAngle(const ActionOptions&); 61 : }; 62 : 63 : PLUMED_REGISTER_ACTION(XAngle,"XANGLES") 64 : PLUMED_REGISTER_ACTION(XAngle,"YANGLES") 65 : PLUMED_REGISTER_ACTION(XAngle,"ZANGLES") 66 : 67 9 : void XAngle::registerKeywords(Keywords& keys) { 68 9 : ActionShortcut::registerKeywords( keys ); 69 18 : keys.add("numbered","ATOMS","the pairs of atoms that you would like to calculate the angles for"); 70 18 : keys.reset_style("ATOMS","atoms"); 71 9 : MultiColvarShortcuts::shortcutKeywords( keys ); 72 9 : keys.needsAction("DISTANCE"); 73 9 : keys.needsAction("COMBINE"); 74 9 : keys.needsAction("CUSTOM"); 75 9 : } 76 : 77 1 : XAngle::XAngle(const ActionOptions& ao): 78 : Action(ao), 79 1 : ActionShortcut(ao) { 80 : // Create distances 81 1 : std::string dline = getShortcutLabel() + "_dists: DISTANCE COMPONENTS"; 82 1 : for(unsigned i=1;; ++i) { 83 : std::string atstring; 84 6 : parseNumbered("ATOMS",i,atstring); 85 3 : if( atstring.length()==0 ) { 86 : break; 87 : } 88 : std::string num; 89 2 : Tools::convert( i, num ); 90 4 : dline += " ATOMS" + num + "=" + atstring; 91 2 : } 92 1 : readInputLine( dline ); 93 : // Normalize the vectors 94 2 : readInputLine( getShortcutLabel() + "_norm2: COMBINE ARG=" + getShortcutLabel() + "_dists.x" + "," + getShortcutLabel() + "_dists.y," + getShortcutLabel() + "_dists.z POWERS=2,2,2 PERIODIC=NO"); 95 2 : readInputLine( getShortcutLabel() + "_norm: CUSTOM ARG=" + getShortcutLabel() + "_norm2 FUNC=sqrt(x) PERIODIC=NO"); 96 2 : readInputLine( getShortcutLabel() + "_norm_x: CUSTOM ARG=" + getShortcutLabel() + "_dists.x," + getShortcutLabel() + "_norm FUNC=x/y PERIODIC=NO"); 97 2 : readInputLine( getShortcutLabel() + "_norm_y: CUSTOM ARG=" + getShortcutLabel() + "_dists.y," + getShortcutLabel() + "_norm FUNC=x/y PERIODIC=NO"); 98 2 : readInputLine( getShortcutLabel() + "_norm_z: CUSTOM ARG=" + getShortcutLabel() + "_dists.z," + getShortcutLabel() + "_norm FUNC=x/y PERIODIC=NO"); 99 : // Now compute the angles with matheval 100 1 : if( getName()=="XANGLES" ) { 101 2 : readInputLine( getShortcutLabel() + "_ang: CUSTOM FUNC=acos(x) PERIODIC=NO ARG=" + getShortcutLabel() + "_norm_x"); 102 : } 103 1 : if( getName()=="YANGLES" ) { 104 0 : readInputLine( getShortcutLabel() + "_ang: CUSTOM FUNC=acos(x) PERIODIC=NO ARG=" + getShortcutLabel() + "_norm_y"); 105 : } 106 1 : if( getName()=="ZANGLES" ) { 107 0 : readInputLine( getShortcutLabel() + "_ang: CUSTOM FUNC=acos(x) PERIODIC=NO ARG=" + getShortcutLabel() + "_norm_z"); 108 : } 109 : // Add shortcuts to label 110 2 : MultiColvarShortcuts::expandFunctions( getShortcutLabel(), getShortcutLabel() + "_ang", "", this ); 111 1 : } 112 : 113 : } 114 : }