def run(self,
            production_steps=200,
            start='ala2_1stFrame.pdb',
            production='ala2_production.pdb'):  #### ?!!!!!!!!!!!!!!!!
        #from __future__ import print_function
        from simtk.openmm import app
        import simtk.openmm as mm
        from simtk import unit
        from sys import stdout

        nonbondedCutoff = 1.0 * unit.nanometers
        timestep = 2.0 * unit.femtoseconds
        temperature = 300 * unit.kelvin
        #save_frequency = 100 #Every 100 steps, save the trajectory
        save_frequency = 10  #Every 1 steps, save the trajectory

        pdb = app.PDBFile(start)
        forcefield = app.ForceField('amber99sb.xml', 'tip3p.xml')
        ala2_model = app.Modeller(pdb.topology, pdb.positions)

        #Hydrogens will be constrained after equilibrating
        system = forcefield.createSystem(ala2_model.topology,
                                         nonbondedMethod=app.PME,
                                         nonbondedCutoff=nonbondedCutoff,
                                         constraints=app.HBonds,
                                         rigidWater=True,
                                         ewaldErrorTolerance=0.0005)

        system.addForce(mm.MonteCarloBarostat(
            1 * unit.bar, temperature,
            100))  #Apply Monte Carlo Pressure changes in 100 timesteps
        integrator = mm.LangevinIntegrator(temperature, 1.0 / unit.picoseconds,
                                           timestep)
        integrator.setConstraintTolerance(0.00001)

        platform = mm.Platform.getPlatformByName('CPU')
        simulation = app.Simulation(ala2_model.topology, system, integrator,
                                    platform)
        simulation.context.setPositions(ala2_model.positions)

        simulation.context.setVelocitiesToTemperature(temperature)

        simulation.reporters.append(app.PDBReporter(production,
                                                    save_frequency))
        simulation.reporters.append(
            app.StateDataReporter('stateReporter_constantPressure.txt',
                                  1000,
                                  step=True,
                                  totalEnergy=True,
                                  temperature=True,
                                  volume=True,
                                  progress=True,
                                  remainingTime=True,
                                  speed=True,
                                  totalSteps=production_steps,
                                  separator='\t'))

        print('Running Production...')
        simulation.step(production_steps)
        print('Done!')

        import mdtraj as md
        trj = md.load(production)
        return trj
Esempio n. 2
0
    def equilibrate(self, ff_name, water_name):

        input_pdb_filename = self.get_initial_pdb_filename(ff_name, water_name)
        equil_pdb_filename = self.get_equil_pdb_filename(ff_name, water_name)
        equil_dcd_filename = self.get_equil_dcd_filename(ff_name, water_name)
        equil_protein_pdb_filename = self.get_equil_protein_pdb_filename(
            ff_name, water_name)

        utils.make_path(equil_pdb_filename)

        if os.path.exists(equil_pdb_filename):
            return

        ff = app.ForceField('%s.xml' % ff_name, '%s.xml' % water_name)
        pdb = app.PDBFile(input_pdb_filename)
        modeller = app.Modeller(pdb.topology, pdb.positions)
        modeller.addSolvent(ff,
                            model=water_mapping[water_name],
                            padding=self.padding,
                            ionicStrength=self.ionic_strength)
        topology = modeller.getTopology()
        positions = modeller.getPositions()

        system = ff.createSystem(topology,
                                 nonbondedMethod=app.PME,
                                 nonbondedCutoff=self.cutoff,
                                 constraints=app.HBonds)
        integrator = mm.LangevinIntegrator(self.temperature,
                                           self.equil_friction,
                                           self.equil_timestep)
        system.addForce(
            mm.MonteCarloBarostat(self.pressure, self.temperature,
                                  self.barostat_frequency))

        platform = mm.Platform.getPlatformByName("CUDA")
        platform.setPropertyDefaultValue("CudaDeviceIndex",
                                         os.environ["CUDA_VISIBLE_DEVICES"])

        simulation = app.Simulation(topology,
                                    system,
                                    integrator,
                                    platform=platform)
        simulation.context.setPositions(positions)

        print('Minimizing.')
        simulation.minimizeEnergy()

        simulation.context.setVelocitiesToTemperature(self.temperature)
        print('Equilibrating.')

        simulation.reporters.append(
            app.PDBReporter(equil_pdb_filename, self.n_equil_steps - 1))
        simulation.reporters.append(
            app.DCDReporter(equil_dcd_filename, self.equil_output_frequency))
        simulation.step(self.n_equil_steps)
        del simulation
        del system
        traj = md.load(equil_dcd_filename, top=equil_pdb_filename)[-1]
        traj.save(equil_pdb_filename)

        top, bonds = traj.top.to_dataframe()
        atom_indices = top.index[top.chainID == 0].values
        traj.restrict_atoms(atom_indices)
        traj.save(equil_protein_pdb_filename)
Esempio n. 3
0
    ref_pdb = app.PDBFile(ini_pdb_file)
    topology, positions = ref_pdb.topology, ref_pdb.positions

    templates = sop.util.template_dict(topology, n_beads)

    ff_kwargs = {}
    ff_kwargs["mass_ply"] = mass_ply
    ff_kwargs["eps_ply"] = coeff[0]*0.5*unit.kilojoule_per_mole
    ff_kwargs["sigma_ply"] = sigma_ply

    ff_filename = "ff_cgs.xml"
    sop.build_ff.polymer_in_solvent(n_beads, "r12", "NONE",
            saveas=ff_filename, bond_cutoff=bond_cutoff - 1,
            **ff_kwargs)

    forcefield = app.ForceField(ff_filename)

    system = forcefield.createSystem(topology, ignoreExternalBonds=True, residueTemplates=templates)

    if using_cv:
        system.addForce(Ucv_force)
    else:
        system.addForce(Up_force)

    if collision_rate == 0:
        # gamma = m/D ? does temperature enter?
        collision_rate = ((mass_ply/unit.amu)/D)/unit.picosecond
    else:
        collision_rate = collision_rate/unit.picosecond

    ensemble = "NVT"
Esempio n. 4
0
from __future__ import print_function
from simtk.openmm import app
import simtk.openmm as mm
from simtk import unit
from sys import stdout

# Load the PDB file into an object
pdb = app.PDBFile('trpcage.pdb')

# Load the force field file into an object
forcefield = app.ForceField('amber99sbildn.xml', 'tip3p.xml')

# Create system object using information in the force field:
# forcefield: contains parameters of interactions
# topology: lists of atoms, residues, and bonds
system = forcefield.createSystem(pdb.topology,
                                 nonbondedMethod=app.PME,
                                 nonbondedCutoff=1.0 * unit.nanometers,
                                 constraints=app.HBonds,
                                 rigidWater=True,
                                 ewaldErrorTolerance=0.0005)

# Create a Langevin integrator for temperature control
integrator = mm.LangevinIntegrator(300 * unit.kelvin, 1.0 / unit.picoseconds,
                                   2.0 * unit.femtoseconds)

# Add a Monte Carlo barostat to the system for pressure control
system.addForce(
    mm.MonteCarloBarostat(1 * unit.atmospheres, 300 * unit.kelvin, 25))

# Use the CPU platform
Esempio n. 5
0
if len(sys.argv) != 8:
    print(
        'usage %s <cuda device index> < temp K > < t_equil ns > < t_sim ns > < fric 1/ps > < pdb > < frame > '
    )
    exit(1)

temp = float(sys.argv[2])
t_equil = float(sys.argv[3])
t_sim = float(sys.argv[4])
fric = float(sys.argv[5])
pdb_str = sys.argv[6]
pdb_frame = int(sys.argv[7])

pdb = md.load(pdb_str)
forcefield = app.ForceField('amber99sbildn.xml', 'amber99_obc.xml')

system = forcefield.createSystem(pdb.topology.to_openmm(),
                                 nonbondedMethod=app.CutoffNonPeriodic,
                                 nonbondedCutoff=2.0 * unit.nanometers,
                                 constraints=app.HBonds)
integrator = mm.LangevinIntegrator(temp * unit.kelvin, fric / unit.picoseconds,
                                   2.0 * unit.femtoseconds)
integrator.setConstraintTolerance(0.00001)

platform = mm.Platform.getPlatformByName('CUDA')
properties = {'CudaPrecision': 'mixed', 'CudaDeviceIndex': sys.argv[1]}
simulation = app.Simulation(pdb.topology.to_openmm(), system, integrator,
                            platform, properties)
