pyiron / FAQs

General question board for pyiron users
3 stars 0 forks source link

How to setup constrained atoms in a LAMMPS `jobtype`? #54

Open aageo25 opened 1 month ago

aageo25 commented 1 month ago

I have two constraints I need to implement to certain atoms in my simulation cell.

  1. Keep the atoms completely fixed.
    • I managed that by using FixAtoms attached to my ASE's Atoms object that I later converted with ase_to_pyiron function. I checked the content of control.inp and pyiron successfully created a group called constrainedxyz and then fix constrained xyz setforce 0.0 0.0 0.0
      1. Allow atoms to relax in the xy plane, but not along z
    • My first attempt was to use ASE's FixPlane, but this constrained method is not implemented in pyiron. When I tried converting my ASE's Atoms object to pyiron Atoms, I got UserWarning: Unsupported ASE constraint: FixedPlane

I see that I can achieve (possibly 1 and 2 simultaneously) by adding set_tag in pyiron Atoms object and defining selective_dynamics. Here is where I would like some help.

samwaseda commented 1 month ago

I think you guessed everything correctly. Can you give it a try?

aageo25 commented 1 month ago

I think you guessed everything correctly. Can you give it a try?

I am currently trying, but the problem is that I only get fix constraintxyz constraintxyz setforce 0.0 0.0 0.0 and apparently for all atoms in the cell.

Do I need to specify job.calc_minimize to allow atoms relax? My test job.run() is minimal, and here is the end of my control.inp file after the long list of IDs in the constraintxyz group.

fix ensemble all nve
variable dumptime equal 100
variable thermotime equal 100
fix constraintxyz constraintxyz setforce 0.0 0.0 0.0
dump 1 all custom ${dumptime} dump.out id type xsu ysu zsu fx fy fz vx vy vz
dump_modify 1 sort id format line "%d %d %20.15g %20.15g %20.15g %20.15g %20.15g %20.15g %20.15g %20.15g %20.15g"
thermo_style custom step temp pe etotal pxx pxy pxz pyy pyz pzz vol
thermo_modify format float %20.15g
thermo ${thermotime}
run 0
jan-janssen commented 1 month ago

You can take a look at the corresponding unit test https://github.com/pyiron/pyiron_atomistics/blob/0939b3d341c67bec6f4c0c12660bdaa76c7d0b91/tests/lammps/test_base.py#L61

atoms.add_tag(selective_dynamics=[True, True, True])
atoms.selective_dynamics[1] = [True, True, False]
atoms.selective_dynamics[2] = [True, False, True]
atoms.selective_dynamics[3] = [False, True, True]
atoms.selective_dynamics[4] = [False, True, False]
atoms.selective_dynamics[5] = [False, False, True]
atoms.selective_dynamics[6] = [True, False, False]
atoms.selective_dynamics[7] = [False, False, False]
aageo25 commented 1 month ago

Thanks @jan-janssen . What method would you recommend me to use, add_tag or set_array?

jan-janssen commented 1 month ago

set_array is the more modern ASE compatible command

aageo25 commented 1 month ago

Thanks @jan-janssen . What method would you recommend me to use, add_tag or set_array?

I tried both ways. Here is what I get:

aageo25 commented 1 month ago

You can take a look at the corresponding unit test https://github.com/pyiron/pyiron_atomistics/blob/0939b3d341c67bec6f4c0c12660bdaa76c7d0b91/tests/lammps/test_base.py#L61

atoms.add_tag(selective_dynamics=[True, True, True])
atoms.selective_dynamics[1] = [True, True, False]
atoms.selective_dynamics[2] = [True, False, True]
atoms.selective_dynamics[3] = [False, True, True]
atoms.selective_dynamics[4] = [False, True, False]
atoms.selective_dynamics[5] = [False, False, True]
atoms.selective_dynamics[6] = [True, False, False]
atoms.selective_dynamics[7] = [False, False, False]

I looked it up in the unit test and realized that it is the ASE's Atoms object that receives the add_tag, but I get AttributeError when I try atoms.add_tag(selective_dynamics=[True,True,True]). My ASE version is 3.22.1

aageo25 commented 1 month ago

Thanks @jan-janssen . What method would you recommend me to use, add_tag or set_array?

I tried both ways. Here is what I get:

  • With set_tag defined in ASE's Atoms object then converted to pyrion with ase_to_pyiron, I found no group created in control.inp.
  • With job.structure.add_tag(selective_dynamics=[True, True, True]) followed by manually modifying the list for each id, I get all atoms included in the constrainedxyz group.

UPDATE

The manual constrained worked. I see now in the control.inp only the IDs I asked to constraint.

So the way apparently is using @jan-janssen suggestion with add_tag.

Here is what I get in my tests. The comments in each line is the group created in control.inp

# First all atoms are free to move in any direction
job.structure.add_tag(selective_dynamics=[True, True, True])
job.structure.selective_dynamics[0] = [False, False, False] # group constrainedxyz
job.structure.selective_dynamics[1] = [True, True, False] # group constrainedz
job.structure.selective_dynamics[2] = [False, False, True] # group constrained xy
jan-janssen commented 1 month ago

I looked it up in the unit test and realized that it is the ASE's Atoms object that receives the add_tag

No, it is from pyiron_atomistics.atomistics.structure.atoms import Atoms that is our overloaded version. add_tag was never available in ASE. For ASE you always need set_array.

aageo25 commented 1 month ago

I looked it up in the unit test and realized that it is the ASE's Atoms object that receives the add_tag

No, it is from pyiron_atomistics.atomistics.structure.atoms import Atoms that is our overloaded version. add_tag was never available in ASE. For ASE you always need set_array.

I was initially confused which Atoms object you were referring to, ASE's or pyiron. I looked it up a little more in my notebook today and realized that you meant pyiron's.

What I also noticed was that if I convert with ase_to_pyiron my ASE's Atoms containing an array named selective_dynamics, pyiron does not set_array automatically, so I have to assign set_array in the pyiron's Atoms object, i.e. job.structure.set_array('selective_dynamics', my_ase_atoms.arrays['selective_dynamics'])

Would it be possible for pyiron identify the existense of an array named selective_dynamics and make set_array when I convert my ASE's Atoms? This would ensure a better equivalence between the two Atoms object.

jan-janssen commented 1 month ago

I guess the goal is to replace the pyiron Atoms with ASE Atoms everywhere. This is already done in atomistics and structuretoolkit but it is going to take some more time to clean up pyiron_atomistics.

aageo25 commented 1 month ago

This would be excellent in terms of compatibility between the two libraries/packages. I am looking forward to it. Meanwhile, we can use the workaround for selective_dynamics we discussed here.

Cheers!