def setX(self, xVec): currentParams = AmberParm(self.currentPrmtop) for x, p in zip(xVec, self.parameter2optimize): if p.kind == "bond": for b in currentParams.bonds: if set([b.atom1.type, b.atom2.type]) == p.atomMask: if p.valueType == "req": b.type.req = x elif p.valueType == "kr": b.type.k = x break elif p.kind == "angle": for a in currentParams.angles: angleTypes = [a.atom1.type, a.atom2.type, a.atom3] angleTypesRev = reversed(angleTypes) if angleTypes == p.atomMask or angleTypesRev == p.atomMask: if p.valueType == "kt": a.type.k = x elif p.valueType == "theq": a.type.theteq = x break currentParams.write_parm(self.currentPrmtop)
def setup_hmr(self): if not SETTINGS["md"]["use_hmr"]: return top_file = SETTINGS["data_files"]["top_file"] logger.info(f"Applying HMR on topology file {top_file}") parm = AmberParm(top_file) HMassRepartition(parm).execute() parm.write_parm(top_file) logger.info("HMR applied")
def solvate(self, solvent, suffix=None, tmp=True): """ Solvate system in OFF using solvent *solvent*. A PRMTOP and PRMCRD files will be saved and paths stored to :attr:`top` and :attr:`crd`. :arg solvent: Solvent Instance or Name to fetch the Solvent Instance in the database. :type: str or :class:`~Solvents.Solvent` :arg str suffix: Suffix for output files. Prefix will be the system name. E.g.: ``systemname_suffix.prmtop`` and ``systemname_suffix.prmcrd``. :arg bool tmp: Work in temporary folder. """ if not self.amberOFF: raise SystemError, "Can not solvate if no Amber Object File is assigned." if isinstance(solvent, str): solvent = Solvents.getSolvent(solvent) if not solvent: raise SystemError, 'Invalid solvent instance or name.' # Build a loger just for this method log = logging.getLogger("SystemLogger") log.info("Solvating %s with solvent mixture %s"%(self.name, solvent.name)) suffix = suffix or solvent.name name = '{0}_{1}'.format(self.name, suffix) prmtop = name+'.prmtop' prmcrd = name+'.prmcrd' if tmp: if isinstance(tmp, str): path = tmp else: path = T.tempDir() prmtop = osp.join(path, prmtop) prmcrd = osp.join(path, prmcrd) # Initiate AmberCreateSystem with loaded AmberOFF # Solvate, neutralize self.__initCreate() self.create.solvateOrganic(self.unitName, solvent=solvent) # It will work even if its water self.create.saveAmberParm(self.unitName, prmtop, prmcrd) # Added by Xiaofeng 01/12/2016 parm = AmberParm(prmtop) action = HMassRepartition(parm) action.execute() log.info(str(action)) parm.write_parm(prmtop) # self.__cleanCreate() s = SolvatedSystem(name, prmtop, prmcrd, solvent=solvent.name, ref=self.ref) return s
def prepare_prefinal_topology(self): import os # self.path_to_final_struct from runmd2.MD import TleapInput from parmed.amber import AmberParm, AmberMask from parmed.topologyobjects import Atom final_tleap = TleapInput() final_tleap.source(os.environ["PRMTOP_HOME"] + "/cmd/leaprc.protein.chlorolys.ff14SB") final_tleap.source(os.environ["PRMTOP_HOME"] + "/cmd/leaprc.water.tip3p") final_tleap.add_command("loadamberparams frcmod.ionsjc_tip3p") final_tleap.load_pdb("./input2.pdb") #final_tleap.add_command("bond wbox.32.SG wbox.69.C2 ") final_tleap.solvate_oct("TIP3PBOX", 15.0) final_tleap.add_ions("Na+", target_charge=0) final_tleap.save_params(output_name=MD._build_dir + "/prefinal_box") final_tleap.save_pdb(output_name=MD._build_dir + "/prefinal_box") final_tleap.add_command("quit") final_tleap.write_commands_to(MD._build_dir + "/prefinal_tleap.rc") self.call_cmd( ["tleap", "-s", "-f", MD._build_dir + "/prefinal_tleap.rc"]) # strip redundant water molecules parm_old = AmberParm(MD._build_dir + "/box.prmtop") parm_new = AmberParm(MD._build_dir + "/prefinal_box.prmtop") old_res = set() new_res = set() for r in parm_old.residues: old_res.add(r.number) number = r.number old_res.add(number + 1) for r in parm_new.residues: new_res.add(r.number) residues_to_delete = sorted(list(new_res - old_res)) res_mask = ":" + ','.join(list(map(str, residues_to_delete))) parm_new.strip(res_mask) parm_new.write_parm(MD._build_dir + "/prefinal_box.mod.prmtop")
def main(opt): # Check all of the arguments if not os.path.exists(opt.prmtop): raise AmberError('prmtop file (%s) is missing' % opt.prmtop) # Process the arguments that take multiple args resstates = process_arglist(opt.resstates, int) resnums = process_arglist(opt.resnums, int) notresnums = process_arglist(opt.notresnums, int) resnames = process_arglist(opt.resnames, str) notresnames = process_arglist(opt.notresnames, str) minpka = opt.minpka maxpka = opt.maxpka if not opt.igb in (1, 2, 5, 7, 8): raise AmberError('-igb must be 1, 2, 5, 7, or 8!') if resnums is not None and notresnums is not None: raise AmberError('Cannot specify -resnums and -notresnums together') if resnames is not None and notresnames is not None: raise AmberError('Cannot specify -resnames and -notresnames together') if opt.intdiel != 1 and opt.intdiel != 2: raise AmberError('-intdiel must be either 1 or 2 currently') # Print warning about old format if opt.oldfmt: sys.stderr.write( 'Warning: The old format of the CPIN file can only be used for simulations with temp0=300.0!\n' ' You should use the new format for simulations with temperatures other than 300.0 Kelvins\n' ) # Set the list of residue names we will be willing to titrate titratable_residues = [] if notresnames is not None: for resname in residues.titratable_residues: if resname in notresnames: continue titratable_residues.append(resname) elif resnames is not None: for resname in resnames: if not resname in residues.titratable_residues: raise AmberError('%s is not a titratable residue!' % resname) elif not getattr(residues, resname).typ == "ph": raise AmberError('%s is not a pH titratable residue!' % resname) titratable_residues.append(resname) else: for resname in residues.titratable_residues: if getattr(residues, resname).typ == "ph": titratable_residues.append(resname) solvent_ions = [ 'WAT', 'Na+', 'Br-', 'Cl-', 'Cs+', 'F-', 'I-', 'K+', 'Li+', 'Mg+', 'Rb+', 'CIO', 'IB', 'MG2' ] # Filter titratable residues based on min and max pKa new_reslist = [] for res in titratable_residues: if getattr(residues, res).pKa < minpka: continue if getattr(residues, res).pKa > maxpka: continue new_reslist.append(res) titratable_residues = new_reslist del new_reslist # Make sure we still have a couple residues if len(titratable_residues) == 0: raise AmberError('No titratable residues fit your criteria!') # Load the topology file parm = AmberParm(opt.prmtop) # Replace an un-set notresnums with an empty list so we get __contains__() if notresnums is None: notresnums = [] # If we have a list of residue numbers, check that they're all titratable if resnums is not None: for resnum in resnums: if resnum > parm.ptr('nres'): raise AmberError('%s only has %d residues. (%d chosen)' % (parm, parm.ptr('nres'), resnum)) if resnum <= 0: raise AmberError('Cannot select negative residue numbers.') resname = parm.parm_data['RESIDUE_LABEL'][resnum - 1] if not resname in titratable_residues: raise AmberError('Residue number %s [%s] is not titratable' % (resnum, resname)) else: # Select every residue except those in notresnums resnums = [] for resnum in range(1, parm.ptr('nres') + 1): if resnum in notresnums: continue resnums.append(resnum) solvated = False first_solvent = 0 if 'WAT' in parm.parm_data['RESIDUE_LABEL']: solvated = True for i, res in enumerate(parm.parm_data['RESIDUE_LABEL']): if res in solvent_ions: first_solvent = parm.parm_data['RESIDUE_POINTER'][i] break main_reslist = TitratableResidueList(system_name=opt.system, solvated=solvated, first_solvent=first_solvent) for resnum in resnums: resname = parm.parm_data['RESIDUE_LABEL'][resnum - 1] if not resname in titratable_residues: continue res = getattr(residues, resname) # Filter out termini (make sure the residue in the prmtop has as many # atoms as the titratable residue defined in residues.py) if resnum == parm.ptr('nres'): natoms = (parm.ptr('natom') + 1 - parm.parm_data['RESIDUE_POINTER'][resnum - 1]) else: natoms = (parm.parm_data['RESIDUE_POINTER'][resnum] - parm.parm_data['RESIDUE_POINTER'][resnum - 1]) if natoms != len(res.atom_list): continue # If we have gotten this far, add it to the list. main_reslist.add_residue(res, resnum, parm.parm_data['RESIDUE_POINTER'][resnum - 1]) # Set the states if requested if resstates is not None: main_reslist.set_states(resstates) # Open the output file if opt.output is None: output = sys.stdout else: output = open(opt.output, 'w') main_reslist.write_cpin(output, opt.igb, opt.intdiel, opt.oldfmt, "ph") if opt.output is not None: output.close() if solvated: if opt.outparm is None: has_carboxylate = False for res in main_reslist: if res is residues.AS4 or res is residues.GL4 or res is residues.PRN: has_carboxylate = True break if has_carboxylate: sys.stderr.write( 'Warning: Carboxylate residues in explicit solvent ' 'simulations require a modified topology file!\n' 'Use the -op flag to print one.\n') else: changeRadii(parm, 'mbondi2').execute() change(parm, 'RADII', ':AS4,GL4,PRN@OD=,OE=,O1=,O2=', 1.3).execute() parm.overwrite = True parm.write_parm(opt.outparm) else: if opt.outparm is not None: sys.stderr.write( 'A new prmtop is only necessary for explicit solvent ' 'CpHMD/pH-REMD simulations.\n') sys.stderr.write('CPIN generation complete!\n')
def main(opt): # Check all of the arguments if not os.path.exists(opt.prmtop): raise AmberError('prmtop file (%s) is missing' % opt.prmtop) # Process the arguments that take multiple args resstates = process_arglist(opt.resstates, int) resnums = process_arglist(opt.resnums, int) notresnums = process_arglist(opt.notresnums, int) resnames = process_arglist(opt.resnames, str) notresnames = process_arglist(opt.notresnames, str) minpka = opt.minpka maxpka = opt.maxpka if not opt.igb in (1, 2, 5, 7, 8): raise AmberError('-igb must be 1, 2, 5, 7, or 8!') if resnums is not None and notresnums is not None: raise AmberError('Cannot specify -resnums and -notresnums together') if resnames is not None and notresnames is not None: raise AmberError('Cannot specify -resnames and -notresnames together') if opt.intdiel != 1 and opt.intdiel != 2: raise AmberError('-intdiel must be either 1 or 2 currently') # Print warning about old format if opt.oldfmt: sys.stderr.write('Warning: The old format of the CPIN file can only be used for simulations with temp0=300.0!\n' ' You should use the new format for simulations with temperatures other than 300.0 Kelvins\n') # Set the list of residue names we will be willing to titrate titratable_residues = [] if notresnames is not None: for resname in residues.titratable_residues: if resname in notresnames: continue titratable_residues.append(resname) elif resnames is not None: for resname in resnames: if not resname in residues.titratable_residues: raise AmberError('%s is not a titratable residue!' % resname) elif not getattr(residues, resname).typ == "ph": raise AmberError('%s is not a pH-active titratable residue!' % resname) titratable_residues.append(resname) else: for resname in residues.titratable_residues: if getattr(residues, resname).typ == "ph": titratable_residues.append(resname) solvent_ions = ['WAT', 'Na+', 'Br-', 'Cl-', 'Cs+', 'F-', 'I-', 'K+', 'Li+', 'Mg+', 'Rb+', 'CIO', 'IB', 'MG2'] # Filter titratable residues based on min and max pKa new_reslist = [] for res in titratable_residues: # @jaimergp: If None values are not filtered out, comparisons # will fail in Py3k. This patch was discussed and approved in # GitLab issue 122 (@vwcruzeiro, @swails) # Error obtained in serial tests in conda-forge builds: # Traceback (most recent call last): # File "/home/conda/amber/bin/cpinutil.py", line 325, in <module> # main(opt) # File "/home/conda/amber/bin/cpinutil.py", line 191, in main # if getattr(residues, res).pKa < minpka: continue # TypeError: '<' not supported between instances of 'NoneType' and 'int' # ./Run.cpin: Program error # make[1]: *** [test.cpinutil] Error 1 if getattr(residues, res).pKa is None: continue # /@jaimergp if getattr(residues, res).pKa < minpka: continue if getattr(residues, res).pKa > maxpka: continue new_reslist.append(res) titratable_residues = new_reslist del new_reslist # Make sure we still have a couple residues if len(titratable_residues) == 0: raise AmberError('No titratable residues fit your criteria!') # Load the topology file parm = AmberParm(opt.prmtop) # Replace an un-set notresnums with an empty list so we get __contains__() if notresnums is None: notresnums = [] # If we have a list of residue numbers, check that they're all titratable if resnums is not None: for resnum in resnums: if resnum > parm.ptr('nres'): raise AmberError('%s only has %d residues. (%d chosen)' % (parm, parm.ptr('nres'), resnum)) if resnum <= 0: raise AmberError('Cannot select negative residue numbers.') resname = parm.parm_data['RESIDUE_LABEL'][resnum-1] if not resname in titratable_residues: raise AmberError('Residue number %s [%s] is not titratable' % (resnum, resname)) else: # Select every residue except those in notresnums resnums = [] for resnum in range(1, parm.ptr('nres') + 1): if resnum in notresnums: continue resnums.append(resnum) solvated = False first_solvent = 0 if 'WAT' in parm.parm_data['RESIDUE_LABEL']: solvated = True for i, res in enumerate(parm.parm_data['RESIDUE_LABEL']): if res in solvent_ions: first_solvent = parm.parm_data['RESIDUE_POINTER'][i] break main_reslist = TitratableResidueList(system_name=opt.system, solvated=solvated, first_solvent=first_solvent) trescnt = 0 for resnum in resnums: resname = parm.parm_data['RESIDUE_LABEL'][resnum-1] if not resname in titratable_residues: continue res = getattr(residues, resname) # Filter out termini (make sure the residue in the prmtop has as many # atoms as the titratable residue defined in residues.py) if resnum == parm.ptr('nres'): natoms = (parm.ptr('natom') + 1 - parm.parm_data['RESIDUE_POINTER'][resnum-1]) else: natoms = (parm.parm_data['RESIDUE_POINTER'][resnum] - parm.parm_data['RESIDUE_POINTER'][resnum-1]) if natoms != len(res.atom_list): continue # If we have gotten this far, add it to the list. main_reslist.add_residue(res, resnum, parm.parm_data['RESIDUE_POINTER'][resnum-1]) trescnt += 1 # Prints a warning if the number of titratable residues is larger than 50 if trescnt > 50: sys.stderr.write('Warning: Your CPIN file has more than 50 titratable residues! pmemd and sander have a\n' ' default limit of 50 titrable residues, thus this CPIN file can only be used\n' ' if the definitions for this limit are modified at the top of\n' ' $AMBERHOME/src/pmemd/src/constantph.F90 or $AMBERHOME/AmberTools/src/sander/constantph.F90.\n' ' AMBER needs to be recompilied after these files are modified.\n') # Set the states if requested if resstates is not None: main_reslist.set_states(resstates) # Open the output file if opt.output is None: output = sys.stdout else: output = open(opt.output, 'w') main_reslist.write_cpin(output, opt.igb, opt.intdiel, opt.oldfmt, "ph") if opt.output is not None: output.close() if solvated: if opt.outparm is None: has_carboxylate = False for res in main_reslist: if res is residues.AS4 or res is residues.GL4 or res is residues.PRN: has_carboxylate = True break if has_carboxylate: sys.stderr.write( 'Warning: Carboxylate residues in explicit solvent ' 'simulations require a modified topology file!\n' ' Use the -op flag to print one.\n' ) else: changeRadii(parm, 'mbondi2').execute() change(parm, 'RADII', ':AS4,GL4,PRN@OD=,OE=,O1=,O2=', 1.3).execute() parm.overwrite = True parm.write_parm(opt.outparm) else: if opt.outparm is not None: sys.stderr.write( 'A new prmtop is only necessary for explicit solvent ' 'CpHMD/pH-REMD simulations.\n' ) sys.stderr.write('CPIN generation complete!\n')
def main(opt): # Check all of the arguments if not os.path.exists(opt.prmtop): raise AmberError('prmtop file (%s) is missing' % opt.prmtop) # Process the arguments that take multiple args resstates = process_arglist(opt.resstates, int) resnums = process_arglist(opt.resnums, int) notresnums = process_arglist(opt.notresnums, int) resnames = process_arglist(opt.resnames, str) notresnames = process_arglist(opt.notresnames, str) minpka = opt.minpka maxpka = opt.maxpka if not opt.igb in (1, 2, 5, 7, 8): raise AmberError('-igb must be 1, 2, 5, 7, or 8!') if resnums is not None and notresnums is not None: raise AmberError('Cannot specify -resnums and -notresnums together') if resnames is not None and notresnames is not None: raise AmberError('Cannot specify -resnames and -notresnames together') if opt.intdiel != 1 and opt.intdiel != 2: raise AmberError('-intdiel must be either 1 or 2 currently') # Print warning about old format if opt.oldfmt: sys.stderr.write('Warning: The old format of the CPIN file can only be used for simulations with temp0=300.0!\n' ' You should use the new format for simulations with temperatures other than 300.0 Kelvins\n') # Set the list of residue names we will be willing to titrate titratable_residues = [] if notresnames is not None: for resname in residues.titratable_residues: if resname in notresnames: continue titratable_residues.append(resname) elif resnames is not None: for resname in resnames: if not resname in residues.titratable_residues: raise AmberError('%s is not a titratable residue!' % resname) elif not getattr(residues, resname).typ == "ph": raise AmberError('%s is not a pH-active titratable residue!' % resname) titratable_residues.append(resname) else: for resname in residues.titratable_residues: if getattr(residues, resname).typ == "ph": titratable_residues.append(resname) solvent_ions = ['WAT', 'Na+', 'Br-', 'Cl-', 'Cs+', 'F-', 'I-', 'K+', 'Li+', 'Mg+', 'Rb+', 'CIO', 'IB', 'MG2'] # Filter titratable residues based on min and max pKa new_reslist = [] for res in titratable_residues: if getattr(residues, res).pKa < minpka: continue if getattr(residues, res).pKa > maxpka: continue new_reslist.append(res) titratable_residues = new_reslist del new_reslist # Make sure we still have a couple residues if len(titratable_residues) == 0: raise AmberError('No titratable residues fit your criteria!') # Load the topology file parm = AmberParm(opt.prmtop) # Replace an un-set notresnums with an empty list so we get __contains__() if notresnums is None: notresnums = [] # If we have a list of residue numbers, check that they're all titratable if resnums is not None: for resnum in resnums: if resnum > parm.ptr('nres'): raise AmberError('%s only has %d residues. (%d chosen)' % (parm, parm.ptr('nres'), resnum)) if resnum <= 0: raise AmberError('Cannot select negative residue numbers.') resname = parm.parm_data['RESIDUE_LABEL'][resnum-1] if not resname in titratable_residues: raise AmberError('Residue number %s [%s] is not titratable' % (resnum, resname)) else: # Select every residue except those in notresnums resnums = [] for resnum in range(1, parm.ptr('nres') + 1): if resnum in notresnums: continue resnums.append(resnum) solvated = False first_solvent = 0 if 'WAT' in parm.parm_data['RESIDUE_LABEL']: solvated = True for i, res in enumerate(parm.parm_data['RESIDUE_LABEL']): if res in solvent_ions: first_solvent = parm.parm_data['RESIDUE_POINTER'][i] break main_reslist = TitratableResidueList(system_name=opt.system, solvated=solvated, first_solvent=first_solvent) trescnt = 0 for resnum in resnums: resname = parm.parm_data['RESIDUE_LABEL'][resnum-1] if not resname in titratable_residues: continue res = getattr(residues, resname) # Filter out termini (make sure the residue in the prmtop has as many # atoms as the titratable residue defined in residues.py) if resnum == parm.ptr('nres'): natoms = (parm.ptr('natom') + 1 - parm.parm_data['RESIDUE_POINTER'][resnum-1]) else: natoms = (parm.parm_data['RESIDUE_POINTER'][resnum] - parm.parm_data['RESIDUE_POINTER'][resnum-1]) if natoms != len(res.atom_list): continue # If we have gotten this far, add it to the list. main_reslist.add_residue(res, resnum, parm.parm_data['RESIDUE_POINTER'][resnum-1]) trescnt += 1 # Prints a warning if the number of titratable residues is larger than 50 if trescnt > 50: sys.stderr.write('Warning: Your CPIN file has more than 50 titratable residues! pmemd and sander have a\n' ' default limit of 50 titrable residues, thus this CPIN file can only be used\n' ' if the definitions for this limit are modified at the top of\n' ' $AMBERHOME/src/pmemd/src/constantph.F90 or $AMBERHOME/AmberTools/src/sander/constantph.F90.\n' ' AMBER needs to be recompilied after these files are modified.\n') # Set the states if requested if resstates is not None: main_reslist.set_states(resstates) # Open the output file if opt.output is None: output = sys.stdout else: output = open(opt.output, 'w') main_reslist.write_cpin(output, opt.igb, opt.intdiel, opt.oldfmt, "ph") if opt.output is not None: output.close() if solvated: if opt.outparm is None: has_carboxylate = False for res in main_reslist: if res is residues.AS4 or res is residues.GL4 or res is residues.PRN: has_carboxylate = True break if has_carboxylate: sys.stderr.write( 'Warning: Carboxylate residues in explicit solvent ' 'simulations require a modified topology file!\n' ' Use the -op flag to print one.\n' ) else: changeRadii(parm, 'mbondi2').execute() change(parm, 'RADII', ':AS4,GL4,PRN@OD=,OE=,O1=,O2=', 1.3).execute() parm.overwrite = True parm.write_parm(opt.outparm) else: if opt.outparm is not None: sys.stderr.write( 'A new prmtop is only necessary for explicit solvent ' 'CpHMD/pH-REMD simulations.\n' ) sys.stderr.write('CPIN generation complete!\n')
def prepare_prmtop(args, name): """ Places appropriate prmtop file into the calculation folder and scales it's charges if necessary. Parameters ---------- args : Namespace Command line arguments Returns ------- out : string Path to prmtop file. """ # The atom specification in ParmedActions is terrible and requires the use # of masks. A good description of what it is can be found in Amber14 manual # section 28.2.3 if args.file.endswith('.prmtop'): prmtop_name = args.file else: prmtop_name = generate_prmtop(name, args) if args.new_name: new_name = args.new_name else: new_name = prmtop_name if args.minimize: minimize_solute(name, prmtop_name, args) if args.nomod: # we are done return 0 parm = AmberParm(prmtop_name) if args.charge_model == 'opls' or args.lennard_jones == 'opls': opls_radii, opls_epss, opls_chgs = get_opls_parameters(args, name) # account for scenario when charge_f is submitted along with existing prmtop if args.charge_f and args.file.endswith('.prmtop'): chargef_charges = get_chargef_charges(args.charge_f) #iterate over atoms for i, atom in enumerate(parm.atoms): attyp, atname, attchg = atom.type, atom.name, float(atom.charge) #print(attchg) nbidx = parm.LJ_types[attyp] lj_r = float(parm.LJ_radius[nbidx - 1]) lj_eps = float(parm.LJ_depth[nbidx - 1]) # change attyp to atnmae act = pact.change(parm, '@{} AMBER_ATOM_TYPE {}'.format(atname, atname)) act.execute() # deal with chgs if args.input_chg: print() attchg = get_usr_input('charge', atname, attchg) elif args.charge_model == 'opls': attchg = opls_chgs[i] elif args.charge_f and args.file.endswith('.prmtop'): attchg = float(chargef_charges[i]) attchg = attchg * args.scale_chg act = pact.change(parm, '@{} charge {:f}'.format(atname, float(attchg))) act.execute() # deal with lj if args.input_lj: if args.lj_radius_type == 'sigma': lj_r = lj_r*2./(2**(1./6)) # convert to sigma lj_r = get_usr_input('lj_r', atname, lj_r) if args.lj_radius_type == 'sigma': lj_r = lj_r/2.*(2**(1./6)) lj_eps = get_usr_input('lj_eps', atname, lj_eps) elif args.lennard_jones== 'opls': lj_r = opls_radii[i] lj_eps = opls_epss[i] lj_r = lj_r * args.scale_r lj_eps = lj_eps * args.scale_eps #print(lj_r, lj_eps) act = pact.changeLJSingleType(parm, '@{} {:f} {:f}'.format(atname, lj_r, lj_eps)) act.execute() #parm.overwrite = True parm.write_parm(new_name)