simulation.context.setPositions(pdb.xyz[pdb_frame])
Esempio n. 6
0
def runOneTest(testName, options):
    """Perform a single benchmarking simulation."""
    explicit = (testName in ('rf', 'pme', 'amoebapme'))
    amoeba = (testName in ('amoebagk', 'amoebapme'))
    apoa1 = testName.startswith('apoa1')
    hydrogenMass = None
    print()
    if amoeba:
        print('Test: %s (epsilon=%g)' % (testName, options.epsilon))
    elif testName == 'pme':
        print('Test: pme (cutoff=%g)' % options.cutoff)
    else:
        print('Test: %s' % testName)
    platform = mm.Platform.getPlatformByName(options.platform)
    
    # Create the System.
    
    if amoeba:
        constraints = None
        epsilon = float(options.epsilon)
        if explicit:
            ff = app.ForceField('amoeba2009.xml')
            pdb = app.PDBFile('5dfr_solv-cube_equil.pdb')
            cutoff = 0.7*unit.nanometers
            vdwCutoff = 0.9*unit.nanometers
            system = ff.createSystem(pdb.topology, nonbondedMethod=app.PME, nonbondedCutoff=cutoff, vdwCutoff=vdwCutoff, constraints=constraints, ewaldErrorTolerance=0.00075, mutualInducedTargetEpsilon=epsilon, polarization=options.polarization)
        else:
            ff = app.ForceField('amoeba2009.xml', 'amoeba2009_gk.xml')
            pdb = app.PDBFile('5dfr_minimized.pdb')
            cutoff = 2.0*unit.nanometers
            vdwCutoff = 1.2*unit.nanometers
            system = ff.createSystem(pdb.topology, nonbondedMethod=app.NoCutoff, constraints=constraints, mutualInducedTargetEpsilon=epsilon, polarization=options.polarization)
        for f in system.getForces():
            if isinstance(f, mm.AmoebaMultipoleForce) or isinstance(f, mm.AmoebaVdwForce) or isinstance(f, mm.AmoebaGeneralizedKirkwoodForce) or isinstance(f, mm.AmoebaWcaDispersionForce):
                f.setForceGroup(1)
        dt = 0.002*unit.picoseconds
        integ = mm.MTSIntegrator(dt, [(0,2), (1,1)])
    else:
        if apoa1:
            ff = app.ForceField('amber14/protein.ff14SB.xml', 'amber14/lipid17.xml', 'amber14/tip3p.xml')
            pdb = app.PDBFile('apoa1.pdb')
            if testName == 'apoa1pme':
                method = app.PME
                cutoff = options.cutoff
            elif testName == 'apoa1ljpme':
                method = app.LJPME
                cutoff = options.cutoff
            else:
                method = app.CutoffPeriodic
                cutoff = 1*unit.nanometers
            friction = 1*(1/unit.picoseconds)
        elif explicit:
            ff = app.ForceField('amber99sb.xml', 'tip3p.xml')
            pdb = app.PDBFile('5dfr_solv-cube_equil.pdb')
            if testName == 'pme':
                method = app.PME
                cutoff = options.cutoff
            else:
                method = app.CutoffPeriodic
                cutoff = 1*unit.nanometers
            friction = 1*(1/unit.picoseconds)
        else:
            ff = app.ForceField('amber99sb.xml', 'amber99_obc.xml')
            pdb = app.PDBFile('5dfr_minimized.pdb')
            method = app.CutoffNonPeriodic
            cutoff = 2*unit.nanometers
            friction = 91*(1/unit.picoseconds)
        if options.heavy:
            dt = 0.005*unit.picoseconds
            constraints = app.AllBonds
            hydrogenMass = 4*unit.amu
            integ = mm.LangevinIntegrator(300*unit.kelvin, friction, dt)
        else:
            dt = 0.004*unit.picoseconds
            constraints = app.HBonds
            hydrogenMass = None
            integ = mm.LangevinMiddleIntegrator(300*unit.kelvin, friction, dt)
        system = ff.createSystem(pdb.topology, nonbondedMethod=method, nonbondedCutoff=cutoff, constraints=constraints, hydrogenMass=hydrogenMass)
    print('Step Size: %g fs' % dt.value_in_unit(unit.femtoseconds))
    properties = {}
    initialSteps = 5
    if options.device is not None and platform.getName() in ('CUDA', 'OpenCL'):
        properties['DeviceIndex'] = options.device
        if ',' in options.device or ' ' in options.device:
            initialSteps = 250
    if options.precision is not None and platform.getName() in ('CUDA', 'OpenCL'):
        properties['Precision'] = options.precision
    
    # Run the simulation.
    
    integ.setConstraintTolerance(1e-5)
    if len(properties) > 0:
        context = mm.Context(system, integ, platform, properties)
    else:
        context = mm.Context(system, integ, platform)
    context.setPositions(pdb.positions)
    context.setVelocitiesToTemperature(300*unit.kelvin)
    steps = 20
    while True:
        time = timeIntegration(context, steps, initialSteps)
        if time >= 0.5*options.seconds:
            break
        if time < 0.5:
            steps = int(steps*1.0/time) # Integrate enough steps to get a reasonable estimate for how many we'll need.
        else:
            steps = int(steps*options.seconds/time)
    print('Integrated %d steps in %g seconds' % (steps, time))
    print('%g ns/day' % (dt*steps*86400/time).value_in_unit(unit.nanoseconds))
Esempio n. 7
0
    def __init__(self, **kwargs):
        super(LoopSoftening, self).__init__(**kwargs)
        self.description = 'Alchemical Loop Softening script'

        padding = 9.0 * unit.angstrom
        explicit_solvent_model = 'tip3p'
        setup_path = 'data/mtor'

        # Create topology, positions, and system.
        from pkg_resources import resource_filename
        gaff_xml_filename = resource_filename('sams', 'data/gaff.xml')
        system_generators = dict()
        ffxmls = [gaff_xml_filename, 'amber99sbildn.xml', 'tip3p.xml']
        forcefield_kwargs = {
            'nonbondedMethod': app.CutoffPeriodic,
            'nonbondedCutoff': 9.0 * unit.angstrom,
            'implicitSolvent': None,
            'constraints': app.HBonds,
            'rigidWater': True
        }

        # Load topologies and positions for all components
        print('Creating mTOR test system...')
        forcefield = app.ForceField(*ffxmls)
        from simtk.openmm.app import PDBFile, Modeller
        pdb_filename = resource_filename(
            'sams', os.path.join(setup_path, 'mtor_pdbfixer_apo.pdb'))

        pdbfile = PDBFile(pdb_filename)
        modeller = app.Modeller(pdbfile.topology, pdbfile.positions)
        print('Adding solvent...')
        modeller.addSolvent(forcefield,
                            model=explicit_solvent_model,
                            padding=padding)
        self.topology = modeller.getTopology()
        self.positions = modeller.getPositions()
        print('Creating system...')
        self.system = forcefield.createSystem(self.topology,
                                              **forcefield_kwargs)

        # DEBUG: Write PDB
        outfile = open('initial.pdb', 'w')
        PDBFile.writeFile(self.topology, self.positions, outfile)
        outfile.close()

        # Atom Selection using MDtraj
        res_pairs = [[403, 483], [1052, 1109]]
        t = md.load(pdb_filename)
        alchemical_atoms = set()
        for x in res_pairs:
            start = min(t.top.select('residue %s' % min(x)))
            end = max(t.top.select('residue %s' % max(x))) + 1
            alchemical_atoms.union(set(range(start, end)))

        # Create thermodynamic states.
        print('Creating alchemically-modified system...')
        temperature = 300 * unit.kelvin
        pressure = 1.0 * unit.atmospheres

        from alchemy import AbsoluteAlchemicalFactory
        factory = AbsoluteAlchemicalFactory(
            self.system,
            ligand_atoms=alchemical_atoms,
            annihilate_electrostatics=True,
            alchemical_torsions=True,
            annihilate_sterics=True,
            softcore_beta=0.0)  # turn off softcore electrostatics
        self.system = factory.createPerturbedSystem()
        print('Setting up alchemical intermediates...')
        from sams import ThermodynamicState
        self.thermodynamic_states = list()
        for state in range(26):
            parameters = {
                'lambda_sterics': 1.0,
                'lambda_electrostatics': (1.0 - float(state) / 25.0)
            }
            self.thermodynamic_states.append(
                ThermodynamicState(system=self.system,
                                   temperature=temperature,
                                   parameters=parameters))
        for state in range(1, 26):
            parameters = {
                'lambda_sterics': (1.0 - float(state) / 25.0),
                'lambda_electrostatics': 0.0
            }
            self.thermodynamic_states.append(
                ThermodynamicState(system=self.system,
                                   temperature=temperature,
                                   parameters=parameters))

        #minimize(self.system, self.positions)
        minimize(self.system)

        # Create SAMS samplers
        print('Setting up samplers...')
        from sams.samplers import SamplerState, MCMCSampler, ExpandedEnsembleSampler, SAMSSampler
        thermodynamic_state_index = 0  # initial thermodynamic state index
        thermodynamic_state = self.thermodynamic_states[
            thermodynamic_state_index]
        sampler_state = SamplerState(positions=self.system.positions)
        self.mcmc_sampler = MCMCSampler(
            sampler_state=sampler_state,
            thermodynamic_state=thermodynamic_state,
            ncfile=self.ncfile)
        self.mcmc_sampler.pdbfile = open('output.pdb', 'w')
        self.mcmc_sampler.topology = self.topology
        self.mcmc_sampler.verbose = True
        self.exen_sampler = ExpandedEnsembleSampler(self.mcmc_sampler,
                                                    self.thermodynamic_states)
        self.exen_sampler.verbose = True
        self.sams_sampler = SAMSSampler(self.exen_sampler)
        self.sams_sampler.verbose = True
Esempio n. 8
0
    def openmm_system(self):
        """Initialise the OpenMM system we will use to evaluate the energies."""

        # load the initial coords into the system and initialise
        pdb = app.PDBFile(self.pdb)

        # count the amount of atoms in the structure
        for atom in pdb.topology.atoms():
            self.natoms += 1

        # must use a custom version of the tip3p water moddel
        forcefield = app.ForceField(self.xml, 'tip3p_opls.xml')
        self.modeller = app.Modeller(
            pdb.topology,
            pdb.positions)  # set the intial positions from the pdb

        # Now we need to solvate the system
        self.modeller.addSolvent(forcefield,
                                 model='tip3p',
                                 padding=1 * unit.nanometer)

        # write out the solvated system coords
        app.PDBFile.writeFile(self.modeller.topology, self.modeller.positions,
                              open('output.pdb', 'w'))

        # now we create the system and add the lj correction
        self.system = forcefield.createSystem(self.modeller.topology,
                                              nonbondedMethod=app.PME,
                                              constraints=None,
                                              nonbondedCutoff=1.1 *
                                              unit.nanometer)
        if self.opls:
            self.opls_lj()

        # set control parameters
        temperature = 298.15 * unit.kelvin
        integrator = mm.LangevinIntegrator(temperature, 5 / unit.picoseconds,
                                           0.001 * unit.picoseconds)

        # add preasure to the system
        self.system.addForce(
            mm.MonteCarloBarostat(1 * unit.bar, 300 * unit.kelvin))

        # create the simulation context
        self.simulation = app.Simulation(self.modeller.topology, self.system,
                                         integrator)

        # set the positions to the solvated system
        self.simulation.context.setPositions(self.modeller.positions)

        # get the energy of the sytem
        print(
            self.simulation.context.getState(
                getEnergy=True).getPotentialEnergy())

        # check the energy break down
        struct = pmd.load_file('output.pdb')
        ecomps = (pmd.openmm.energy_decomposition_system(struct, self.system))
        tot_ene = 0.0
        for i in range(0, len(ecomps)):
            tot_ene += ecomps[i][1]
            print(ecomps[i][0], ecomps[i][1])
        print('Total-energy %6.6f' % tot_ene)

        # serialize the system
        serialized_system = mm.XmlSerializer.serialize(self.system)
        outfile = open('test.xml', 'w')
        outfile.write(serialized_system)
        outfile.close()

        # now minimize the system
        self.simulation.minimizeEnergy(maxIterations=100)

        # now run the simulation
        self.simulation.reporters.append(app.PDBReporter('run.pdb', 1000))
        self.simulation.reporters.append(
            app.StateDataReporter('run.txt',
                                  1000,
                                  step=True,
                                  potentialEnergy=True,
                                  temperature=True))
        self.simulation.step(100000)
Esempio n. 9
0
temp = 298.15 * unit.kelvin
rcut = 12 * unit.angstroms
rswitch = 11 * unit.angstroms
rcutIn = 8 * unit.angstroms
rswitchIn = 5 * unit.angstroms
tau = 10 * unit.femtoseconds
gamma = 0.1 / unit.femtoseconds
reportInterval = 90 // args.timestep

platform = openmm.Platform.getPlatformByName(platform_name)
properties = dict(Precision='mixed') if platform_name == 'CUDA' else dict()
if args.device != 'None':
    properties['DeviceIndex'] = args.device

pdb = app.PDBFile('water.pdb')
forcefield = app.ForceField('water.xml')
openmm_system = forcefield.createSystem(pdb.topology,
                                        nonbondedMethod=openmm.app.PME,
                                        nonbondedCutoff=rcut,
                                        rigidWater=False,
                                        removeCMMotion=False)

nbforce = openmm_system.getForce(atomsmm.findNonbondedForce(openmm_system))
nbforce.setUseSwitchingFunction(True)
nbforce.setSwitchingDistance(rswitch)
nbforce.setUseDispersionCorrection(False)

if args.timestep > 3:
    respa_system = atomsmm.RESPASystem(openmm_system,
                                       rcutIn,
                                       rswitchIn,
Esempio n. 10
0
def create_system(guest_mol, host_pdb, handlers, restr_search_radius,
                  restr_force_constant, intg_temperature, stage):
    """
    Initialize a self-encompassing System object that we can serialize and simulate.

    Parameters
    ----------

    guest_mol: rdkit.ROMol
        guest molecule
        
    host_pdb: openmm.PDBFile
        host system from OpenMM

    handlers: list of timemachine.ops.Gradients
        forcefield handlers used to parameterize the system

    restr_search_radius: float
        how far away we search from the ligand to define the binding pocket atoms.

    restr_force_constant: float
        strength of the harmonic oscillator for the restraint

    intg_temperature: float
        temperature of the integrator in Kelvin

    stage: int (0 or 1)
        a free energy specific variable that determines how we decouple.
 
    """

    guest_masses = np.array([a.GetMass() for a in guest_mol.GetAtoms()],
                            dtype=np.float64)

    amber_ff = app.ForceField('amber99sbildn.xml', 'amber99_obc.xml')
    host_system = amber_ff.createSystem(host_pdb.topology,
                                        nonbondedMethod=app.NoCutoff,
                                        constraints=None,
                                        rigidWater=False)

    host_fns, host_masses = openmm_deserializer.deserialize_system(host_system)

    num_host_atoms = len(host_masses)
    num_guest_atoms = guest_mol.GetNumAtoms()

    # Name, Args, vjp_fn
    final_gradients = []

    for item in host_fns:

        if item[0] == 'LennardJones':
            host_lj_params = item[1]
        elif item[0] == 'Charges':
            host_charge_params = item[1]
        elif item[0] == 'GBSA':
            host_gb_params = item[1][0]
            host_gb_props = item[1][1:]
        elif item[0] == 'Exclusions':
            host_exclusions = item[1]
        else:
            final_gradients.append((item[0], item[1]))

    guest_exclusion_idxs, guest_scales = nonbonded.generate_exclusion_idxs(
        guest_mol, scale12=1.0, scale13=1.0, scale14=0.5)

    guest_exclusion_idxs += num_host_atoms
    guest_lj_exclusion_scales = guest_scales
    guest_charge_exclusion_scales = guest_scales

    host_exclusion_idxs = host_exclusions[0]
    host_lj_exclusion_scales = host_exclusions[1]
    host_charge_exclusion_scales = host_exclusions[2]

    combined_exclusion_idxs = np.concatenate(
        [host_exclusion_idxs, guest_exclusion_idxs])
    combined_lj_exclusion_scales = np.concatenate(
        [host_lj_exclusion_scales, guest_lj_exclusion_scales])
    combined_charge_exclusion_scales = np.concatenate(
        [host_charge_exclusion_scales, guest_charge_exclusion_scales])

    # We build up a map of handles to a corresponding vjp_fn that takes in adjoints of output parameters
    # for nonbonded terms, the vjp_fn has been modified to take in combined parameters
    handler_vjp_fns = {}

    for handle in handlers:
        results = handle.parameterize(guest_mol)

        if isinstance(handle, bonded.HarmonicBondHandler):
            bond_idxs, (bond_params, handler_vjp_fn) = results
            bond_idxs += num_host_atoms
            final_gradients.append(("HarmonicBond", (bond_idxs, bond_params)))
        elif isinstance(handle, bonded.HarmonicAngleHandler):
            angle_idxs, (angle_params, handler_vjp_fn) = results
            angle_idxs += num_host_atoms
            final_gradients.append(
                ("HarmonicAngle", (angle_idxs, angle_params)))
        elif isinstance(handle, bonded.ProperTorsionHandler):
            torsion_idxs, (torsion_params, handler_vjp_fn) = results
            torsion_idxs += num_host_atoms
            final_gradients.append(
                ("PeriodicTorsion", (torsion_idxs, torsion_params)))
        elif isinstance(handle, bonded.ImproperTorsionHandler):
            torsion_idxs, (torsion_params, handler_vjp_fn) = results
            torsion_idxs += num_host_atoms
            final_gradients.append(
                ("PeriodicTorsion", (torsion_idxs, torsion_params)))
        elif isinstance(handle, nonbonded.LennardJonesHandler):
            guest_lj_params, guest_lj_vjp_fn = results
            combined_lj_params, handler_vjp_fn = concat_with_vjps(
                host_lj_params, guest_lj_params, None, guest_lj_vjp_fn)
        elif isinstance(handle, nonbonded.SimpleChargeHandler):
            guest_charge_params, guest_charge_vjp_fn = results
            combined_charge_params, handler_vjp_fn = concat_with_vjps(
                host_charge_params, guest_charge_params, None,
                guest_charge_vjp_fn)
        elif isinstance(handle, nonbonded.GBSAHandler):
            guest_gb_params, guest_gb_vjp_fn = results
            combined_gb_params, handler_vjp_fn = concat_with_vjps(
                host_gb_params, guest_gb_params, None, guest_gb_vjp_fn)
        elif isinstance(handle, nonbonded.AM1BCCHandler):
            guest_charge_params, guest_charge_vjp_fn = results
            combined_charge_params, handler_vjp_fn = concat_with_vjps(
                host_charge_params, guest_charge_params, None,
                guest_charge_vjp_fn)
        elif isinstance(handle, nonbonded.AM1CCCHandler):
            guest_charge_params, guest_charge_vjp_fn = results
            combined_charge_params, handler_vjp_fn = concat_with_vjps(
                host_charge_params, guest_charge_params, None,
                guest_charge_vjp_fn)
        else:
            raise Exception("Unknown Handler", handle)

        handler_vjp_fns[handle] = handler_vjp_fn

    host_conf = []
    for x, y, z in host_pdb.positions:
        host_conf.append([to_md_units(x), to_md_units(y), to_md_units(z)])
    host_conf = np.array(host_conf)

    conformer = guest_mol.GetConformer(0)
    mol_a_conf = np.array(conformer.GetPositions(), dtype=np.float64)
    mol_a_conf = mol_a_conf / 10  # convert to md_units

    x0 = np.concatenate([host_conf, mol_a_conf])  # combined geometry
    v0 = np.zeros_like(x0)

    pocket_atoms = find_protein_pocket_atoms(x0, num_host_atoms,
                                             restr_search_radius)

    N_C = num_host_atoms + num_guest_atoms
    N_A = num_host_atoms

    cutoff = 100000.0

    if stage == 0:
        combined_lambda_plane_idxs = np.zeros(N_C, dtype=np.int32)
        combined_lambda_offset_idxs = np.zeros(N_C, dtype=np.int32)
    elif stage == 1:
        combined_lambda_plane_idxs = np.zeros(N_C, dtype=np.int32)
        combined_lambda_offset_idxs = np.zeros(N_C, dtype=np.int32)
        combined_lambda_offset_idxs[num_host_atoms:] = 1
    else:
        assert 0

    final_gradients.append(
        ('Nonbonded',
         (np.asarray(combined_charge_params), np.asarray(combined_lj_params),
          combined_exclusion_idxs, combined_charge_exclusion_scales,
          combined_lj_exclusion_scales, combined_lambda_plane_idxs,
          combined_lambda_offset_idxs, cutoff)))

    final_gradients.append(
        ('GBSA', (np.asarray(combined_charge_params),
                  np.asarray(combined_gb_params), combined_lambda_plane_idxs,
                  combined_lambda_offset_idxs, *host_gb_props, cutoff,
                  cutoff)))

    ligand_idxs = np.arange(N_A, N_C, dtype=np.int32)

    # restraints
    if stage == 0:
        lamb_flag = 1
        lamb_offset = 0
    if stage == 1:
        lamb_flag = 0
        lamb_offset = 1

    # unweighted center of mass restraints
    avg_xi = np.mean(x0[ligand_idxs], axis=0)
    avg_xj = np.mean(x0[pocket_atoms], axis=0)
    ctr_dij = np.sqrt(np.sum((avg_xi - avg_xj)**2))

    combined_masses = np.concatenate([host_masses, guest_masses])

    # restraints
    final_gradients.append(
        ('CentroidRestraint',
         (ligand_idxs, pocket_atoms, combined_masses, restr_force_constant,
          ctr_dij, lamb_flag, lamb_offset)))

    ssc = standard_state.harmonic_com_ssc(restr_force_constant, ctr_dij,
                                          intg_temperature)

    return x0, combined_masses, ssc, final_gradients, handler_vjp_fns
Esempio n. 11
0
def generate_vacuum_hostguest_proposal(current_mol_name="B2",
                                       proposed_mol_name="MOL"):
    """
    Generate a test vacuum topology proposal, current positions, and new positions triplet
    from two IUPAC molecule names.

    Parameters
    ----------
    current_mol_name : str, optional
        name of the first molecule
    proposed_mol_name : str, optional
        name of the second molecule

    Returns
    -------
    topology_proposal : perses.rjmc.topology_proposal
        The topology proposal representing the transformation
    current_positions : np.array, unit-bearing
        The positions of the initial system
    new_positions : np.array, unit-bearing
        The positions of the new system
    """
    from openmoltools import forcefield_generators
    from openmmtools import testsystems

    from perses.utils.openeye import smiles_to_oemol
    from perses.utils.data import get_data_filename

    host_guest = testsystems.HostGuestVacuum()
    unsolv_old_system, old_positions, top_old = host_guest.system, host_guest.positions, host_guest.topology

    ligand_topology = [res for res in top_old.residues()]
    current_mol = forcefield_generators.generateOEMolFromTopologyResidue(
        ligand_topology[1])  # guest is second residue in topology
    proposed_mol = smiles_to_oemol('C1CC2(CCC1(CC2)C)C')

    initial_smiles = oechem.OEMolToSmiles(current_mol)
    final_smiles = oechem.OEMolToSmiles(proposed_mol)

    gaff_xml_filename = get_data_filename("data/gaff.xml")
    forcefield = app.ForceField(gaff_xml_filename, 'tip3p.xml')
    forcefield.registerTemplateGenerator(
        forcefield_generators.gaffTemplateGenerator)

    solvated_system = forcefield.createSystem(top_old, removeCMMotion=False)

    gaff_filename = get_data_filename('data/gaff.xml')
    system_generator = SystemGenerator(
        [gaff_filename, 'amber99sbildn.xml', 'tip3p.xml'],
        forcefield_kwargs={
            'removeCMMotion': False,
            'nonbondedMethod': app.NoCutoff
        })
    geometry_engine = geometry.FFAllAngleGeometryEngine()
    proposal_engine = SmallMoleculeSetProposalEngine(
        [initial_smiles, final_smiles],
        system_generator,
        residue_name=current_mol_name)

    #generate topology proposal
    topology_proposal = proposal_engine.propose(solvated_system,
                                                top_old,
                                                current_mol=current_mol,
                                                proposed_mol=proposed_mol)

    #generate new positions with geometry engine
    new_positions, _ = geometry_engine.propose(topology_proposal,
                                               old_positions, beta)

    return topology_proposal, old_positions, new_positions
Esempio n. 12
0
def benchmark_dhfr(verbose=False, num_batches=100, steps_per_batch=1000):

    pdb_path = "tests/data/5dfr_solv_equil.pdb"
    host_pdb = app.PDBFile(pdb_path)
    protein_ff = app.ForceField("amber99sbildn.xml", "tip3p.xml")
    host_system = protein_ff.createSystem(
        host_pdb.topology, nonbondedMethod=app.NoCutoff, constraints=None, rigidWater=False
    )
    host_coords = host_pdb.positions
    box = host_pdb.topology.getPeriodicBoxVectors()
    box = np.asarray(box / box.unit)

    host_fns, host_masses = openmm_deserializer.deserialize_system(host_system, cutoff=1.0)

    host_conf = []
    for x, y, z in host_coords:
        host_conf.append([to_md_units(x), to_md_units(y), to_md_units(z)])
    host_conf = np.array(host_conf)

    x0 = host_conf
    v0 = np.zeros_like(host_conf)

    benchmark(
        "dhfr-apo",
        host_masses,
        0.0,
        x0,
        v0,
        box,
        host_fns,
        verbose=verbose,
        num_batches=num_batches,
        steps_per_batch=steps_per_batch,
    )
    benchmark(
        "dhfr-apo-barostat-interval-25",
        host_masses,
        0.0,
        x0,
        v0,
        box,
        host_fns,
        verbose=verbose,
        num_batches=num_batches,
        steps_per_batch=steps_per_batch,
        barostat_interval=25,
    )
    benchmark(
        "dhfr-apo-hmr-barostat-interval-25",
        host_masses,
        0.0,
        x0,
        v0,
        box,
        host_fns,
        verbose=verbose,
        hmr=True,
        num_batches=num_batches,
        steps_per_batch=steps_per_batch,
        barostat_interval=25,
    )
Esempio n. 13
0
    def _built_template(molecule, force_field_source):
        """Builds a force field template object.

        Parameters
        ----------
        molecule: openforcefield.topology.Molecule
            The molecule to templatize.
        force_field_source: LigParGenForceFieldSource
            The tleap source which describes which parameters to apply.

        Returns
        -------
        simtk.openmm.app.ForceField
            The force field template.
        """
        from simtk import unit as simtk_unit

        initial_request_url = force_field_source.request_url
        empty_stream = io.BytesIO(b"\r\n")

        total_charge = molecule.total_charge

        if isinstance(total_charge, simtk_unit.Quantity):
            total_charge = total_charge.value_in_unit(
                simtk_unit.elementary_charge)

        charge_model = "cm1abcc"

        if (force_field_source.preferred_charge_model
                == LigParGenForceFieldSource.ChargeModel.CM1A_1_14
                or not np.isclose(total_charge, 0.0)):

            charge_model = "cm1a"

            if (force_field_source.preferred_charge_model !=
                    LigParGenForceFieldSource.ChargeModel.CM1A_1_14):
                logger.warning(
                    f"The preferred charge model is {str(force_field_source.preferred_charge_model)}, "
                    f"however the system is charged and so the "
                    f"{str(LigParGenForceFieldSource.ChargeModel.CM1A_1_14)} model will be used in its "
                    f"place.")

        data_body = {
            "smiData": (None, molecule.to_smiles()),
            "molpdbfile": ("", empty_stream),
            "checkopt": (None, 0),
            "chargetype": (None, charge_model),
            "dropcharge": (None, str(total_charge)),
        }

        # Perform the initial request for LigParGen to parameterize the molecule.
        request = requests.post(url=initial_request_url, files=data_body)

        # Cleanup the empty stream
        empty_stream.close()

        if request.status_code != requests.codes.ok:
            return f"The request failed with return code {request.status_code}."

        response_content = request.content

        # Retrieve the server file name.
        force_field_file_name = re.search(r"value=\"/tmp/(.*?).xml\"",
                                          response_content.decode())

        if force_field_file_name is None:
            return "The request could not successfully be completed."

        force_field_file_name = force_field_file_name.group(1)

        # Download the force field xml file.
        download_request_url = force_field_source.download_url

        download_force_field_body = {
            "go": (None, "XML"),
            "fileout": (None, f"/tmp/{force_field_file_name}.xml"),
        }

        request = requests.post(url=download_request_url,
                                files=download_force_field_body)

        if request.status_code != requests.codes.ok:
            return f"The request to download the system xml file failed with return code {request.status_code}."

        force_field_response = request.content
        force_field_path = "template.xml"

        with open(force_field_path, "wb") as file:
            file.write(force_field_response)

        return app.ForceField(force_field_path)
Esempio n. 14
0
def test_ffxml_simulation():
    """Test converting toluene and benzene smiles to oemol to ffxml to openmm simulation."""
    with utils.enter_temp_directory():
        m0 = openmoltools.openeye.smiles_to_oemol("Cc1ccccc1")
        charged0 = openmoltools.openeye.get_charges(m0)
        m1 = openmoltools.openeye.smiles_to_oemol("c1ccccc1")
        charged1 = openmoltools.openeye.get_charges(m1)
        ligands = [charged0, charged1]
        n_atoms = [15, 12]

        trajectories, ffxml = openmoltools.openeye.oemols_to_ffxml(ligands)
        eq(len(trajectories), len(ligands))

        pdb_filename = utils.get_data_filename("chemicals/proteins/1vii.pdb")

        temperature = 300 * u.kelvin
        friction = 0.3 / u.picosecond
        timestep = 0.01 * u.femtosecond

        protein_traj = md.load(pdb_filename)
        protein_traj.center_coordinates()

        protein_top = protein_traj.top.to_openmm()
        protein_xyz = protein_traj.openmm_positions(0)

        for k, ligand in enumerate(ligands):
            ligand_traj = trajectories[k]
            ligand_traj.center_coordinates()

            eq(ligand_traj.n_atoms, n_atoms[k])
            eq(ligand_traj.n_frames, 1)

            #Move the pre-centered ligand sufficiently far away from the protein to avoid a clash.
            min_atom_pair_distance = (
                (ligand_traj.xyz[0]**2.).sum(1)**0.5).max() + (
                    (protein_traj.xyz[0]**2.).sum(1)**0.5).max() + 0.3
            ligand_traj.xyz += np.array([1.0, 0.0, 0.0
                                         ]) * min_atom_pair_distance

            ligand_xyz = ligand_traj.openmm_positions(0)
            ligand_top = ligand_traj.top.to_openmm()

            ffxml.seek(0)
            forcefield = app.ForceField("amber10.xml", ffxml, "tip3p.xml")

            model = app.modeller.Modeller(protein_top, protein_xyz)
            model.add(ligand_top, ligand_xyz)
            model.addSolvent(forcefield, padding=0.4 * u.nanometer)

            system = forcefield.createSystem(model.topology,
                                             nonbondedMethod=app.PME,
                                             nonbondedCutoff=1.0 *
                                             u.nanometers,
                                             constraints=app.HAngles)

            integrator = mm.LangevinIntegrator(temperature, friction, timestep)

            simulation = app.Simulation(model.topology, system, integrator)
            simulation.context.setPositions(model.positions)
            print("running")
            simulation.step(1)
Esempio n. 15
0
if args.L is not None:
    print('CAUTION: (cubic) box L {} entered, overriding boxfile {}'.format(
        args.L, args.boxfile))
    box_L = args.L
    periodic_box_vectors = [[box_L, 0., 0.], [0., box_L, 0.], [0., 0., box_L]]
else:
    periodic_box_vectors = np.loadtxt(args.boxfile)

ff_list = args.fflist
pdb = app.PDBFile

sys_pdb = app.PDBFile(args.initpdb)
top = sys_pdb.topology

# === Set up simulation ===
forcefield = app.ForceField(*ff_list)
unmatched_residues = forcefield.getUnmatchedResidues(top)
print('\n=== Unmatched residues ===\n')
print(unmatched_residues)

print('\n=== Periodic Box ===')
print(periodic_box_vectors)
top.setPeriodicBoxVectors(periodic_box_vectors * unit.nanometer)

print('\n=== Making System ===')
system = forcefield.createSystem(sys_pdb.topology,
                                 nonbondedMethod=nonbonded_method,
                                 nonbondedCutoff=nonbonded_cutoff,
                                 ewaldErrorTolerance=ewald_tol,
                                 rigidWater=True,
                                 constraints=None)
Esempio n. 16
0
temp = 298.15 * unit.kelvin
rcut = 12 * unit.angstroms
rswitch = 11 * unit.angstroms
rcutIn = 8 * unit.angstroms
rswitchIn = 5 * unit.angstroms
tau = 10 * unit.femtoseconds
gamma = 0.1 / unit.femtoseconds
reportInterval = 90 // args.timestep

platform = openmm.Platform.getPlatformByName(platform_name)
properties = dict(Precision='mixed') if platform_name == 'CUDA' else dict()
if args.device != 'None':
    properties['DeviceIndex'] = args.device

pdb = app.PDBFile('ethylene_glycol.pdb')
forcefield = app.ForceField('ethylene_glycol.xml')
openmm_system = forcefield.createSystem(pdb.topology,
                                        nonbondedMethod=openmm.app.PME,
                                        nonbondedCutoff=rcut,
                                        rigidWater=False,
                                        removeCMMotion=False)

nbforce = openmm_system.getForce(atomsmm.findNonbondedForce(openmm_system))
nbforce.setUseSwitchingFunction(True)
nbforce.setSwitchingDistance(rswitch)
nbforce.setUseDispersionCorrection(False)

if args.timestep > 3:
    respa_system = atomsmm.RESPASystem(openmm_system,
                                       rcutIn,
                                       rswitchIn,
Esempio n. 17
0
nc_filename = "repex.nc"

n_replicas = 3 # number of temperature replicas
T_min = 298.0 * u.kelvin # minimum temperature
T_max = 600.0 * u.kelvin # maximum temperature

T_i = [ T_min + (T_max - T_min) * (math.exp(float(i) / float(n_replicas-1)) - 1.0) / (math.e - 1.0) for i in range(n_replicas) ]

pdb_filename = "1VII.pdb"

temperature = 300 * u.kelvin
friction = 0.3 / u.picosecond
timestep = 2.0 * u.femtosecond

forcefield = app.ForceField("amber10.xml", "tip3p.xml")

pdb = app.PDBFile(pdb_filename)

model = app.modeller.Modeller(pdb.topology, pdb.positions)
model.addSolvent(forcefield, padding=0.4 * u.nanometer)

system = forcefield.createSystem(model.topology, nonbondedMethod=app.PME, nonbondedCutoff=1.0 * u.nanometers, constraints=app.HAngles)

states = [ ThermodynamicState(system=system, temperature=T_i[i]) for i in range(n_replicas) ]

simulation = ReplicaExchange(states, [model.getPositions()] * n_replicas, nc_filename) # initialize the replica-exchange simulation
simulation.minimize = False
simulation.number_of_iterations = 2 # set the simulation to only run 2 iterations
simulation.timestep = 2.0 * u.femtoseconds # set the timestep for integration
simulation.nsteps_per_iteration = 50 # run 50 timesteps per iteration
output_frequency = 250
dcd_frequency = 5000

steps_per_hmc = 250

timestep = 2.0 * u.femtoseconds
friction = 1.0 / u.picoseconds
temperature = 300. * u.kelvin
pressure = 1.0 * u.atmospheres
barostat_frequency = 25
n_steps = 500000000
cutoff = 1.0 * u.nanometers
output_frequency = 500

ffxml_filename = "%s.xml" % cas
ff = app.ForceField(ffxml_filename)

dcd_filename = "./water/production_%s.dcd" % integrator_type
log_filename = "./water/production_%s.log" % integrator_type

pdb = app.PDBFile("../tip3p.pdb")

topology = pdb.topology
positions = pdb.positions

system = ff.createSystem(topology,
                         nonbondedMethod=app.PME,
                         nonbondedCutoff=cutoff,
                         constraints=app.HBonds)

integrators = {
Esempio n. 19
0
def prepare_pdb(pdb,
                chains='A',
                ff=('amber99sbildn.xml', 'tip3p.xml'),
                ph=7,
                pad=10 * unit.angstroms,
                nbonded=app.PME,
                constraints=app.HBonds,
                crystal_water=True):
    """
    Fetch, solvate and minimize a protein PDB structure.

    Parameters
    ----------
    pdb : str
        PDB Id.
    chains : str or list
        Chain(s) to keep in the system.
    ff : tuple of xml ff files.
        Forcefields for parametrization.
    ph : float
        pH value for adding missing hydrogens.
    pad: Quantity object
        Padding around macromolecule for filling box with water.
    nbonded : object
        The method to use for nonbonded interactions.  Allowed values are
        NoCutoff, CutoffNonPeriodic, CutoffPeriodic, Ewald, PME, or LJPME.
    constraints : object
        Specifies which bonds and angles should be implemented with
        constraints. Allowed values are None, HBonds, AllBonds, or HAngles.
    crystal_water : bool
        Keep crystal water.

    """

    # Load forcefield.
    logger.info('Retrieving %s from PDB...', pdb)
    ff = app.ForceField(*ff)

    # Retrieve structure from PDB.
    fixer = PDBFixer(pdbid=pdb)

    # Remove unselected chains.
    logger.info('Removing all chains but %s', chains)
    all_chains = [c.id for c in fixer.topology.chains()]
    fixer.removeChains(chainIds=set(all_chains) - set(chains))

    # Find missing residues.
    logger.info('Finding missing residues...')
    fixer.findMissingResidues()

    # Replace nonstandard residues.
    logger.info('Replacing nonstandard residues...')
    fixer.findNonstandardResidues()
    fixer.replaceNonstandardResidues()

    # Add missing atoms.
    logger.info('Adding missing atoms...')
    fixer.findMissingAtoms()
    fixer.addMissingAtoms()

    # Remove heterogens.
    logger.info('Removing heterogens...')
    fixer.removeHeterogens(keepWater=crystal_water)

    # Add missing hydrogens.
    logger.info('Adding missing hydrogens appropriate for pH %s', ph)
    fixer.addMissingHydrogens(ph)

    if nbonded in [app.PME, app.CutoffPeriodic, app.Ewald]:
        # Add solvent.
        logger.info('Adding solvent...')
        fixer.addSolvent(padding=pad)

    # Write PDB file.
    logger.info('Writing PDB file to "%s"...', '%s-pdbfixer.pdb' % pdb)
    app.PDBFile.writeFile(fixer.topology, fixer.positions,
                          open('%s-pdbfixer.pdb' % pdb, 'w'))

    # Create OpenMM System.
    logger.info('Creating OpenMM system...')
    system = ff.createSystem(fixer.topology,
                             nonbondedMethod=nbonded,
                             constraints=constraints,
                             rigidWater=True,
                             removeCMMotion=False)

    # Minimimze to update positions.
    logger.info('Minimizing...')
    integrator = mm.VerletIntegrator(1.0 * unit.femtosecond)
    context = mm.Context(system, integrator)
    context.setPositions(fixer.positions)
    mm.LocalEnergyMinimizer.minimize(context)
    # pylint: disable=unexpected-keyword-arg, no-value-for-parameter
    state = context.getState(getPositions=True)
    fixer.positions = state.getPositions()

    # Write final coordinates.
    logger.info('Writing PDB file to "%s"...', '%s-minimized.pdb' % pdb)
    with open('%s-minimized.pdb' % pdb, 'w') as fp:
        app.PDBFile.writeFile(fixer.topology, fixer.positions, fp)

    # Serialize final coordinates.
    logger.info('Serializing to XML...')
    serialize_system(context, system, integrator)
Esempio n. 20
0
def runOneTest(testName, options):
    """Perform a single benchmarking simulation."""
    explicit = (testName in ('rf', 'pme', 'amoebapme'))
    amoeba = (testName in ('amoebagk', 'amoebapme'))
    hydrogenMass = None
    print()
    if amoeba:
        print('Test: %s (epsilon=%g)' % (testName, options.epsilon))
    elif testName == 'pme':
        print('Test: pme (cutoff=%g)' % options.cutoff)
    else:
        print('Test: %s' % testName)
    platform = mm.Platform.getPlatformByName(options.platform)

    # Create the System.

    if amoeba:
        constraints = None
        epsilon = float(options.epsilon)
        if epsilon == 0:
            polarization = 'direct'
        else:
            polarization = 'mutual'
        if explicit:
            ff = app.ForceField('amoeba2009.xml')
            pdb = app.PDBFile('5dfr_solv-cube_equil.pdb')
            cutoff = 0.7 * unit.nanometers
            vdwCutoff = 0.9 * unit.nanometers
            system = ff.createSystem(pdb.topology,
                                     nonbondedMethod=app.PME,
                                     nonbondedCutoff=cutoff,
                                     vdwCutoff=vdwCutoff,
                                     constraints=constraints,
                                     ewaldErrorTolerance=0.00075,
                                     mutualInducedTargetEpsilon=epsilon,
                                     polarization=polarization)
        else:
            ff = app.ForceField('amoeba2009.xml', 'amoeba2009_gk.xml')
            pdb = app.PDBFile('5dfr_minimized.pdb')
            cutoff = 2.0 * unit.nanometers
            vdwCutoff = 1.2 * unit.nanometers
            system = ff.createSystem(pdb.topology,
                                     nonbondedMethod=app.NoCutoff,
                                     constraints=constraints,
                                     mutualInducedTargetEpsilon=epsilon,
                                     polarization=polarization)
        dt = 0.001 * unit.picoseconds
    else:
        if explicit:
            ff = app.ForceField('amber99sb.xml', 'tip3p.xml')
            pdb = app.PDBFile('5dfr_solv-cube_equil.pdb')
            if testName == 'pme':
                method = app.PME
                cutoff = options.cutoff
            else:
                method = app.CutoffPeriodic
                cutoff = 1 * unit.nanometers
        else:
            ff = app.ForceField('amber99sb.xml', 'amber99_obc.xml')
            pdb = app.PDBFile('5dfr_minimized.pdb')
            method = app.CutoffNonPeriodic
            cutoff = 2 * unit.nanometers
        if options.heavy:
            dt = 0.005 * unit.picoseconds
            constraints = app.AllBonds
            hydrogenMass = 4 * unit.amu
        else:
            dt = 0.002 * unit.picoseconds
            constraints = app.HBonds
            hydrogenMass = None
        system = ff.createSystem(pdb.topology,
                                 nonbondedMethod=method,
                                 nonbondedCutoff=cutoff,
                                 constraints=constraints,
                                 hydrogenMass=hydrogenMass)
    print('Step Size: %g fs' % dt.value_in_unit(unit.femtoseconds))
    properties = {}
    initialSteps = 5
    if options.device is not None:
        if platform.getName() == 'CUDA':
            properties['CudaDeviceIndex'] = options.device
        elif platform.getName() == 'OpenCL':
            properties['OpenCLDeviceIndex'] = options.device
        if ',' in options.device or ' ' in options.device:
            initialSteps = 250
    if options.precision is not None:
        if platform.getName() == 'CUDA':
            properties['CudaPrecision'] = options.precision
        elif platform.getName() == 'OpenCL':
            properties['OpenCLPrecision'] = options.precision

    # Run the simulation.

    integ = mm.LangevinIntegrator(300 * unit.kelvin,
                                  91 * (1 / unit.picoseconds), dt)
    integ.setConstraintTolerance(1e-5)
    if len(properties) > 0:
        context = mm.Context(system, integ, platform, properties)
    else:
        context = mm.Context(system, integ, platform)
    context.setPositions(pdb.positions)
    context.setVelocitiesToTemperature(300 * unit.kelvin)
    steps = 20
    while True:
        time = timeIntegration(context, steps, initialSteps)
        if time >= 0.5 * options.seconds:
            break
        if time < 0.5:
            steps = int(
                steps * 1.0 / time
            )  # Integrate enough steps to get a reasonable estimate for how many we'll need.
        else:
            steps = int(steps * options.seconds / time)
    print('Integrated %d steps in %g seconds' % (steps, time))
    print('%g ns/day' %
          (dt * steps * 86400 / time).value_in_unit(unit.nanoseconds))
Esempio n. 21
0
from __future__ import print_function
from simtk.openmm import app
import simtk.openmm as mm
from simtk import unit
import sys
import mbpol

pdb = app.PDBFile("water14_cluster.pdb")
forcefield = app.ForceField("mbpol.xml")
#<MBPolElectrostaticsForce thole-charge-charge="0.4" thole-charge-dipole="0.4" thole-dipole-dipole="0.055" thole-dipole-dipole-singlebond="0.626">
expected = [0.4, 0.4, 0.055, 0.626, 0.055]
#<MBPolElectrostaticsForce thole-charge-charge="1" thole-charge-dipole="2" thole-dipole-dipole="3" thole-dipole-dipole-singlebond="4">
#expected = [1, 2, 3, 4, 3]
for param, expected_param in zip(forcefield._forces[0].thole, expected):
    assert (param == expected_param)
print("Test Passed")
Esempio n. 22
0
def solvate_and_minimize(topology, positions, phase=''):
    """
    Solvate the given system and minimize.

    Parameters
    ----------
    topology : simtk.openmm.Topology
        The topology
    positions : simtk.unit.Quantity of numpy.array of (natoms,3) with units compatible with nanometer.
        The positions
    phase : string, optional, default=''
        The phase prefix to prepend to written files.

    Returns
    -------
    topology : simtk.openmm.app.Topology
        The new Topology object
    system : simtk.openm.System
        The solvated system.
    positions : simtk.unit.Quantity of dimension natoms x 3 with units compatible with angstroms
        The minimized positions.

    """

    # Solvate (if desired) and create system.
    logger.info("Solvating...")
    forcefield = app.ForceField(*ffxmls)
    modeller = app.Modeller(topology, positions)
    modeller.addHydrogens(forcefield=forcefield, pH=pH) # DEBUG
    if is_periodic:
        # Add solvent if in a periodic box.
        modeller.addSolvent(forcefield, padding=padding, model=water_name)
    system = forcefield.createSystem(modeller.topology, nonbondedMethod=nonbonded_method, nonbondedCutoff=nonbonded_cutoff, constraints=constraints)
    if is_periodic:
        system.addForce(openmm.MonteCarloBarostat(pressure, temperature, barostat_frequency))
    logger.info("System has %d atoms." % system.getNumParticles())

    # DEBUG
    print "modeller.topology.chains(): %s" % str([ chain.id for chain in modeller.topology.chains() ])

    # Serialize to XML files.
    logger.info("Serializing to XML...")
    system_filename = os.path.join(workdir, 'system.xml')
    write_file(system_filename, openmm.XmlSerializer.serialize(system))

    if minimize:
        # Create simulation.
        logger.info("Creating simulation...")
        errorTol = 0.001
        integrator = openmm.VariableLangevinIntegrator(temperature, collision_rate, errorTol)
        simulation = app.Simulation(modeller.topology, system, integrator)
        simulation.context.setPositions(modeller.positions)

        # Print potential energy.
        potential = simulation.context.getState(getEnergy=True).getPotentialEnergy()
        logger.info("Potential energy is %12.3f kcal/mol" % (potential / unit.kilocalories_per_mole))

        # Write modeller positions.
        logger.info("Writing modeller output...")
        filename = os.path.join(workdir, phase + 'modeller.pdb')
        app.PDBFile.writeFile(simulation.topology, modeller.positions, open(filename, 'w'))

        # Minimize energy.
        logger.info("Minimizing energy...")
        simulation.minimizeEnergy(maxIterations=max_minimization_iterations)
        #integrator.step(max_minimization_iterations)
        state = simulation.context.getState(getEnergy=True)
        potential_energy = state.getPotentialEnergy()
        if np.isnan(potential_energy / unit.kilocalories_per_mole):
            raise Exception("Potential energy is NaN after minimization.")
        logger.info("Potential energy after minimiziation: %.3f kcal/mol" % (potential_energy / unit.kilocalories_per_mole))
        modeller.positions = simulation.context.getState(getPositions=True).getPositions()

        # Print potential energy.
        potential = simulation.context.getState(getEnergy=True).getPotentialEnergy()
        logger.info("Potential energy is %12.3f kcal/mol" % (potential / unit.kilocalories_per_mole))

        # Write minimized positions.
        filename = os.path.join(workdir, phase + 'minimized.pdb')
        app.PDBFile.writeFile(simulation.topology, modeller.positions, open(filename, 'w'))

        # Clean up
        del simulation

    # Return the modeller instance.
    return [modeller.topology, system, modeller.positions]
molecule_structure = forcefield.create_parmed_structure(topology=molecule.to_topology(), positions=molecule.positions)
print('Molecule:', molecule_structure)

#
# Load and parameterize the protein
#

# Load the protein topology
protein_pdb_filename = get_data_filename('proteins/T4-protein.pdb')
protein_pdbfile = app.PDBFile(protein_pdb_filename)

# Load the AMBER protein force field, along with a solvent force field
from simtk.openmm import app
protein_forcefield = 'amber99sbildn.xml'
solvent_forcefield = 'tip3p.xml'
forcefield = app.ForceField(protein_forcefield, solvent_forcefield)

# Parameterize the protein
protein_system = forcefield.createSystem(proteinpdb.topology)

# Create a ParmEd Structure for the protein
protein_structure = parmed.openmm.load_topology(proteinpdb.topology,
                                                protein_system,
                                                xyz=proteinpdb.positions)
print('Protein:', protein_structure)

# Combine the ParmEd Structure objects to produce a fully parameterized complex
# that can now be exported to AMBER, CHARMM, OpenMM, and other packages
# Note that the addition should always add the small molecule second so the box vectors if the first item (the protein) are to be preserved
complex_structure = protein_structure + molecule_structure
print('Complex:', complex_structure)
Esempio n. 24
0
    def __init__(self, molecules: List[str], output_filename: str, ncmc_switching_times: Dict[str, int], equilibrium_steps: Dict[str, int], timestep: unit.Quantity, initial_molecule: str=None, geometry_options: Dict=None):
        self._molecules = [SmallMoleculeSetProposalEngine.canonicalize_smiles(molecule) for molecule in molecules]
        environments = ['explicit', 'vacuum']
        temperature = 298.15 * unit.kelvin
        pressure = 1.0 * unit.atmospheres
        constraints = app.HBonds
        self._storage = NetCDFStorage(output_filename)
        self._ncmc_switching_times = ncmc_switching_times
        self._n_equilibrium_steps = equilibrium_steps
        self._geometry_options = geometry_options

        # Create a system generator for our desired forcefields.
        from perses.rjmc.topology_proposal import SystemGenerator
        system_generators = dict()
        from pkg_resources import resource_filename
        gaff_xml_filename = resource_filename('perses', 'data/gaff.xml')
        barostat = openmm.MonteCarloBarostat(pressure, temperature)
        system_generators['explicit'] = SystemGenerator([gaff_xml_filename, 'tip3p.xml'],
                                                        forcefield_kwargs={'nonbondedMethod': app.PME,
                                                                           'nonbondedCutoff': 9.0 * unit.angstrom,
                                                                           'implicitSolvent': None,
                                                                           'constraints': constraints,
                                                                           'ewaldErrorTolerance': 1e-5,
                                                                           'hydrogenMass': 3.0*unit.amu},
                                                        barostat=barostat)
        system_generators['vacuum'] = SystemGenerator([gaff_xml_filename],
                                                      forcefield_kwargs={'nonbondedMethod': app.NoCutoff,
                                                                         'implicitSolvent': None,
                                                                         'constraints': constraints,
                                                                         'hydrogenMass': 3.0*unit.amu})

        #
        # Create topologies and positions
        #
        topologies = dict()
        positions = dict()

        from openmoltools import forcefield_generators
        forcefield = app.ForceField(gaff_xml_filename, 'tip3p.xml')
        forcefield.registerTemplateGenerator(forcefield_generators.gaffTemplateGenerator)

        # Create molecule in vacuum.
        from perses.utils.openeye import extractPositionsFromOEMol
        from openmoltools.openeye import smiles_to_oemol, generate_conformers
        if initial_molecule:
            smiles = initial_molecule
        else:
            smiles = np.random.choice(molecules)
        molecule = smiles_to_oemol(smiles)
        molecule = generate_conformers(molecule, max_confs=1)
        topologies['vacuum'] = forcefield_generators.generateTopologyFromOEMol(molecule)
        positions['vacuum'] = extractPositionsFromOEMol(molecule)

        # Create molecule in solvent.
        modeller = app.Modeller(topologies['vacuum'], positions['vacuum'])
        modeller.addSolvent(forcefield, model='tip3p', padding=9.0 * unit.angstrom)
        topologies['explicit'] = modeller.getTopology()
        positions['explicit'] = modeller.getPositions()

        # Set up the proposal engines.
        proposal_metadata = {}
        proposal_engines = dict()

        for environment in environments:
            proposal_engines[environment] = SmallMoleculeSetProposalEngine(self._molecules,
                                                                               system_generators[environment])

        # Generate systems
        systems = dict()
        for environment in environments:
            systems[environment] = system_generators[environment].build_system(topologies[environment])

        # Define thermodynamic state of interest.

        thermodynamic_states = dict()
        thermodynamic_states['explicit'] = states.ThermodynamicState(system=systems['explicit'],
                                                                     temperature=temperature, pressure=pressure)
        thermodynamic_states['vacuum'] = states.ThermodynamicState(system=systems['vacuum'], temperature=temperature)

        # Create SAMS samplers
        from perses.samplers.samplers import ExpandedEnsembleSampler, SAMSSampler
        mcmc_samplers = dict()
        exen_samplers = dict()
        sams_samplers = dict()
        for environment in environments:
            storage = NetCDFStorageView(self._storage, envname=environment)

            if self._geometry_options:
                n_torsion_divisions = self._geometry_options['n_torsion_divsions'][environment]
                use_sterics = self._geometry_options['use_sterics'][environment]

            else:
                n_torsion_divisions = 180
                use_sterics = False

            geometry_engine = geometry.FFAllAngleGeometryEngine(storage=storage, n_torsion_divisions=n_torsion_divisions, use_sterics=use_sterics)
            move = mcmc.LangevinSplittingDynamicsMove(timestep=timestep, splitting="V R O R V",
                                                       n_restart_attempts=10)
            chemical_state_key = proposal_engines[environment].compute_state_key(topologies[environment])
            if environment == 'explicit':
                sampler_state = states.SamplerState(positions=positions[environment],
                                                    box_vectors=systems[environment].getDefaultPeriodicBoxVectors())
            else:
                sampler_state = states.SamplerState(positions=positions[environment])
            mcmc_samplers[environment] = mcmc.MCMCSampler(thermodynamic_states[environment], sampler_state, move)


            exen_samplers[environment] = ExpandedEnsembleSampler(mcmc_samplers[environment], topologies[environment],
                                                                 chemical_state_key, proposal_engines[environment],
                                                                 geometry_engine,
                                                                 options={'nsteps': self._ncmc_switching_times[environment]}, storage=storage, ncmc_write_interval=self._ncmc_switching_times[environment])
            exen_samplers[environment].verbose = True
            sams_samplers[environment] = SAMSSampler(exen_samplers[environment], storage=storage)
            sams_samplers[environment].verbose = True

        # Create test MultiTargetDesign sampler.
        from perses.samplers.samplers import MultiTargetDesign
        target_samplers = {sams_samplers['explicit']: 1.0, sams_samplers['vacuum']: -1.0}
        designer = MultiTargetDesign(target_samplers, storage=self._storage)

        # Store things.
        self.molecules = molecules
        self.environments = environments
        self.topologies = topologies
        self.positions = positions
        self.system_generators = system_generators
        self.proposal_engines = proposal_engines
        self.thermodynamic_states = thermodynamic_states
        self.mcmc_samplers = mcmc_samplers
        self.exen_samplers = exen_samplers
        self.sams_samplers = sams_samplers
        self.designer = designer
solvated_pdb_filename = 'solvated.pdb'
minimized_pdb_filename = 'minimized.pdb'
equilibrated_pdb_filename = 'equilibrated.pdb'

system_xml_filename = 'system.xml'
integrator_xml_filename = 'integrator.xml'
state_xml_filename = 'state.xml'

# Read in the heavy atom model
pdb_filename = 'input/6nb8_2ajf_complex_fixed.pdb'
print('Loading %s' % pdb_filename)
pdb = app.PDBFile(pdb_filename)

# Use Amber 14SB
print("Loading forcefield: %s" % ffxml_filenames)
forcefield = app.ForceField(*ffxml_filenames)

# Add hydrogens and solvate
print('Adding hydrogens and solvent...')
modeller = app.Modeller(pdb.topology, pdb.positions)
modeller.addHydrogens(forcefield)
modeller.addSolvent(forcefield,
                    model=water_model,
                    padding=solvent_padding,
                    ionicStrength=ionic_strength)
print('System has %d atoms' % modeller.topology.getNumAtoms())

# Write initial model
print('Writing initial solvated system to %s' % output_prefix +
      solvated_pdb_filename)
with open(output_prefix + solvated_pdb_filename, 'w') as outfile:
Esempio n. 26
0
import simtk.openmm as mm
from simtk import unit
import sys
import mbpol

##### Input system in pdb format

# In[ ]:

pdb = app.PDBFile("water14_cluster.pdb")

##### Define the type of potential, first file defines all elements, only the water model is in the second xml file

# In[ ]:

forcefield = app.ForceField(mbpol.__file__.replace('mbpol.py', 'mbpol.xml'))
# use tip4p
#forcefield = app.ForceField("tip4pfb.xml")

##### Create the System, define an integrator, define the Simulation

# In[ ]:

system = forcefield.createSystem(pdb.topology,
                                 nonbondedMethod=app.CutoffNonPeriodic,
                                 nonbondedCutoff=1e3 * unit.nanometer)
integrator = mm.VerletIntegrator(0.00001 * unit.femtoseconds)

# In[ ]:

platform = mm.Platform.getPlatformByName('Reference')
Esempio n. 27
0
def test_mutate_from_every_amino_to_every_other():
    """
    Make sure mutations are successful between every possible pair of before-and-after residues
    Mutate Ecoli F-ATPase alpha subunit to all 20 amino acids (test going FROM all possibilities)
    Mutate each residue to all 19 alternatives
    """
    import perses.rjmc.topology_proposal as topology_proposal

    aminos = [
        'ALA', 'ARG', 'ASN', 'ASP', 'CYS', 'GLN', 'GLU', 'GLY', 'HIS', 'ILE',
        'LEU', 'LYS', 'MET', 'PHE', 'PRO', 'SER', 'THR', 'TRP', 'TYR', 'VAL'
    ]

    failed_mutants = 0

    pdbid = "2A7U"
    topology, positions = load_pdbid_to_openmm(pdbid)
    modeller = app.Modeller(topology, positions)
    for chain in modeller.topology.chains():
        pass

    modeller.delete([chain])

    ff_filename = "amber99sbildn.xml"
    max_point_mutants = 1

    ff = app.ForceField(ff_filename)
    system = ff.createSystem(modeller.topology)
    chain_id = 'A'

    metadata = dict()

    system_generator = topology_proposal.SystemGenerator([ff_filename])

    pm_top_engine = topology_proposal.PointMutationEngine(
        modeller.topology,
        system_generator,
        chain_id,
        proposal_metadata=metadata,
        max_point_mutants=max_point_mutants,
        always_change=True)

    current_system = system
    current_topology = modeller.topology
    current_positions = modeller.positions

    pm_top_engine._allowed_mutations = list()
    for k, proposed_amino in enumerate(aminos):
        pm_top_engine._allowed_mutations.append((str(k + 2), proposed_amino))
    pm_top_proposal = pm_top_engine.propose(current_system, current_topology)
    current_system = pm_top_proposal.new_system
    current_topology = pm_top_proposal.new_topology

    for chain in current_topology.chains():
        if chain.id == chain_id:
            # num_residues : int
            num_residues = len(chain._residues)
            break
    new_sequence = list()
    for residue in current_topology.residues():
        if residue.index == 0:
            continue
        if residue.index == (num_residues - 1):
            continue
        if residue.name in ['HID', 'HIE']:
            residue.name = 'HIS'
        new_sequence.append(residue.name)
    for i in range(len(aminos)):
        assert new_sequence[i] == aminos[i]

    pm_top_engine = topology_proposal.PointMutationEngine(
        current_topology,
        system_generator,
        chain_id,
        proposal_metadata=metadata,
        max_point_mutants=max_point_mutants)

    from perses.rjmc.topology_proposal import append_topology
    old_topology = app.Topology()
    append_topology(old_topology, current_topology)
    new_topology = app.Topology()
    append_topology(new_topology, current_topology)

    old_chemical_state_key = pm_top_engine.compute_state_key(old_topology)

    for chain in new_topology.chains():
        if chain.id == chain_id:
            # num_residues : int
            num_residues = len(chain._residues)
            break
    for proposed_location in range(1, num_residues - 1):
        print('Making mutations at residue %s' % proposed_location)
        original_residue_name = chain._residues[proposed_location].name
        matching_amino_found = 0
        for proposed_amino in aminos:
            pm_top_engine._allowed_mutations = [(str(proposed_location + 1),
                                                 proposed_amino)]
            new_topology = app.Topology()
            append_topology(new_topology, current_topology)
            old_system = current_system
            old_topology_natoms = sum([1 for atom in old_topology.atoms()])
            old_system_natoms = old_system.getNumParticles()
            if old_topology_natoms != old_system_natoms:
                msg = 'PolymerProposalEngine: old_topology has %d atoms, while old_system has %d atoms' % (
                    old_topology_natoms, old_system_natoms)
                raise Exception(msg)
            metadata = dict()

            for atom in new_topology.atoms():
                atom.old_index = atom.index

            index_to_new_residues, metadata = pm_top_engine._choose_mutant(
                new_topology, metadata)
            if len(index_to_new_residues) == 0:
                matching_amino_found += 1
                continue
            print('Mutating %s to %s' %
                  (original_residue_name, proposed_amino))

            residue_map = pm_top_engine._generate_residue_map(
                new_topology, index_to_new_residues)
            for res_pair in residue_map:
                residue = res_pair[0]
                name = res_pair[1]
                assert residue.index in index_to_new_residues.keys()
                assert index_to_new_residues[residue.index] == name
                assert residue.name + '-' + str(
                    residue.id) + '-' + name in metadata['mutations']

            new_topology, missing_atoms = pm_top_engine._delete_excess_atoms(
                new_topology, residue_map)
            new_topology = pm_top_engine._add_new_atoms(
                new_topology, missing_atoms, residue_map)
            for res_pair in residue_map:
                residue = res_pair[0]
                name = res_pair[1]
                assert residue.name == name

            atom_map = pm_top_engine._construct_atom_map(
                residue_map, old_topology, index_to_new_residues, new_topology)
            templates = pm_top_engine._ff.getMatchingTemplates(new_topology)
            assert [
                templates[index].name == residue.name
                for index, (residue, name) in enumerate(residue_map)
            ]

            new_chemical_state_key = pm_top_engine.compute_state_key(
                new_topology)
            new_system = pm_top_engine._system_generator.build_system(
                new_topology)
            pm_top_proposal = topology_proposal.TopologyProposal(
                new_topology=new_topology,
                new_system=new_system,
                old_topology=old_topology,
                old_system=old_system,
                old_chemical_state_key=old_chemical_state_key,
                new_chemical_state_key=new_chemical_state_key,
                logp_proposal=0.0,
                new_to_old_atom_map=atom_map)

        assert matching_amino_found == 1
import mdtraj as md

import numpy as np


# ## Setting up the engine

# Now we set things up for the OpenMM simulation. We will need a `openmm.System` object and an `openmm.Integrator` object.
# 
# To learn more about OpenMM, read the [OpenMM documentation](http://docs.openmm.org). The code we use here is based on output from the convenient web-based [OpenMM builder](http://builder.openmm.org).

# In[2]:


# this cell is all OpenMM specific
forcefield = app.ForceField('amber96.xml', 'tip3p.xml')
pdb = app.PDBFile("AD_initial_frame.pdb")
system = forcefield.createSystem(
    pdb.topology, 
    nonbondedMethod=app.PME, 
    nonbondedCutoff=1.0*unit.nanometers,
    constraints=app.HBonds, 
    rigidWater=True,
    ewaldErrorTolerance=0.0005
)
hi_T_integrator = VVVRIntegrator(
    500*unit.kelvin, 
    1.0/unit.picoseconds, 
    2.0*unit.femtoseconds)
hi_T_integrator.setConstraintTolerance(0.00001)
Esempio n. 29
0
#from mbnrgplugin import MBnrgForce
#system = System()
#force = MBnrgForce()
#system.addForce(force)

from simtk.openmm import app, System
import simtk.openmm as mm
from simtk import unit
import sys
import mbnrg


pdb = app.PDBFile("water3.pdb")
print(pdb.topology)

forcefield = app.ForceField(mbnrg.__file__.replace('mbnrg.py', 'mbnrg.xml'))

system = forcefield.createSystem(pdb.topology)

integrator = mm.VerletIntegrator(0.00001*unit.femtoseconds)
platform = mm.Platform.getPlatformByName('Reference')
simulation = app.Simulation(pdb.topology, system, integrator, platform)
simulation.context.setPositions(pdb.positions)

state = simulation.context.getState(getForces=True, getEnergy=True)
potential_energy = state.getPotentialEnergy()

print("Energy:")
print(potential_energy.in_units_of(unit.kilocalorie_per_mole))
print("Gradients")
kilocalorie_per_mole_per_angstrom = unit.kilocalorie_per_mole/unit.angstrom
Esempio n. 30
0
import parmed
from simtk.openmm import app, XmlSerializer

# convert to sdf first
off_mol = OFFMolecule.from_file("MOL.pdb")
off_mol.to_file("MOL.sdf", "sdf")

# make the qube mol
qb_mol1 = Ligand.from_file("MOL.sdf")
# apply params
OpenFF(qb_mol1)
# write out the params
qb_mol1.write_parameters("temp")

# now load a second molecule
qb_mol2 = Ligand.from_file("MOL.sdf")
# apply params from xml
XML(qb_mol2, input_file="MOL.xml")

# transfer the torsions
qb_mol2.PeriodicTorsionForce = qb_mol1.PeriodicTorsionForce
qb_mol2.combination = "opls"
qb_mol2.write_parameters(name="new")

# now build the parmed system
pdb = app.PDBFile("MOL.pdb")
ff = app.ForceField("new.xml")
system = ff.createSystem(pdb.topology)
p_sys = parmed.openmm.load_topology(pdb.topology, system, xyz=pdb.positions)
p_sys.save("test.prmtop")