├── src ├── __init__.py ├── libs │ ├── __init__.py │ ├── pyquaternion │ │ ├── __init__.py │ │ └── LICENSE.txt │ ├── constants.py │ ├── utils.py │ ├── readers.py │ ├── topology.py │ ├── reader_lammps_init.py │ └── pdb.py ├── scadnano_oxDNA.py ├── oxDNA_LAMMPS.py ├── rpoly_oxDNA.py ├── PDB_oxDNA.py ├── LAMMPS_oxDNA.py ├── oxDNA_PDB.py └── XYZ_oxDNA.py ├── requirements.txt ├── logo.png ├── .gitignore ├── tests ├── LAMMPS_oxDNA │ ├── correct_trajectory_output.top │ ├── correct_output.top │ ├── run_single_conf.sh │ ├── run_trajectory.sh │ ├── correct_output.dat │ ├── trajectory_datafile.dat │ └── init_lammps.dat ├── oxDNA_PDB │ ├── ds.top │ ├── run.sh │ └── ds.dat ├── oxDNA_LAMMPS │ ├── ds.top │ ├── run.sh │ ├── ds.dat │ └── correct_output.dat ├── PDB_oxDNA │ ├── correct_output.top │ ├── run.sh │ └── correct_output.dat ├── Tiamat_oxDNA │ ├── correct_output.top │ ├── run.sh │ ├── correct_output.dat │ └── input.dnajson ├── run_all.sh ├── CanDo_oxDNA │ ├── run.sh │ ├── correct_output.top │ ├── junction.cndo │ └── correct_output.dat ├── cadnano_oxDNA │ ├── run.sh │ ├── correct_output.top │ └── init.json ├── rpoly_oxDNA │ ├── run.sh │ ├── input.rpoly │ └── correct_output.top ├── scadnano_oxDNA │ ├── run.sh │ └── input.scadnano ├── vHelix_oxDNA │ ├── run_no_deletion.sh │ ├── run_with_deletion.sh │ └── correct_output_with_deletion.top ├── XYZ_oxDNA │ ├── run_open.sh │ ├── run_simple.sh │ ├── sequence.dat │ ├── correct_simple_output.top │ ├── centerline.dat │ └── centerline_open.dat └── conf_diff.py ├── .project ├── .pydevproject ├── CHANGELOG ├── .github └── workflows │ └── test.yml └── README.md /src/__init__.py: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /src/libs/__init__.py: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /requirements.txt: -------------------------------------------------------------------------------- 1 | numpy 2 | scadnano 3 | -------------------------------------------------------------------------------- /src/libs/pyquaternion/__init__.py: -------------------------------------------------------------------------------- 1 | from .quaternion import Quaternion 2 | -------------------------------------------------------------------------------- /logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/lorenzo-rovigatti/tacoxDNA/HEAD/logo.png -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Byte-compiled / optimized / DLL files 2 | __pycache__/ 3 | *.py[cod] 4 | *$py.class 5 | .DS_Store 6 | log.dat 7 | -------------------------------------------------------------------------------- /src/libs/constants.py: -------------------------------------------------------------------------------- 1 | mass_in_lammps = 3.1575 2 | inertia_in_lammps = 0.435179 3 | number_oxdna_to_lammps = {0 : 0, 1 : 2, 2 : 1, 3 : 3} 4 | -------------------------------------------------------------------------------- /tests/LAMMPS_oxDNA/correct_trajectory_output.top: -------------------------------------------------------------------------------- 1 | 10 2 2 | 1 A -1 1 3 | 1 C 0 2 4 | 1 G 1 3 5 | 1 T 2 4 6 | 1 A 3 -1 7 | 2 T -1 6 8 | 2 A 5 7 9 | 2 C 6 8 10 | 2 G 7 9 11 | 2 T 8 -1 12 | -------------------------------------------------------------------------------- /tests/oxDNA_PDB/ds.top: -------------------------------------------------------------------------------- 1 | 16 2 2 | 1 A -1 1 3 | 1 G 0 2 4 | 1 C 1 3 5 | 1 T 2 4 6 | 1 C 3 5 7 | 1 C 4 6 8 | 1 A 5 7 9 | 1 C 6 -1 10 | 2 G -1 9 11 | 2 T 8 10 12 | 2 G 9 11 13 | 2 G 10 12 14 | 2 A 11 13 15 | 2 G 12 14 16 | 2 C 13 15 17 | 2 T 14 -1 18 | -------------------------------------------------------------------------------- /tests/oxDNA_LAMMPS/ds.top: -------------------------------------------------------------------------------- 1 | 16 2 2 | 1 A -1 1 3 | 1 G 0 2 4 | 1 C 1 3 5 | 1 T 2 4 6 | 1 C 3 5 7 | 1 C 4 6 8 | 1 A 5 7 9 | 1 C 6 -1 10 | 2 G -1 9 11 | 2 T 8 10 12 | 2 G 9 11 13 | 2 G 10 12 14 | 2 A 11 13 15 | 2 G 12 14 16 | 2 C 13 15 17 | 2 T 14 -1 18 | -------------------------------------------------------------------------------- /tests/LAMMPS_oxDNA/correct_output.top: -------------------------------------------------------------------------------- 1 | 16 2 2 | 1 A -1 1 3 | 1 G 0 2 4 | 1 C 1 3 5 | 1 T 2 4 6 | 1 C 3 5 7 | 1 C 4 6 8 | 1 A 5 7 9 | 1 C 6 -1 10 | 2 G -1 9 11 | 2 T 8 10 12 | 2 G 9 11 13 | 2 G 10 12 14 | 2 A 11 13 15 | 2 G 12 14 16 | 2 C 13 15 17 | 2 T 14 -1 18 | -------------------------------------------------------------------------------- /tests/PDB_oxDNA/correct_output.top: -------------------------------------------------------------------------------- 1 | 24 2 2 | 1 G -1 1 3 | 1 C 0 2 4 | 1 G 1 3 5 | 1 C 2 4 6 | 1 T 3 5 7 | 1 T 4 6 8 | 1 A 5 7 9 | 1 A 6 8 10 | 1 G 7 9 11 | 1 C 8 10 12 | 1 G 9 11 13 | 1 C 10 -1 14 | 2 G -1 13 15 | 2 C 12 14 16 | 2 G 13 15 17 | 2 C 14 16 18 | 2 T 15 17 19 | 2 T 16 18 20 | 2 A 17 19 21 | 2 A 18 20 22 | 2 G 19 21 23 | 2 C 20 22 24 | 2 G 21 23 25 | 2 C 22 -1 26 | -------------------------------------------------------------------------------- /tests/Tiamat_oxDNA/correct_output.top: -------------------------------------------------------------------------------- 1 | 26 2 2 | 1 G -1 1 3 | 1 G 0 2 4 | 1 A 1 3 5 | 1 G 2 4 6 | 1 A 3 5 7 | 1 A 4 6 8 | 1 A 5 7 9 | 1 G 6 8 10 | 1 A 7 9 11 | 1 A 8 10 12 | 1 A 9 11 13 | 1 G 10 12 14 | 1 A 11 -1 15 | 2 T -1 14 16 | 2 C 13 15 17 | 2 T 14 16 18 | 2 U 15 17 19 | 2 U 16 18 20 | 2 C 17 19 21 | 2 U 18 20 22 | 2 U 19 21 23 | 2 U 20 22 24 | 2 C 21 23 25 | 2 T 22 24 26 | 2 C 23 25 27 | 2 C 24 -1 -------------------------------------------------------------------------------- /tests/run_all.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | passed=0 4 | tot=0 5 | for f in $(ls -1 */*.sh) 6 | do 7 | d=$(dirname $f) 8 | cd $d 9 | 10 | tot=$[tot + 1] 11 | 12 | bash $(basename $f) &> log.dat 13 | 14 | if [ $? -eq 0 ] 15 | then 16 | passed=$[passed + 1] 17 | else 18 | echo "$d: TEST FAILED" 19 | exit 1 20 | fi 21 | 22 | cd .. 23 | done 24 | 25 | echo "$passed/$tot TESTS PASSED" 26 | exit 0 27 | -------------------------------------------------------------------------------- /.project: -------------------------------------------------------------------------------- 1 | 2 | 3 | tacoxDNA 4 | 5 | 6 | 7 | 8 | 9 | org.python.pydev.PyDevBuilder 10 | 11 | 12 | 13 | 14 | 15 | org.python.pydev.pythonNature 16 | 17 | 18 | -------------------------------------------------------------------------------- /.pydevproject: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | /${PROJECT_DIR_NAME}/src 5 | 6 | python interpreter 7 | python3 8 | 9 | -------------------------------------------------------------------------------- /tests/oxDNA_PDB/run.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | CORRECT_OUTPUT="correct_output.pdb" 4 | OUTPUT="ds.dat.pdb" 5 | 6 | if [ ! -s ds.dat ] || [ ! -s ds.top ] 7 | then 8 | echo "Can't find input files. Are you sure you are in the right folder?" 9 | exit 1 10 | fi 11 | 12 | rm $OUTPUT 2> /dev/null 13 | python3 ../../src/oxDNA_PDB.py ds.top ds.dat 53 14 | diff_lines=$(diff $CORRECT_OUTPUT $OUTPUT) 15 | 16 | if [ $? -ne 0 ] 17 | then 18 | echo "TEST FAILED"; 19 | exit 1 20 | else 21 | echo "TEST PASSED"; 22 | rm $OUTPUT 23 | exit 0 24 | fi 25 | -------------------------------------------------------------------------------- /tests/oxDNA_LAMMPS/run.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | CORRECT_OUTPUT="correct_output.dat" 4 | OUTPUT="ds.dat.lammps" 5 | 6 | if [ ! -s ds.dat ] || [ ! -s ds.top ] 7 | then 8 | echo "Can't find input files. Are you sure you are in the right folder?" 9 | exit 1 10 | fi 11 | 12 | rm $OUTPUT 2> /dev/null 13 | python3 ../../src/oxDNA_LAMMPS.py ds.top ds.dat 14 | diff_lines=$(diff $CORRECT_OUTPUT $OUTPUT) 15 | 16 | if [ $? -ne 0 ] 17 | then 18 | echo "TEST FAILED"; 19 | exit 1 20 | else 21 | echo "TEST PASSED"; 22 | rm $OUTPUT 23 | exit 0 24 | fi 25 | -------------------------------------------------------------------------------- /CHANGELOG: -------------------------------------------------------------------------------- 1 | v 1.1 (19th February 2021) 2 | - Port the code to Python 3 3 | - Normalise the usage and output of all the different tools 4 | - Add a vHelix -> oxDNA converter 5 | - Add a rpoly -> oxDNA converter 6 | - Make the LAMMPS -> oxDNA converter support the conversion of whole trajectory files 7 | - Add an option to the cadnano converter to output an oxview-related file 8 | - Add RNA support to the PDB reader 9 | - Improve the parsing of PDB files 10 | - Fix several bugs in the PDB -> oxDNA and oxDNA -> PDB converters 11 | - Fix several bugs in the cadnano converter 12 | 13 | v 1.0 (19th June 2019) 14 | - First release 15 | -------------------------------------------------------------------------------- /.github/workflows/test.yml: -------------------------------------------------------------------------------- 1 | name: Test the package 2 | 3 | on: 4 | workflow_dispatch: 5 | 6 | push: 7 | branches: 8 | - master 9 | 10 | jobs: 11 | 12 | build: 13 | runs-on: ubuntu-latest 14 | 15 | steps: 16 | - uses: actions/checkout@v2 17 | 18 | - name: Set up Python 19 | uses: actions/setup-python@v2 20 | with: 21 | python-version: "3.10" 22 | 23 | - name: Install dependencies 24 | run: | 25 | python -m pip install -r requirements.txt 26 | 27 | - name: Run tests 28 | run: | 29 | pushd tests 30 | bash run_all.sh 31 | popd 32 | -------------------------------------------------------------------------------- /tests/PDB_oxDNA/run.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | CORRECT_OUTPUT="correct_output.dat" 4 | CORRECT_TOP="correct_output.top" 5 | OUTPUT_CONF="input.pdb.oxdna" 6 | OUTPUT_TOP="input.pdb.top" 7 | CONF_DIFF_BIN="python3 ../conf_diff.py" 8 | 9 | if [ ! -s input.pdb ] 10 | then 11 | echo "Can't find the input file. Are you sure you are in the right folder?" 12 | exit 1 13 | fi 14 | 15 | rm $OUTPUT_CONF $OUTPUT_TOP 2> /dev/null 16 | python3 ../../src/PDB_oxDNA.py input.pdb 53 17 | ($CONF_DIFF_BIN $CORRECT_OUTPUT $OUTPUT_CONF > /dev/null) && (diff $CORRECT_TOP $OUTPUT_TOP > /dev/null) 18 | 19 | if [ $? -ne 0 ] 20 | then 21 | echo "TEST FAILED"; 22 | exit 1 23 | else 24 | echo "TEST PASSED"; 25 | rm $OUTPUT_CONF $OUTPUT_TOP 26 | exit 0 27 | fi 28 | -------------------------------------------------------------------------------- /tests/CanDo_oxDNA/run.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | CORRECT_OUTPUT="correct_output.dat" 4 | CORRECT_TOP="correct_output.top" 5 | OUTPUT_CONF="junction.cndo.oxdna" 6 | OUTPUT_TOP="junction.cndo.top" 7 | CONF_DIFF_BIN="python3 ../conf_diff.py" 8 | 9 | if [ ! -s junction.cndo ] 10 | then 11 | echo "Can't find input file. Are you sure you are in the right folder?" 12 | exit 1 13 | fi 14 | 15 | rm $OUTPUT_CONF $OUTPUT_TOP 2> /dev/null 16 | python3 ../../src/CanDo_oxDNA.py junction.cndo 17 | ($CONF_DIFF_BIN $CORRECT_OUTPUT $OUTPUT_CONF > /dev/null) && (diff $CORRECT_TOP $OUTPUT_TOP > /dev/null) 18 | 19 | if [ $? -ne 0 ] 20 | then 21 | echo "TEST FAILED"; 22 | exit 1 23 | else 24 | echo "TEST PASSED"; 25 | rm $OUTPUT_CONF $OUTPUT_TOP 26 | exit 0 27 | fi 28 | -------------------------------------------------------------------------------- /tests/cadnano_oxDNA/run.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | CORRECT_OUTPUT="correct_output.dat" 4 | CORRECT_TOP="correct_output.top" 5 | OUTPUT_CONF="init.json.oxdna" 6 | OUTPUT_TOP="init.json.top" 7 | CONF_DIFF_BIN="python3 ../conf_diff.py" 8 | 9 | if [ ! -s init.json ] 10 | then 11 | echo "Can't find input file. Are you sure you are in the right folder?" 12 | exit 1 13 | fi 14 | 15 | rm $OUTPUT_CONF $OUTPUT_TOP 2> /dev/null 16 | python3 ../../src/cadnano_oxDNA.py init.json sq --seed 123456 17 | ($CONF_DIFF_BIN $CORRECT_OUTPUT $OUTPUT_CONF > /dev/null) && (diff $CORRECT_TOP $OUTPUT_TOP > /dev/null) 18 | 19 | if [ $? -ne 0 ] 20 | then 21 | echo "TEST FAILED"; 22 | exit 1 23 | else 24 | echo "TEST PASSED"; 25 | rm $OUTPUT_CONF $OUTPUT_TOP 26 | exit 0 27 | fi 28 | -------------------------------------------------------------------------------- /tests/rpoly_oxDNA/run.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | CORRECT_OUTPUT="correct_output.dat" 4 | CORRECT_TOP="correct_output.top" 5 | OUTPUT_CONF="input.rpoly.oxdna" 6 | OUTPUT_TOP="input.rpoly.top" 7 | CONF_DIFF_BIN="python3 ../conf_diff.py" 8 | 9 | if [ ! -s input.rpoly ] 10 | then 11 | echo "Can't find the input file. Are you sure you are in the right folder?" 12 | exit 1 13 | fi 14 | 15 | rm $OUTPUT_CONF $OUTPUT_TOP 2> /dev/null 16 | python3 ../../src/rpoly_oxDNA.py -e 123456 input.rpoly 17 | ($CONF_DIFF_BIN $CORRECT_OUTPUT $OUTPUT_CONF > /dev/null) && (diff $CORRECT_TOP $OUTPUT_TOP > /dev/null) 18 | 19 | if [ $? -ne 0 ] 20 | then 21 | echo "TEST FAILED"; 22 | exit 1 23 | else 24 | echo "TEST PASSED"; 25 | rm $OUTPUT_CONF $OUTPUT_TOP 26 | exit 0 27 | fi 28 | -------------------------------------------------------------------------------- /tests/scadnano_oxDNA/run.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | CORRECT_OUTPUT="correct_output.dat" 4 | CORRECT_TOP="correct_output.top" 5 | OUTPUT_CONF="input.scadnano.oxdna" 6 | OUTPUT_TOP="input.scadnano.top" 7 | CONF_DIFF_BIN="python3 ../conf_diff.py" 8 | 9 | if [ ! -s input.scadnano ] 10 | then 11 | echo "Can't find the input file. Are you sure you are in the right folder?" 12 | exit 1 13 | fi 14 | 15 | rm $OUTPUT_CONF $OUTPUT_TOP 2> /dev/null 16 | python3 ../../src/scadnano_oxDNA.py input.scadnano 17 | ($CONF_DIFF_BIN $CORRECT_OUTPUT $OUTPUT_CONF > /dev/null) && (diff $CORRECT_TOP $OUTPUT_TOP > /dev/null) 18 | 19 | if [ $? -ne 0 ] 20 | then 21 | echo "TEST FAILED"; 22 | exit 1 23 | else 24 | echo "TEST PASSED"; 25 | rm $OUTPUT_CONF $OUTPUT_TOP 26 | exit 0 27 | fi 28 | -------------------------------------------------------------------------------- /tests/LAMMPS_oxDNA/run_single_conf.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | CORRECT_OUTPUT="correct_output.dat" 4 | CORRECT_TOP="correct_output.top" 5 | OUTPUT_CONF="init_lammps.dat.oxdna" 6 | OUTPUT_TOP="init_lammps.dat.top" 7 | CONF_DIFF_BIN="python3 ../conf_diff.py" 8 | 9 | if [ ! -s init_lammps.dat ] 10 | then 11 | echo "Can't find input file. Are you sure you are in the right folder?" 12 | exit 1 13 | fi 14 | 15 | rm $OUTPUT_CONF $OUTPUT_TOP 2> /dev/null 16 | python3 ../../src/LAMMPS_oxDNA.py init_lammps.dat 17 | ($CONF_DIFF_BIN $CORRECT_OUTPUT $OUTPUT_CONF > /dev/null) && (diff $CORRECT_TOP $OUTPUT_TOP > /dev/null) 18 | 19 | if [ $? -ne 0 ] 20 | then 21 | echo "TEST FAILED"; 22 | exit 1 23 | else 24 | echo "TEST PASSED"; 25 | rm $OUTPUT_CONF $OUTPUT_TOP 26 | exit 0 27 | fi 28 | -------------------------------------------------------------------------------- /tests/Tiamat_oxDNA/run.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | CORRECT_OUTPUT="correct_output.dat" 4 | CORRECT_TOP="correct_output.top" 5 | OUTPUT_CONF="input.dnajson.oxdna" 6 | OUTPUT_TOP="input.dnajson.top" 7 | CONF_DIFF_BIN="python3 ../conf_diff.py" 8 | 9 | if [ ! -s input.dnajson ] 10 | then 11 | echo "Can't find the input file. Are you sure you are in the right folder?" 12 | exit 1 13 | fi 14 | 15 | rm $OUTPUT_CONF $OUTPUT_TOP 2> /dev/null 16 | python3 ../../src/Tiamat_oxDNA.py --molecule=DNA --tiamat-version=2 input.dnajson 17 | ($CONF_DIFF_BIN $CORRECT_OUTPUT $OUTPUT_CONF > /dev/null) && (diff $CORRECT_TOP $OUTPUT_TOP > /dev/null) 18 | 19 | if [ $? -ne 0 ] 20 | then 21 | echo "TEST FAILED"; 22 | exit 1 23 | else 24 | echo "TEST PASSED"; 25 | rm $OUTPUT_CONF $OUTPUT_TOP 26 | exit 0 27 | fi 28 | -------------------------------------------------------------------------------- /tests/LAMMPS_oxDNA/run_trajectory.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | CORRECT_OUTPUT="correct_trajectory_output.dat" 4 | CORRECT_TOP="correct_trajectory_output.top" 5 | OUTPUT_CONF="trajectory_datafile.dat.oxdna" 6 | OUTPUT_TOP="trajectory_datafile.dat.top" 7 | CONF_DIFF_BIN="python3 ../conf_diff.py" 8 | 9 | if [ ! -s init_lammps.dat ] 10 | then 11 | echo "Can't find input file. Are you sure you are in the right folder?" 12 | exit 1 13 | fi 14 | 15 | rm $OUTPUT_CONF $OUTPUT_TOP 2> /dev/null 16 | python3 ../../src/LAMMPS_oxDNA.py trajectory_datafile.dat trajectory.dat 17 | ($CONF_DIFF_BIN $CORRECT_OUTPUT $OUTPUT_CONF > /dev/null) && (diff $CORRECT_TOP $OUTPUT_TOP > /dev/null) 18 | 19 | if [ $? -ne 0 ] 20 | then 21 | echo "TEST FAILED"; 22 | exit 1 23 | else 24 | echo "TEST PASSED"; 25 | rm $OUTPUT_CONF $OUTPUT_TOP 26 | exit 0 27 | fi 28 | -------------------------------------------------------------------------------- /tests/vHelix_oxDNA/run_no_deletion.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | INPUT="input_no_deletion.ma" 4 | CORRECT_OUTPUT="correct_output_no_deletion.dat" 5 | CORRECT_TOP="correct_output_no_deletion.top" 6 | OUTPUT_CONF="input_no_deletion.ma.oxdna" 7 | OUTPUT_TOP="input_no_deletion.ma.top" 8 | CONF_DIFF_BIN="python3 ../conf_diff.py" 9 | 10 | if [ ! -s $INPUT ] 11 | then 12 | echo "Can't find the input file. Are you sure you are in the right folder?" 13 | exit 1 14 | fi 15 | 16 | rm $OUTPUT_CONF $OUTPUT_TOP 2> /dev/null 17 | python3 ../../src/vHelix_oxDNA.py -e 12345 $INPUT 18 | # we don't check the topology in this case 19 | ($CONF_DIFF_BIN $CORRECT_OUTPUT $OUTPUT_CONF > /dev/null) 20 | 21 | if [ $? -ne 0 ] 22 | then 23 | echo "TEST FAILED"; 24 | exit 1 25 | else 26 | echo "TEST PASSED"; 27 | rm $OUTPUT_CONF $OUTPUT_TOP 28 | exit 0 29 | fi 30 | -------------------------------------------------------------------------------- /tests/vHelix_oxDNA/run_with_deletion.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | INPUT="input_with_deletion.ma" 4 | CORRECT_OUTPUT="correct_output_with_deletion.dat" 5 | CORRECT_TOP="correct_output_with_deletion.top" 6 | OUTPUT_CONF="input_with_deletion.ma.oxdna" 7 | OUTPUT_TOP="input_with_deletion.ma.top" 8 | CONF_DIFF_BIN="python3 ../conf_diff.py" 9 | 10 | if [ ! -s $INPUT ] 11 | then 12 | echo "Can't find the input file. Are you sure you are in the right folder?" 13 | exit 1 14 | fi 15 | 16 | rm $OUTPUT_CONF $OUTPUT_TOP 2> /dev/null 17 | python3 ../../src/vHelix_oxDNA.py -e 12345 $INPUT 18 | # we don't check the topology in this case 19 | ($CONF_DIFF_BIN $CORRECT_OUTPUT $OUTPUT_CONF > /dev/null) 20 | 21 | if [ $? -ne 0 ] 22 | then 23 | echo "TEST FAILED"; 24 | exit 1 25 | else 26 | echo "TEST PASSED"; 27 | rm $OUTPUT_CONF $OUTPUT_TOP 28 | exit 0 29 | fi -------------------------------------------------------------------------------- /tests/XYZ_oxDNA/run_open.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | CORRECT_OUTPUT_CONF="correct_open_output.oxdna" 4 | CORRECT_OUTPUT_TOP="correct_open_output.top" 5 | OUTPUT_CONF="centerline_open.dat.oxdna" 6 | OUTPUT_TOP="centerline_open.dat.top" 7 | CONF_DIFF_BIN="python3 ../conf_diff.py" 8 | 9 | if [ ! -s centerline_open.dat ] 10 | then 11 | echo "Can't find input files. Are you sure you are in the right folder?" 12 | exit 1 13 | fi 14 | 15 | rm $OUTPUT_CONF $OUTPUT_TOP 2> /dev/null 16 | python3 ../../src/XYZ_oxDNA.py centerline_open.dat -p 0.1 --dsDNA --open --seed=1000 17 | ($CONF_DIFF_BIN $CORRECT_OUTPUT_CONF $OUTPUT_CONF > /dev/null) && (diff $CORRECT_OUTPUT_TOP $OUTPUT_TOP > /dev/null) 18 | 19 | if [ $? -ne 0 ] 20 | then 21 | echo "TEST FAILED"; 22 | exit 1 23 | else 24 | echo "TEST PASSED"; 25 | rm $OUTPUT_CONF $OUTPUT_TOP 26 | exit 0 27 | fi 28 | -------------------------------------------------------------------------------- /tests/XYZ_oxDNA/run_simple.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | 3 | CORRECT_OUTPUT_CONF="correct_simple_output.oxdna" 4 | CORRECT_OUTPUT_TOP="correct_simple_output.top" 5 | OUTPUT_CONF="centerline.dat.oxdna" 6 | OUTPUT_TOP="centerline.dat.top" 7 | CONF_DIFF_BIN="python3 ../conf_diff.py" 8 | 9 | if [ ! -s centerline.dat ] || [ ! -s sequence.dat ] 10 | then 11 | echo "Can't find input files. Are you sure you are in the right folder?" 12 | exit 1 13 | fi 14 | 15 | rm $OUTPUT_CONF $OUTPUT_TOP 2> /dev/null 16 | python3 ../../src/XYZ_oxDNA.py centerline.dat -p 0.05 -q sequence.dat --dsDNA --closed 17 | ($CONF_DIFF_BIN $CORRECT_OUTPUT_CONF $OUTPUT_CONF > /dev/null) && (diff $CORRECT_OUTPUT_TOP $OUTPUT_TOP > /dev/null) 18 | 19 | if [ $? -ne 0 ] 20 | then 21 | echo "TEST FAILED"; 22 | exit 1 23 | else 24 | echo "TEST PASSED"; 25 | rm $OUTPUT_CONF $OUTPUT_TOP 26 | exit 0 27 | fi 28 | -------------------------------------------------------------------------------- /src/scadnano_oxDNA.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import scadnano as sc 4 | import argparse 5 | import os 6 | 7 | if __name__ == '__main__': 8 | parser = argparse.ArgumentParser(description="scadnano -> oxDNA converter") 9 | parser.add_argument("scadnano_file", help="The scadnano input design") 10 | 11 | args = parser.parse_args() 12 | scadnano_file = args.scadnano_file 13 | 14 | design = sc.Design.from_scadnano_file(scadnano_file) 15 | configuration, topology = design.to_oxdna_format() 16 | 17 | basename = os.path.basename(scadnano_file) 18 | topology_file = basename + ".top" 19 | configuration_file = basename + ".oxdna" 20 | 21 | with open(topology_file, "w") as f: 22 | f.write(topology) 23 | 24 | with open(configuration_file, "w") as f: 25 | f.write(configuration) 26 | -------------------------------------------------------------------------------- /tests/CanDo_oxDNA/correct_output.top: -------------------------------------------------------------------------------- 1 | 64 4 2 | 1 A -1 1 3 | 1 C 0 2 4 | 1 G 1 3 5 | 1 T 2 4 6 | 1 T 3 5 7 | 1 A 4 6 8 | 1 G 5 7 9 | 1 G 6 8 10 | 1 T 7 9 11 | 1 G 8 10 12 | 1 A 9 11 13 | 1 T 10 12 14 | 1 A 11 13 15 | 1 C 12 14 16 | 1 G 13 15 17 | 1 T 14 -1 18 | 2 A -1 17 19 | 2 C 16 18 20 | 2 A 17 19 21 | 2 C 18 20 22 | 2 G 19 21 23 | 2 A 20 22 24 | 2 G 21 23 25 | 2 T 22 24 26 | 2 C 23 25 27 | 2 C 24 26 28 | 2 T 25 27 29 | 2 A 26 28 30 | 2 A 27 29 31 | 2 C 28 30 32 | 2 G 29 31 33 | 2 T 30 -1 34 | 3 A -1 33 35 | 3 C 32 34 36 | 3 G 33 35 37 | 3 T 34 36 38 | 3 A 35 37 39 | 3 T 36 38 40 | 3 C 37 39 41 | 3 A 38 40 42 | 3 G 39 41 43 | 3 G 40 42 44 | 3 C 41 43 45 | 3 T 42 44 46 | 3 T 43 45 47 | 3 A 44 46 48 | 3 G 45 47 49 | 3 T 46 -1 50 | 4 A -1 49 51 | 4 C 48 50 52 | 4 T 49 51 53 | 4 A 50 52 54 | 4 A 51 53 55 | 4 G 52 54 56 | 4 C 53 55 57 | 4 C 54 56 58 | 4 A 55 57 59 | 4 C 56 58 60 | 4 T 57 59 61 | 4 C 58 60 62 | 4 G 59 61 63 | 4 T 60 62 64 | 4 G 61 63 65 | 4 T 62 -1 66 | -------------------------------------------------------------------------------- /src/libs/pyquaternion/LICENSE.txt: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2015 Kieran Wynn 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | 23 | -------------------------------------------------------------------------------- /tests/XYZ_oxDNA/sequence.dat: -------------------------------------------------------------------------------- 1 | GAAAAAAACAAAA 2 | A 3 | A 4 | A 5 | A 6 | A 7 | A 8 | A 9 | A 10 | A 11 | A 12 | A 13 | A 14 | A 15 | A 16 | A 17 | A 18 | A 19 | A 20 | A 21 | C 22 | C 23 | A 24 | A 25 | A 26 | A 27 | A 28 | A 29 | A 30 | A 31 | A 32 | T 33 | A 34 | A 35 | A 36 | A 37 | A 38 | A 39 | A 40 | A 41 | A 42 | A 43 | A 44 | A 45 | A 46 | A 47 | A 48 | 49 | A 50 | A 51 | A 52 | A 53 | A 54 | A 55 | A 56 | A 57 | A 58 | A 59 | A 60 | A 61 | A 62 | A 63 | A 64 | A 65 | A 66 | A 67 | A 68 | A 69 | A 70 | A 71 | A 72 | A 73 | A 74 | A 75 | A 76 | A 77 | A 78 | A 79 | A 80 | A 81 | A 82 | A 83 | A 84 | A 85 | A 86 | A 87 | A 88 | A 89 | A 90 | A 91 | A 92 | A 93 | A 94 | A 95 | A 96 | A 97 | A 98 | A 99 | A 100 | A 101 | A 102 | A 103 | A 104 | A 105 | A 106 | A 107 | A 108 | A 109 | A 110 | A 111 | A 112 | A 113 | A 114 | A 115 | A 116 | A 117 | A 118 | A 119 | A 120 | A 121 | A 122 | A 123 | A 124 | A 125 | A 126 | A 127 | A 128 | A 129 | A 130 | A 131 | A 132 | A 133 | A 134 | A 135 | A 136 | A 137 | A 138 | A 139 | A 140 | A 141 | A 142 | A 143 | A 144 | A 145 | A 146 | A 147 | A 148 | A 149 | A 150 | A 151 | A 152 | A 153 | A 154 | A 155 | A 156 | A 157 | A 158 | A 159 | A 160 | A 161 | A 162 | A 163 | A 164 | A 165 | A 166 | A 167 | A 168 | A 169 | C 170 | A 171 | A 172 | A 173 | A 174 | A 175 | A 176 | A 177 | A 178 | A 179 | A 180 | A 181 | A 182 | G 183 | A 184 | A 185 | A 186 | A 187 | A 188 | A 189 | A 190 | A 191 | A 192 | A 193 | A 194 | A 195 | A 196 | A 197 | A 198 | A 199 | A 200 | -------------------------------------------------------------------------------- /tests/conf_diff.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import numpy as np 4 | import sys 5 | 6 | EPS = 1e-6 7 | 8 | def line_differ(line1, line2): 9 | try: 10 | a1 = np.array([float(x) for x in line1.split()]) 11 | a2 = np.array([float(x) for x in line2.split()]) 12 | except ValueError: 13 | return line1 != line2 14 | return np.any(np.abs(a1 - a2) > EPS) 15 | 16 | if len(sys.argv) < 3: 17 | print("Usage is %s conf1 conf2" % sys.argv[0]) 18 | exit(1) 19 | 20 | try: 21 | with open(sys.argv[1]) as inp1, open(sys.argv[2]) as inp2: 22 | # the first three lines are headers 23 | for _ in range(3): 24 | l1 = inp1.readline() 25 | l2 = inp2.readline() 26 | if l1 != l2: 27 | print("Found a difference in the header line ('%s' vs '%s')" % (l1.strip(), l2.strip()), file=sys.stderr) 28 | exit(1) 29 | 30 | lines_1 = inp1.readlines() 31 | lines_2 = inp2.readlines() 32 | 33 | if len(lines_1) != len(lines_2): 34 | print("The two files have different numbers of lines (%d vs %d)" % (len(lines_1), len(lines_2)), file=sys.stderr) 35 | exit(1) 36 | 37 | for i, pair in enumerate(zip(lines_1, lines_2)): 38 | if line_differ(pair[0], pair[1]): 39 | print("Found difference on line %d:" % (i + 3), file=sys.stderr) 40 | print("> %s\n< %s\n" % (pair[0].strip(), pair[1].strip()), file=sys.stderr) 41 | 42 | except FileNotFoundError as e: 43 | print(e) 44 | exit(1) 45 | 46 | exit(0) 47 | -------------------------------------------------------------------------------- /tests/rpoly_oxDNA/input.rpoly: -------------------------------------------------------------------------------- 1 | # Relaxation of original E:\Erik\Dropbox\exjobb\ideas\autoDNA\octahedron\octahedron1.ply file. 12 helices. 2 | # Total separation: Initial: min: 0.352769, max: 8.32776, average: 2.97041, total: 71.2899 nm, final: min: 0.137649, max: 0.802955, average: 0.351587, total: 8.43808 nm 3 | hb helix_1 27 4.2265 0.0254484 3.97966 0.0726497 -0.376816 -0.204382 0.900533 4 | hb helix_2 27 -0.00271292 -4.05862 4.0645 0.504493 0.780986 -0.34012 0.140946 5 | hb helix_3 26 -4.16121 -3.96619 0.0447757 -0.509213 0.509474 0.690222 -0.0687898 6 | hb helix_4 31 -3.96959 0.068022 -4.03136 0.878931 0.228342 0.404694 0.107535 7 | hb helix_5 26 0.0933089 -4.02111 -3.97957 0.345332 -0.153046 0.27172 0.885151 8 | hb helix_6 32 3.89305 -4.04125 -0.047638 -0.675471 0.181485 -0.380193 0.60519 9 | hb helix_7 26 4.2053 -0.011796 -4.01464 0.924188 0.0577255 -0.377524 -0.00451721 10 | hb helix_8 26 -0.0665507 4.03438 -4.04144 -0.153518 -0.331358 -0.754888 0.544774 11 | hb helix_9 26 -4.17436 3.99043 -0.0844567 -0.124858 -0.699686 0.555741 0.431279 12 | hb helix_10 32 -4.03016 -0.0609232 4.05971 -0.126003 0.370949 -0.254682 0.884114 13 | hb helix_11 26 0.00836778 4.0668 4.03965 -0.738569 0.567279 0.257221 0.257971 14 | hb helix_12 32 3.95165 3.95239 0.0276942 0.561361 0.446606 0.128742 0.684721 15 | 16 | c helix_1 f3' helix_2 f5' 17 | c helix_11 b3' helix_1 b5' 18 | c helix_2 f3' helix_3 f5' 19 | c helix_6 b3' helix_2 b5' 20 | c helix_3 f3' helix_4 f5' 21 | c helix_10 b3' helix_3 b5' 22 | c helix_4 f3' helix_5 f5' 23 | c helix_8 b3' helix_4 b5' 24 | c helix_5 f3' helix_6 f5' 25 | c helix_3 b3' helix_5 b5' 26 | c helix_6 f3' helix_7 f5' 27 | c helix_1 b3' helix_6 b5' 28 | c helix_7 f3' helix_8 f5' 29 | c helix_5 b3' helix_7 b5' 30 | c helix_8 f3' helix_9 f5' 31 | c helix_12 b3' helix_8 b5' 32 | c helix_9 f3' helix_10 f5' 33 | c helix_4 b3' helix_9 b5' 34 | c helix_10 f3' helix_11 f5' 35 | c helix_2 b3' helix_10 b5' 36 | c helix_11 f3' helix_12 f5' 37 | c helix_9 b3' helix_11 b5' 38 | c helix_12 f3' helix_1 f5' 39 | c helix_7 b3' helix_12 b5' 40 | 41 | autostaple 42 | ps helix_1 f3' 43 | -------------------------------------------------------------------------------- /tests/cadnano_oxDNA/correct_output.top: -------------------------------------------------------------------------------- 1 | 128 3 2 | 1 C 63 1 3 | 1 A 0 2 4 | 1 G 1 3 5 | 1 C 2 4 6 | 1 G 3 5 7 | 1 A 4 6 8 | 1 T 5 7 9 | 1 A 6 8 10 | 1 C 7 9 11 | 1 A 8 10 12 | 1 C 9 11 13 | 1 G 10 12 14 | 1 C 11 13 15 | 1 T 12 14 16 | 1 C 13 15 17 | 1 T 14 16 18 | 1 G 15 17 19 | 1 A 16 18 20 | 1 A 17 19 21 | 1 T 18 20 22 | 1 A 19 21 23 | 1 G 20 22 24 | 1 G 21 23 25 | 1 A 22 24 26 | 1 A 23 25 27 | 1 C 24 26 28 | 1 C 25 27 29 | 1 T 26 28 30 | 1 G 27 29 31 | 1 G 28 30 32 | 1 G 29 31 33 | 1 A 30 32 34 | 1 T 31 33 35 | 1 G 32 34 36 | 1 T 33 35 37 | 1 T 34 36 38 | 1 A 35 37 39 | 1 T 36 38 40 | 1 G 37 39 41 | 1 G 38 40 42 | 1 T 39 41 43 | 1 G 40 42 44 | 1 A 41 43 45 | 1 A 42 44 46 | 1 A 43 45 47 | 1 T 44 46 48 | 1 A 45 47 49 | 1 G 46 48 50 | 1 C 47 49 51 | 1 A 48 50 52 | 1 T 49 51 53 | 1 C 50 52 54 | 1 C 51 53 55 | 1 C 52 54 56 | 1 C 53 55 57 | 1 C 54 56 58 | 1 T 55 57 59 | 1 C 56 58 60 | 1 C 57 59 61 | 1 C 58 60 62 | 1 T 59 61 63 | 1 T 60 62 64 | 1 A 61 63 65 | 1 T 62 0 66 | 2 A -1 65 67 | 2 T 64 66 68 | 2 A 65 67 69 | 2 A 66 68 70 | 2 G 67 69 71 | 2 G 68 70 72 | 2 G 69 71 73 | 2 A 70 72 74 | 2 G 71 73 75 | 2 G 72 74 76 | 2 G 73 75 77 | 2 G 74 76 78 | 2 G 75 77 79 | 2 A 76 78 80 | 2 T 77 79 81 | 2 G 78 80 82 | 2 A 79 81 83 | 2 G 80 82 84 | 2 A 81 83 85 | 2 G 82 84 86 | 2 C 83 85 87 | 2 G 84 86 88 | 2 T 85 87 89 | 2 G 86 88 90 | 2 T 87 89 91 | 2 A 88 90 92 | 2 T 89 91 93 | 2 C 90 92 94 | 2 G 91 93 95 | 2 C 92 94 96 | 2 T 93 95 97 | 2 G 94 -1 98 | 3 T -1 97 99 | 3 C 96 98 100 | 3 C 97 99 101 | 3 C 98 100 102 | 3 A 99 101 103 | 3 G 100 102 104 | 3 G 101 103 105 | 3 T 102 104 106 | 3 T 103 105 107 | 3 C 104 106 108 | 3 C 105 107 109 | 3 T 106 108 110 | 3 A 107 109 111 | 3 T 108 110 112 | 3 T 109 111 113 | 3 C 110 112 114 | 3 C 111 113 115 | 3 T 112 114 116 | 3 A 113 115 117 | 3 T 114 116 118 | 3 T 115 117 119 | 3 T 116 118 120 | 3 C 117 119 121 | 3 A 118 120 122 | 3 C 119 121 123 | 3 C 120 122 124 | 3 A 121 123 125 | 3 T 122 124 126 | 3 A 123 125 127 | 3 A 124 126 128 | 3 C 125 127 129 | 3 A 126 -1 130 | -------------------------------------------------------------------------------- /src/libs/utils.py: -------------------------------------------------------------------------------- 1 | import numpy as np 2 | import math 3 | 4 | from .base import FLT_EPSILON 5 | 6 | 7 | def get_angle(a, b): 8 | """ 9 | Get angle between a,b 10 | 11 | >>> a = [0, 1, 0] 12 | >>> b = [0, 0, 1] 13 | >>> round(get_angle(a,b),3) 14 | 1.571 15 | 16 | """ 17 | ab = np.dot(a, b) 18 | if ab > (1. - FLT_EPSILON): 19 | return 0 20 | elif ab < (-1. + FLT_EPSILON): 21 | return np.pi 22 | else: 23 | return np.arccos(ab) 24 | 25 | 26 | def get_orthonormalized_base(v1, v2, v3): 27 | v1_norm2 = np.dot(v1, v1) 28 | v2_v1 = np.dot(v2, v1) 29 | 30 | v2 -= (v2_v1 / v1_norm2) * v1 31 | 32 | v3_v1 = np.dot(v3, v1) 33 | v3_v2 = np.dot(v3, v2) 34 | v2_norm2 = np.dot(v2, v2) 35 | 36 | v3 -= (v3_v1 / v1_norm2) * v1 + (v3_v2 / v2_norm2) * v2 37 | 38 | v1 /= np.sqrt(v1_norm2) 39 | v2 /= np.sqrt(v2_norm2) 40 | v3 /= np.sqrt(np.dot(v3, v3)) 41 | 42 | return v1, v2, v3 43 | 44 | 45 | def get_random_vector_in_sphere(r=1): 46 | r2 = r * r 47 | v = np.random.uniform(-r, r, 3) 48 | 49 | while np.dot(v, v) > r2: 50 | v = np.random.uniform(-r, r, 3) 51 | 52 | return v 53 | 54 | 55 | def get_random_vector(): 56 | ransq = 1. 57 | 58 | while ransq >= 1.: 59 | ran1 = 1. - 2. * np.random.random() 60 | ran2 = 1. - 2. * np.random.random() 61 | ransq = ran1 * ran1 + ran2 * ran2 62 | 63 | ranh = 2. * np.sqrt(1. - ransq) 64 | return np.array([ran1 * ranh, ran2 * ranh, 1. - 2. * ransq]) 65 | 66 | 67 | def get_random_rotation_matrix(): 68 | v1, v2, v3 = get_orthonormalized_base(get_random_vector(), get_random_vector(), get_random_vector()) 69 | 70 | R = np.array([v1, v2, v3]) 71 | # rotations have det == 1 72 | if np.linalg.det(R) < 0: R = np.array([v2, v1, v3]) 73 | 74 | return R 75 | 76 | 77 | def get_rotation_matrix(axis, angle): 78 | ct = math.cos(angle) 79 | st = math.sin(angle) 80 | olc = 1. - ct 81 | x, y, z = axis / math.sqrt(np.dot(axis, axis)) 82 | 83 | return np.array([[olc * x * x + ct, olc * x * y - st * z, olc * x * z + st * y], 84 | [olc * x * y + st * z, olc * y * y + ct, olc * y * z - st * x], 85 | [olc * x * z - st * y, olc * y * z + st * x, olc * z * z + ct]]) 86 | -------------------------------------------------------------------------------- /tests/vHelix_oxDNA/correct_output_with_deletion.top: -------------------------------------------------------------------------------- 1 | 148 4 2 | 1 T -1 1 3 | 1 T 0 2 4 | 1 C 1 3 5 | 1 T 2 4 6 | 1 G 3 5 7 | 1 T 4 6 8 | 1 C 5 7 9 | 1 A 6 8 10 | 1 T 7 9 11 | 1 C 8 10 12 | 1 G 9 11 13 | 1 G 10 12 14 | 1 A 11 13 15 | 1 T 12 14 16 | 1 G 13 15 17 | 1 C 14 16 18 | 1 C 15 17 19 | 1 T 16 18 20 | 1 A 17 19 21 | 1 G 18 20 22 | 1 C 19 21 23 | 1 C 20 22 24 | 1 A 21 23 25 | 1 T 22 24 26 | 1 A 23 25 27 | 1 C 24 -1 28 | 2 T -1 27 29 | 2 A 26 28 30 | 2 G 27 29 31 | 2 A 28 30 32 | 2 G 29 31 33 | 2 G 30 32 34 | 2 T 31 33 35 | 2 A 32 34 36 | 2 A 33 35 37 | 2 G 34 36 38 | 2 A 35 37 39 | 2 C 36 38 40 | 2 C 37 39 41 | 2 A 38 40 42 | 2 C 39 41 43 | 2 G 40 42 44 | 2 C 41 43 45 | 2 C 42 44 46 | 2 A 43 45 47 | 2 T 44 46 48 | 2 C 45 47 49 | 2 T 46 48 50 | 2 C 47 49 51 | 2 A 48 50 52 | 2 C 49 51 53 | 2 T 50 -1 54 | 3 G -1 53 55 | 3 C 52 54 56 | 3 T 53 55 57 | 3 A 54 56 58 | 3 G 55 57 59 | 3 G 56 58 60 | 3 C 57 59 61 | 3 A 58 60 62 | 3 G 59 61 63 | 3 G 60 62 64 | 3 A 61 63 65 | 3 G 62 64 66 | 3 C 63 65 67 | 3 T 64 66 68 | 3 G 65 67 69 | 3 A 66 68 70 | 3 G 67 69 71 | 3 T 68 70 72 | 3 A 69 71 73 | 3 A 70 72 74 | 3 A 71 73 75 | 3 C 72 74 76 | 3 G 73 75 77 | 3 G 74 76 78 | 3 T 75 77 79 | 3 G 76 78 80 | 3 C 77 79 81 | 3 G 78 80 82 | 3 G 79 81 83 | 3 T 80 82 84 | 3 A 81 83 85 | 3 T 82 84 86 | 3 T 83 85 87 | 3 C 84 86 88 | 3 T 85 87 89 | 3 A 86 88 90 | 3 T 87 89 91 | 3 C 88 90 92 | 3 C 89 91 93 | 3 G 90 92 94 | 3 T 91 93 95 | 3 C 92 94 96 | 3 C 93 95 97 | 3 G 94 96 98 | 3 A 95 97 99 | 3 T 96 98 100 | 3 G 97 99 101 | 3 A 98 -1 102 | 4 G -1 101 103 | 4 A 100 102 104 | 4 T 101 103 105 | 4 G 102 104 106 | 4 G 103 105 107 | 4 C 104 106 108 | 4 G 105 107 109 | 4 T 106 108 110 | 4 C 107 109 111 | 4 C 108 110 112 | 4 G 109 111 113 | 4 T 110 112 114 | 4 T 111 113 115 | 4 T 112 114 116 | 4 A 113 115 117 | 4 C 114 116 118 | 4 T 115 117 119 | 4 C 116 118 120 | 4 A 117 119 121 | 4 G 118 120 122 | 4 C 119 121 123 | 4 T 120 122 124 | 4 C 121 123 125 | 4 C 122 124 126 | 4 C 123 125 127 | 4 G 124 126 128 | 4 G 125 127 129 | 4 A 126 128 130 | 4 T 127 129 131 | 4 A 128 130 132 | 4 G 129 131 133 | 4 A 130 132 134 | 4 A 131 133 135 | 4 T 132 134 136 | 4 A 133 135 137 | 4 C 134 136 138 | 4 C 135 137 139 | 4 G 136 138 140 | 4 C 137 139 141 | 4 A 138 140 142 | 4 G 139 141 143 | 4 G 140 142 144 | 4 T 141 143 145 | 4 C 142 144 146 | 4 T 143 145 147 | 4 T 144 146 148 | 4 A 145 147 149 | 4 C 146 -1 150 | -------------------------------------------------------------------------------- /tests/oxDNA_LAMMPS/ds.dat: -------------------------------------------------------------------------------- 1 | t = 0 2 | b = 20.0 20.0 20.0 3 | E = 0. 0. 0. 4 | 15.558686015 9.32774651969 17.4007226195 -0.578670889676 0.702781060404 0.413810080326 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 5 | 15.8720325272 9.76341578435 17.3744289462 -0.5878030543 0.208335272447 0.78171860897 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 6 | 16.0513893147 10.2465750809 17.5263280543 -0.373619011053 -0.365260568693 0.852639168428 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 7 | 16.1455796368 10.6464732193 17.8725862877 -0.0174908589295 -0.800087812955 0.599627852434 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 8 | 16.2357829171 10.8639913156 18.355529709 0.345282362933 -0.930948320321 0.118807890057 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 9 | 16.4046933229 10.869299713 18.8655553925 0.576877042303 -0.708125996171 -0.407149176115 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 10 | 16.7051028686 10.7131907673 19.2827714085 0.589306488433 -0.21627476684 -0.778423463109 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 11 | 17.1398448469 10.5077819817 19.5225457716 0.377848546928 0.357742862334 -0.853961661922 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 12 | 17.5932631032 10.9370734165 18.4977917773 -0.377848546928 -0.357742862334 0.853961661922 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 13 | 17.4122706547 10.4536610471 18.3486632528 -0.589306488433 0.21627476684 0.778423463109 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 14 | 17.0969457736 10.0195485176 18.3769763812 -0.576877042303 0.708125996171 0.407149176115 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 15 | 16.6501217526 9.74685333126 18.498099177 -0.345282362933 0.930948320321 -0.118807890057 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 16 | 16.1245906061 9.6863678438 18.5921397106 0.0174908589295 0.800087812955 -0.599627852434 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 17 | 15.6030465014 9.80826239848 18.5494950564 0.373619011053 0.365260568693 -0.852639168428 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 18 | 15.166668862 10.0134181113 18.3124912769 0.5878030543 -0.208335272447 -0.78171860897 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 19 | 14.8642809474 10.1710837922 17.8972947159 0.578670889676 -0.702781060404 -0.413810080326 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 20 | -------------------------------------------------------------------------------- /tests/oxDNA_PDB/ds.dat: -------------------------------------------------------------------------------- 1 | t = 0 2 | b = 20.0 20.0 20.0 3 | E = 0. 0. 0. 4 | 15.558686015 9.32774651969 17.4007226195 -0.578670889676 0.702781060404 0.413810080326 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 5 | 15.8720325272 9.76341578435 17.3744289462 -0.5878030543 0.208335272447 0.78171860897 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 6 | 16.0513893147 10.2465750809 17.5263280543 -0.373619011053 -0.365260568693 0.852639168428 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 7 | 16.1455796368 10.6464732193 17.8725862877 -0.0174908589295 -0.800087812955 0.599627852434 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 8 | 16.2357829171 10.8639913156 18.355529709 0.345282362933 -0.930948320321 0.118807890057 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 9 | 16.4046933229 10.869299713 18.8655553925 0.576877042303 -0.708125996171 -0.407149176115 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 10 | 16.7051028686 10.7131907673 19.2827714085 0.589306488433 -0.21627476684 -0.778423463109 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 11 | 17.1398448469 10.5077819817 19.5225457716 0.377848546928 0.357742862334 -0.853961661922 0.789883410776 0.356631705794 0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 12 | 17.5932631032 10.9370734165 18.4977917773 -0.377848546928 -0.357742862334 0.853961661922 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 13 | 17.4122706547 10.4536610471 18.3486632528 -0.589306488433 0.21627476684 0.778423463109 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 14 | 17.0969457736 10.0195485176 18.3769763812 -0.576877042303 0.708125996171 0.407149176115 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 15 | 16.6501217526 9.74685333126 18.498099177 -0.345282362933 0.930948320321 -0.118807890057 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 16 | 16.1245906061 9.6863678438 18.5921397106 0.0174908589295 0.800087812955 -0.599627852434 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 17 | 15.6030465014 9.80826239848 18.5494950564 0.373619011053 0.365260568693 -0.852639168428 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 18 | 15.166668862 10.0134181113 18.3124912769 0.5878030543 -0.208335272447 -0.78171860897 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 19 | 14.8642809474 10.1710837922 17.8972947159 0.578670889676 -0.702781060404 -0.413810080326 -0.789883410776 -0.356631705794 -0.498896806767 0.0 0.0 0.0 0.0 0.0 0.0 20 | -------------------------------------------------------------------------------- /tests/Tiamat_oxDNA/correct_output.dat: -------------------------------------------------------------------------------- 1 | t = 0 2 | b = 250 250 250 3 | E = 0 0 0 4 | -1.459907 0.506201 -2.654917 -0.001893 -0.958221 0.286023 0.995957 -0.047853 0.076027 0 0 0 0 0 0 5 | -1.080032 0.283756 -2.417295 0.002010 -0.952847 -0.303444 0.994976 -0.039650 0.091932 0 0 0 0 0 0 6 | -0.689980 -0.027031 -2.335518 0.005215 -0.616338 -0.787464 0.995223 -0.080831 0.054758 0 0 0 0 0 0 7 | -0.298675 -0.328425 -2.442573 0.006608 -0.065637 -0.997822 0.995579 -0.093920 0.000860 0 0 0 0 0 0 8 | 0.093630 -0.515683 -2.700347 0.005705 0.507872 -0.861413 0.995923 -0.074372 -0.051043 0 0 0 0 0 0 9 | 0.486332 -0.523729 -3.018374 0.002819 0.904886 -0.425644 0.996134 -0.028974 -0.082933 0 0 0 0 0 0 10 | 0.878698 -0.349770 -3.285217 -0.001047 0.987431 0.158046 0.996140 0.026489 -0.083689 0 0 0 0 0 0 11 | 1.270097 -0.054257 -3.407257 -0.004549 0.726822 0.686810 0.995936 0.072752 -0.053098 0 0 0 0 0 0 12 | 1.660263 0.260112 -3.341174 -0.006473 0.213625 0.976894 0.995597 0.093722 -0.001729 0 0 0 0 0 0 13 | 2.049311 0.484086 -3.109031 -0.006138 -0.373812 0.927484 0.995236 0.082136 0.052517 0 0 0 0 0 0 14 | 2.437814 0.539826 -2.790618 -0.003681 -0.831339 0.555753 0.994984 0.041996 0.090794 0 0 0 0 0 0 15 | 2.826452 0.407971 -2.495685 0.000063 -0.999958 -0.009113 0.994925 -0.012735 0.099813 0 0 0 0 0 0 16 | 3.215926 0.134331 -2.325823 0.003780 -0.821069 -0.570816 0.995079 -0.063039 0.076446 0 0 0 0 0 0 17 | 3.179341 -0.552415 -2.793646 -0.003780 0.821069 0.570816 -0.996952 0.023799 0.074293 0 0 0 0 0 0 18 | 2.795971 -0.414463 -2.503381 -0.000063 0.999958 0.009113 -0.996160 0.011034 0.086851 0 0 0 0 0 0 19 | 2.404244 -0.143919 -2.333734 0.003681 0.831339 -0.555753 -0.996011 0.061759 0.064406 0 0 0 0 0 0 20 | 2.013737 0.176640 -2.346415 0.006138 0.373812 -0.927484 -0.995699 0.091022 0.017270 0 0 0 0 0 0 21 | 1.624395 0.435810 -2.537913 0.006473 -0.213625 -0.976894 -0.995333 0.088644 -0.038143 0 0 0 0 0 0 22 | 1.235824 0.543529 -2.842584 0.004549 -0.726822 -0.686810 -0.995038 0.055467 -0.082604 0 0 0 0 0 0 23 | 0.847298 0.462361 -3.155433 0.001047 -0.987431 -0.158046 -0.994919 0.003021 -0.100631 0 0 0 0 0 0 24 | 0.458115 0.220507 -3.368652 -0.002819 -0.904886 0.425644 -0.995015 -0.050489 -0.086001 0 0 0 0 0 0 25 | 0.067786 -0.097974 -3.409036 -0.005705 -0.507872 0.861413 -0.995295 -0.086442 -0.043758 0 0 0 0 0 0 26 | -0.323776 -0.382408 -3.263445 -0.006608 0.065637 0.997822 -0.995660 -0.092363 0.011395 0 0 0 0 0 0 27 | -0.716227 -0.533947 -2.983382 -0.005215 0.616338 0.787464 -0.995985 -0.066178 0.060293 0 0 0 0 0 0 28 | -1.108917 -0.499924 -2.667065 -0.002010 0.952847 0.303444 -0.996154 -0.016999 0.085955 0 0 0 0 0 0 29 | -1.501114 -0.292171 -2.425333 0.001893 0.958221 -0.286023 -0.996111 0.038087 0.079455 0 0 0 0 0 0 30 | -------------------------------------------------------------------------------- /tests/LAMMPS_oxDNA/correct_output.dat: -------------------------------------------------------------------------------- 1 | t = 0 2 | b = 20.000000 20.000000 20.000000 3 | E = 0.000000 0.000000 0.000000 4 | 15.558686015 9.32774651969 17.4007226195 -0.5786708896759324 0.7027810604038937 0.41381008032579825 0.789883410776417 0.3566317057940096 0.4988968067673606 0.0 0.0 0.0 0.0 0.0 0.0 5 | 15.8720325272 9.76341578435 17.3744289462 -0.5878030543001229 0.20833527244698508 0.7817186089699331 0.789883410776506 0.35663170579404224 0.4988968067671961 0.0 0.0 0.0 0.0 0.0 0.0 6 | 16.0513893147 10.2465750809 17.5263280543 -0.37361901105291345 -0.36526056869295775 0.8526391684282044 0.7898834107763257 0.35663170579413217 0.4988968067674173 0.0 0.0 0.0 0.0 0.0 0.0 7 | 16.1455796368 10.6464732193 17.8725862877 -0.017490858929579748 -0.8000878129550649 0.5996278524340635 0.7898834107763874 0.356631705794241 0.49889680676724235 0.0 0.0 0.0 0.0 0.0 0.0 8 | 16.2357829171 10.8639913156 18.355529709 0.3452823629326003 -0.9309483203206669 0.11880789005705422 0.7898834107761179 0.3566317057943055 0.4988968067676227 0.0 0.0 0.0 0.0 0.0 0.0 9 | 16.4046933229 10.869299713 18.8655553925 0.5768770423029844 -0.7081259961708384 -0.4071491761146261 0.7898834107765105 0.35663170579393677 0.498896806767265 0.0 0.0 0.0 0.0 0.0 0.0 10 | 16.7051028686 10.7131907673 19.2827714085 0.5893064884331575 -0.21627476684004304 -0.7784234631091651 0.7898834107764419 0.3566317057940628 0.49889680676728304 0.0 0.0 0.0 0.0 0.0 0.0 11 | 17.1398448469 10.5077819817 19.5225457716 0.37784854692835024 0.3577428623340821 -0.8539616619223327 0.7898834107764974 0.3566317057941621 0.4988968067671245 0.0 0.0 0.0 0.0 0.0 0.0 12 | 17.5932631032 10.9370734165 18.4977917773 -0.3778485469283502 -0.35774286233408226 0.8539616619223326 -0.7898834107764973 -0.3566317057941622 -0.4988968067671245 0.0 0.0 0.0 0.0 0.0 0.0 13 | 17.4122706547 10.4536610471 18.3486632528 -0.5893064884331575 0.21627476684004304 0.7784234631091651 -0.7898834107764419 -0.3566317057940628 -0.4988968067672831 0.0 0.0 0.0 0.0 0.0 0.0 14 | 17.0969457736 10.0195485176 18.3769763812 -0.5768770423029844 0.7081259961708384 0.4071491761146261 -0.7898834107765105 -0.35663170579393677 -0.49889680676726506 0.0 0.0 0.0 0.0 0.0 0.0 15 | 16.6501217526 9.74685333126 18.498099177 -0.34528236293305303 0.9309483203205966 -0.11880789005628786 -0.7898834107763398 -0.3566317057943401 -0.4988968067672462 0.0 0.0 0.0 0.0 0.0 0.0 16 | 16.1245906061 9.6863678438 18.5921397106 0.017490858929579692 0.8000878129550647 -0.5996278524340634 -0.7898834107763872 -0.356631705794241 -0.4988968067672423 0.0 0.0 0.0 0.0 0.0 0.0 17 | 15.6030465014 9.80826239848 18.5494950564 0.37361901105291334 0.36526056869295775 -0.8526391684282044 -0.7898834107763257 -0.35663170579413217 -0.4988968067674174 0.0 0.0 0.0 0.0 0.0 0.0 18 | 15.166668862 10.0134181113 18.3124912769 0.5878030543001228 -0.20833527244698513 -0.7817186089699333 -0.7898834107765063 -0.35663170579404224 -0.49889680676719605 0.0 0.0 0.0 0.0 0.0 0.0 19 | 14.8642809474 10.1710837922 17.8972947159 0.5786708896759326 -0.7027810604038935 -0.41381008032579814 -0.7898834107764168 -0.3566317057940097 -0.4988968067673608 0.0 0.0 0.0 0.0 0.0 0.0 20 | -------------------------------------------------------------------------------- /tests/cadnano_oxDNA/init.json: -------------------------------------------------------------------------------- 1 | {"name":"test.json","vstrands":[{"stap_colors":[[47,11184640]],"num":0,"scafLoop":[],"stap":[[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[0,17,-1,-1],[0,18,0,16],[0,19,0,17],[0,20,0,18],[0,21,0,19],[0,22,0,20],[0,23,0,21],[0,24,0,22],[0,25,0,23],[0,26,0,24],[0,27,0,25],[0,28,0,26],[0,29,0,27],[0,30,0,28],[0,31,0,29],[1,31,0,30],[0,33,1,32],[0,34,0,32],[0,35,0,33],[0,36,0,34],[0,37,0,35],[0,38,0,36],[0,39,0,37],[0,40,0,38],[0,41,0,39],[0,42,0,40],[0,43,0,41],[0,44,0,42],[0,45,0,43],[0,46,0,44],[0,47,0,45],[-1,-1,0,46],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1]],"skip":[0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],"scaf":[[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[1,16,0,17],[0,16,0,18],[0,17,0,19],[0,18,0,20],[0,19,0,21],[0,20,0,22],[0,21,0,23],[0,22,0,24],[0,23,0,25],[0,24,0,26],[0,25,0,27],[0,26,0,28],[0,27,0,29],[0,28,0,30],[0,29,0,31],[0,30,0,32],[0,31,0,33],[0,32,0,34],[0,33,0,35],[0,34,0,36],[0,35,0,37],[0,36,0,38],[0,37,0,39],[0,38,0,40],[0,39,0,41],[0,40,0,42],[0,41,0,43],[0,42,0,44],[0,43,0,45],[0,44,0,46],[0,45,0,47],[0,46,1,47],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1]],"stapLoop":[],"col":20,"loop":[0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],"row":14},{"stap_colors":[[16,3355443]],"num":1,"scafLoop":[],"stap":[[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,1,17],[1,16,1,18],[1,17,1,19],[1,18,1,20],[1,19,1,21],[1,20,1,22],[1,21,1,23],[1,22,1,24],[1,23,1,25],[1,24,1,26],[1,25,1,27],[1,26,1,28],[1,27,1,29],[1,28,1,30],[1,29,1,31],[1,30,0,31],[0,32,1,33],[1,32,1,34],[1,33,1,35],[1,34,1,36],[1,35,1,37],[1,36,1,38],[1,37,1,39],[1,38,1,40],[1,39,1,41],[1,40,1,42],[1,41,1,43],[1,42,1,44],[1,43,1,45],[1,44,1,46],[1,45,1,47],[1,46,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1]],"skip":[0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],"scaf":[[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[1,17,0,16],[1,18,1,16],[1,19,1,17],[1,20,1,18],[1,21,1,19],[1,22,1,20],[1,23,1,21],[1,24,1,22],[1,25,1,23],[1,26,1,24],[1,27,1,25],[1,28,1,26],[1,29,1,27],[1,30,1,28],[1,31,1,29],[1,32,1,30],[1,33,1,31],[1,34,1,32],[1,35,1,33],[1,36,1,34],[1,37,1,35],[1,38,1,36],[1,39,1,37],[1,40,1,38],[1,41,1,39],[1,42,1,40],[1,43,1,41],[1,44,1,42],[1,45,1,43],[1,46,1,44],[1,47,1,45],[0,47,1,46],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1],[-1,-1,-1,-1]],"stapLoop":[],"col":21,"loop":[0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],"row":14}]} -------------------------------------------------------------------------------- /src/libs/readers.py: -------------------------------------------------------------------------------- 1 | from . import base 2 | import numpy as np 3 | import os.path 4 | 5 | class LorenzoReader: 6 | def __init__(self, topology, configuration): 7 | self._conf = False 8 | 9 | if not os.path.isfile(configuration): 10 | base.Logger.die("Configuration file '%s' is not readable" % configuration) 11 | 12 | if not os.path.isfile(topology): 13 | base.Logger.die("Topology file '%s' is not readable" % topology) 14 | 15 | self._conf = open(configuration, "r") 16 | 17 | f = open(topology, "r") 18 | self.N, self.N_strands = [int(x) for x in f.readline().split()] 19 | self._top_lines = f.readlines() 20 | if len(self._top_lines) != self.N: 21 | raise Exception("The number of nucleotides specified in the topology file header (%d) is different from the number of nucleotide lines found in the same file (%d)" % (self.N, len(self._top_lines))) 22 | 23 | def __del__(self): 24 | if self._conf: self._conf.close() 25 | 26 | def _read(self, only_strand_ends=False, skip=False): 27 | try: 28 | timeline = self._conf.readline() 29 | time = float(timeline.split()[2]) 30 | 31 | box = np.array([float(x) for x in self._conf.readline().split()[2:]]) 32 | self._conf.readline() 33 | except Exception as e: 34 | raise Exception("The header lines of the configuration file are invalid (caught a '%s' exception)" % e) 35 | 36 | if skip: 37 | for tl in self._top_lines: 38 | self._conf.readline() 39 | 40 | return False 41 | 42 | system = base.System(box, time=time) 43 | base.Nucleotide.index = 0 44 | base.Strand.index = 0 45 | 46 | s = False 47 | strandid_current = 0 48 | for i_line, tl in enumerate(self._top_lines): 49 | tls = tl.split() 50 | n3 = int(tls[2]) 51 | n5 = int(tls[3]) 52 | strandid = int(tls[0]) 53 | if (len (tls[1]) == 1): 54 | b = base.base_to_number[tls[1]] 55 | bb = b 56 | else: 57 | try: 58 | tmp = int (tls[1]) 59 | except: 60 | raise Exception("The line n. %d in the topology file contains an incorrect specific base pairing" % i_line) 61 | 62 | if tmp > 0: 63 | b = tmp % 4 64 | else: 65 | b = (3 - ((3 - tmp) % 4)) 66 | bb = tmp 67 | 68 | if strandid != strandid_current: 69 | # check for circular strand 70 | if n3 != -1: 71 | iscircular = True 72 | else: 73 | iscircular = False 74 | 75 | if s: 76 | system.add_strand(s) 77 | s = base.Strand() 78 | if iscircular: 79 | s.make_circular() 80 | strandid_current = strandid 81 | 82 | ls = self._conf.readline().split() 83 | if len(ls) == 0: 84 | raise Exception("The %d-th nucleotide line in the configuration file is empty" % i_line) 85 | elif len(ls) != 15: 86 | raise Exception("The %d-th nucleotide line in the configuration file is invalid" % i_line) 87 | cm = [float(x) for x in ls[0:3]] 88 | a1 = [float(x) for x in ls[3:6]] 89 | a3 = [float(x) for x in ls[6:9]] 90 | v = [float(x) for x in ls[9:12]] 91 | L = [float(x) for x in ls[12:15]] 92 | if not only_strand_ends or n3 == -1 or n5 == -1: 93 | s.add_nucleotide(base.Nucleotide(cm, a1, a3, b, bb, v, L, n3)) 94 | 95 | system.add_strand(s) 96 | 97 | return system 98 | 99 | 100 | # if only_strand_ends == True then a strand will contain only the first and the last nucleotide 101 | # useful for some analysis like csd for coaxial interactions 102 | def get_system(self, only_strand_ends=False, N_skip=0): 103 | for _ in range(N_skip): 104 | self._read(skip=True) 105 | 106 | return self._read(only_strand_ends=only_strand_ends, skip=False) 107 | -------------------------------------------------------------------------------- /src/libs/topology.py: -------------------------------------------------------------------------------- 1 | import numpy as np 2 | import math as mt 3 | import numpy.linalg as la 4 | 5 | #angle between vectors (-pi,pi) with a reference direction vplane 6 | def py_ang(v1, v2, vplane): 7 | v1n = v1 / la.norm(v1) 8 | v2n = v2 / la.norm(v2) 9 | 10 | return np.arctan2 (la.norm(np.cross(v1n, v2n)) , np.dot (v1n, v2n)) * np.sign(np.dot(np.cross(v1n, v2n), vplane)) 11 | 12 | 13 | def get_twist(axis, ssdna1): 14 | numrows = len(axis) 15 | distn = np.copy(axis) 16 | dist = np.copy(axis) 17 | p = np.copy(axis) 18 | a = np.copy(axis) 19 | 20 | TW = 0 21 | 22 | #axis vectors 23 | for c in range(0, numrows): 24 | ind = c 25 | ind1 = (c + 1) % numrows 26 | 27 | dist[ind, :] = axis[ind1, :] - axis[ind, :] 28 | distn[ind, :] = dist[ind, :] / np.sqrt(np.dot(dist[ind, :], dist[ind, :])) 29 | # print ind,ind1, dist[ind,:],axis[ind,:],axis[ind1,:] 30 | 31 | # vector perpendicular to two consecutive axis vectors 32 | for c in range(0, numrows): 33 | ind_1 = (c - 1 + numrows) % numrows 34 | ind = c 35 | 36 | p[ind, :] = np.cross(dist[ind_1, :] , dist[ind, :]) 37 | p[ind, :] /= np.sqrt(np.dot(p[ind, :] , p[ind, :])) 38 | # print p[ind,0], p[ind,1], p[ind,2] 39 | 40 | # axis to base vectors (perpendicular to axis) 41 | weight = 0.5 # 1 #0.5 42 | for c in range(0, numrows): 43 | a[c, :] = weight * ssdna1[c, :] + (1 - weight) * ssdna1[(c - 1 + numrows) % numrows, :] - axis[c, :] 44 | 45 | for c in range(0, numrows): 46 | proj = np.dot(a[c, :], distn[c, :]) 47 | a[c, :] = a[c, :] - proj * distn[c, :] 48 | 49 | # twist angles 50 | for c in range(0, numrows): 51 | ind_1 = (c - 1 + numrows) % numrows 52 | ind = c 53 | 54 | # the angle should be computed selecting dist as the axis, so we need to choose the right order 55 | 56 | alpha = py_ang(a[ind_1, :] , p[ind, :] , dist[ind_1, :]) 57 | gamma = py_ang(p[ind, :] , a[ind, :] , dist[ind, :]) 58 | 59 | angle = (alpha + gamma + 4 * np.pi) % (2 * np.pi) 60 | # Now we have the angle in 0 - 2pi . if it exceeds pi, let's take angle-2*pi instead 61 | if angle > np.pi: 62 | angle = angle - 2 * np.pi 63 | 64 | # print angle 65 | 66 | TW += angle / (2 * np.pi) 67 | 68 | return TW 69 | 70 | 71 | #curve xyz coordinate as input 72 | def get_writhe(coordxyz): 73 | numrows = len(coordxyz) 74 | dist = np.copy(coordxyz) 75 | # distn=np.copy(coordxyz) 76 | 77 | WR = 0 78 | 79 | for c in range(0, numrows): 80 | ind = int(c - mt.floor(c / float(numrows)) * numrows) 81 | ind1 = int(c + 1 - mt.floor((c + 1) / float(numrows)) * numrows) 82 | 83 | dist[ind, :] = coordxyz[ind1, :] - coordxyz[ind, :] 84 | # distn[ind,:]=dist[ind,:]/np.sqrt(np.dot(dist[ind,:],dist[ind,:])) 85 | # print ind,ind1, coordxyz[ind,:],coordxyz[ind1,:],dist[ind,:] 86 | 87 | for i in range(1, numrows): 88 | for j in range(0, i): 89 | ind_i = int(i - mt.floor(i / float(numrows)) * numrows) 90 | ind_i1 = int(i + 1 - mt.floor((i + 1) / float(numrows)) * numrows) 91 | ind_j = int(j - mt.floor(j / float(numrows)) * numrows) 92 | ind_j1 = int(j + 1 - mt.floor((j + 1) / float(numrows)) * numrows) 93 | 94 | r12 = dist[ind_i, :] # rii1 95 | r34 = dist[ind_j, :] # rjj1 96 | r13 = coordxyz[ind_j, :] - coordxyz[ind_i, :] # rij 97 | r23 = coordxyz[ind_j, :] - coordxyz[ind_i1, :] # ri1j 98 | r24 = coordxyz[ind_j1, :] - coordxyz[ind_i1, :] # ri1j1 99 | r14 = coordxyz[ind_j1, :] - coordxyz[ind_i, :] # rij1 100 | 101 | # print ind_i,ind_i1,ind_j,ind_j1,r12,dist[ind_i,:],r34,r13,r23,r24,r14 102 | 103 | # do action only if 4 points are coplanar (from wolfram), otherwise solid angle is zero 104 | # if(ind_i==ind_j+1): 105 | # if(np.dot( r13 , np.cross(r12,r34) )> 5*mt.exp(-17)): 106 | # print np.dot( r13 , np.cross(r12,r34) ),ind_i,ind_j 107 | if(abs (np.dot(r13 , np.cross(r12, r34))) > 5 * mt.exp(-17)): 108 | n1 = np.cross(r13 , r14) 109 | n1 /= np.sqrt(np.dot(n1, n1)) 110 | n2 = np.cross(r14 , r24) 111 | n2 /= np.sqrt(np.dot(n2, n2)) 112 | n3 = np.cross(r24 , r23) 113 | n3 /= np.sqrt(np.dot(n3, n3)) 114 | n4 = np.cross(r23 , r13) 115 | n4 /= np.sqrt(np.dot(n4, n4)) 116 | 117 | # print ind_i,ind_j, np.dot( r13 , np.cross(r12,r34) ), n1,n2,n3,n4 118 | 119 | wr_loc = np.arcsin(np.dot(n1, n2)) + np.arcsin(np.dot(n2, n3)) + np.arcsin(np.dot(n3, n4)) + np.arcsin(np.dot(n4, n1)) 120 | 121 | wr_loc = wr_loc * np.sign(np.dot(np.cross(r34 , r12) , r13)) / 4 / np.pi 122 | 123 | WR += 2 * wr_loc 124 | # print wr_loc,WR 125 | 126 | return WR 127 | -------------------------------------------------------------------------------- /tests/LAMMPS_oxDNA/trajectory_datafile.dat: -------------------------------------------------------------------------------- 1 | # LAMMPS data file 2 | 10 atoms 3 | 10 ellipsoids 4 | 8 bonds 5 | 6 | 4 atom types 7 | 1 bond types 8 | 9 | # System size 10 | -20.000000 20.000000 xlo xhi 11 | -20.000000 20.000000 ylo yhi 12 | -20.000000 20.000000 zlo zhi 13 | 14 | Masses 15 | 16 | 1 3.1575 17 | 2 3.1575 18 | 3 3.1575 19 | 4 3.1575 20 | 21 | # Atom-ID, type, position, molecule-ID, ellipsoid flag, density 22 | Atoms 23 | 24 | 1 1 -6.000000000000001e-01 0.000000000000000e+00 0.000000000000000e+00 1 1 1 25 | 2 2 -4.860249842674776e-01 -3.518234140414736e-01 3.897628551303122e-01 1 1 1 26 | 3 3 -1.874009511073395e-01 -5.699832309147915e-01 7.795257102606244e-01 1 1 1 27 | 4 4 1.824198365552941e-01 -5.715968887521518e-01 1.169288565390937e+00 1 1 1 28 | 5 1 4.829362784135484e-01 -3.560513319622209e-01 1.559051420521249e+00 1 1 1 29 | 6 4 -4.829362784135484e-01 3.560513319622209e-01 1.559051420521249e+00 2 1 1 30 | 7 1 -1.824198365552941e-01 5.715968887521516e-01 1.169288565390937e+00 2 1 1 31 | 8 2 1.874009511073395e-01 5.699832309147913e-01 7.795257102606243e-01 2 1 1 32 | 9 3 4.860249842674775e-01 3.518234140414733e-01 3.897628551303121e-01 2 1 1 33 | 10 4 5.999999999999996e-01 -1.332267629550188e-16 -1.110223024625157e-16 2 1 1 34 | 35 | # Atom-ID, translational velocity, angular momentum 36 | Velocities 37 | 38 | 1 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 39 | 2 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 40 | 3 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 41 | 4 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 42 | 5 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 43 | 6 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 44 | 7 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 45 | 8 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 46 | 9 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 47 | 10 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 48 | 49 | # Atom-ID, shape, quaternion 50 | Ellipsoids 51 | 52 | 1 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 1.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 53 | 2 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 9.513258223252946e-01 0.000000000000000e+00 0.000000000000000e+00 3.081869234362515e-01 54 | 3 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 8.100416404457962e-01 0.000000000000000e+00 0.000000000000000e+00 5.863723567357894e-01 55 | 4 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 5.899012371043606e-01 0.000000000000000e+00 0.000000000000000e+00 8.074754054847398e-01 56 | 5 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 3.123349185122326e-01 0.000000000000000e+00 0.000000000000000e+00 9.499720515246527e-01 57 | 6 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 0.000000000000000e+00 9.499720515246527e-01 -3.123349185122326e-01 -0.000000000000000e+00 58 | 7 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 0.000000000000000e+00 8.074754054847401e-01 -5.899012371043604e-01 0.000000000000000e+00 59 | 8 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 0.000000000000000e+00 5.863723567357896e-01 -8.100416404457959e-01 0.000000000000000e+00 60 | 9 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -0.000000000000000e+00 -3.081869234362514e-01 9.513258223252947e-01 0.000000000000000e+00 61 | 10 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -0.000000000000000e+00 1.110223024625157e-16 1.000000000000000e+00 -0.000000000000000e+00 62 | 63 | # Bond topology 64 | Bonds 65 | 66 | 1 1 1 2 67 | 2 1 2 3 68 | 3 1 3 4 69 | 4 1 4 5 70 | 5 1 6 7 71 | 6 1 7 8 72 | 7 1 8 9 73 | 8 1 9 10 74 | -------------------------------------------------------------------------------- /tests/PDB_oxDNA/correct_output.dat: -------------------------------------------------------------------------------- 1 | t = 0 2 | b = 9.110329 9.110329 9.110329 3 | E = 0.000000 0.000000 0.000000 4 | 0.4771314724527989 -0.38235984696766706 4.278686656630249 -0.7188097232212063 0.6900349123618182 0.08464278778768226 -0.05061547987154588 0.06923044142535789 -0.9963158230086598 0.0 0.0 0.0 0.0 0.0 0.0 5 | 0.08695703216717539 -0.6749002113172107 3.8643304375048926 0.16428016631139256 0.9828051962699063 0.08429693435453187 0.0005153508685993667 0.08539486142696004 -0.9963470540205118 0.0 0.0 0.0 0.0 0.0 0.0 6 | -0.21853543654435878 -0.5570200715774793 3.4800209182693336 0.4344432819466438 0.8967163356087005 0.08460997709451029 0.050184098897678046 0.06949957124184307 -0.9963189076872064 0.0 0.0 0.0 0.0 0.0 0.0 7 | -0.6149996086718321 -0.2912655552946701 3.0707169132034124 0.9854549403875491 0.14755763378773984 0.0842929722855666 0.08137014698774156 0.025909483501283633 -0.9963471271820329 0.0 0.0 0.0 0.0 0.0 0.0 8 | -0.6702020720826484 0.1461463958675745 2.679942474759334 0.8861234416748427 -0.45342892859100636 0.09585120151121572 0.09439139648140939 -0.02598559595262883 -0.9951959671709266 0.0 0.0 0.0 0.0 0.0 0.0 9 | -0.4563057642639117 0.5121764205212491 2.2831357126085945 0.4503846150976045 -0.8876777113066229 0.09582264519840049 0.061072754728392464 -0.07649020913053818 -0.9951981544079812 0.0 0.0 0.0 0.0 0.0 0.0 10 | -0.1156007865696173 0.6080579361352428 1.89421299013853 0.17890913280488324 -0.9791547747467255 0.09616365888262442 0.0014887355727025372 -0.09752595137387673 -0.9952318686994578 0.0 0.0 0.0 0.0 0.0 0.0 11 | 0.263886035454332 0.5598805470767786 1.4974062279877907 -0.4309190469891188 -0.8972509914384161 0.09617397415501129 -0.056116569487118254 -0.07978669646967042 -0.9952311358149191 0.0 0.0 0.0 0.0 0.0 0.0 12 | 0.5042049990394671 0.3221911531373845 1.0991803453648958 -0.8784673041928773 -0.47024717240609787 0.08463328132696181 -0.08147026327226933 -0.026750616230860808 -0.9963167170802747 0.0 0.0 0.0 0.0 0.0 0.0 13 | 0.6687485325193706 -0.12585896532832436 0.6898763402989747 -0.8839720871748296 0.45987402867464183 0.0843162312151709 -0.08107358192042022 0.026882655011130328 -0.9963455209786138 0.0 0.0 0.0 0.0 0.0 0.0 14 | 0.4622297167495571 -0.3799689783488797 0.3055668210634165 -0.7188097232212064 0.6900349123618184 0.08464278778768036 -0.05061547987154392 0.06923044142535681 -0.9963158230086601 0.0 0.0 0.0 0.0 0.0 0.0 15 | 0.10882836346560223 -0.646789990943548 -0.09518498641532219 0.16428016631139253 0.9828051962699061 0.08429693435453291 0.0005153508685999064 0.08539486142696068 -0.9963470540205117 0.0 0.0 0.0 0.0 0.0 0.0 16 | 0.16123986575141916 0.5897960029280556 0.08613248069831358 -0.17557762727257553 -0.9808065114981851 -0.0848002582784567 -0.0008765382931123474 -0.08574172492604928 0.9963170119431498 0.0 0.0 0.0 0.0 0.0 0.0 17 | -0.3263833450731784 0.5971198246849806 0.5004539406746498 0.7105072998365461 -0.6986415402744985 -0.08413902234906467 0.050088825119957985 -0.06917642475923842 0.9963461907668598 0.0 0.0 0.0 0.0 0.0 0.0 18 | -0.5042049990394671 0.3221662504357973 0.884792987399233 0.8784533989513661 -0.47023972887294524 -0.08481876714672922 0.08129002745221357 -0.027331622994225587 0.9963156697660235 0.0 0.0 0.0 0.0 0.0 0.0 19 | -0.6687485325193705 -0.12587853173671434 1.2940674649761286 0.8839854726779011 0.4598809922940961 -0.08413772650259492 0.08125852658985469 0.026264709068436722 0.9963469360187727 0.0 0.0 0.0 0.0 0.0 0.0 20 | -0.4564378375205447 -0.511959967128434 1.6860655376849025 0.4506355310660947 0.8874501176765706 -0.09674661118933106 0.05608173655978933 0.07998143886863789 0.9952174678234605 0.0 0.0 0.0 0.0 0.0 0.0 21 | -0.06834057290443764 -0.6824848849495186 2.082872299835642 -0.1573131268308956 0.9827978466984507 -0.0967521196231642 -0.0016173062717414683 0.09768993343464222 0.9952155853009732 0.0 0.0 0.0 0.0 0.0 0.0 22 | 0.2636732507630899 -0.5599539211082414 2.4715125322845735 -0.43088541414160586 0.8973673309220729 -0.09523462224323541 -0.060631623952393625 0.07645876615525235 0.9952275434567273 0.0 0.0 0.0 0.0 0.0 0.0 23 | 0.5424358710965015 -0.29801963489081945 2.8683192944353135 -0.876060758689494 0.4727000178801184 -0.09524830801921931 -0.09400004567840707 0.026235792960703958 0.9952264438710321 0.0 0.0 0.0 0.0 0.0 0.0 24 | 0.5972841825154572 0.035746049364269596 3.2656335603036695 -0.987102900725657 -0.13578501586141015 -0.08479559449942269 -0.0818174215618 -0.025676926530540913 0.9963165184683649 0.0 0.0 0.0 0.0 0.0 0.0 25 | 0.4670384284260781 0.49492056038193616 3.6749080378805665 -0.44498032347868294 -0.8915787572245608 -0.08414173389415093 -0.05029704422566595 -0.0690139799738653 0.9963469666287584 0.0 0.0 0.0 0.0 0.0 0.0 26 | 0.15058663649882248 0.5791016528278796 4.0592470846051505 -0.17557762727257556 -0.9808065114981853 -0.0848002582784555 -0.0008765382931128705 -0.0857417249260482 0.9963170119431499 0.0 0.0 0.0 0.0 0.0 0.0 27 | -0.292162814879415 0.5872312414047561 4.459979706839298 0.7105072998365461 -0.6986415402744985 -0.08413902234906404 0.05008882511995828 -0.06917642475923735 0.9963461907668598 0.0 0.0 0.0 0.0 0.0 0.0 28 | -------------------------------------------------------------------------------- /src/oxDNA_LAMMPS.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import numpy as np 4 | import sys 5 | from libs.readers import LorenzoReader 6 | from libs.constants import mass_in_lammps, inertia_in_lammps, number_oxdna_to_lammps 7 | 8 | def exyz_to_quat(mya1, mya3): 9 | mya2 = np.cross(mya3, mya1) 10 | myquat = [1, 0, 0, 0] 11 | 12 | q0sq = 0.25 * (mya1[0] + mya2[1] + mya3[2] + 1.0) 13 | q1sq = q0sq - 0.5 * (mya2[1] + mya3[2]) 14 | q2sq = q0sq - 0.5 * (mya1[0] + mya3[2]) 15 | q3sq = q0sq - 0.5 * (mya1[0] + mya2[1]) 16 | 17 | # some component must be greater than 1/4 since they sum to 1 18 | # compute other components from it 19 | 20 | if q0sq >= 0.25: 21 | myquat[0] = np.sqrt(q0sq) 22 | myquat[1] = (mya2[2] - mya3[1]) / (4.0 * myquat[0]) 23 | myquat[2] = (mya3[0] - mya1[2]) / (4.0 * myquat[0]) 24 | myquat[3] = (mya1[1] - mya2[0]) / (4.0 * myquat[0]) 25 | elif q1sq >= 0.25: 26 | myquat[1] = np.sqrt(q1sq) 27 | myquat[0] = (mya2[2] - mya3[1]) / (4.0 * myquat[1]) 28 | myquat[2] = (mya2[0] + mya1[1]) / (4.0 * myquat[1]) 29 | myquat[3] = (mya1[2] + mya3[0]) / (4.0 * myquat[1]) 30 | elif q2sq >= 0.25: 31 | myquat[2] = np.sqrt(q2sq) 32 | myquat[0] = (mya3[0] - mya1[2]) / (4.0 * myquat[2]) 33 | myquat[1] = (mya2[0] + mya1[1]) / (4.0 * myquat[2]) 34 | myquat[3] = (mya3[1] + mya2[2]) / (4.0 * myquat[2]) 35 | elif q3sq >= 0.25: 36 | myquat[3] = np.sqrt(q3sq) 37 | myquat[0] = (mya1[1] - mya2[0]) / (4.0 * myquat[3]) 38 | myquat[1] = (mya3[0] + mya1[2]) / (4.0 * myquat[3]) 39 | myquat[2] = (mya3[1] + mya2[2]) / (4.0 * myquat[3]) 40 | 41 | norm = 1.0 / np.sqrt(myquat[0] * myquat[0] + myquat[1] * myquat[1] + \ 42 | myquat[2] * myquat[2] + myquat[3] * myquat[3]) 43 | myquat[0] *= norm 44 | myquat[1] *= norm 45 | myquat[2] *= norm 46 | myquat[3] *= norm 47 | 48 | return np.array([myquat[0], myquat[1], myquat[2], myquat[3]]) 49 | 50 | 51 | if __name__ == '__main__': 52 | if len(sys.argv) < 3: 53 | print("Usage is %s topology configuration" % sys.argv[0], file=sys.stderr) 54 | sys.exit(1) 55 | 56 | try: 57 | lr = LorenzoReader(sys.argv[1], sys.argv[2]) 58 | s = lr.get_system() 59 | except Exception as e: 60 | print("Parser error: %s" % e, file=sys.stderr) 61 | exit(1) 62 | 63 | s.map_nucleotides_to_strands() 64 | box = s._box 65 | 66 | # get total number of bonds 67 | N_bonds = 0 68 | for strand in s._strands: 69 | N_bonds += strand.get_lammps_N_of_bonds_strand() 70 | 71 | out_name = sys.argv[2] + ".lammps" 72 | out = open (out_name, "w") 73 | 74 | out.write('# LAMMPS data file\n') 75 | out.write('%d atoms\n' % s.N) 76 | out.write('%d ellipsoids\n' % s.N) 77 | out.write('%d bonds\n' % N_bonds) 78 | out.write('\n') 79 | out.write('4 atom types\n') 80 | out.write('1 bond types\n') 81 | out.write('\n') 82 | out.write('# System size\n') 83 | out.write('%f %f xlo xhi\n' % (0, box[0])) 84 | out.write('%f %f ylo yhi\n' % (0, box[1])) 85 | out.write('%f %f zlo zhi\n' % (0, box[2])) 86 | 87 | out.write('\n') 88 | out.write('Masses\n') 89 | out.write('\n') 90 | out.write('1 3.1575\n') 91 | out.write('2 3.1575\n') 92 | out.write('3 3.1575\n') 93 | out.write('4 3.1575\n') 94 | 95 | out.write('\n') 96 | out.write('# Atom-ID, type, position, molecule-ID, ellipsoid flag, density\n') 97 | out.write('Atoms\n') 98 | out.write('\n') 99 | 100 | for nucleotide in s._nucleotides: 101 | out.write('%d %d %22.15le %22.15le %22.15le %d 1 1\n' \ 102 | % (nucleotide.index + 1, number_oxdna_to_lammps[nucleotide._base] + 1, \ 103 | nucleotide.cm_pos[0], nucleotide.cm_pos[1], nucleotide.cm_pos[2], \ 104 | s._nucleotide_to_strand[nucleotide.index] + 1)) 105 | 106 | out.write('\n') 107 | out.write('# Atom-ID, translational, rotational velocity\n') 108 | out.write('Velocities\n') 109 | out.write('\n') 110 | 111 | for nucleotide in s._nucleotides: 112 | v_rescaled = np.array(nucleotide._v) / np.sqrt(mass_in_lammps) 113 | L_rescaled = np.array(nucleotide._L) * np.sqrt(inertia_in_lammps) 114 | out.write("%d %22.15le %22.15le %22.15le %22.15le %22.15le %22.15le\n" \ 115 | % (nucleotide.index + 1, v_rescaled[0], v_rescaled[1], v_rescaled[2], L_rescaled[0], L_rescaled[1], L_rescaled[2])) 116 | 117 | out.write('\n') 118 | out.write('# Atom-ID, shape, quaternion\n') 119 | out.write('Ellipsoids\n') 120 | out.write('\n') 121 | 122 | for nucleotide in s._nucleotides: 123 | quaternions = exyz_to_quat(nucleotide._a1, nucleotide._a3) 124 | out.write(\ 125 | "%d %22.15le %22.15le %22.15le %22.15le %22.15le %22.15le %22.15le\n" \ 126 | % (nucleotide.index + 1, 1.1739845031423408, 1.1739845031423408, 1.1739845031423408, \ 127 | quaternions[0], quaternions[1], quaternions[2], quaternions[3])) 128 | 129 | out.write('\n') 130 | out.write('# Bond topology\n') 131 | out.write('Bonds\n') 132 | out.write('\n') 133 | idx = 1 134 | for strand in s._strands: 135 | bonds = strand.get_lammps_bonds() 136 | for b in bonds: 137 | out.write("%d %d %s\n" % (idx, 1, b)) 138 | idx += 1 139 | 140 | out.close() 141 | 142 | print("## Wrote data to '%s'" % out_name, file=sys.stderr) 143 | print("## DONE", file=sys.stderr) 144 | 145 | -------------------------------------------------------------------------------- /tests/scadnano_oxDNA/input.scadnano: -------------------------------------------------------------------------------- 1 | { 2 | "version": "0.11.2", 3 | "grid": "square", 4 | "geometry": { 5 | "inter_helix_gap": 1 6 | }, 7 | "helices": [ 8 | {"grid_position": [0, 0]}, 9 | {"grid_position": [0, 1]}, 10 | {"grid_position": [0, 2]}, 11 | {"grid_position": [0, 3]}, 12 | {"grid_position": [0, 4]}, 13 | {"grid_position": [0, 5]}, 14 | {"grid_position": [0, 6]}, 15 | {"grid_position": [0, 7]}, 16 | {"grid_position": [0, 8]}, 17 | {"grid_position": [0, 9]}, 18 | {"grid_position": [0, 10]}, 19 | {"grid_position": [0, 11]}, 20 | {"grid_position": [0, 12]}, 21 | {"grid_position": [0, 13]}, 22 | {"grid_position": [0, 14]}, 23 | {"grid_position": [0, 15]}, 24 | {"grid_position": [0, 16]}, 25 | {"grid_position": [0, 17]}, 26 | {"grid_position": [0, 18]}, 27 | {"grid_position": [0, 19]}, 28 | {"grid_position": [0, 20]}, 29 | {"grid_position": [0, 21]}, 30 | {"grid_position": [0, 22]}, 31 | {"grid_position": [0, 23]}, 32 | {"grid_position": [0, 24]}, 33 | {"grid_position": [0, 25]}, 34 | {"grid_position": [0, 26]}, 35 | {"grid_position": [0, 27]}, 36 | {"grid_position": [0, 28]}, 37 | {"grid_position": [0, 29]}, 38 | {"grid_position": [0, 30]}, 39 | {"grid_position": [0, 31]} 40 | ], 41 | "strands": [ 42 | { 43 | "color": "#0066cc", 44 | "is_scaffold": true, 45 | "domains": [ 46 | {"helix": 31, "forward": false, "start": 0, "end": 112}, 47 | {"helix": 30, "forward": true, "start": 0, "end": 112}, 48 | {"helix": 29, "forward": false, "start": 0, "end": 112}, 49 | {"helix": 28, "forward": true, "start": 0, "end": 112}, 50 | {"helix": 27, "forward": false, "start": 0, "end": 112}, 51 | {"helix": 26, "forward": true, "start": 0, "end": 112}, 52 | {"helix": 25, "forward": false, "start": 0, "end": 112}, 53 | {"helix": 24, "forward": true, "start": 0, "end": 112}, 54 | {"helix": 23, "forward": false, "start": 0, "end": 112}, 55 | {"helix": 22, "forward": true, "start": 0, "end": 112}, 56 | {"helix": 21, "forward": false, "start": 0, "end": 112}, 57 | {"helix": 20, "forward": true, "start": 0, "end": 112}, 58 | {"helix": 19, "forward": false, "start": 0, "end": 112}, 59 | {"helix": 18, "forward": true, "start": 0, "end": 112}, 60 | {"helix": 17, "forward": false, "start": 0, "end": 112}, 61 | {"helix": 16, "forward": true, "start": 0, "end": 112}, 62 | {"helix": 15, "forward": false, "start": 0, "end": 112}, 63 | {"helix": 14, "forward": true, "start": 0, "end": 112}, 64 | {"helix": 13, "forward": false, "start": 0, "end": 112}, 65 | {"helix": 12, "forward": true, "start": 0, "end": 112}, 66 | {"helix": 11, "forward": false, "start": 0, "end": 112}, 67 | {"helix": 10, "forward": true, "start": 0, "end": 112}, 68 | {"helix": 9, "forward": false, "start": 0, "end": 112}, 69 | {"helix": 8, "forward": true, "start": 0, "end": 112}, 70 | {"helix": 7, "forward": false, "start": 0, "end": 112}, 71 | {"helix": 6, "forward": true, "start": 0, "end": 112}, 72 | {"helix": 5, "forward": false, "start": 0, "end": 112}, 73 | {"helix": 4, "forward": true, "start": 0, "end": 112}, 74 | {"helix": 3, "forward": false, "start": 0, "end": 112}, 75 | {"helix": 2, "forward": true, "start": 0, "end": 112}, 76 | {"helix": 1, "forward": false, "start": 0, "end": 112}, 77 | {"helix": 0, "forward": true, "start": 0, "end": 224}, 78 | {"helix": 1, "forward": false, "start": 112, "end": 224}, 79 | {"helix": 2, "forward": true, "start": 112, "end": 224}, 80 | {"helix": 3, "forward": false, "start": 112, "end": 224}, 81 | {"helix": 4, "forward": true, "start": 112, "end": 224}, 82 | {"helix": 5, "forward": false, "start": 112, "end": 224}, 83 | {"helix": 6, "forward": true, "start": 112, "end": 224}, 84 | {"helix": 7, "forward": false, "start": 112, "end": 224}, 85 | {"helix": 8, "forward": true, "start": 112, "end": 224}, 86 | {"helix": 9, "forward": false, "start": 112, "end": 224}, 87 | {"helix": 10, "forward": true, "start": 112, "end": 224}, 88 | {"helix": 11, "forward": false, "start": 112, "end": 224}, 89 | {"helix": 12, "forward": true, "start": 112, "end": 224}, 90 | {"helix": 13, "forward": false, "start": 112, "end": 224}, 91 | {"helix": 14, "forward": true, "start": 112, "end": 224}, 92 | {"helix": 15, "forward": false, "start": 112, "end": 224}, 93 | {"helix": 16, "forward": true, "start": 112, "end": 224}, 94 | {"helix": 17, "forward": false, "start": 112, "end": 224}, 95 | {"helix": 18, "forward": true, "start": 112, "end": 224}, 96 | {"helix": 19, "forward": false, "start": 112, "end": 224}, 97 | {"helix": 20, "forward": true, "start": 112, "end": 224}, 98 | {"helix": 21, "forward": false, "start": 112, "end": 224}, 99 | {"helix": 22, "forward": true, "start": 112, "end": 224}, 100 | {"helix": 23, "forward": false, "start": 112, "end": 224}, 101 | {"helix": 24, "forward": true, "start": 112, "end": 224}, 102 | {"helix": 25, "forward": false, "start": 112, "end": 224}, 103 | {"helix": 26, "forward": true, "start": 112, "end": 224}, 104 | {"helix": 27, "forward": false, "start": 112, "end": 224}, 105 | {"helix": 28, "forward": true, "start": 112, "end": 224}, 106 | {"helix": 29, "forward": false, "start": 112, "end": 224}, 107 | {"helix": 30, "forward": true, "start": 112, "end": 224}, 108 | {"helix": 31, "forward": false, "start": 112, "end": 224} 109 | ] 110 | } 111 | ] 112 | } -------------------------------------------------------------------------------- /src/rpoly_oxDNA.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import sys 4 | import re 5 | import os 6 | from libs.pyquaternion import Quaternion 7 | import numpy as np 8 | from libs import cadnano_utils as cu 9 | from libs import base 10 | 11 | 12 | class Options(object): 13 | 14 | def __init__(self): 15 | object.__init__(self) 16 | 17 | self.seed = None 18 | self.file_name_in = None 19 | self.print_oxview = None 20 | 21 | def check(self): 22 | return True 23 | 24 | 25 | def move_along_vector(point, vector, length): # rpoly file contains center coordinate of helix, "generate" needs end coordiates of helix: 26 | move_distance = float(length) * 0.4 / 2.0 # 0.4 is the length of a base pair in oxDNA units, move half the helixlength down 27 | return [point[0] - move_distance * vector[0] , point[1] - move_distance * vector[1] , point[2] - move_distance * vector[2] ] 28 | 29 | 30 | def rpoly_to_oxDNA(opts): 31 | # Read File 32 | # 'data' stores helix coordinates + rotaion in quaternion 33 | data = [] 34 | 35 | rev_helix_connections = [] # staple connection information, 36 | fwd_helix_connections = [] # scaffold connections 37 | count = 0 38 | polyFile = open(opts.file_name_in, 'r') 39 | 40 | try: 41 | for line in polyFile: 42 | if line.startswith('hb'): 43 | data.insert(count, line.split(' ')) 44 | count += 1 45 | elif line.startswith('c'): 46 | if 'f3' not in line: 47 | rev_helix_connections.append([int(re.search('c helix_(.+?) ', line).group(1)), int(re.search('\' helix_(.+?) ', line).group(1))]) # Extract connection information 48 | else: 49 | fwd_helix_connections.append([int(re.search('c helix_(.+?) ', line).group(1)), int(re.search('\' helix_(.+?) ', line).group(1))]) 50 | except Exception: 51 | print('Failed to read the file') 52 | 53 | generator = cu.StrandGenerator() 54 | 55 | staple_fragments = base.System([100, 100, 100]) # temporary system to store staple fragments before later connecting them 56 | scaffold_fragments = base.System([100,100,100]) 57 | 58 | # Reads orientation from the "data" and produces rotations from the Quaternian coordinates 59 | largest_size = 0.0 60 | for n, i in enumerate(data): 61 | 62 | position = [float(i[3]) / 0.84 , float(i[4]) / 0.84 , float(i[5]) / 0.84] # 0.84 scaling is ad hoc solution to get good looking models 63 | 64 | n_bp = int(i[2]) 65 | 66 | q = Quaternion(w=float(i[9]), x=float(i[6]), y=float(i[7]), z=float(i[8])) # find the helix roation Info from file 67 | vec = q.rotate(np.array([0.0, 0.0, 1.0])) # use it to figure out direction 68 | vec2 = q.rotate([0.65, -0.76, 0.0]) # ad hoc onversion between rpoly rotation and cadnano utils 69 | 70 | new_position = move_along_vector(position , vec , n_bp) # rpoly helix coordinates are defined in center of helix, cadnano utils have positions in the base of helix. 71 | 72 | for j in new_position: # go through every coordinate to find the largest coordinate to figure out box size 73 | if j > largest_size: 74 | largest_size = j 75 | else: 76 | pass 77 | 78 | # strand 0 is the scaffold and strand 1 is the staple 79 | new_strands = generator.generate_or_sq(bp=n_bp, start_pos=new_position, direction=vec, perp=vec2) 80 | 81 | #for oxview export, cluster nucleotide by helix 82 | if opts.print_oxview is not None: 83 | for i in [0,1]: 84 | for nucleotide in new_strands[i]._nucleotides: 85 | nucleotide.cluster = n+1 86 | 87 | # cut strand 1 into two equal lengh staple fragments for later connections 88 | fragment1, fragment2 = new_strands[1].cut_in_two(copy=False) 89 | 90 | # store the fragments in this system for later connections 91 | staple_fragments.add_strand(fragment1) 92 | staple_fragments.add_strand(fragment2) 93 | 94 | scaffold_fragments.add_strand(new_strands[0]) 95 | 96 | 97 | output_system = base.System([largest_size * 3.0, largest_size * 3.0, largest_size * 3.0]) 98 | for n in rev_helix_connections: # iterate through staple strand connections and connect the previously generated fragments 99 | connect_from = n[0] * 2 - 1 100 | connect_to = n[1] * 2 - 2 101 | staple_strand = staple_fragments._strands[connect_from] 102 | staple_strand = staple_strand.append(staple_fragments._strands[connect_to]) 103 | 104 | output_system.add_strand(staple_strand) 105 | 106 | scaffold_strand = scaffold_fragments._strands[0] 107 | for n in fwd_helix_connections[:-1]: 108 | next_segment_adress = n[1]-1 109 | next_segment = scaffold_fragments._strands[next_segment_adress] 110 | scaffold_strand = scaffold_strand.append(next_segment) 111 | 112 | 113 | 114 | scaffold_strand.make_circular() 115 | output_system.add_strand(scaffold_strand) 116 | 117 | basename = os.path.basename(opts.file_name_in) 118 | top_file = basename + ".top" 119 | conf_file = basename + ".oxdna" 120 | 121 | output_system.print_lorenzo_output(conf_file, top_file) 122 | 123 | if opts.print_oxview is not None: 124 | oxview_file = basename + ".oxview" 125 | output_system.print_oxview_output(oxview_file) 126 | 127 | 128 | def print_usage(): 129 | print("USAGE:", file=sys.stderr) 130 | print("\t%s rpoly_file" % sys.argv[0], file=sys.stderr) 131 | print("\t[-e\--seed=VALUE]", file=sys.stderr) 132 | print("\t[-o\--print-oxview]", file=sys.stderr) 133 | exit(1) 134 | 135 | 136 | def parse_options(): 137 | shortArgs = 'e:o' 138 | longArgs = ['seed=', '--print-oxview'] 139 | 140 | opts = Options() 141 | 142 | try: 143 | import getopt 144 | args, files = getopt.gnu_getopt(sys.argv[1:], shortArgs, longArgs) 145 | for k in args: 146 | if k[0] == '-e' or k[0] == "--seed": 147 | opts.seed = int(k[1]) 148 | if k[0] == '-o' or k[0] == "--print-oxview": 149 | opts.print_oxview = True 150 | 151 | opts.file_name_in = files[0] 152 | except Exception: 153 | print_usage() 154 | 155 | return opts 156 | 157 | 158 | if __name__ == '__main__': 159 | if len(sys.argv) < 2: 160 | print_usage() 161 | 162 | opts = parse_options() 163 | if opts.seed is not None: 164 | np.random.seed(opts.seed) 165 | rpoly_to_oxDNA(opts) 166 | -------------------------------------------------------------------------------- /tests/Tiamat_oxDNA/input.dnajson: -------------------------------------------------------------------------------- 1 | { 2 | "bases": [ 3 | { 4 | "id": 0, 5 | "position": [-1.26034, -0.999978, -2.45815], 6 | "molecule": "DNA", 7 | "type": "Cytosine", 8 | "across": 1, 9 | "up": null, 10 | "down": 2 11 | }, 12 | { 13 | "id": 1, 14 | "position": [-1.25672, 0.832723, -3.0052], 15 | "molecule": "DNA", 16 | "type": "Guanine", 17 | "across": 0, 18 | "up": 3, 19 | "down": null 20 | }, 21 | { 22 | "id": 2, 23 | "position": [-0.924628, -0.82249, -3.01809], 24 | "molecule": "DNA", 25 | "type": "Cytosine", 26 | "across": 3, 27 | "up": 0, 28 | "down": 4 29 | }, 30 | { 31 | "id": 3, 32 | "position": [-0.928472, 0.999933, -2.43772], 33 | "molecule": "DNA", 34 | "type": "Guanine", 35 | "across": 2, 36 | "up": 5, 37 | "down": 1 38 | }, 39 | { 40 | "id": 4, 41 | "position": [-0.590222, -0.359169, -3.38038], 42 | "molecule": "DNA", 43 | "type": "Thymine", 44 | "across": 5, 45 | "up": 2, 46 | "down": 6 47 | }, 48 | { 49 | "id": 5, 50 | "position": [-0.600196, 0.819644, -1.87427], 51 | "molecule": "DNA", 52 | "type": "Adenine", 53 | "across": 4, 54 | "up": 7, 55 | "down": 3 56 | }, 57 | { 58 | "id": 6, 59 | "position": [-0.257963, 0.228972, -3.41834], 60 | "molecule": "DNA", 61 | "type": "Cytosine", 62 | "across": 7, 63 | "up": 4, 64 | "down": 8 65 | }, 66 | { 67 | "id": 7, 68 | "position": [-0.270602, 0.35451, -1.5099], 69 | "molecule": "DNA", 70 | "type": "Guanine", 71 | "across": 6, 72 | "up": 9, 73 | "down": 5 74 | }, 75 | { 76 | "id": 8, 77 | "position": [0.0720551, 0.73754, -3.11802], 78 | "molecule": "DNA", 79 | "type": "Uracil", 80 | "across": 9, 81 | "up": 6, 82 | "down": 10 83 | }, 84 | { 85 | "id": 9, 86 | "position": [0.0611442, -0.233823, -1.47047], 87 | "molecule": "DNA", 88 | "type": "Adenine", 89 | "across": 8, 90 | "up": 11, 91 | "down": 7 92 | }, 93 | { 94 | "id": 10, 95 | "position": [0.400519, 0.989796, -2.58302], 96 | "molecule": "DNA", 97 | "type": "Uracil", 98 | "across": 11, 99 | "up": 8, 100 | "down": 12 101 | }, 102 | { 103 | "id": 11, 104 | "position": [0.395128, -0.740898, -1.76893], 105 | "molecule": "DNA", 106 | "type": "Adenine", 107 | "across": 10, 108 | "up": 13, 109 | "down": 9 110 | }, 111 | { 112 | "id": 12, 113 | "position": [0.728656, 0.898076, -1.9985], 114 | "molecule": "DNA", 115 | "type": "Uracil", 116 | "across": 13, 117 | "up": 10, 118 | "down": 14 119 | }, 120 | { 121 | "id": 13, 122 | "position": [0.730658, -0.990494, -2.30078], 123 | "molecule": "DNA", 124 | "type": "Adenine", 125 | "across": 12, 126 | "up": 15, 127 | "down": 11 128 | }, 129 | { 130 | "id": 14, 131 | "position": [1.0578, 0.494255, -1.56684], 132 | "molecule": "DNA", 133 | "type": "Cytosine", 134 | "across": 15, 135 | "up": 12, 136 | "down": 16 137 | }, 138 | { 139 | "id": 15, 140 | "position": [1.0665, -0.895872, -2.88044], 141 | "molecule": "DNA", 142 | "type": "Guanine", 143 | "across": 14, 144 | "up": 17, 145 | "down": 13 146 | }, 147 | { 148 | "id": 16, 149 | "position": [1.38895, -0.0813316, -1.43727], 150 | "molecule": "DNA", 151 | "type": "Uracil", 152 | "across": 17, 153 | "up": 14, 154 | "down": 18 155 | }, 156 | { 157 | "id": 17, 158 | "position": [1.40133, -0.489913, -3.30569], 159 | "molecule": "DNA", 160 | "type": "Adenine", 161 | "across": 16, 162 | "up": 19, 163 | "down": 15 164 | }, 165 | { 166 | "id": 18, 167 | "position": [1.7224, -0.628653, -1.65407], 168 | "molecule": "DNA", 169 | "type": "Uracil", 170 | "across": 19, 171 | "up": 16, 172 | "down": 20 173 | }, 174 | { 175 | "id": 19, 176 | "position": [1.73414, 0.0863006, -3.42798], 177 | "molecule": "DNA", 178 | "type": "Adenine", 179 | "across": 18, 180 | "up": 21, 181 | "down": 17 182 | }, 183 | { 184 | "id": 20, 185 | "position": [2.05763, -0.957504, -2.14112], 186 | "molecule": "DNA", 187 | "type": "Thymine", 188 | "across": 21, 189 | "up": 18, 190 | "down": 22 191 | }, 192 | { 193 | "id": 21, 194 | "position": [2.06467, 0.632524, -3.20406], 195 | "molecule": "DNA", 196 | "type": "Adenine", 197 | "across": 20, 198 | "up": 23, 199 | "down": 19 200 | }, 201 | { 202 | "id": 22, 203 | "position": [2.39353, -0.9536, -2.72841], 204 | "molecule": "DNA", 205 | "type": "Cytosine", 206 | "across": 23, 207 | "up": 20, 208 | "down": 24 209 | }, 210 | { 211 | "id": 23, 212 | "position": [2.39341, 0.95893, -2.71098], 213 | "molecule": "DNA", 214 | "type": "Guanine", 215 | "across": 22, 216 | "up": 25, 217 | "down": 21 218 | }, 219 | { 220 | "id": 24, 221 | "position": [2.72873, -0.618299, -3.21107], 222 | "molecule": "DNA", 223 | "type": "Thymine", 224 | "across": 25, 225 | "up": 22, 226 | "down": null 227 | }, 228 | { 229 | "id": 25, 230 | "position": [2.7215, 0.952087, -2.11932], 231 | "molecule": "DNA", 232 | "type": "Adenine", 233 | "across": 24, 234 | "up": null, 235 | "down": 23 236 | } 237 | ] 238 | } 239 | -------------------------------------------------------------------------------- /tests/CanDo_oxDNA/junction.cndo: -------------------------------------------------------------------------------- 1 | "CanDo (.cndo) file format version 1.0, Keyao Pan, Laboratory for Computational Biology and Biophysics, Massachusetts Institute of Technology, November 2015" 2 | 3 | dnaTop,id,up,down,across,seq 4 | 1,1,-1,3,2,T 5 | 2,2,4,-1,1,A 6 | 3,3,1,5,4,G 7 | 4,4,6,2,3,C 8 | 5,5,3,7,6,C 9 | 6,6,8,4,5,G 10 | 7,7,5,9,8,A 11 | 8,8,10,6,7,T 12 | 9,9,7,11,10,A 13 | 10,10,12,8,9,T 14 | 11,11,9,13,12,T 15 | 12,12,14,10,11,A 16 | 13,13,11,15,14,C 17 | 14,14,16,12,13,G 18 | 15,15,13,17,16,C 19 | 16,16,47,14,15,G 20 | 17,17,15,19,18,T 21 | 18,18,20,49,17,A 22 | 19,19,17,21,20,G 23 | 20,20,22,18,19,C 24 | 21,21,19,23,22,A 25 | 22,22,24,20,21,T 26 | 23,23,21,25,24,G 27 | 24,24,26,22,23,C 28 | 25,25,23,27,26,C 29 | 26,26,28,24,25,G 30 | 27,27,25,29,28,A 31 | 28,28,30,26,27,T 32 | 29,29,27,31,30,C 33 | 30,30,32,28,29,G 34 | 31,31,29,-1,32,A 35 | 32,32,-1,30,31,T 36 | 33,33,-1,35,34,T 37 | 34,34,36,-1,33,A 38 | 35,35,33,37,36,G 39 | 36,36,38,34,35,C 40 | 37,37,35,39,38,C 41 | 38,38,40,36,37,G 42 | 39,39,37,41,40,A 43 | 40,40,42,38,39,T 44 | 41,41,39,43,42,T 45 | 42,42,44,40,41,A 46 | 43,43,41,45,44,A 47 | 44,44,46,42,43,T 48 | 45,45,43,47,46,G 49 | 46,46,48,44,45,C 50 | 47,47,45,16,48,T 51 | 48,48,50,46,47,A 52 | 49,49,18,51,50,C 53 | 50,50,52,48,49,G 54 | 51,51,49,53,52,C 55 | 52,52,54,50,51,G 56 | 53,53,51,55,54,G 57 | 54,54,56,52,53,C 58 | 55,55,53,57,56,A 59 | 56,56,58,54,55,T 60 | 57,57,55,59,58,A 61 | 58,58,60,56,57,T 62 | 59,59,57,61,60,T 63 | 60,60,62,58,59,A 64 | 61,61,59,63,62,C 65 | 62,62,64,60,61,G 66 | 63,63,61,-1,64,A 67 | 64,64,-1,62,63,T 68 | 69 | dNode,"e0(1)","e0(2)","e0(3)" 70 | 1,-40.872920,2.493298,3.145057 71 | 2,-37.472920,2.493298,3.145057 72 | 3,-34.072920,2.493298,3.145057 73 | 4,-30.672920,2.493298,3.145057 74 | 5,-27.272920,2.493298,3.145057 75 | 6,-23.872920,2.493298,3.145057 76 | 7,-20.472920,2.493298,3.145057 77 | 8,-17.072920,2.493298,3.145057 78 | 9,-13.672920,2.493298,3.145058 79 | 10,-10.272920,2.493298,3.145058 80 | 11,-6.872920,2.493298,3.145058 81 | 12,-3.472920,2.493298,3.145058 82 | 13,-0.072920,2.493298,3.145058 83 | 14,3.327080,2.493298,3.145058 84 | 15,6.727080,2.493298,3.145058 85 | 16,10.127080,2.493298,3.145058 86 | 17,-2.622920,24.587987,21.631874 87 | 18,-4.322920,21.643501,21.633631 88 | 19,-6.022920,18.699015,21.635389 89 | 20,-7.722920,15.754529,21.637146 90 | 21,-9.422920,12.810043,21.638903 91 | 22,-11.122920,9.865557,21.640661 92 | 23,-12.822920,6.921072,21.642418 93 | 24,-14.522920,3.976586,21.644176 94 | 25,-16.222920,1.032100,21.645933 95 | 26,-17.922920,-1.912386,21.647691 96 | 27,-19.622920,-4.856872,21.649448 97 | 28,-21.322920,-7.801358,21.651205 98 | 29,-23.022920,-10.745843,21.652962 99 | 30,-24.722920,-13.690329,21.654720 100 | 31,-26.422920,-16.634815,21.656477 101 | 32,-28.122920,-19.579301,21.658234 102 | 103 | triad,"e1(1)","e1(2)","e1(3)","e2(1)","e2(2)","e2(3)","e3(1)","e3(2)","e3(3)" 104 | 1,-0.000000,0.221939,-0.975061,0.000000,0.975061,0.221939,1.000000,-0.000000,-0.000000 105 | 2,-0.000000,0.732646,-0.680610,0.000000,0.680610,0.732646,1.000000,-0.000000,-0.000000 106 | 3,-0.000000,0.988742,-0.149632,0.000000,0.149632,0.988742,1.000000,-0.000000,-0.000000 107 | 4,0.000000,0.901228,0.433346,0.000000,-0.433346,0.901228,1.000000,-0.000000,-0.000000 108 | 5,0.000000,0.500517,0.865727,0.000000,-0.865727,0.500517,1.000000,-0.000000,-0.000000 109 | 6,0.000000,-0.074135,0.997248,-0.000000,-0.997248,-0.074135,1.000000,-0.000000,-0.000000 110 | 7,0.000000,-0.623023,0.782203,-0.000000,-0.782203,-0.623023,1.000000,-0.000000,-0.000000 111 | 8,0.000000,-0.955397,0.295325,-0.000000,-0.295325,-0.955397,1.000000,-0.000000,-0.000000 112 | 9,0.000000,-0.955749,-0.294185,0.000000,0.294185,-0.955749,1.000000,0.000000,0.000000 113 | 10,0.000000,-0.623956,-0.781459,0.000000,0.781459,-0.623956,1.000000,0.000000,0.000000 114 | 11,0.000000,-0.075325,-0.997159,0.000000,0.997159,-0.075325,1.000000,0.000000,0.000000 115 | 12,0.000000,0.499483,-0.866324,-0.000000,0.866324,0.499483,1.000000,0.000000,0.000000 116 | 13,0.000000,0.900710,-0.434421,-0.000000,0.434421,0.900710,1.000000,0.000000,0.000000 117 | 14,-0.000000,0.988920,0.148452,-0.000000,-0.148452,0.988920,1.000000,0.000000,0.000000 118 | 15,-0.000000,0.733458,0.679735,-0.000000,-0.679735,0.733458,1.000000,0.000000,0.000000 119 | 16,-0.000000,0.223103,0.974795,-0.000000,-0.974795,0.223103,1.000000,0.000000,0.000000 120 | 17,-0.192709,0.111842,0.974861,-0.844312,0.487331,-0.222812,-0.500000,-0.866025,0.000517 121 | 18,-0.634842,0.366932,0.679954,-0.589047,0.339649,-0.733255,-0.500000,-0.866025,0.000517 122 | 19,-0.856353,0.494504,0.148747,-0.129074,0.073931,-0.988875,-0.500000,-0.866025,0.000517 123 | 20,-0.780262,0.450225,-0.434153,0.375754,-0.217480,-0.900839,-0.500000,-0.866025,0.000517 124 | 21,-0.433013,0.249483,-0.866174,0.750000,-0.433311,-0.499741,-0.500000,-0.866025,0.000517 125 | 22,0.064718,-0.037960,-0.997181,0.863604,-0.498557,0.075028,-0.500000,-0.866025,0.000517 126 | 23,0.539958,-0.312211,-0.781645,0.677086,-0.390544,0.623723,-0.500000,-0.866025,0.000517 127 | 24,0.827550,-0.477962,-0.294470,0.255265,-0.146807,0.955661,-0.500000,-0.866025,0.000517 128 | 25,0.827550,-0.477610,0.295040,-0.255265,0.147948,0.955485,-0.500000,-0.866025,0.000517 129 | 26,0.539958,-0.311278,0.782017,-0.677086,0.391288,0.623256,-0.500000,-0.866025,0.000517 130 | 27,0.064718,-0.036770,0.997226,-0.863604,0.498646,0.074433,-0.500000,-0.866025,0.000517 131 | 28,-0.433013,0.250517,0.865876,-0.750000,0.432714,-0.500258,-0.500000,-0.866025,0.000517 132 | 29,-0.780262,0.450743,0.433615,-0.375754,0.216404,-0.901098,-0.500000,-0.866025,0.000517 133 | 30,-0.856353,0.494326,-0.149337,0.129074,-0.075111,-0.988786,-0.500000,-0.866025,0.000517 134 | 31,-0.634842,0.366120,-0.680391,0.589047,-0.340524,-0.732849,-0.500000,-0.866025,0.000517 135 | 32,-0.192709,0.110679,-0.974994,0.844312,-0.487597,-0.222230,-0.500000,-0.866025,0.000517 136 | 137 | id_nt,id1,id2 138 | 1,1,2 139 | 2,3,4 140 | 3,5,6 141 | 4,7,8 142 | 5,9,10 143 | 6,11,12 144 | 7,13,14 145 | 8,15,16 146 | 9,17,18 147 | 10,19,20 148 | 11,21,22 149 | 12,23,24 150 | 13,25,26 151 | 14,27,28 152 | 15,29,30 153 | 16,31,32 154 | 17,64,63 155 | 18,62,61 156 | 19,60,59 157 | 20,58,57 158 | 21,56,55 159 | 22,54,53 160 | 23,52,51 161 | 24,50,49 162 | 25,48,47 163 | 26,46,45 164 | 27,44,43 165 | 28,42,41 166 | 29,40,39 167 | 30,38,37 168 | 31,36,35 169 | 32,34,33 170 | -------------------------------------------------------------------------------- /src/PDB_oxDNA.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import sys 4 | import os 5 | import itertools 6 | import numpy as np 7 | 8 | from libs.pdb import Atom, Nucleotide, FROM_ANGSTROM_TO_OXDNA 9 | from libs import base 10 | 11 | def print_usage(): 12 | print("USAGE:", file=sys.stderr) 13 | print("\t%s PDB_file direction [use 35 or 53 if the PDB file has the nucleotides listed in the 3' -> 5' or 5' -> 3' direction, respectively]" % sys.argv[0], file=sys.stderr) 14 | print("\t[-m/--models-as-strands]", file=sys.stderr) 15 | exit(1) 16 | 17 | def parse_options(): 18 | shortArgs = 'm' 19 | longArgs = ['models-as-strands',] 20 | 21 | opts = { 22 | "PDB_file" : "", 23 | "oxDNA_direction" : True, 24 | "models_as_strands" : False, 25 | } 26 | 27 | try: 28 | import getopt 29 | args, positional_args = getopt.gnu_getopt(sys.argv[1:], shortArgs, longArgs) 30 | for k in args: 31 | if k[0] == '-m' or k[0] == '--models-as-strands': 32 | print("## Different models will be interpreted as different strands", file=sys.stderr) 33 | opts["models_as_strands"] = True 34 | 35 | opts['PDB_file'] = positional_args[0] 36 | direction = positional_args[1] 37 | 38 | if direction == "35": 39 | opts["oxDNA_direction"] = True 40 | elif direction == "53": 41 | opts["oxDNA_direction"] = False 42 | else: 43 | print("The 'direction' argument should be either 35 or 53", file=sys.stderr) 44 | exit(1) 45 | except Exception: 46 | print_usage() 47 | 48 | return opts 49 | 50 | if __name__ == '__main__': 51 | if len(sys.argv) < 3: 52 | print_usage() 53 | 54 | opts = parse_options() 55 | 56 | pdb_file = opts['PDB_file'] 57 | oxDNA_direction = opts['oxDNA_direction'] 58 | models_as_strands = opts['models_as_strands'] 59 | 60 | pdb_strands = [] 61 | with open(pdb_file) as f: 62 | strand = [] 63 | old_residue = "" 64 | old_chain = "" 65 | for line in f.readlines(): 66 | line = line.strip() 67 | if line.startswith("ATOM"): 68 | na = Atom(line) 69 | if old_chain != "": 70 | if na.chain_id != old_chain and len(strand) != 0: 71 | print("WARNING: a TER statement separating different strands (%s and %s) is missing" % (na.chain_id, old_chain), file=sys.stderr) 72 | pdb_strands.append(strand) 73 | strand = [] 74 | elif na.chain_id == old_chain and len(strand) == 0: 75 | print("WARNING: a TER statement separates strands having the same chain id (%s)" % na.chain_id, file=sys.stderr) 76 | 77 | if na.alternate != "": 78 | if na.alternate == "A" or na.alternate == "1": 79 | print("Alternate location for atom '%s' of residue '%s' encountered, using the line marked with the '%s' character." % (na.name, na.residue, na.alternate), file=sys.stderr) 80 | if na.residue_idx != old_residue: 81 | nn = Nucleotide(na.residue, na.residue_idx) 82 | if oxDNA_direction: 83 | strand.append(nn) 84 | else: 85 | strand.insert(0, nn) 86 | old_residue = na.residue_idx 87 | nn.add_atom(na) 88 | old_chain = na.chain_id 89 | elif line.startswith("MODEL"): 90 | if not models_as_strands: 91 | N_model = line.split()[1] 92 | print("MODEL line detected: using the first MODEL encountered (%s)" % (N_model), file=sys.stderr) 93 | elif line.startswith("ENDMDL"): 94 | if not models_as_strands: 95 | # by default we treat ENDMDL as the end of the file 96 | break; 97 | else: 98 | # otherwise we treat it as the end of the strand 99 | if len(strand) > 0: 100 | pdb_strands.append(strand) 101 | strand = [] 102 | elif line.startswith("TER"): 103 | pdb_strands.append(strand) 104 | strand = [] 105 | # if the file does not contain any TER line we need to manually add the current strand to the list of strands 106 | elif line == "END" and len(pdb_strands) == 0 and len(strand) > 0: 107 | pdb_strands.append(strand) 108 | strand = [] 109 | 110 | # sometimes files just end (without any END or TER line) 111 | if len(strand) > 0: 112 | pdb_strands.append(strand) 113 | 114 | box_low = np.array([1e6, 1e6, 1e6], dtype=np.float64) 115 | box_high = np.array([-1e6, -1e6, -1e6], dtype=np.float64) 116 | for nucl in itertools.chain(*pdb_strands): 117 | com = nucl.get_com() 118 | for i in range(3): 119 | if com[i] < box_low[i]: 120 | box_low[i] = com[i] 121 | elif com[i] > box_high[i]: 122 | box_high[i] = com[i] 123 | 124 | L = 2 * np.max(box_high - box_low) * FROM_ANGSTROM_TO_OXDNA 125 | box = np.array([L, L, L]) 126 | 127 | print("Using a box of size %g in oxDNA units (twice as big as the PDB bounding box size)" % (L), file=sys.stderr) 128 | 129 | system = base.System(box) 130 | strand = base.Strand() 131 | 132 | for pdb_strand in pdb_strands: 133 | strand = base.Strand() 134 | 135 | for nucl in pdb_strand: 136 | nucl.compute_as() 137 | 138 | com = nucl.get_com() * FROM_ANGSTROM_TO_OXDNA 139 | new_oxDNA_nucl = base.Nucleotide(com, nucl.a1, nucl.a3, nucl.base[0]) 140 | strand.add_nucleotide(new_oxDNA_nucl) 141 | 142 | system.add_strand(strand, check_overlap=False) 143 | 144 | basename = os.path.basename(pdb_file) 145 | topology_file = basename + ".top" 146 | configuration_file = basename + ".oxdna" 147 | system.print_lorenzo_output(configuration_file, topology_file) 148 | 149 | print("## Wrote data to '%s' / '%s'" % (configuration_file, topology_file), file=sys.stderr) 150 | print("## DONE", file=sys.stderr) 151 | -------------------------------------------------------------------------------- /tests/CanDo_oxDNA/correct_output.dat: -------------------------------------------------------------------------------- 1 | t = 0 2 | b = 100.000000 100.000000 100.000000 3 | E = 0 0 0 4 | -4.808579 -0.233204 0.250160 0.000000 0.975061 0.221939 1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 5 | -4.408579 -0.074200 -0.025622 0.000000 0.680610 0.732646 1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 6 | -4.008579 0.212528 -0.163914 0.000000 0.149632 0.988742 1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 7 | -3.608579 0.527336 -0.116656 0.000000 -0.433346 0.901228 1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 8 | -3.208579 0.760822 0.099728 0.000000 -0.865727 0.500517 1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 9 | -2.808579 0.831843 0.410040 -0.000000 -0.997248 -0.074135 1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 10 | -2.408579 0.715719 0.706439 -0.000000 -0.782203 -0.623023 1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 11 | -2.008579 0.452805 0.885921 -0.000000 -0.295325 -0.955397 1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 12 | -1.770736 0.041532 2.030618 -0.255265 0.147948 0.955485 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 13 | -1.742952 -0.436282 2.210229 -0.677086 0.391288 0.623256 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 14 | -1.842233 -0.840666 2.506800 -0.863604 0.498646 0.074433 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 15 | -2.103579 -1.151472 2.817340 -0.750000 0.432714 -0.500258 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 16 | -2.505672 -1.381075 3.034000 -0.375754 0.216404 -0.901098 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 17 | -2.978279 -1.570067 3.081559 0.129074 -0.075111 -0.988786 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 18 | -3.426664 -1.773154 2.943559 0.589047 -0.340524 -0.732849 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 19 | -3.764507 -2.040145 2.668032 0.844312 -0.487597 -0.222230 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 20 | 1.191421 -0.233060 0.490482 0.000000 0.974795 -0.223103 -1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 21 | 0.791421 -0.073728 0.766074 0.000000 0.679735 -0.733458 -1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 22 | 0.391421 0.213165 0.904024 0.000000 0.148452 -0.988920 -1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 23 | -0.008579 0.527917 0.856390 0.000000 -0.434421 -0.900710 -1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 24 | -0.408579 0.761144 0.639728 0.000000 -0.866324 -0.499483 -1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 25 | -0.808579 0.831795 0.329331 -0.000000 -0.997159 0.075325 -1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 26 | -1.208579 0.715317 0.033071 -0.000000 -0.781459 0.623956 -1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 27 | -1.608579 0.452189 -0.146098 -0.000000 -0.294185 0.955749 -1.000000 -0.000000 -0.000000 0. 0. 0. 0. 0. 0. 28 | -2.008579 0.133854 -0.145908 0.000000 0.295325 0.955397 -1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 29 | -2.408579 -0.129060 0.033574 0.000000 0.782203 0.623023 -1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 30 | -2.808579 -0.245185 0.329974 0.000000 0.997248 0.074135 -1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 31 | -3.208579 -0.174163 0.640286 -0.000000 0.865727 -0.500517 -1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 32 | -3.608579 0.059322 0.856670 -0.000000 0.433346 -0.901228 -1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 33 | -4.008579 0.374130 0.903927 -0.000000 -0.149632 -0.988742 -1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 34 | -4.408579 0.660859 0.765636 -0.000000 -0.680610 -0.732646 -1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 35 | -4.808579 0.819862 0.489854 -0.000000 -0.975061 -0.221939 -1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 36 | -2.852650 -2.566750 2.428023 -0.844312 0.487597 0.222230 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 37 | -2.790493 -2.140920 2.152082 -0.589047 0.340524 0.732849 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 38 | -2.838879 -1.651187 2.013670 -0.129074 0.075111 0.988786 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 39 | -2.911486 -1.147359 2.060814 0.375754 -0.216404 0.901098 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 40 | -2.913579 -0.684141 2.277061 0.750000 -0.432714 0.500258 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 41 | -2.774925 -0.302128 2.587188 0.863604 -0.498646 -0.074433 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 42 | -2.474205 -0.013691 2.883345 0.677086 -0.391288 -0.623256 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 43 | -2.046422 0.201315 3.062542 0.255265 -0.147948 -0.955485 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 44 | -1.570736 0.388558 3.062431 -0.255265 0.146807 -0.955661 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 45 | -1.142952 0.603350 2.882977 -0.677086 0.390544 -0.623723 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 46 | -0.842233 0.891433 2.586475 -0.863604 0.498557 -0.075028 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 47 | -0.703579 1.273076 2.275893 -0.750000 0.433311 0.499741 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 48 | -0.705672 1.736035 2.059094 -0.375754 0.217480 0.900839 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 49 | -0.778279 2.239807 2.011347 0.129074 -0.073931 0.988875 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 50 | -0.826664 2.729705 2.149175 0.589047 -0.339649 0.733255 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 51 | -0.764507 3.155863 2.424608 0.844312 -0.487331 0.222812 0.500000 0.866025 -0.000517 0. 0. 0. 0. 0. 0. 52 | 0.147350 2.629546 2.665245 -0.844312 0.487331 -0.222812 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 53 | -0.190493 2.362884 2.941091 -0.589047 0.339649 -0.733255 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 54 | -0.638879 2.159961 3.079332 -0.129074 0.073931 -0.988875 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 55 | -1.111486 1.970913 3.032000 0.375754 -0.217480 -0.900839 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 56 | -1.513579 1.741052 2.815613 0.750000 -0.433311 -0.499741 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 57 | -1.774925 1.429875 2.505445 0.863604 -0.498557 0.075028 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 58 | -1.874205 1.025138 2.209356 0.677086 -0.390544 0.623723 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 59 | -1.846422 0.547109 2.030317 0.255265 -0.146807 0.955661 -0.500000 -0.866025 0.000517 0. 0. 0. 0. 0. 0. 60 | -1.608579 0.134469 0.886111 0.000000 0.294185 -0.955749 1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 61 | -1.208579 -0.128659 0.706943 0.000000 0.781459 -0.623956 1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 62 | -0.808579 -0.245137 0.410682 0.000000 0.997159 -0.075325 1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 63 | -0.408579 -0.174486 0.100286 -0.000000 0.866324 0.499483 1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 64 | -0.008579 0.058742 -0.116377 -0.000000 0.434421 0.900710 1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 65 | 0.391421 0.373493 -0.164010 -0.000000 -0.148452 0.988920 1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 66 | 0.791421 0.660386 -0.026060 -0.000000 -0.679735 0.733458 1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 67 | 1.191421 0.819718 0.249531 -0.000000 -0.974795 0.223103 1.000000 0.000000 0.000000 0. 0. 0. 0. 0. 0. 68 | -------------------------------------------------------------------------------- /tests/LAMMPS_oxDNA/init_lammps.dat: -------------------------------------------------------------------------------- 1 | # LAMMPS data file 2 | 16 atoms 3 | 16 ellipsoids 4 | 14 bonds 5 | 6 | 4 atom types 7 | 1 bond types 8 | 9 | # System size 10 | 0.000000 20.000000 xlo xhi 11 | 0.000000 20.000000 ylo yhi 12 | 0.000000 20.000000 zlo zhi 13 | 14 | Masses 15 | 16 | 1 3.1575 17 | 2 3.1575 18 | 3 3.1575 19 | 4 3.1575 20 | 21 | # Atom-ID, type, position, molecule-ID, ellipsoid flag, density 22 | Atoms 23 | 24 | 1 1 1.555868601500000e+01 9.327746519690001e+00 1.740072261950000e+01 1 1 1 25 | 2 3 1.587203252720000e+01 9.763415784350000e+00 1.737442894620000e+01 1 1 1 26 | 3 2 1.605138931470000e+01 1.024657508090000e+01 1.752632805430000e+01 1 1 1 27 | 4 4 1.614557963680000e+01 1.064647321930000e+01 1.787258628770000e+01 1 1 1 28 | 5 2 1.623578291710000e+01 1.086399131560000e+01 1.835552970900000e+01 1 1 1 29 | 6 2 1.640469332290000e+01 1.086929971300000e+01 1.886555539250000e+01 1 1 1 30 | 7 1 1.670510286860000e+01 1.071319076730000e+01 1.928277140850000e+01 1 1 1 31 | 8 2 1.713984484690000e+01 1.050778198170000e+01 1.952254577160000e+01 1 1 1 32 | 9 3 1.759326310320000e+01 1.093707341650000e+01 1.849779177730000e+01 2 1 1 33 | 10 4 1.741227065470000e+01 1.045366104710000e+01 1.834866325280000e+01 2 1 1 34 | 11 3 1.709694577360000e+01 1.001954851760000e+01 1.837697638120000e+01 2 1 1 35 | 12 3 1.665012175260000e+01 9.746853331260001e+00 1.849809917700000e+01 2 1 1 36 | 13 1 1.612459060610000e+01 9.686367843799999e+00 1.859213971060000e+01 2 1 1 37 | 14 3 1.560304650140000e+01 9.808262398480000e+00 1.854949505640000e+01 2 1 1 38 | 15 2 1.516666886200000e+01 1.001341811130000e+01 1.831249127690000e+01 2 1 1 39 | 16 4 1.486428094740000e+01 1.017108379220000e+01 1.789729471590000e+01 2 1 1 40 | 41 | # Atom-ID, translational, rotational velocity 42 | Velocities 43 | 44 | 1 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 45 | 2 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 46 | 3 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 47 | 4 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 48 | 5 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 49 | 6 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 50 | 7 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 51 | 8 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 52 | 9 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 53 | 10 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 54 | 11 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 55 | 12 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 56 | 13 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 57 | 14 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 58 | 15 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 59 | 16 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 60 | 61 | # Atom-ID, shape, quaternion 62 | Ellipsoids 63 | 64 | 1 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 2.759833058363645e-01 3.667393762083170e-01 3.406667382569866e-01 8.205373960297678e-01 65 | 2 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 9.671149726124194e-03 4.538776726309783e-01 2.110607848547155e-01 8.656528589721015e-01 66 | 3 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -2.575824769045076e-01 4.968317240930596e-01 6.090841116799247e-02 8.264984397900866e-01 67 | 4 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -4.997608730415329e-01 4.914200243294680e-01 -9.517329617284410e-02 7.068857567955277e-01 68 | 5 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 6.932883701200924e-01 -4.381693934114134e-01 2.419900396579633e-01 -5.184589079570696e-01 69 | 6 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 8.193253845842962e-01 -3.422636926804935e-01 3.652494507717708e-01 -2.795609371128728e-01 70 | 7 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 8.656024203634226e-01 -2.130391843712408e-01 4.529524285604339e-01 -1.344816882056156e-02 71 | 8 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 8.276144841336460e-01 -6.307566183857234e-02 4.965612323773009e-01 2.539737565886701e-01 72 | 9 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -4.965612323773010e-01 -2.539737565886702e-01 8.276144841336462e-01 -6.307566183857236e-02 73 | 10 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -4.529524285604339e-01 1.344816882056156e-02 8.656024203634226e-01 -2.130391843712408e-01 74 | 11 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -3.652494507717708e-01 2.795609371128728e-01 8.193253845842962e-01 -3.422636926804935e-01 75 | 12 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -2.419900396582725e-01 5.184589079567070e-01 6.932883701202278e-01 -4.381693934114575e-01 76 | 13 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -9.517329617284412e-02 7.068857567955278e-01 4.997608730415330e-01 -4.914200243294681e-01 77 | 14 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 6.090841116799247e-02 8.264984397900866e-01 2.575824769045076e-01 -4.968317240930596e-01 78 | 15 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 2.110607848547155e-01 8.656528589721014e-01 -9.671149726124194e-03 -4.538776726309783e-01 79 | 16 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 3.406667382569866e-01 8.205373960297679e-01 -2.759833058363645e-01 -3.667393762083169e-01 80 | 81 | # Bond topology 82 | Bonds 83 | 84 | 1 1 1 2 85 | 2 1 2 3 86 | 3 1 3 4 87 | 4 1 4 5 88 | 5 1 5 6 89 | 6 1 6 7 90 | 7 1 7 8 91 | 8 1 9 10 92 | 9 1 10 11 93 | 10 1 11 12 94 | 11 1 12 13 95 | 12 1 13 14 96 | 13 1 14 15 97 | 14 1 15 16 98 | -------------------------------------------------------------------------------- /tests/oxDNA_LAMMPS/correct_output.dat: -------------------------------------------------------------------------------- 1 | # LAMMPS data file 2 | 16 atoms 3 | 16 ellipsoids 4 | 14 bonds 5 | 6 | 4 atom types 7 | 1 bond types 8 | 9 | # System size 10 | 0.000000 20.000000 xlo xhi 11 | 0.000000 20.000000 ylo yhi 12 | 0.000000 20.000000 zlo zhi 13 | 14 | Masses 15 | 16 | 1 3.1575 17 | 2 3.1575 18 | 3 3.1575 19 | 4 3.1575 20 | 21 | # Atom-ID, type, position, molecule-ID, ellipsoid flag, density 22 | Atoms 23 | 24 | 1 1 1.555868601500000e+01 9.327746519690001e+00 1.740072261950000e+01 1 1 1 25 | 2 3 1.587203252720000e+01 9.763415784350000e+00 1.737442894620000e+01 1 1 1 26 | 3 2 1.605138931470000e+01 1.024657508090000e+01 1.752632805430000e+01 1 1 1 27 | 4 4 1.614557963680000e+01 1.064647321930000e+01 1.787258628770000e+01 1 1 1 28 | 5 2 1.623578291710000e+01 1.086399131560000e+01 1.835552970900000e+01 1 1 1 29 | 6 2 1.640469332290000e+01 1.086929971300000e+01 1.886555539250000e+01 1 1 1 30 | 7 1 1.670510286860000e+01 1.071319076730000e+01 1.928277140850000e+01 1 1 1 31 | 8 2 1.713984484690000e+01 1.050778198170000e+01 1.952254577160000e+01 1 1 1 32 | 9 3 1.759326310320000e+01 1.093707341650000e+01 1.849779177730000e+01 2 1 1 33 | 10 4 1.741227065470000e+01 1.045366104710000e+01 1.834866325280000e+01 2 1 1 34 | 11 3 1.709694577360000e+01 1.001954851760000e+01 1.837697638120000e+01 2 1 1 35 | 12 3 1.665012175260000e+01 9.746853331260001e+00 1.849809917700000e+01 2 1 1 36 | 13 1 1.612459060610000e+01 9.686367843799999e+00 1.859213971060000e+01 2 1 1 37 | 14 3 1.560304650140000e+01 9.808262398480000e+00 1.854949505640000e+01 2 1 1 38 | 15 2 1.516666886200000e+01 1.001341811130000e+01 1.831249127690000e+01 2 1 1 39 | 16 4 1.486428094740000e+01 1.017108379220000e+01 1.789729471590000e+01 2 1 1 40 | 41 | # Atom-ID, translational, rotational velocity 42 | Velocities 43 | 44 | 1 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 45 | 2 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 46 | 3 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 47 | 4 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 48 | 5 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 49 | 6 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 50 | 7 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 51 | 8 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 52 | 9 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 53 | 10 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 54 | 11 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 55 | 12 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 56 | 13 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 57 | 14 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 58 | 15 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 59 | 16 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 0.000000000000000e+00 60 | 61 | # Atom-ID, shape, quaternion 62 | Ellipsoids 63 | 64 | 1 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 2.759833058363645e-01 3.667393762083170e-01 3.406667382569866e-01 8.205373960297678e-01 65 | 2 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 9.671149726124194e-03 4.538776726309783e-01 2.110607848547155e-01 8.656528589721015e-01 66 | 3 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -2.575824769045076e-01 4.968317240930596e-01 6.090841116799247e-02 8.264984397900866e-01 67 | 4 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -4.997608730415329e-01 4.914200243294680e-01 -9.517329617284410e-02 7.068857567955277e-01 68 | 5 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 6.932883701200924e-01 -4.381693934114134e-01 2.419900396579633e-01 -5.184589079570696e-01 69 | 6 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 8.193253845842962e-01 -3.422636926804935e-01 3.652494507717708e-01 -2.795609371128728e-01 70 | 7 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 8.656024203634226e-01 -2.130391843712408e-01 4.529524285604339e-01 -1.344816882056156e-02 71 | 8 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 8.276144841336460e-01 -6.307566183857234e-02 4.965612323773009e-01 2.539737565886701e-01 72 | 9 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -4.965612323773010e-01 -2.539737565886702e-01 8.276144841336462e-01 -6.307566183857236e-02 73 | 10 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -4.529524285604339e-01 1.344816882056156e-02 8.656024203634226e-01 -2.130391843712408e-01 74 | 11 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -3.652494507717708e-01 2.795609371128728e-01 8.193253845842962e-01 -3.422636926804935e-01 75 | 12 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -2.419900396582725e-01 5.184589079567070e-01 6.932883701202278e-01 -4.381693934114575e-01 76 | 13 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 -9.517329617284412e-02 7.068857567955278e-01 4.997608730415330e-01 -4.914200243294681e-01 77 | 14 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 6.090841116799247e-02 8.264984397900866e-01 2.575824769045076e-01 -4.968317240930596e-01 78 | 15 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 2.110607848547155e-01 8.656528589721014e-01 -9.671149726124194e-03 -4.538776726309783e-01 79 | 16 1.173984503142341e+00 1.173984503142341e+00 1.173984503142341e+00 3.406667382569866e-01 8.205373960297679e-01 -2.759833058363645e-01 -3.667393762083169e-01 80 | 81 | # Bond topology 82 | Bonds 83 | 84 | 1 1 1 2 85 | 2 1 2 3 86 | 3 1 3 4 87 | 4 1 4 5 88 | 5 1 5 6 89 | 6 1 6 7 90 | 7 1 7 8 91 | 8 1 9 10 92 | 9 1 10 11 93 | 10 1 11 12 94 | 11 1 12 13 95 | 12 1 13 14 96 | 13 1 14 15 97 | 14 1 15 16 98 | -------------------------------------------------------------------------------- /tests/XYZ_oxDNA/correct_simple_output.top: -------------------------------------------------------------------------------- 1 | 420 2 2 | 1 G 209 1 3 | 1 A 0 2 4 | 1 A 1 3 5 | 1 A 2 4 6 | 1 A 3 5 7 | 1 A 4 6 8 | 1 A 5 7 9 | 1 A 6 8 10 | 1 C 7 9 11 | 1 A 8 10 12 | 1 A 9 11 13 | 1 A 10 12 14 | 1 A 11 13 15 | 1 A 12 14 16 | 1 A 13 15 17 | 1 A 14 16 18 | 1 A 15 17 19 | 1 A 16 18 20 | 1 A 17 19 21 | 1 A 18 20 22 | 1 A 19 21 23 | 1 A 20 22 24 | 1 A 21 23 25 | 1 A 22 24 26 | 1 A 23 25 27 | 1 A 24 26 28 | 1 A 25 27 29 | 1 A 26 28 30 | 1 A 27 29 31 | 1 A 28 30 32 | 1 A 29 31 33 | 1 A 30 32 34 | 1 C 31 33 35 | 1 C 32 34 36 | 1 A 33 35 37 | 1 A 34 36 38 | 1 A 35 37 39 | 1 A 36 38 40 | 1 A 37 39 41 | 1 A 38 40 42 | 1 A 39 41 43 | 1 A 40 42 44 | 1 A 41 43 45 | 1 T 42 44 46 | 1 A 43 45 47 | 1 A 44 46 48 | 1 A 45 47 49 | 1 A 46 48 50 | 1 A 47 49 51 | 1 A 48 50 52 | 1 A 49 51 53 | 1 A 50 52 54 | 1 A 51 53 55 | 1 A 52 54 56 | 1 A 53 55 57 | 1 A 54 56 58 | 1 A 55 57 59 | 1 A 56 58 60 | 1 A 57 59 61 | 1 A 58 60 62 | 1 A 59 61 63 | 1 A 60 62 64 | 1 A 61 63 65 | 1 A 62 64 66 | 1 A 63 65 67 | 1 A 64 66 68 | 1 A 65 67 69 | 1 A 66 68 70 | 1 A 67 69 71 | 1 A 68 70 72 | 1 A 69 71 73 | 1 A 70 72 74 | 1 A 71 73 75 | 1 A 72 74 76 | 1 A 73 75 77 | 1 A 74 76 78 | 1 A 75 77 79 | 1 A 76 78 80 | 1 A 77 79 81 | 1 A 78 80 82 | 1 A 79 81 83 | 1 A 80 82 84 | 1 A 81 83 85 | 1 A 82 84 86 | 1 A 83 85 87 | 1 A 84 86 88 | 1 A 85 87 89 | 1 A 86 88 90 | 1 A 87 89 91 | 1 A 88 90 92 | 1 A 89 91 93 | 1 A 90 92 94 | 1 A 91 93 95 | 1 A 92 94 96 | 1 A 93 95 97 | 1 A 94 96 98 | 1 A 95 97 99 | 1 A 96 98 100 | 1 A 97 99 101 | 1 A 98 100 102 | 1 A 99 101 103 | 1 A 100 102 104 | 1 A 101 103 105 | 1 A 102 104 106 | 1 A 103 105 107 | 1 A 104 106 108 | 1 A 105 107 109 | 1 A 106 108 110 | 1 A 107 109 111 | 1 A 108 110 112 | 1 A 109 111 113 | 1 A 110 112 114 | 1 A 111 113 115 | 1 A 112 114 116 | 1 A 113 115 117 | 1 A 114 116 118 | 1 A 115 117 119 | 1 A 116 118 120 | 1 A 117 119 121 | 1 A 118 120 122 | 1 A 119 121 123 | 1 A 120 122 124 | 1 A 121 123 125 | 1 A 122 124 126 | 1 A 123 125 127 | 1 A 124 126 128 | 1 A 125 127 129 | 1 A 126 128 130 | 1 A 127 129 131 | 1 A 128 130 132 | 1 A 129 131 133 | 1 A 130 132 134 | 1 A 131 133 135 | 1 A 132 134 136 | 1 A 133 135 137 | 1 A 134 136 138 | 1 A 135 137 139 | 1 A 136 138 140 | 1 A 137 139 141 | 1 A 138 140 142 | 1 A 139 141 143 | 1 A 140 142 144 | 1 A 141 143 145 | 1 A 142 144 146 | 1 A 143 145 147 | 1 A 144 146 148 | 1 A 145 147 149 | 1 A 146 148 150 | 1 A 147 149 151 | 1 A 148 150 152 | 1 A 149 151 153 | 1 A 150 152 154 | 1 A 151 153 155 | 1 A 152 154 156 | 1 A 153 155 157 | 1 A 154 156 158 | 1 A 155 157 159 | 1 A 156 158 160 | 1 A 157 159 161 | 1 A 158 160 162 | 1 A 159 161 163 | 1 A 160 162 164 | 1 A 161 163 165 | 1 A 162 164 166 | 1 A 163 165 167 | 1 A 164 166 168 | 1 A 165 167 169 | 1 A 166 168 170 | 1 A 167 169 171 | 1 A 168 170 172 | 1 A 169 171 173 | 1 A 170 172 174 | 1 A 171 173 175 | 1 A 172 174 176 | 1 A 173 175 177 | 1 A 174 176 178 | 1 A 175 177 179 | 1 A 176 178 180 | 1 A 177 179 181 | 1 C 178 180 182 | 1 A 179 181 183 | 1 A 180 182 184 | 1 A 181 183 185 | 1 A 182 184 186 | 1 A 183 185 187 | 1 A 184 186 188 | 1 A 185 187 189 | 1 A 186 188 190 | 1 A 187 189 191 | 1 A 188 190 192 | 1 A 189 191 193 | 1 A 190 192 194 | 1 G 191 193 195 | 1 A 192 194 196 | 1 A 193 195 197 | 1 A 194 196 198 | 1 A 195 197 199 | 1 A 196 198 200 | 1 A 197 199 201 | 1 A 198 200 202 | 1 A 199 201 203 | 1 A 200 202 204 | 1 A 201 203 205 | 1 A 202 204 206 | 1 A 203 205 207 | 1 A 204 206 208 | 1 A 205 207 209 | 1 A 206 208 210 | 1 A 207 209 211 | 1 A 208 0 212 | 2 T 419 211 213 | 2 T 210 212 214 | 2 T 211 213 215 | 2 T 212 214 216 | 2 T 213 215 217 | 2 T 214 216 218 | 2 T 215 217 219 | 2 T 216 218 220 | 2 T 217 219 221 | 2 T 218 220 222 | 2 T 219 221 223 | 2 T 220 222 224 | 2 T 221 223 225 | 2 T 222 224 226 | 2 T 223 225 227 | 2 T 224 226 228 | 2 T 225 227 229 | 2 C 226 228 230 | 2 T 227 229 231 | 2 T 228 230 232 | 2 T 229 231 233 | 2 T 230 232 234 | 2 T 231 233 235 | 2 T 232 234 236 | 2 T 233 235 237 | 2 T 234 236 238 | 2 T 235 237 239 | 2 T 236 238 240 | 2 T 237 239 241 | 2 T 238 240 242 | 2 G 239 241 243 | 2 T 240 242 244 | 2 T 241 243 245 | 2 T 242 244 246 | 2 T 243 245 247 | 2 T 244 246 248 | 2 T 245 247 249 | 2 T 246 248 250 | 2 T 247 249 251 | 2 T 248 250 252 | 2 T 249 251 253 | 2 T 250 252 254 | 2 T 251 253 255 | 2 T 252 254 256 | 2 T 253 255 257 | 2 T 254 256 258 | 2 T 255 257 259 | 2 T 256 258 260 | 2 T 257 259 261 | 2 T 258 260 262 | 2 T 259 261 263 | 2 T 260 262 264 | 2 T 261 263 265 | 2 T 262 264 266 | 2 T 263 265 267 | 2 T 264 266 268 | 2 T 265 267 269 | 2 T 266 268 270 | 2 T 267 269 271 | 2 T 268 270 272 | 2 T 269 271 273 | 2 T 270 272 274 | 2 T 271 273 275 | 2 T 272 274 276 | 2 T 273 275 277 | 2 T 274 276 278 | 2 T 275 277 279 | 2 T 276 278 280 | 2 T 277 279 281 | 2 T 278 280 282 | 2 T 279 281 283 | 2 T 280 282 284 | 2 T 281 283 285 | 2 T 282 284 286 | 2 T 283 285 287 | 2 T 284 286 288 | 2 T 285 287 289 | 2 T 286 288 290 | 2 T 287 289 291 | 2 T 288 290 292 | 2 T 289 291 293 | 2 T 290 292 294 | 2 T 291 293 295 | 2 T 292 294 296 | 2 T 293 295 297 | 2 T 294 296 298 | 2 T 295 297 299 | 2 T 296 298 300 | 2 T 297 299 301 | 2 T 298 300 302 | 2 T 299 301 303 | 2 T 300 302 304 | 2 T 301 303 305 | 2 T 302 304 306 | 2 T 303 305 307 | 2 T 304 306 308 | 2 T 305 307 309 | 2 T 306 308 310 | 2 T 307 309 311 | 2 T 308 310 312 | 2 T 309 311 313 | 2 T 310 312 314 | 2 T 311 313 315 | 2 T 312 314 316 | 2 T 313 315 317 | 2 T 314 316 318 | 2 T 315 317 319 | 2 T 316 318 320 | 2 T 317 319 321 | 2 T 318 320 322 | 2 T 319 321 323 | 2 T 320 322 324 | 2 T 321 323 325 | 2 T 322 324 326 | 2 T 323 325 327 | 2 T 324 326 328 | 2 T 325 327 329 | 2 T 326 328 330 | 2 T 327 329 331 | 2 T 328 330 332 | 2 T 329 331 333 | 2 T 330 332 334 | 2 T 331 333 335 | 2 T 332 334 336 | 2 T 333 335 337 | 2 T 334 336 338 | 2 T 335 337 339 | 2 T 336 338 340 | 2 T 337 339 341 | 2 T 338 340 342 | 2 T 339 341 343 | 2 T 340 342 344 | 2 T 341 343 345 | 2 T 342 344 346 | 2 T 343 345 347 | 2 T 344 346 348 | 2 T 345 347 349 | 2 T 346 348 350 | 2 T 347 349 351 | 2 T 348 350 352 | 2 T 349 351 353 | 2 T 350 352 354 | 2 T 351 353 355 | 2 T 352 354 356 | 2 T 353 355 357 | 2 T 354 356 358 | 2 T 355 357 359 | 2 T 356 358 360 | 2 T 357 359 361 | 2 T 358 360 362 | 2 T 359 361 363 | 2 T 360 362 364 | 2 T 361 363 365 | 2 T 362 364 366 | 2 T 363 365 367 | 2 T 364 366 368 | 2 T 365 367 369 | 2 T 366 368 370 | 2 T 367 369 371 | 2 T 368 370 372 | 2 T 369 371 373 | 2 T 370 372 374 | 2 T 371 373 375 | 2 T 372 374 376 | 2 T 373 375 377 | 2 T 374 376 378 | 2 A 375 377 379 | 2 T 376 378 380 | 2 T 377 379 381 | 2 T 378 380 382 | 2 T 379 381 383 | 2 T 380 382 384 | 2 T 381 383 385 | 2 T 382 384 386 | 2 T 383 385 387 | 2 T 384 386 388 | 2 G 385 387 389 | 2 G 386 388 390 | 2 T 387 389 391 | 2 T 388 390 392 | 2 T 389 391 393 | 2 T 390 392 394 | 2 T 391 393 395 | 2 T 392 394 396 | 2 T 393 395 397 | 2 T 394 396 398 | 2 T 395 397 399 | 2 T 396 398 400 | 2 T 397 399 401 | 2 T 398 400 402 | 2 T 399 401 403 | 2 T 400 402 404 | 2 T 401 403 405 | 2 T 402 404 406 | 2 T 403 405 407 | 2 T 404 406 408 | 2 T 405 407 409 | 2 T 406 408 410 | 2 T 407 409 411 | 2 T 408 410 412 | 2 T 409 411 413 | 2 G 410 412 414 | 2 T 411 413 415 | 2 T 412 414 416 | 2 T 413 415 417 | 2 T 414 416 418 | 2 T 415 417 419 | 2 T 416 418 420 | 2 T 417 419 421 | 2 C 418 210 422 | -------------------------------------------------------------------------------- /src/libs/reader_lammps_init.py: -------------------------------------------------------------------------------- 1 | import numpy as np 2 | import sys 3 | 4 | SECTIONS = set([ 5 | 'Atoms', 6 | 'Velocities', 7 | 'Ellipsoids', 8 | 'Bonds', 9 | ]) 10 | 11 | HEADERS = set([ 12 | 'atoms', 13 | 'bonds', 14 | 'atom types', 15 | 'bond types', 16 | 'ellipsoids', 17 | 'xlo xhi', 18 | 'ylo yhi', 19 | 'zlo zhi', 20 | ]) 21 | 22 | 23 | class Lammps_parser(object): 24 | 25 | def __init__(self, filename): 26 | self.filename = filename 27 | 28 | head, sects = self.grab_datafile() 29 | 30 | self.natoms = int(head['atoms']) 31 | self.nbonds = int(head['bonds']) 32 | self.nellipsoids = int(head['ellipsoids']) 33 | x1, x2 = np.float32(head['xlo xhi'].split()) 34 | self.Lx = x2 - x1 35 | y1, y2 = np.float32(head['ylo yhi'].split()) 36 | self.Ly = y2 - y1 37 | z1, z2 = np.float32(head['zlo zhi'].split()) 38 | self.Lz = z2 - z1 39 | 40 | self.parse_Atoms_header(sects['Atoms']) 41 | self.parse_bonds(sects['Bonds']) 42 | self.parse_ellipsoids(sects['Ellipsoids']) 43 | 44 | self.parse_velocities(sects['Velocities']) 45 | 46 | # checking the nucleotides have indexes ordered the same way as bonds and are compatible with strands 47 | for i in range(self.natoms): 48 | next_bond = self.bonds[i][1] 49 | 50 | if next_bond != -1: 51 | #check the consecutive bond is on the same strand 52 | if self.strand[i] != self.strand[next_bond]: 53 | print("Wrong bond arising between two different strands", file=sys.stderr) 54 | #check the right bond is an higher index (except from the circular closure) 55 | if next_bond == i-1: 56 | print("The bonds should be in incremental order (i i+1) except for strand circularization N 0", file=sys.stderr) 57 | if next_bond > i+1: 58 | print("The bonds should be in incremental order (i i+1) except for strand circularization N 0", file=sys.stderr) 59 | if next_bond < i+1: 60 | if self.bonds[next_bond][1] != next_bond + 1: 61 | print("The bonds should be in incremental order (i i+1) except for strand circularization N 0", file=sys.stderr) 62 | 63 | # more check to insert about completely random ordering 64 | 65 | def parse_Atoms_header(self, datalines): 66 | if self.natoms != len(datalines): 67 | raise ValueError("Number of atoms in header %d and in Atoms %d do not coincide" % (self.natoms, len(datalines))) 68 | # Fields per line 69 | if len(datalines[1].split()) < 8: 70 | raise ValueError("Atoms section should be the default one # Atom-ID, type, position, molecule-ID, ellipsoid flag, density with at least 8 columns and not %d" % len(datalines[1].split())) 71 | N = self.natoms 72 | # atom ids aren't necessarily sequential 73 | self.bases = np.zeros(N, dtype=int) 74 | self.strand = np.zeros(N, dtype=int) 75 | self.xyz = np.zeros((N, 3), dtype=float) 76 | for _, line in enumerate(datalines): 77 | line = line.split() 78 | index = int(line[0]) - 1 79 | self.bases[index] = line[1] 80 | self.strand[index] = line[5] 81 | self.xyz[index, :] = line[2:5] 82 | 83 | self.nstrands = len(np.unique(self.strand)) 84 | 85 | def parse_velocities(self, datalines): 86 | if self.natoms != len(datalines): 87 | raise ValueError("Velocities section do not contain the same amount of particles as number of atoms %d != %d " % self.natoms, len(datalines)) 88 | if len(datalines[1].split()) != 7: 89 | raise ValueError("Velocities section should be the default one # Atom-ID, translational, rotational velocity with 7 columns and not %d" % len(datalines[1].split())) 90 | else: 91 | N = self.natoms 92 | self.v = np.zeros((N, 3), dtype=float) 93 | self.Lv = np.zeros((N, 3), dtype=float) 94 | for _, line in enumerate(datalines): 95 | line = line.split() 96 | index = int(line[0]) - 1 97 | self.v[index] = line[1:4] 98 | self.Lv[index] = line[4:7] 99 | 100 | def _N_strands_from_bonds(self, bonds): 101 | ''' 102 | This method partition nucleotides into strands according to their nearest neighbours and returns the number of such strands. 103 | ''' 104 | def flip_neighs(bonds, clusters, i): 105 | for neigh in bonds[i]: 106 | if clusters[i] > clusters[neigh]: 107 | clusters[i] = clusters[neigh] 108 | flip_neighs(bonds, clusters, neigh) 109 | 110 | 111 | N = len(bonds) 112 | strands = np.arange(0, N, 1, dtype=np.int_) 113 | 114 | for i in range(N): 115 | flip_neighs(bonds, strands, i) 116 | 117 | return len(np.unique(strands)) 118 | 119 | def parse_bonds(self, datalines): 120 | if len(datalines[1].split()) != 4: 121 | raise ValueError("Bonds section should have 4 columns and not %d" % len(datalines[1].split())) 122 | 123 | if self.nbonds != len(datalines): 124 | raise ValueError("Number of atoms in header %d and in Bonds %d do not coincide" % self.nbonds, len(datalines)) 125 | 126 | # creating a vector indicating for each particle who it is bonded too on its left and right in order of increasing index 127 | natoms = self.natoms 128 | self.bonds = np.ones((natoms, 2), dtype=int) * (-1) 129 | for _, line in enumerate(datalines): 130 | line = line.split() 131 | p1 = int(line[2]) - 1 132 | p2 = int(line[3]) - 1 133 | 134 | self.bonds[p1][1] = p2 135 | self.bonds[p2][0] = p1 136 | 137 | N_strands = self._N_strands_from_bonds(self.bonds) 138 | if N_strands != self.nstrands: 139 | raise ValueError("There is a mismatch between the number of strands as detected by the Atoms (%d) and Bonds (%d) sections" % (self.nstrands, N_strands)) 140 | 141 | N_ends_3p = 0 142 | N_ends_5p = 0 143 | for b in self.bonds: 144 | if b[0] == -1: 145 | N_ends_3p += 1 146 | elif b[1] == -1: 147 | N_ends_5p += 1 148 | 149 | if N_ends_3p != N_ends_5p: 150 | raise ValueError("There is a mismatch between the number of 3' ends (%d) and 5' ends (%d)" % (N_ends_3p, N_ends_5p), file=sys.stderr) 151 | 152 | def parse_ellipsoids(self, datalines): 153 | if len(datalines[1].split()) != 8: 154 | raise ValueError("Ellipsoid section should be the default one # Atom-ID, shape, quaternion with 8 columns and not %d" % len(datalines[1].split())) 155 | 156 | if self.nellipsoids != len(datalines): 157 | raise ValueError("Number of ellipsoids in header %d and in Bonds %d do not coincide" % self.nellipsoids, len(datalines)) 158 | 159 | nellipsoids = self.nellipsoids 160 | self.ellipsoids = np.zeros((nellipsoids, 4), dtype=float) 161 | for _, line in enumerate(datalines): 162 | line = line.split() 163 | index = int(line[0]) - 1 164 | self.ellipsoids[index, :] = line[4:8] 165 | 166 | def iterdata(self): 167 | with open(self.filename) as f: 168 | for line in f: 169 | line = line.partition('#')[0].strip() 170 | if line: 171 | yield line 172 | 173 | def grab_datafile(self): 174 | f = list(self.iterdata()) 175 | starts = [i for i, line in enumerate(f) 176 | if line.split()[0] in SECTIONS] 177 | starts += [None] 178 | 179 | # we save here the lammps init header information (mass, N, etc) 180 | header = {} 181 | for line in f[:starts[0]]: 182 | for token in HEADERS: 183 | if line.endswith(token): 184 | header[token] = line.split(token)[0] 185 | 186 | # we associate to each section the content (Atoms, Bonds, etc) 187 | sects = {f[l]:f[l + 1:starts[i + 1]] for i, l in enumerate(starts[:-1])} 188 | 189 | if 'Atoms' not in sects: 190 | raise ValueError("Data file was missing Atoms section") 191 | 192 | return header, sects 193 | 194 | -------------------------------------------------------------------------------- /src/LAMMPS_oxDNA.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import numpy as np 4 | import sys, os, inspect 5 | from libs import base 6 | from libs import reader_lammps_init 7 | from libs.constants import mass_in_lammps, inertia_in_lammps, number_oxdna_to_lammps 8 | 9 | 10 | def quat_to_exyz(myquat): 11 | sqw = myquat[0] * myquat[0]; 12 | sqx = myquat[1] * myquat[1]; 13 | sqy = myquat[2] * myquat[2]; 14 | sqz = myquat[3] * myquat[3]; 15 | 16 | invs = 1 / (sqx + sqy + sqz + sqw) 17 | m00 = (sqx - sqy - sqz + sqw) * invs ; 18 | m22 = (-sqx - sqy + sqz + sqw) * invs ; 19 | 20 | tmp1 = myquat[1] * myquat[2]; 21 | tmp2 = myquat[3] * myquat[0]; 22 | m10 = 2.0 * (tmp1 + tmp2) * invs ; 23 | 24 | tmp1 = myquat[1] * myquat[3]; 25 | tmp2 = myquat[2] * myquat[0]; 26 | m20 = 2.0 * (tmp1 - tmp2) * invs ; 27 | m02 = 2.0 * (tmp1 + tmp2) * invs ; 28 | tmp1 = myquat[2] * myquat[3]; 29 | tmp2 = myquat[1] * myquat[0]; 30 | m12 = 2.0 * (tmp1 - tmp2) * invs ; 31 | 32 | mya1 = np.array([m00, m10, m20]) 33 | mya3 = np.array([m02, m12, m22]) 34 | 35 | return mya1, mya3 36 | 37 | 38 | if __name__ == '__main__': 39 | if len(sys.argv) < 2: 40 | print("USAGE:", file=sys.stderr) 41 | print("\t%s lammps_data_file [lammps_trajectory_file]" % sys.argv[0], file=sys.stderr) 42 | sys.exit(1) 43 | 44 | try: 45 | conf = reader_lammps_init.Lammps_parser(sys.argv[1]) 46 | except ValueError as e: 47 | print(e, file=sys.stderr) 48 | exit(1) 49 | 50 | N = conf.natoms 51 | box = np.array([0, 0., 0.]) 52 | box[0] = conf.Lx 53 | box[1] = conf.Ly 54 | box[2] = conf.Lz 55 | 56 | system = base.System(box) 57 | 58 | strands = [] 59 | for i in range(conf.nstrands): 60 | strands.append(base.Strand()) 61 | 62 | for i in range(N): 63 | cm = conf.xyz[i,:] 64 | quaternions = conf.ellipsoids[i,:] 65 | a1, a3 = quat_to_exyz(quaternions) 66 | b = number_oxdna_to_lammps[(conf.bases[i]+3)%4] 67 | 68 | v = np.array(conf.v[i,:]) * np.sqrt(mass_in_lammps) 69 | Lv = np.array(conf.Lv[i,:]) / np.sqrt(inertia_in_lammps) 70 | 71 | strands[conf.strand[i] - 1].add_nucleotide(base.Nucleotide(cm, a1, a3, b, b, v, Lv)) 72 | 73 | # close strand 74 | next_bond = conf.bonds[i][1] 75 | if next_bond != -1 and next_bond != i + 1: 76 | if conf.strand[i] != conf.strand[next_bond]: 77 | print("Wrong bond arising between two different strands", file=sys.stderr) 78 | else: 79 | strands[conf.strand[i] - 1].make_circular() 80 | 81 | for i in range(conf.nstrands): 82 | system.add_strand(strands[i]) 83 | 84 | basename = os.path.basename(sys.argv[1]) 85 | topology_file = basename + ".top" 86 | configuration_file = basename + ".oxdna" 87 | system.print_lorenzo_output(configuration_file, topology_file) 88 | 89 | # optional conversion of LAMMPS trajectory into native oxDNA format 90 | if len(sys.argv) == 3: 91 | with open(sys.argv[2], 'r') as lmptrj, open(configuration_file, 'w') as oxconf: 92 | line = lmptrj.readline() 93 | 94 | while line: 95 | if line.startswith('ITEM: TIMESTEP'): 96 | t = int(lmptrj.readline()) 97 | 98 | if line.startswith('ITEM: NUMBER OF ATOMS'): 99 | natoms = int(lmptrj.readline()) 100 | if natoms != conf.natoms: 101 | print("ERROR: A configuration stored in the trajectory file contains a number of nucleotides %d that differs from the %d in the datafile" % \ 102 | (natoms, conf.natoms), file=sys.stderr) 103 | sys.exit(1) 104 | if line.startswith('ITEM: BOX BOUNDS'): 105 | line = lmptrj.readline() 106 | xlo, xhi = np.float32(line.split()[0]), np.float32(line.split()[1]) 107 | Lx = xhi - xlo 108 | line = lmptrj.readline() 109 | ylo, yhi = np.float32(line.split()[0]), np.float32(line.split()[1]) 110 | Ly = yhi - ylo 111 | line = lmptrj.readline() 112 | zlo, zhi = np.float32(line.split()[0]), np.float32(line.split()[1]) 113 | Lz = zhi - zlo 114 | 115 | if line.startswith('ITEM: ATOMS'): 116 | aux = line.split() 117 | 118 | # find column number in trajectory file (the -2 and -1 handle the "ITEM:" and "ATOMS" keywords) 119 | 120 | line_ref1 = inspect.currentframe().f_lineno 121 | try: 122 | keyx = aux.index('x') - 2 # x 123 | keyz = aux.index('z') - 1 # z (exclusive) 124 | 125 | keyvx = aux.index('vx') - 2 # vx 126 | keyvz = aux.index('vz') - 1 # vz (exclusive) 127 | 128 | keylx = aux.index('angmomx') - 2 if 'angmomx' in aux else \ 129 | aux.index('AngularMomentumX') - 2 # angular momentum x 130 | keylz = aux.index('angmomz') - 1 if 'angmomz' in aux else \ 131 | aux.index('AngularMomentumZ') - 1 # angular momentum z (exclusive) 132 | 133 | keyq0 = aux.index('c_quat[1]') - 2 if 'c_quat[1]' in aux else \ 134 | aux.index('quatw') - 2 if 'quatw' in aux else \ 135 | aux.index('c_quat1') - 2 # quat0 136 | keyq3 = aux.index('c_quat[4]') - 1 if 'c_quat[4]' in aux else \ 137 | aux.index('quatk') - 1 if 'quatk' in aux else \ 138 | aux.index('c_quat4') - 1 # quat3 (exclusive) 139 | except ValueError as e: 140 | line_ref2 = inspect.currentframe().f_lineno 141 | print(f"ValueError: {e}.\n Required columns not found in the LAMMPS dump/trajectory file.",\ 142 | f"\n See Lines {line_ref1} to {line_ref2} in LAMMPS_oxDNA.py for accepted syntax and values.", file=sys.stderr) 143 | sys.exit(1) 144 | 145 | N = natoms 146 | 147 | # read position, velocity, quaternions, angular momentum 148 | 149 | xyz = np.zeros((N, 3), dtype=float) 150 | vel = np.zeros((N, 3), dtype=float) 151 | quat = np.zeros((N, 4), dtype=float) 152 | angmom = np.zeros((N, 3), dtype=float) 153 | 154 | for n in range(N): 155 | line = lmptrj.readline() 156 | try: 157 | index = int(line.split()[0]) - 1 158 | except ValueError: 159 | raise Exception(f"Likely cause is that 'ITEMS: ATOMS' in dump file does not start with 'ITEM: ATOMS id'.") 160 | 161 | xyz[index,:] = np.float32(line.split()[keyx:keyz]) 162 | vel[index,:] = np.float32(line.split()[keyvx:keyvz]) 163 | quat[index,:] = np.float32(line.split()[keyq0:keyq3]) 164 | angmom[index,:] = np.float32(line.split()[keylx:keylz]) 165 | 166 | # write oxDNA data to file 167 | 168 | # header 169 | oxconf.write('t = %d\n' % t) 170 | oxconf.write('b = %f %f %f\n' % (Lx, Ly, Lz)) 171 | oxconf.write('E = 0.000000 0.000000 0.000000\n') 172 | 173 | # atom data 174 | for n in range(N): 175 | cm = xyz[n,:] 176 | quaternions = quat[n,:] 177 | a1, a3 = quat_to_exyz(quaternions) 178 | v = np.array(vel[n,:]) * np.sqrt(mass_in_lammps) 179 | Lv = np.array(angmom[n,:]) / np.sqrt(inertia_in_lammps) 180 | 181 | oxconf.write('%le %le %le %le %le %le %le %le %le %le %le %le %le %le %le \n' % \ 182 | (cm[0], cm[1], cm[2], a1[0], a1[1], a1[2], a3[0], a3[1], a3[2], v[0], v[1], v[2], Lv[0], Lv[1], Lv[2])) 183 | 184 | line = lmptrj.readline() 185 | 186 | print("## Wrote data to '%s' / '%s'" % (configuration_file, topology_file), file=sys.stderr) 187 | print("## DONE", file=sys.stderr) 188 | -------------------------------------------------------------------------------- /src/oxDNA_PDB.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | 3 | import sys 4 | import os 5 | import numpy as np 6 | import copy 7 | from math import sqrt, sin 8 | from collections import defaultdict 9 | 10 | from libs.pdb import Atom, Nucleotide, FROM_OXDNA_TO_ANGSTROM 11 | from libs import base 12 | from libs import utils 13 | from libs.readers import LorenzoReader 14 | 15 | DD12_PDB_PATH = "dd12_na.pdb" 16 | 17 | def print_usage(): 18 | print("USAGE:", file=sys.stderr) 19 | print("\t%s topology configuration direction" % sys.argv[0], file=sys.stderr) 20 | print("\t[-H\--hydrogens=True] [-u\--uniform-residue-names] [-o\--one-file-per-strand] [--rmsf-file]", file=sys.stderr) 21 | exit(1) 22 | 23 | def parse_options(): 24 | shortArgs = 'H:uo' 25 | longArgs = ['hydrogens=', 'uniform-residue-names', 'one-file-per-strand', 'rmsf-file='] 26 | 27 | opts = { 28 | "configuration" : "", 29 | "topology" : "", 30 | "oxDNA_direction" : True, 31 | "print_hydrogens" : True, 32 | "uniform_residue_names" : False, 33 | "one_file_per_strand" : False, 34 | "rmsf_bfactor" : "", 35 | } 36 | 37 | try: 38 | import getopt 39 | args, positional_args = getopt.gnu_getopt(sys.argv[1:], shortArgs, longArgs) 40 | for k in args: 41 | if k[0] == '-H' or k[0] == '--hydrogens': 42 | k_arg = k[1].lower() 43 | if k_arg.lower() == "true": 44 | opts["print_hydrogens"] = True 45 | elif k_arg == "false": 46 | print("## Hydrogen atoms will *not* be printed", file=sys.stderr) 47 | opts["print_hydrogens"] = False 48 | else: 49 | print("The argument of '%s' should be either 'true' or 'false' (got '%s' instead)" % (k[0], k[1]), file=sys.stderr) 50 | exit(1) 51 | elif k[0] == '-u' or k[0] == '--uniform-residue-names': 52 | opts["uniform_residue_names"] = True 53 | elif k[0] == '-o' or k[0] == '--one-file-per-strand': 54 | opts["one_file_per_strand"] = True 55 | elif k[0] == '--rmsf-file': 56 | opts["rmsf_bfactor"] = k[1] 57 | 58 | opts['topology'] = positional_args[0] 59 | opts['configuration'] = positional_args[1] 60 | direction = positional_args[2] 61 | 62 | if direction == "35": 63 | opts["oxDNA_direction"] = True 64 | elif direction == "53": 65 | opts["oxDNA_direction"] = False 66 | else: 67 | print("The 'direction' argument should be either 35 or 53", file=sys.stderr) 68 | exit(1) 69 | except Exception: 70 | print_usage() 71 | 72 | return opts 73 | 74 | def align(full_base, ox_base): 75 | theta = utils.get_angle(full_base.a3, ox_base._a3) 76 | # if the two bases are already essentially aligned then we do nothing 77 | if sin(theta) > 1e-3: 78 | axis = np.cross(full_base.a3, ox_base._a3) 79 | axis /= sqrt(np.dot(axis, axis)) 80 | R = utils.get_rotation_matrix(axis, theta) 81 | full_base.rotate(R) 82 | 83 | theta = utils.get_angle(full_base.a1, ox_base._a1) 84 | if sin(theta) > 1e-3: 85 | axis = np.cross(full_base.a1, ox_base._a1) 86 | axis /= sqrt(np.dot(axis, axis)) 87 | R = utils.get_rotation_matrix(axis, theta) 88 | full_base.rotate(R) 89 | 90 | if __name__ == '__main__': 91 | opts = parse_options() 92 | 93 | with open(os.path.join(os.path.dirname(__file__), DD12_PDB_PATH)) as f: 94 | nucleotides = [] 95 | old_residue = "" 96 | for line in f.readlines(): 97 | if len(line) > 77: 98 | na = Atom(line) 99 | if na.residue_idx != old_residue: 100 | nn = Nucleotide(na.residue, na.residue_idx) 101 | nucleotides.append(nn) 102 | old_residue = na.residue_idx 103 | nn.add_atom(na) 104 | 105 | bases = {} 106 | for n in nucleotides: 107 | n.compute_as() 108 | if n.base in bases: 109 | if n.check < bases[n.base].check: bases[n.base] = copy.deepcopy(n) 110 | else: 111 | bases[n.base] = n 112 | 113 | for n in nucleotides: 114 | n.a1, n.a2, n.a3 = utils.get_orthonormalized_base(n.a1, n.a2, n.a3) 115 | 116 | try: 117 | lr = LorenzoReader(opts['topology'], opts['configuration']) 118 | s = lr.get_system() 119 | except Exception as e: 120 | print("Parser error: %s" % e, file=sys.stderr) 121 | exit(1) 122 | 123 | rmsf_file = opts["rmsf_bfactor"] 124 | if rmsf_file: 125 | with open(rmsf_file) as f: 126 | try: 127 | # https://github.com/sulcgroup/oxdna_analysis_tools 128 | substrings = f.read().split("[")[1].split("]")[0].split(",") 129 | except Exception as e: 130 | print("Parsing error in RMSF file. Invalid Format: %s" % e, file=sys.stderr) 131 | exit(1) 132 | try: 133 | rmsf_per_nucleotide = {i: float(s) 134 | for i, s in enumerate(substrings)} 135 | except Exception as e: 136 | print("Parsing error in RMSF file. Conversion to float failed : %s" % e, file=sys.stderr) 137 | exit(1) 138 | else: 139 | rmsf_per_nucleotide = defaultdict(lambda: 1.00) 140 | 141 | ox_nucleotides = [] 142 | s.map_nucleotides_to_strands() 143 | com = np.array([0., 0., 0.]) 144 | for my_strand in s._strands: 145 | com += my_strand.cm_pos 146 | com /= s.N_strands 147 | 148 | box_angstrom = s._box * FROM_OXDNA_TO_ANGSTROM 149 | correct_for_large_boxes = False 150 | if np.any(box_angstrom[box_angstrom > 999]): 151 | print("At least one of the box sizes is larger than 999: all the atoms which are outside of the box will be brought back through periodic boundary conditions", file=sys.stderr) 152 | correct_for_large_boxes = True 153 | 154 | if opts['one_file_per_strand']: 155 | out_name = opts['configuration'] + "_1.pdb" 156 | else: 157 | out_name = opts['configuration'] + ".pdb" 158 | 159 | out = open(out_name, "w") 160 | 161 | current_base_identifier = 'A' 162 | for s_id, strand in enumerate(s._strands): 163 | strand_pdb = [] 164 | nucleotides_in_strand = strand._nucleotides 165 | if not opts['oxDNA_direction']: 166 | nucleotides_in_strand = reversed(nucleotides_in_strand) 167 | for n_idx, nucleotide in enumerate(nucleotides_in_strand, 1): 168 | nb = base.number_to_base[nucleotide._base] 169 | my_base = copy.deepcopy(bases[nb]) 170 | my_base.chain_id = s._nucleotide_to_strand[nucleotide.index] 171 | residue_type = "" 172 | 173 | if not strand.is_circular(): 174 | # 3' end 175 | if nucleotide == strand._nucleotides[0]: 176 | residue_type = "3" 177 | # 5' end 178 | elif nucleotide == strand._nucleotides[-1]: 179 | residue_type = "5" 180 | 181 | if opts["uniform_residue_names"] == True: 182 | residue_suffix = "" 183 | else: 184 | residue_suffix = residue_type 185 | 186 | align(my_base, nucleotide) 187 | my_base.set_base((nucleotide.pos_base - com) * FROM_OXDNA_TO_ANGSTROM) 188 | 189 | if correct_for_large_boxes: 190 | my_base.correct_for_large_boxes(box_angstrom) 191 | 192 | residue_serial = n_idx % 9999 193 | base_identifier = current_base_identifier 194 | nucleotide_pdb = my_base.to_pdb(base_identifier, opts['print_hydrogens'], residue_serial, residue_suffix, 195 | residue_type, bfactor=rmsf_per_nucleotide[nucleotide.index]) 196 | strand_pdb.append(nucleotide_pdb) 197 | 198 | 199 | print("\n".join(x for x in strand_pdb), file=out) 200 | print("TER", file=out) 201 | 202 | if opts['one_file_per_strand']: 203 | out.close() 204 | print("## Wrote strand %d's data to '%s'" % (s_id + 1, out_name), file=sys.stderr) 205 | # open a new file if needed 206 | if strand != s._strands[-1]: 207 | out_name = opts['configuration'] + "_%d.pdb" % (s_id + 2, ) 208 | out = open(out_name, "w") 209 | else: 210 | # we update the base identifier only if a single file is printed 211 | if current_base_identifier == 'Z': 212 | current_base_identifier = 'A' 213 | else: 214 | current_base_identifier = chr(ord(current_base_identifier) + 1) 215 | 216 | if not opts['one_file_per_strand']: 217 | out.close() 218 | print("## Wrote data to '%s'" % out_name, file=sys.stderr) 219 | 220 | print("## DONE", file=sys.stderr) 221 | -------------------------------------------------------------------------------- /src/XYZ_oxDNA.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python3 2 | # TODO: how do we choose the simulation box? 3 | 4 | import numpy as np 5 | import numpy.linalg as la 6 | import sys 7 | import os 8 | from libs import topology as top 9 | from libs import base 10 | from libs import utils 11 | 12 | 13 | class Options(object): 14 | 15 | def __init__(self): 16 | object.__init__(self) 17 | 18 | self.closed = True 19 | self.double = True 20 | self.nicked = False 21 | self.supercoiling = 0. 22 | self.writhe = 0. 23 | self.seed = None 24 | self.sequence_file = None 25 | 26 | def check(self): 27 | if self.nicked and not self.double: 28 | print("The --nicked and --ssDNA options are incompatible", file=sys.stderr) 29 | exit(1) 30 | 31 | 32 | def print_usage(): 33 | print("USAGE:", file=sys.stderr) 34 | print("\t%s centerline_file" % sys.argv[0], file=sys.stderr) 35 | print("\t[-c\--closed] [-o\--open] [-h\--help] [-d\--dsDNA] [-s\--ssDNA] [-n\--nicked] [-p\--supercoiling VALUE] [-w\--writhe VALUE] [-e\--seed VALUE] [-q\--sequence FILE]", file=sys.stderr) 36 | exit(1) 37 | 38 | 39 | def parse_options(): 40 | shortArgs = 'cohdsnp:w:e:q:' 41 | longArgs = ['closed', 'open', 'help', 'dsDNA', 'ssDNA', 'nicked', 'supercoiling=', 'writhe=', 'seed=', 'sequence='] 42 | 43 | opts = Options() 44 | 45 | try: 46 | import getopt 47 | args, files = getopt.gnu_getopt(sys.argv[1:], shortArgs, longArgs) 48 | for k in args: 49 | if k[0] == '-c' or k[0] == '--closed': opts.closed = True 50 | if k[0] == '-o' or k[0] == '--open': opts.closed = False 51 | if k[0] == '-h' or k[0] == '--help': print_usage() 52 | if k[0] == '-d' or k[0] == '--dsDNA': opts.double = True 53 | if k[0] == '-s' or k[0] == "--ssDNA": opts.double = False 54 | if k[0] == '-n' or k[0] == "--nicked": opts.nicked = True 55 | if k[0] == '-p' or k[0] == "--supercoiling": opts.supercoiling = float(k[1]) 56 | if k[0] == '-w' or k[0] == "--writhe": opts.writhe = float(k[1]) 57 | if k[0] == '-e' or k[0] == "--seed": opts.seed = int(k[1]) 58 | if k[0] == '-q' or k[0] == "--sequence": opts.sequence_file = k[1] 59 | 60 | opts.centerline_file = files[0] 61 | except Exception: 62 | print_usage() 63 | 64 | return opts 65 | 66 | 67 | # base-base distance along the helical pitch 68 | BASE_BASE = 0.3897628551303122 69 | # distance between the helix centre and the nucleotides' centre of mass 70 | CM_CENTER_DS = 0.6 71 | 72 | if __name__ == '__main__': 73 | opts = parse_options() 74 | opts.check() 75 | 76 | if opts.seed != None: 77 | np.random.seed(opts.seed) 78 | 79 | # import the coordinates from the user-provided file 80 | coordxyz = np.loadtxt(opts.centerline_file, float) 81 | 82 | # number of base pairs 83 | nbases = len(coordxyz) 84 | 85 | # use the model parameters to scale the distances 86 | scaling = BASE_BASE / la.norm(coordxyz[1, :] - coordxyz[0, :]) 87 | coordxyz *= scaling 88 | 89 | #initialize vectors 90 | dist = np.copy(coordxyz) 91 | dist_norm = np.copy(coordxyz) 92 | p = np.copy(coordxyz) 93 | 94 | ssdna1 = np.copy(coordxyz) 95 | v_perp_ssdna1 = np.copy(coordxyz) 96 | 97 | ssdna2 = np.copy(coordxyz) 98 | v_perp_ssdna2 = np.copy(coordxyz) 99 | 100 | 101 | # take the bounding box as the simulation box for the output configuration 102 | boxx = max(coordxyz[:nbases, 0]) - min(coordxyz[:nbases, 0]) 103 | boxy = max(coordxyz[:nbases, 1]) - min(coordxyz[:nbases, 1]) 104 | boxz = max(coordxyz[:nbases, 2]) - min(coordxyz[:nbases, 2]) 105 | boxmax = 1.5 * max(boxx, boxy, boxz) 106 | 107 | # centerline base_to_base vectors 108 | for c in range(0, nbases): 109 | ind = c 110 | ind1 = (c + 1) % nbases 111 | #open chain cannot compute dist at c=nbases-1 112 | #so we use as reference the previus dist 113 | if opts.closed or (not opts.closed and c!=nbases-1): 114 | dist[ind, :] = coordxyz[ind1, :] - coordxyz[ind, :] 115 | dist_norm[ind, :] = dist[ind, :] / la.norm(dist[ind, :]) 116 | else: 117 | dist[ind, :] = dist[ind-1, :] 118 | dist_norm[ind, :] = dist_norm[ind-1, :] 119 | 120 | # vectors perpendicular between two consecutive centerline vectors (normalized) 121 | for c in range(0, nbases): 122 | ind_1 = (c - 1 + nbases) % nbases 123 | ind = c 124 | 125 | #opens chain have random p at c=0 and at c=nbases-1 due to absence of neighbours 126 | if opts.closed or (not opts.closed and c!=0 and c!=nbases-1): 127 | #check that dist[ind_1, :] and dist[ind, :] are not equals 128 | if not np.all(np.isclose( dist[ind_1, :] , dist[ind, :]) ): 129 | p[ind, :] = np.cross(dist[ind_1, :] , dist[ind, :]) 130 | p[ind, :] /= la.norm(p[ind, :]) 131 | #else assign random p 132 | else: 133 | rv=np.random.uniform(-1,1,3) 134 | p[ind, :] = rv - (np.dot(dist_norm[ind, :],rv)) * dist_norm[ind, :] 135 | p[ind, :] /= la.norm(p[ind, :]) 136 | else: 137 | rv=np.random.uniform(-1,1,3) 138 | p[ind, :] = rv - (np.dot(dist_norm[ind, :],rv)) * dist_norm[ind, :] 139 | p[ind, :] /= la.norm(p[ind, :]) 140 | 141 | # chain writhe 142 | WR = 0. 143 | if opts.closed: 144 | WR = top.get_writhe(coordxyz) 145 | 146 | #oxdna equiibrium pitch 147 | pitch = 10.5 148 | 149 | #global linking number 150 | LK = round((nbases / pitch) * (opts.supercoiling + 1) + opts.writhe) 151 | 152 | TW = LK - WR 153 | 154 | #twisting angle between two consecutive bases 155 | rot_base = TW * 2.0 * np.pi / nbases 156 | 157 | #recap 158 | if opts.closed: 159 | print("Total Linking Number (LK) %f, composed of:" % ((nbases / pitch) * (opts.supercoiling + 1) + opts.writhe), file=sys.stderr) 160 | print("1) Equilibrium number of DNA turns %f" % (nbases / pitch), file=sys.stderr) 161 | print("2) Target writhe %f = Topological writhe %f + Turns imposed by supercoiling %f " % (opts.writhe+(nbases / pitch) *opts.supercoiling,opts.writhe,(nbases / pitch) *opts.supercoiling), file=sys.stderr) 162 | print("LK has been rounded to %f" % LK, file=sys.stderr) 163 | print("Initial chain writhe %f" % WR, file=sys.stderr) 164 | 165 | 166 | #################################### 167 | # Initialize DNA strand 168 | #################################### 169 | 170 | #First hydrogen-hydrogen bond vector 171 | v_perp_ssdna1[0, :] = np.cross(dist_norm[0, :], p[0, :]) 172 | v_perp_ssdna1[0, :] /= la.norm(v_perp_ssdna1[0, :]) 173 | v_perp_ssdna2[0, :] = -v_perp_ssdna1[0, :] 174 | 175 | for c in range(nbases): 176 | #dna center of mass positions 177 | ssdna1[c, :] = coordxyz[c, :] - CM_CENTER_DS * v_perp_ssdna1[c, :] 178 | ssdna2[c, :] = coordxyz[c, :] + CM_CENTER_DS * v_perp_ssdna1[c, :] 179 | 180 | #Update v_perp_ssdna1 181 | 182 | ind_1 = c 183 | ind = (c + 1) % nbases 184 | 185 | alpha = top.py_ang(v_perp_ssdna1[ind_1, :] , p[ind, :] , dist[ind_1, :]) 186 | gamma = rot_base - alpha 187 | #prevent change when ind=0 on open chain 188 | if c!=nbases-1: 189 | R = utils.get_rotation_matrix(dist[ind, :], gamma) 190 | v_perp_ssdna1[ind, :] = np.dot(R , p[ind, :]) 191 | v_perp_ssdna2[ind, :] = -v_perp_ssdna1[ind, :] 192 | 193 | # check LK imposed and measured 194 | if opts.closed: 195 | TW_measured = top.get_twist(coordxyz, ssdna1) 196 | box = np.array([boxmax, boxmax, boxmax]) 197 | system = base.System(box) 198 | 199 | if opts.sequence_file == None: 200 | ssdna1_base = np.zeros(nbases, int) 201 | for c in range(nbases): 202 | ssdna1_base[c] = np.random.randint(0, 4) 203 | else: 204 | try: 205 | seq_file = open(opts.sequence_file) 206 | except Exception: 207 | print("The sequence file '%s' is unreadable" % opts.sequence_file, file=sys.stderr) 208 | exit(1) 209 | 210 | contents = seq_file.read() 211 | # remove all whitespace from the file's contents 212 | sequence = ''.join(contents.split()) 213 | if len(sequence) != nbases: 214 | print("The length of the given sequence (%d) should be equal to the number of coordinates in the centerline file (%d)" % (len(sequence), nbases), file=sys.stderr) 215 | exit(1) 216 | 217 | ssdna1_base = [base.base_to_number[x] for x in sequence] 218 | 219 | seq_file.close() 220 | 221 | strand1 = base.Strand() 222 | for c in range(nbases): 223 | b = ssdna1_base[c] 224 | strand1.add_nucleotide(base.Nucleotide(ssdna1[c], v_perp_ssdna1[c], dist_norm[c], b, b)) 225 | if opts.closed: 226 | strand1.make_circular() 227 | system.add_strand(strand1) 228 | 229 | if opts.double: 230 | strand2 = base.Strand() 231 | for c in range(nbases): 232 | reverse_idx = nbases - 1 - c 233 | b = 3 - ssdna1_base[reverse_idx] 234 | strand2.add_nucleotide(base.Nucleotide(ssdna2[reverse_idx], v_perp_ssdna2[reverse_idx], -dist_norm[reverse_idx], b, b)) 235 | if opts.closed and not opts.nicked: 236 | strand2.make_circular() 237 | system.add_strand(strand2) 238 | 239 | basename = os.path.basename(sys.argv[1]) 240 | topology_file = basename + ".top" 241 | configuration_file = basename + ".oxdna" 242 | system.print_lorenzo_output(configuration_file, topology_file) 243 | 244 | print("## Wrote data to '%s' / '%s'" % (configuration_file, topology_file), file=sys.stderr) 245 | print("## DONE", file=sys.stderr) 246 | -------------------------------------------------------------------------------- /src/libs/pdb.py: -------------------------------------------------------------------------------- 1 | import numpy as np 2 | import itertools 3 | from math import sqrt 4 | import sys 5 | import copy 6 | 7 | BASE_SHIFT = 1.13 8 | COM_SHIFT = 0.5 9 | FROM_OXDNA_TO_ANGSTROM = 8.518 10 | FROM_ANGSTROM_TO_OXDNA = 1. / FROM_OXDNA_TO_ANGSTROM 11 | 12 | NAME_TO_BASE = { 13 | "ADE" : "A", 14 | "CYT" : "C", 15 | "GUA" : "G", 16 | "THY" : "T", 17 | "URA" : "U", 18 | } 19 | 20 | BASES = ["A", "T", "G", "C", "U"] 21 | 22 | class Nucleotide(object): 23 | RNA_warning_printed = False 24 | 25 | def __init__(self, name, idx): 26 | object.__init__(self) 27 | self.name = name.strip() 28 | if self.name in list(NAME_TO_BASE.keys()): 29 | self.base = NAME_TO_BASE[self.name] 30 | elif self.name in BASES: 31 | if self.name == "U" and not Nucleotide.RNA_warning_printed: 32 | print("WARNING: unsupported uracil detected: use at your own risk", file=sys.stderr) 33 | Nucleotide.RNA_warning_printed = True 34 | 35 | self.base = self.name 36 | else: 37 | self.base = name[1:] 38 | self.idx = idx 39 | self.base_atoms = [] 40 | self.phosphate_atoms = [] 41 | self.sugar_atoms = [] 42 | self.named_atoms = {} 43 | self.ring_names = ["C2", "C4", "C5", "C6", "N1", "N3"] 44 | self.chain_id = None 45 | 46 | def get_atoms(self): 47 | return self.base_atoms + self.phosphate_atoms + self.sugar_atoms 48 | 49 | def add_atom(self, a): 50 | if 'P' in a.name or a.name == "HO5'": 51 | self.phosphate_atoms.append(a) 52 | elif "'" in a.name: 53 | self.sugar_atoms.append(a) 54 | else: 55 | self.base_atoms.append(a) 56 | 57 | self.named_atoms[a.name] = a 58 | if self.chain_id == None: 59 | self.chain_id = a.chain_id 60 | 61 | def get_com(self, atoms=None): 62 | if atoms == None: 63 | atoms = self.atoms 64 | com = np.array([0., 0., 0.]) 65 | for a in atoms: 66 | com += a.pos 67 | 68 | return com / len(atoms) 69 | 70 | def compute_a3(self): 71 | base_com = self.get_com(self.base_atoms) 72 | # the O4' oxygen is always (at least for non pathological configurations, as far as I know) oriented 3' -> 5' with respect to the base's centre of mass 73 | parallel_to = self.named_atoms["O4'"].pos - base_com 74 | self.a3 = np.array([0., 0., 0.]) 75 | 76 | for perm in itertools.permutations(self.ring_names, 3): 77 | p = self.named_atoms[perm[0]] 78 | q = self.named_atoms[perm[1]] 79 | r = self.named_atoms[perm[2]] 80 | v1 = p.pos - q.pos 81 | v2 = p.pos - r.pos 82 | v1 /= sqrt(np.dot(v1, v1)) 83 | v2 /= sqrt(np.dot(v2, v2)) 84 | if abs(np.dot(v1, v2)) > 0.01 or 1: 85 | a3 = np.cross(v1, v2) 86 | a3 /= sqrt(np.dot(a3, a3)) 87 | if np.dot(a3, parallel_to) < 0.: 88 | a3 = -a3 89 | self.a3 += a3 90 | 91 | self.a3 /= sqrt(np.dot(self.a3, self.a3)) 92 | 93 | def compute_a1(self): 94 | if "C" in self.name or "T" in self.name or "U" in self.name: 95 | pairs = [ ["N3", "C6"], ["C2", "N1"], ["C4", "C5"] ] 96 | else: 97 | pairs = [ ["N1", "C4"], ["C2", "N3"], ["C6", "C5"] ] 98 | 99 | self.a1 = np.array([0., 0., 0.]) 100 | for pair in pairs: 101 | p = self.named_atoms[pair[0]] 102 | q = self.named_atoms[pair[1]] 103 | diff = p.pos - q.pos 104 | self.a1 += diff 105 | 106 | self.a1 /= sqrt(np.dot(self.a1, self.a1)) 107 | 108 | def compute_as(self): 109 | self.compute_a1() 110 | self.compute_a3() 111 | self.a2 = np.cross(self.a3, self.a1) 112 | self.check = abs(np.dot(self.a1, self.a3)) 113 | 114 | def correct_for_large_boxes(self, box): 115 | for atom in self.atoms: 116 | atom.shift(-np.rint(atom.pos / box ) * box) 117 | 118 | def to_pdb(self, chain_identifier, print_H, residue_serial, residue_suffix, residue_type, bfactor): 119 | res = [] 120 | for a in self.atoms: 121 | if not print_H and 'H' in a.name: 122 | continue 123 | if residue_type == "5": 124 | if 'P' in a.name: 125 | if a.name == 'P': 126 | phosphorus = a 127 | continue 128 | elif a.name == "O5'": 129 | O5prime = a 130 | elif residue_type == "3": 131 | if a.name == "O3'": 132 | O3prime = a 133 | res.append(a.to_pdb(chain_identifier, residue_serial, residue_suffix, bfactor)) 134 | 135 | # if the residue is a 3' or 5' end, it requires one more hydrogen linked to the O3' or O5', respectively 136 | if residue_type == "5": 137 | new_hydrogen = copy.deepcopy(phosphorus) 138 | new_hydrogen.name = "HO5'" 139 | 140 | # we put the new hydrogen at a distance 1 Angstrom from the O5' oxygen along the direction that, in a regular nucleotide, connects O5' and P 141 | dist_P_O = phosphorus.pos - O5prime.pos 142 | dist_P_O *= 1. / np.sqrt(np.dot(dist_P_O, dist_P_O)) 143 | new_hydrogen.pos = O5prime.pos + dist_P_O 144 | res.append(new_hydrogen.to_pdb(chain_identifier, residue_serial, residue_suffix, bfactor)) 145 | elif residue_type == "3": 146 | new_hydrogen = copy.deepcopy(O3prime) 147 | new_hydrogen.name = "HO3'" 148 | 149 | # we put the new hydrogen at a distance 1 Angstrom from the O3' oxygen along a direction which is a linear combination of the three 150 | # orientations that approximately reproduce the crystallographic position 151 | new_distance = 0.2 * self.a2 - 0.2 * self.a1 - self.a3 152 | new_distance *= 1. / np.sqrt(np.dot(new_distance, new_distance)) 153 | new_hydrogen.pos = O3prime.pos + new_distance 154 | res.append(new_hydrogen.to_pdb(chain_identifier, residue_serial, residue_suffix, bfactor)) 155 | 156 | return "\n".join(res) 157 | 158 | def to_mgl(self): 159 | res = [] 160 | for a in self.atoms: 161 | res.append(a.to_mgl()) 162 | 163 | return "\n".join(res) 164 | 165 | def rotate(self, R): 166 | com = self.get_com() 167 | for a in self.atoms: 168 | a.pos = np.dot(R, a.pos - com) + com 169 | 170 | self.compute_as() 171 | 172 | def set_com(self, new_com): 173 | com = self.get_com() 174 | for a in self.atoms: 175 | a.pos += new_com - com - COM_SHIFT * self.a1 176 | 177 | def set_sugar(self, new_base_back_com): 178 | sugar_com = self.get_com(self.sugar_atoms) 179 | for a in self.atoms: 180 | a.pos += new_base_back_com - sugar_com 181 | 182 | self.compute_as() 183 | 184 | def set_base(self, new_base_com): 185 | atoms = [v for k, v in self.named_atoms.items() if k in self.ring_names] 186 | ring_com = self.get_com(atoms) 187 | for a in self.atoms: 188 | a.pos += new_base_com - ring_com - BASE_SHIFT * self.a1 189 | 190 | self.compute_as() 191 | 192 | atoms = property(get_atoms) 193 | 194 | 195 | class Atom(object): 196 | serial_atom = 1 197 | 198 | def __init__(self, pdb_line): 199 | object.__init__(self) 200 | # http://cupnet.net/pdb-format/ 201 | self.name = pdb_line[12:16].strip() 202 | # some PDB files have * in place of ' 203 | if "*" in self.name: 204 | self.name = self.name.replace("*", "'") 205 | 206 | self.alternate = pdb_line[16] 207 | self.residue = pdb_line[17:20].strip() 208 | self.chain_id = pdb_line[21:22].strip() 209 | self.residue_idx = int(pdb_line[22:26]) 210 | self.pos = np.array([float(pdb_line[30:38]), float(pdb_line[38:46]), float(pdb_line[46:54])]) 211 | 212 | def is_hydrogen(self): 213 | return "H" in self.name 214 | 215 | def shift(self, diff): 216 | self.pos += diff 217 | 218 | def to_pdb(self, chain_identifier, residue_serial, residue_suffix, bfactor): 219 | residue = self.residue + residue_suffix 220 | res = "{:6s}{:5d} {:^4s}{:1s}{:3s} {:1s}{:4d}{:1s} {:8.3f}{:8.3f}{:8.3f}{:6.2f}{:6.2f} {:>2s}{:2s}".format("ATOM", Atom.serial_atom, self.name, " ", residue, chain_identifier, residue_serial, " ", self.pos[0], self.pos[1], self.pos[2], 1.00, bfactor, " ", " ", " ") 221 | Atom.serial_atom += 1 222 | if Atom.serial_atom > 99999: 223 | Atom.serial_atom = 1 224 | return res 225 | 226 | def to_mgl(self): 227 | colors = {"C" : "0,1,1", "P" : "1,1,0", "O" : "1,0,0", "H" : "0.5,0.5,0.5", "N" : "0,0,1"} 228 | for c in colors: 229 | if c in self.name: color = colors[c] 230 | r = 0.5 231 | return "%s %s %s @ %f C[%s]" % (self.pos[0], self.pos[1], self.pos[2], r, color) 232 | -------------------------------------------------------------------------------- /tests/XYZ_oxDNA/centerline.dat: -------------------------------------------------------------------------------- 1 | -72.0102081299 101.326339722 1.46443492174 2 | -72.1917953491 101.456100464 1.10554894805 3 | -72.3816452026 101.584411621 0.840744927526 4 | -72.6645851135 101.728240967 0.526777863503 5 | -72.7858772278 101.883255005 0.158528912812 6 | -72.875957489 102.04460144 -0.192686900496 7 | -72.9765472412 102.202831268 -0.518447563052 8 | -73.1556625366 102.445354462 -0.804395616055 9 | -73.2107543945 102.78339386 -1.08540716767 10 | -73.2105445862 103.052684784 -1.33509236574 11 | -73.1252937317 103.338523865 -1.71231603622 12 | -73.0831031799 103.533977509 -2.00449079275 13 | -73.1031913757 103.809577942 -2.36081290245 14 | -72.9943580627 103.999740601 -2.73305726051 15 | -72.9080696106 104.152355194 -3.08433651924 16 | -72.9094543457 104.337947845 -3.46093857288 17 | -72.8593482971 104.527557373 -3.82134652138 18 | -72.6972389221 104.800601959 -4.20120882988 19 | -72.6446304321 105.086704254 -4.54017615318 20 | -72.559928894 105.364135742 -4.86297821999 21 | -72.3671798706 105.655265808 -5.01663470268 22 | -72.0761833191 105.804962158 -5.21425700188 23 | -71.7163581848 106.007396698 -5.45888257027 24 | -71.448474884 106.194217682 -5.55810904503 25 | -71.1475868225 106.382518768 -5.73023986816 26 | -70.793346405 106.690975189 -5.84763216972 27 | -70.6167831421 106.97473526 -6.06108736992 28 | -70.3614883423 107.181980133 -6.23836803436 29 | -70.1906166077 107.404159546 -6.45953989029 30 | -69.8988952637 107.689125061 -6.67266345024 31 | -69.6949539185 107.966083527 -6.87641429901 32 | -69.4234199524 108.166015625 -7.04225325584 33 | -69.161819458 108.415122986 -7.13211679459 34 | -68.8490753174 108.584579468 -7.29318666458 35 | -68.4592132568 108.72052002 -7.44376850128 36 | -68.1438980103 108.990501404 -7.58812856674 37 | -67.8471336365 109.301036835 -7.77265048027 38 | -67.6814537048 109.572853088 -8.00575566292 39 | -67.5470657349 109.872180939 -8.2189412117 40 | -67.4167175293 110.186771393 -8.35457372665 41 | -67.2680206299 110.673137665 -8.45722341537 42 | -67.0376472473 111.054759979 -8.58077573776 43 | -66.9128456116 111.364910126 -8.74979543686 44 | -66.6750831604 111.703128815 -8.93507528305 45 | -66.5228118896 112.100040436 -9.11202144623 46 | -66.3228111267 112.333465576 -9.27975082397 47 | -66.1358566284 112.631252289 -9.41835975647 48 | -65.8943214417 112.889232635 -9.5936384201 49 | -65.5755500793 113.076560974 -9.79666757584 50 | -65.2528190613 113.327964783 -10.0143151283 51 | -65.0240592957 113.488040924 -10.2325005531 52 | -64.6665687561 113.707458496 -10.441637516 53 | -64.3255081177 113.8217659 -10.5815768242 54 | -63.9890842438 113.907920837 -10.8249316216 55 | -63.6142692566 114.014709473 -10.9575529099 56 | -63.2755050659 114.107982635 -11.0504527092 57 | -62.8409862518 114.153533936 -11.1379694939 58 | -62.4970817566 114.274291992 -11.2596850395 59 | -62.0763530731 114.248744965 -11.320417881 60 | -61.7093696594 114.307514191 -11.4591517448 61 | -61.3088874817 114.31344986 -11.5262007713 62 | -60.9716701508 114.303318024 -11.4279966354 63 | -60.615901947 114.292743683 -11.283759594 64 | -60.2343235016 114.21868515 -11.0822086334 65 | -59.8379993439 114.162605286 -10.9500412941 66 | -59.3889274597 114.10528183 -10.8176431656 67 | -58.9914455414 114.012008667 -10.7317142487 68 | -58.6240921021 113.890434265 -10.5892357826 69 | -58.2368183136 113.780323029 -10.5414838791 70 | -57.8888626099 113.778816223 -10.5016298294 71 | -57.4600658417 113.750808716 -10.3846259117 72 | -57.0501995087 113.663291931 -10.3952670097 73 | -56.6570930481 113.534786224 -10.2574515343 74 | -56.2604598999 113.602054596 -10.1058635712 75 | -55.9049968719 113.560344696 -10.0480422974 76 | -55.5475234985 113.614650726 -9.9045920372 77 | -55.1463813782 113.628501892 -9.75338411331 78 | -54.7787208557 113.681251526 -9.64130210876 79 | -54.4187011719 113.723453522 -9.50038480759 80 | -54.0212097168 113.713428497 -9.36332464218 81 | -53.6369457245 113.729904175 -9.24319267273 82 | -53.25248909 113.666706085 -9.17692279816 83 | -52.9180850983 113.563541412 -8.97866344452 84 | -52.6693840027 113.459442139 -8.76754188538 85 | -52.3239078522 113.32541275 -8.58562469482 86 | -52.0143890381 113.129955292 -8.34128808975 87 | -51.7337856293 112.911327362 -8.16405177116 88 | -51.4733715057 112.701522827 -7.98584008217 89 | -51.217218399 112.521606445 -7.8064687252 90 | -50.8923931122 112.304039001 -7.54163050652 91 | -50.670085907 112.177974701 -7.34008979797 92 | -50.3892021179 112.014636993 -7.08208107948 93 | -50.270362854 111.798175812 -6.71044373512 94 | -50.115152359 111.612865448 -6.3839662075 95 | -49.9514408112 111.443000793 -6.03672552109 96 | -49.8253746033 111.259338379 -5.73980164528 97 | -49.6307411194 110.941310883 -5.48824882507 98 | -49.3929271698 110.712985992 -5.23224806786 99 | -49.1250114441 110.496837616 -5.00248026848 100 | -48.8195266724 110.357254028 -4.84323215485 101 | -48.4808387756 110.229328156 -4.63210701942 102 | -48.2154350281 110.013698578 -4.48156452179 103 | -47.8572254181 109.804191589 -4.36565351486 104 | -47.6125106812 109.559215546 -4.10279726982 105 | -47.4583625793 109.248832703 -3.85749554634 106 | -47.3300056458 108.983535767 -3.66505074501 107 | -47.1623210907 108.714454651 -3.32957828045 108 | -46.9753417969 108.419334412 -3.15130150318 109 | -46.9182796478 108.051628113 -2.89205753803 110 | -46.7240409851 107.729373932 -2.66500461102 111 | -46.6194572449 107.480644226 -2.39645755291 112 | -46.4740009308 107.164985657 -2.21698534489 113 | -46.3528575897 106.834461212 -2.03497070074 114 | -46.2560329437 106.447128296 -1.79213029146 115 | -46.1990127563 106.128608704 -1.57150912285 116 | -46.2264137268 105.736701965 -1.38283985853 117 | -46.246175766 105.427021027 -1.23436123133 118 | -46.2910385132 104.992073059 -0.988968014717 119 | -46.2255744934 104.605575562 -0.845229148865 120 | -46.2938022614 104.274951935 -0.655061691999 121 | -46.3367404938 103.970279694 -0.460527539253 122 | -46.3036594391 103.631717682 -0.197035059333 123 | -46.3046474457 103.340671539 0.0471691936255 124 | -46.3386821747 103.063812256 0.322276085615 125 | -46.2748985291 102.732700348 0.583271890879 126 | -46.3793678284 102.402397156 0.842425614595 127 | -46.4336738586 102.056278229 1.03906914592 128 | -46.4913787842 101.754589081 1.31531313062 129 | -46.6605129242 101.425216675 1.56416016817 130 | -46.7773685455 101.116420746 1.8075529933 131 | -46.7865409851 100.821163177 2.09434658289 132 | -46.7973480225 100.570102692 2.3827047348 133 | -46.7923812866 100.350120544 2.66924798489 134 | -46.8210430145 100.073482513 3.00768995285 135 | -46.9331054688 99.8420524597 3.31889855862 136 | -47.042049408 99.6047134399 3.60697805881 137 | -47.2082920074 99.2994155884 3.90441060066 138 | -47.3728427887 99.008102417 4.24697685242 139 | -47.5335693359 98.827922821 4.48352146149 140 | -47.7336883545 98.6160621643 4.779078722 141 | -47.9332714081 98.3295936584 5.07886195183 142 | -48.1951026917 98.0344924927 5.31393885612 143 | -48.3697490692 97.8506202698 5.57374405861 144 | -48.5278701782 97.7549743652 5.89462971687 145 | -48.7848815918 97.6850357056 6.24309778214 146 | -49.0408725739 97.6220092773 6.55680441856 147 | -49.4477767944 97.6474266052 6.76127719879 148 | -49.8140392303 97.6108322144 6.94829177856 149 | -50.2758350372 97.5257987976 7.07813167572 150 | -50.6062316895 97.4584274292 7.1439781189 151 | -51.0026302338 97.3736915588 7.16729855537 152 | -51.3635902405 97.2638816833 7.20988535881 153 | -51.7131729126 97.1181335449 7.2784383297 154 | -52.0149383545 96.9741134644 7.31616473198 155 | -52.4518814087 96.9239349365 7.38178992271 156 | -52.874004364 97.0160255432 7.43856549263 157 | -53.2609882355 97.049621582 7.48605298996 158 | -53.6275901794 97.0886535645 7.60733342171 159 | -54.0547618866 97.1012916565 7.77490234375 160 | -54.4827213287 97.0948562622 7.87228965759 161 | -54.8406028748 96.9853363037 7.94561481476 162 | -55.2439937592 97.0318412781 7.98175287247 163 | -55.64594841 97.047000885 8.00284147263 164 | -55.9656085968 97.020072937 8.02343177795 165 | -56.409116745 97.0094871521 8.10101604462 166 | -56.8085784912 97.0343055725 8.12799477577 167 | -57.145324707 97.0929069519 8.14290452003 168 | -57.5716056824 97.0444717407 8.1503238678 169 | -57.916431427 97.1878395081 8.02180433273 170 | -58.293390274 97.2509307861 7.93755817413 171 | -58.7254314423 97.211769104 7.80406284332 172 | -59.0649108887 97.1915130615 7.62346315384 173 | -59.4237346649 97.1194229126 7.59520530701 174 | -59.8355579376 97.0566444397 7.48576331139 175 | -60.1679344177 96.8652114868 7.32156658173 176 | -60.5961494446 96.8144607544 7.17999958992 177 | -60.9548721313 96.8026008606 7.02638459206 178 | -61.2449741364 96.7806396484 6.88898420334 179 | -61.5750713348 96.7887573242 6.73664450645 180 | -61.9801006317 96.7528800964 6.59461808205 181 | -62.3555049896 96.8255500793 6.41602563858 182 | -62.7113742828 96.8152694702 6.27286410332 183 | -63.1245365143 96.9179039001 6.06205248833 184 | -63.5127983093 96.9445266724 6.00931072235 185 | -63.9205284119 97.0282859802 5.90719008446 186 | -64.3213615417 97.0536117554 5.8168823719 187 | -64.7036933899 97.0328483582 5.70386171341 188 | -65.1062049866 97.0949707031 5.59987926483 189 | -65.463508606 97.2025718689 5.48175430298 190 | -65.7589454651 97.308052063 5.30696296692 191 | -66.0772628784 97.4405555725 5.16395783424 192 | -66.452129364 97.5555381775 4.9481048584 193 | -66.7683830261 97.6876602173 4.71460056305 194 | -67.1346549988 97.8204689026 4.51698088646 195 | -67.4885635376 97.9644432068 4.37984323502 196 | -67.8519172668 98.0699691772 4.23856639862 197 | -68.1792755127 98.2510986328 4.1655381918 198 | -68.4746398926 98.533706665 4.16507446766 199 | -68.8267288208 98.8214454651 4.06454515457 200 | -68.9876213074 99.1171035767 3.89977943897 201 | -69.2261352539 99.3994560242 3.71610271931 202 | -69.5204467773 99.5866737366 3.5143456459 203 | -69.7845573425 99.7899627686 3.3153668642 204 | -70.0758323669 99.9789161682 3.19896292686 205 | -70.4491119385 100.140518188 2.98360037804 206 | -70.7025222778 100.379024506 2.76285493374 207 | -70.9570350647 100.50182724 2.49799013138 208 | -71.236946106 100.701084137 2.25469011068 209 | -71.4867515564 100.862365723 1.96432125568 210 | -71.7262382507 101.058094025 1.68744689226 211 | -------------------------------------------------------------------------------- /tests/rpoly_oxDNA/correct_output.top: -------------------------------------------------------------------------------- 1 | 674 13 2 | 1 A -1 1 3 | 1 A 0 2 4 | 1 A 1 3 5 | 1 G 2 4 6 | 1 T 3 5 7 | 1 A 4 6 8 | 1 G 5 7 9 | 1 G 6 8 10 | 1 G 7 9 11 | 1 T 8 10 12 | 1 G 9 11 13 | 1 C 10 12 14 | 1 A 11 13 15 | 1 G 12 14 16 | 1 G 13 15 17 | 1 G 14 16 18 | 1 A 15 17 19 | 1 G 16 18 20 | 1 G 17 19 21 | 1 G 18 20 22 | 1 A 19 21 23 | 1 A 20 22 24 | 1 T 21 23 25 | 1 A 22 24 26 | 1 T 23 25 27 | 1 G 24 26 28 | 1 G 25 -1 29 | 2 A -1 28 30 | 2 G 27 29 31 | 2 A 28 30 32 | 2 C 29 31 33 | 2 G 30 32 34 | 2 G 31 33 35 | 2 A 32 34 36 | 2 C 33 35 37 | 2 T 34 36 38 | 2 C 35 37 39 | 2 A 36 38 40 | 2 G 37 39 41 | 2 G 38 40 42 | 2 G 39 41 43 | 2 A 40 42 44 | 2 G 41 43 45 | 2 A 42 44 46 | 2 A 43 45 47 | 2 G 44 46 48 | 2 G 45 47 49 | 2 T 46 48 50 | 2 T 47 49 51 | 2 A 48 50 52 | 2 C 49 51 53 | 2 A 50 52 54 | 2 A 51 53 55 | 2 T 52 54 56 | 2 A 53 55 57 | 2 C 54 56 58 | 2 C 55 -1 59 | 3 A -1 58 60 | 3 C 57 59 61 | 3 C 58 60 62 | 3 G 59 61 63 | 3 T 60 62 64 | 3 C 61 63 65 | 3 G 62 64 66 | 3 G 63 65 67 | 3 C 64 66 68 | 3 G 65 67 69 | 3 G 66 68 70 | 3 G 67 69 71 | 3 A 68 70 72 | 3 C 69 71 73 | 3 G 70 72 74 | 3 A 71 73 75 | 3 T 72 74 76 | 3 C 73 75 77 | 3 T 74 76 78 | 3 G 75 77 79 | 3 C 76 78 80 | 3 G 77 79 81 | 3 T 78 80 82 | 3 A 79 81 83 | 3 A 80 82 84 | 3 A 81 83 85 | 3 A 82 84 86 | 3 G 83 85 87 | 3 T 84 -1 88 | 4 G -1 87 89 | 4 T 86 88 90 | 4 A 87 89 91 | 4 C 88 90 92 | 4 G 89 91 93 | 4 G 90 92 94 | 4 T 91 93 95 | 4 C 92 94 96 | 4 G 93 95 97 | 4 A 94 96 98 | 4 C 95 97 99 | 4 A 96 98 100 | 4 A 97 99 101 | 4 C 98 100 102 | 4 C 99 101 103 | 4 C 100 102 104 | 4 A 101 103 105 | 4 G 102 104 106 | 4 G 103 105 107 | 4 T 104 106 108 | 4 T 105 107 109 | 4 C 106 108 110 | 4 C 107 109 111 | 4 T 108 110 112 | 4 A 109 111 113 | 4 T 110 112 114 | 4 T 111 113 115 | 4 C 112 114 116 | 4 A 113 -1 117 | 5 C -1 116 118 | 5 T 115 117 119 | 5 T 116 118 120 | 5 G 117 119 121 | 5 T 118 120 122 | 5 T 119 121 123 | 5 G 120 122 124 | 5 G 121 123 125 | 5 C 122 124 126 | 5 G 123 125 127 | 5 T 124 126 128 | 5 A 125 127 129 | 5 T 126 128 130 | 5 G 127 129 131 | 5 C 128 130 132 | 5 C 129 131 133 | 5 A 130 132 134 | 5 G 131 133 135 | 5 A 132 134 136 | 5 T 133 135 137 | 5 G 134 136 138 | 5 T 135 137 139 | 5 T 136 138 140 | 5 C 137 139 141 | 5 C 138 140 142 | 5 A 139 -1 143 | 6 T -1 142 144 | 6 T 141 143 145 | 6 A 142 144 146 | 6 T 143 145 147 | 6 A 144 146 148 | 6 A 145 147 149 | 6 A 146 148 150 | 6 A 147 149 151 | 6 T 148 150 152 | 6 C 149 151 153 | 6 G 150 152 154 | 6 G 151 153 155 | 6 C 152 154 156 | 6 C 153 155 157 | 6 C 154 156 158 | 6 T 155 157 159 | 6 A 156 158 160 | 6 T 157 159 161 | 6 A 158 160 162 | 6 T 159 161 163 | 6 A 160 162 164 | 6 G 161 163 165 | 6 T 162 164 166 | 6 C 163 165 167 | 6 C 164 166 168 | 6 T 165 167 169 | 6 C 166 168 170 | 6 T 167 169 171 | 6 T 168 -1 172 | 7 G -1 171 173 | 7 A 170 172 174 | 7 C 171 173 175 | 7 T 172 174 176 | 7 T 173 175 177 | 7 T 174 176 178 | 7 T 175 177 179 | 7 T 176 178 180 | 7 T 177 179 181 | 7 A 178 180 182 | 7 T 179 181 183 | 7 A 180 182 184 | 7 T 181 183 185 | 7 T 182 184 186 | 7 G 183 185 187 | 7 C 184 186 188 | 7 C 185 187 189 | 7 C 186 188 190 | 7 A 187 189 191 | 7 C 188 190 192 | 7 T 189 191 193 | 7 C 190 192 194 | 7 C 191 193 195 | 7 A 192 194 196 | 7 A 193 195 197 | 7 T 194 -1 198 | 8 T -1 197 199 | 8 T 196 198 200 | 8 T 197 199 201 | 8 G 198 200 202 | 8 T 199 201 203 | 8 T 200 202 204 | 8 C 201 203 205 | 8 A 202 204 206 | 8 A 203 205 207 | 8 T 204 206 208 | 8 T 205 207 209 | 8 T 206 208 210 | 8 A 207 209 211 | 8 T 208 210 212 | 8 T 209 211 213 | 8 C 210 212 214 | 8 C 211 213 215 | 8 G 212 214 216 | 8 T 213 215 217 | 8 T 214 216 218 | 8 G 215 217 219 | 8 A 216 218 220 | 8 C 217 219 221 | 8 T 218 220 222 | 8 T 219 221 223 | 8 A 220 222 224 | 8 G 221 223 225 | 8 A 222 224 226 | 8 G 223 -1 227 | 9 G -1 226 228 | 9 A 225 227 229 | 9 G 226 228 230 | 9 C 227 229 231 | 9 G 228 230 232 | 9 T 229 231 233 | 9 G 230 232 234 | 9 T 231 233 235 | 9 A 232 234 236 | 9 T 233 235 237 | 9 C 234 236 238 | 9 G 235 237 239 | 9 C 236 238 240 | 9 T 237 239 241 | 9 G 238 240 242 | 9 T 239 241 243 | 9 C 240 242 244 | 9 G 241 243 245 | 9 G 242 244 246 | 9 G 243 245 247 | 9 G 244 246 248 | 9 G 245 247 249 | 9 A 246 248 250 | 9 A 247 249 251 | 9 T 248 250 252 | 9 A 249 251 253 | 9 A 250 252 254 | 9 A 251 -1 255 | 10 A -1 254 256 | 10 C 253 255 257 | 10 T 254 256 258 | 10 T 255 257 259 | 10 T 256 258 260 | 10 A 257 259 261 | 10 T 258 260 262 | 10 C 259 261 263 | 10 G 260 262 264 | 10 T 261 263 265 | 10 A 262 264 266 | 10 G 263 265 267 | 10 G 264 266 268 | 10 T 265 267 269 | 10 C 266 268 270 | 10 A 267 269 271 | 10 T 268 270 272 | 10 C 269 271 273 | 10 A 270 272 274 | 10 A 271 273 275 | 10 T 272 274 276 | 10 T 273 275 277 | 10 T 274 276 278 | 10 G 275 277 279 | 10 T 276 278 280 | 10 G 277 279 281 | 10 C 278 280 282 | 10 A 279 281 283 | 10 A 280 -1 284 | 11 G -1 283 285 | 11 C 282 284 286 | 11 T 283 285 287 | 11 G 284 286 288 | 11 C 285 287 289 | 11 A 286 288 290 | 11 G 287 289 291 | 11 C 288 290 292 | 11 T 289 291 293 | 11 A 290 292 294 | 11 C 291 293 295 | 11 A 292 294 296 | 11 G 293 295 297 | 11 T 294 296 298 | 11 A 295 297 299 | 11 T 296 298 300 | 11 T 297 299 301 | 11 T 298 300 302 | 11 G 299 301 303 | 11 T 300 302 304 | 11 T 301 303 305 | 11 A 302 304 306 | 11 C 303 305 307 | 11 A 304 306 308 | 11 A 305 307 309 | 11 C 306 -1 310 | 12 C -1 309 311 | 12 G 308 310 312 | 12 G 309 311 313 | 12 T 310 312 314 | 12 G 311 313 315 | 12 T 312 314 316 | 12 C 313 315 317 | 12 A 314 316 318 | 12 G 315 317 319 | 12 T 316 318 320 | 12 C 317 319 321 | 12 T 318 320 322 | 12 A 319 321 323 | 12 A 320 322 324 | 12 T 321 323 325 | 12 G 322 324 326 | 12 T 323 325 327 | 12 T 324 326 328 | 12 A 325 327 329 | 12 G 326 328 330 | 12 G 327 329 331 | 12 C 328 330 332 | 12 A 329 331 333 | 12 T 330 332 334 | 12 G 331 333 335 | 12 C 332 334 336 | 12 T 333 335 337 | 12 G 334 336 338 | 12 C 335 -1 339 | 13 G 673 338 340 | 13 C 337 339 341 | 13 C 338 340 342 | 13 G 339 341 343 | 13 A 340 342 344 | 13 T 341 343 345 | 13 T 342 344 346 | 13 T 343 345 347 | 13 T 344 346 348 | 13 A 345 347 349 | 13 T 346 348 350 | 13 A 347 349 351 | 13 A 348 350 352 | 13 C 349 351 353 | 13 C 350 352 354 | 13 A 351 353 355 | 13 T 352 354 356 | 13 A 353 355 357 | 13 T 354 356 358 | 13 T 355 357 359 | 13 C 356 358 360 | 13 C 357 359 361 | 13 C 358 360 362 | 13 T 359 361 363 | 13 C 360 362 364 | 13 C 361 363 365 | 13 C 362 364 366 | 13 C 363 365 367 | 13 C 364 366 368 | 13 T 365 367 369 | 13 A 366 368 370 | 13 C 367 369 371 | 13 G 368 370 372 | 13 A 369 371 373 | 13 T 370 372 374 | 13 A 371 373 375 | 13 A 372 374 376 | 13 A 373 375 377 | 13 G 374 376 378 | 13 T 375 377 379 | 13 G 376 378 380 | 13 G 377 379 381 | 13 T 378 380 382 | 13 A 379 381 383 | 13 T 380 382 384 | 13 T 381 383 385 | 13 G 382 384 386 | 13 T 383 385 387 | 13 A 384 386 388 | 13 A 385 387 389 | 13 C 386 388 390 | 13 C 387 389 391 | 13 T 388 390 392 | 13 T 389 391 393 | 13 A 390 392 394 | 13 T 391 393 395 | 13 A 392 394 396 | 13 C 393 395 397 | 13 G 394 396 398 | 13 C 395 397 399 | 13 C 396 398 400 | 13 A 397 399 401 | 13 A 398 400 402 | 13 C 399 401 403 | 13 A 400 402 404 | 13 A 401 403 405 | 13 G 402 404 406 | 13 A 403 405 407 | 13 C 404 406 408 | 13 T 405 407 409 | 13 T 406 408 410 | 13 T 407 409 411 | 13 T 408 410 412 | 13 A 409 411 413 | 13 C 410 412 414 | 13 G 411 413 415 | 13 C 412 414 416 | 13 A 413 415 417 | 13 G 414 416 418 | 13 A 415 417 419 | 13 C 416 418 420 | 13 A 417 419 421 | 13 G 418 420 422 | 13 C 419 421 423 | 13 G 420 422 424 | 13 A 421 423 425 | 13 T 422 424 426 | 13 A 423 425 427 | 13 C 424 426 428 | 13 A 425 427 429 | 13 C 426 428 430 | 13 G 427 429 431 | 13 C 428 430 432 | 13 T 429 431 433 | 13 C 430 432 434 | 13 T 431 433 435 | 13 G 432 434 436 | 13 A 433 435 437 | 13 A 434 436 438 | 13 T 435 437 439 | 13 A 436 438 440 | 13 G 437 439 441 | 13 G 438 440 442 | 13 A 439 441 443 | 13 A 440 442 444 | 13 C 441 443 445 | 13 C 442 444 446 | 13 T 443 445 447 | 13 G 444 446 448 | 13 G 445 447 449 | 13 G 446 448 450 | 13 A 447 449 451 | 13 T 448 450 452 | 13 A 449 451 453 | 13 T 450 452 454 | 13 A 451 453 455 | 13 A 452 454 456 | 13 A 453 455 457 | 13 A 454 456 458 | 13 A 455 457 459 | 13 A 456 458 460 | 13 G 457 459 461 | 13 T 458 460 462 | 13 C 459 461 463 | 13 T 460 462 464 | 13 G 461 463 465 | 13 G 462 464 466 | 13 A 463 465 467 | 13 A 464 466 468 | 13 C 465 467 469 | 13 A 466 468 470 | 13 T 467 469 471 | 13 C 468 470 472 | 13 T 469 471 473 | 13 G 470 472 474 | 13 G 471 473 475 | 13 C 472 474 476 | 13 C 473 475 477 | 13 T 474 476 478 | 13 C 475 477 479 | 13 C 476 478 480 | 13 C 477 479 481 | 13 T 478 480 482 | 13 G 479 481 483 | 13 A 480 482 484 | 13 G 481 483 485 | 13 T 482 484 486 | 13 C 483 485 487 | 13 C 484 486 488 | 13 G 485 487 489 | 13 T 486 488 490 | 13 C 487 489 491 | 13 T 488 490 492 | 13 A 489 491 493 | 13 A 490 492 494 | 13 G 491 493 495 | 13 A 492 494 496 | 13 G 493 495 497 | 13 G 494 496 498 | 13 A 495 497 499 | 13 C 496 498 500 | 13 T 497 499 501 | 13 A 498 500 502 | 13 T 499 501 503 | 13 A 500 502 504 | 13 T 501 503 505 | 13 A 502 504 506 | 13 G 503 505 507 | 13 G 504 506 508 | 13 T 505 507 509 | 13 A 506 508 510 | 13 G 507 509 511 | 13 A 508 510 512 | 13 C 509 511 513 | 13 T 510 512 514 | 13 G 511 513 515 | 13 A 512 514 516 | 13 C 513 515 517 | 13 A 514 516 518 | 13 C 515 517 519 | 13 C 516 518 520 | 13 G 517 519 521 | 13 A 518 520 522 | 13 T 519 521 523 | 13 T 520 522 524 | 13 G 521 523 525 | 13 G 522 524 526 | 13 A 523 525 527 | 13 G 524 526 528 | 13 T 525 527 529 | 13 G 526 528 530 | 13 G 527 529 531 | 13 G 528 530 532 | 13 C 529 531 533 | 13 A 530 532 534 | 13 T 531 533 535 | 13 T 532 534 536 | 13 G 533 535 537 | 13 T 534 536 538 | 13 C 535 537 539 | 13 G 536 538 540 | 13 A 537 539 541 | 13 C 538 540 542 | 13 C 539 541 543 | 13 G 540 542 544 | 13 T 541 543 545 | 13 A 542 544 546 | 13 C 543 545 547 | 13 C 544 546 548 | 13 T 545 547 549 | 13 C 546 548 550 | 13 T 547 549 551 | 13 A 548 550 552 | 13 A 549 551 553 | 13 G 550 552 554 | 13 T 551 553 555 | 13 C 552 554 556 | 13 A 553 555 557 | 13 A 554 556 558 | 13 C 555 557 559 | 13 G 556 558 560 | 13 C 557 559 561 | 13 T 558 560 562 | 13 G 559 561 563 | 13 T 560 562 564 | 13 A 561 563 565 | 13 G 562 564 566 | 13 C 563 565 567 | 13 T 564 566 568 | 13 G 565 567 569 | 13 C 566 568 570 | 13 A 567 569 571 | 13 G 568 570 572 | 13 C 569 571 573 | 13 T 570 572 574 | 13 T 571 573 575 | 13 T 572 574 576 | 13 A 573 575 577 | 13 T 574 576 578 | 13 T 575 577 579 | 13 C 576 578 580 | 13 C 577 579 581 | 13 C 578 580 582 | 13 C 579 581 583 | 13 C 580 582 584 | 13 G 581 583 585 | 13 A 582 584 586 | 13 T 583 585 587 | 13 C 584 586 588 | 13 G 585 587 589 | 13 T 586 588 590 | 13 C 587 589 591 | 13 C 588 590 592 | 13 C 589 591 593 | 13 G 590 592 594 | 13 C 591 593 595 | 13 C 592 594 596 | 13 G 593 595 597 | 13 A 594 596 598 | 13 C 595 597 599 | 13 G 596 598 600 | 13 G 597 599 601 | 13 T 598 600 602 | 13 T 599 601 603 | 13 T 600 602 604 | 13 G 601 603 605 | 13 C 602 604 606 | 13 A 603 605 607 | 13 C 604 606 608 | 13 A 605 607 609 | 13 A 606 608 610 | 13 A 607 609 611 | 13 T 608 610 612 | 13 T 609 611 613 | 13 G 610 612 614 | 13 A 611 613 615 | 13 T 612 614 616 | 13 G 613 615 617 | 13 A 614 616 618 | 13 T 615 617 619 | 13 G 616 618 620 | 13 C 617 619 621 | 13 A 618 620 622 | 13 C 619 621 623 | 13 C 620 622 624 | 13 C 621 623 625 | 13 T 622 624 626 | 13 A 623 625 627 | 13 C 624 626 628 | 13 T 625 627 629 | 13 T 626 628 630 | 13 T 627 629 631 | 13 G 628 630 632 | 13 T 629 631 633 | 13 T 630 632 634 | 13 G 631 633 635 | 13 T 632 634 636 | 13 A 633 635 637 | 13 A 634 636 638 | 13 C 635 637 639 | 13 A 636 638 640 | 13 A 637 639 641 | 13 A 638 640 642 | 13 T 639 641 643 | 13 A 640 642 644 | 13 G 641 643 645 | 13 A 642 644 646 | 13 A 643 645 647 | 13 T 644 646 648 | 13 A 645 647 649 | 13 A 646 648 650 | 13 A 647 649 651 | 13 T 648 650 652 | 13 T 649 651 653 | 13 G 650 652 654 | 13 A 651 653 655 | 13 A 652 654 656 | 13 C 653 655 657 | 13 A 654 656 658 | 13 A 655 657 659 | 13 A 656 658 660 | 13 G 657 659 661 | 13 C 658 660 662 | 13 A 659 661 663 | 13 G 660 662 664 | 13 C 661 663 665 | 13 A 662 664 666 | 13 T 663 665 667 | 13 G 664 666 668 | 13 C 665 667 669 | 13 C 666 668 670 | 13 T 667 669 671 | 13 A 668 670 672 | 13 A 669 671 673 | 13 C 670 672 674 | 13 A 671 673 675 | 13 T 672 337 676 | -------------------------------------------------------------------------------- /tests/XYZ_oxDNA/centerline_open.dat: -------------------------------------------------------------------------------- 1 | 0 0 0 2 | 0 0 1 3 | 0 0 2 4 | 0 0 3 5 | 0 0 4 6 | 0 0 5 7 | 0 0 6 8 | 0 0 7 9 | 0 0 8 10 | 0 0 9 11 | 0 0 10 12 | 0 0 11 13 | 0 0 12 14 | 0 0 13 15 | 0 0 14 16 | 0 0 15 17 | 0 0 16 18 | 0 0 17 19 | 0 0 18 20 | 0 0 19 21 | 0 0 20 22 | 0 0 21 23 | 0 0 22 24 | 0 0 23 25 | 0 0 24 26 | 0 0 25 27 | 0 0 26 28 | 0 0 27 29 | 0 0 28 30 | 0 0 29 31 | 0 0 30 32 | 0 0 31 33 | 0 0 32 34 | 0 0 33 35 | 0 0 34 36 | 0 0 35 37 | 0 0 36 38 | 0 0 37 39 | 0 0 38 40 | 0 0 39 41 | 0 0 40 42 | 0 0 41 43 | 0 0 42 44 | 0 0 43 45 | 0 0 44 46 | 0 0 45 47 | 0 0 46 48 | 0 0 47 49 | 0 0 48 50 | 0 0 49 51 | 0 0 50 52 | 0 0 51 53 | 0 0 52 54 | 0 0 53 55 | 0 0 54 56 | 0 0 55 57 | 0 0 56 58 | 0 0 57 59 | 0 0 58 60 | 0 0 59 61 | 0 0 60 62 | 0 0 61 63 | 0 0 62 64 | 0 0 63 65 | 0 0 64 66 | 0 0 65 67 | 0 0 66 68 | 0 0 67 69 | 0 0 68 70 | 0 0 69 71 | 0 0 70 72 | 0 0 71 73 | 0 0 72 74 | 0 0 73 75 | 0 0 74 76 | 0 0 75 77 | 0 0 76 78 | 0 0 77 79 | 0 0 78 80 | 0 0 79 81 | 0 0 80 82 | 0 0 81 83 | 0 0 82 84 | 0 0 83 85 | 0 0 84 86 | 0 0 85 87 | 0 0 86 88 | 0 0 87 89 | 0 0 88 90 | 0 0 89 91 | 0 0 90 92 | 0 0 91 93 | 0 0 92 94 | 0 0 93 95 | 0 0 94 96 | 0 0 95 97 | 0 0 96 98 | 0 0 97 99 | 0 0 98 100 | 0 0 99 101 | 0 0 100 102 | 0 0 101 103 | 0 0 102 104 | 0 0 103 105 | 0 0 104 106 | 0 0 105 107 | 0 0 106 108 | 0 0 107 109 | 0 0 108 110 | 0 0 109 111 | 0 0 110 112 | 0 0 111 113 | 0 0 112 114 | 0 0 113 115 | 0 0 114 116 | 0 0 115 117 | 0 0 116 118 | 0 0 117 119 | 0 0 118 120 | 0 0 119 121 | 0 0 120 122 | 0 0 121 123 | 0 0 122 124 | 0 0 123 125 | 0 0 124 126 | 0 0 125 127 | 0 0 126 128 | 0 0 127 129 | 0 0 128 130 | 0 0 129 131 | 0 0 130 132 | 0 0 131 133 | 0 0 132 134 | 0 0 133 135 | 0 0 134 136 | 0 0 135 137 | 0 0 136 138 | 0 0 137 139 | 0 0 138 140 | 0 0 139 141 | 0 0 140 142 | 0 0 141 143 | 0 0 142 144 | 0 0 143 145 | 0 0 144 146 | 0 0 145 147 | 0 0 146 148 | 0 0 147 149 | 0 0 148 150 | 0 0 149 151 | 0 0 150 152 | 0 0 151 153 | 0 0 152 154 | 0 0 153 155 | 0 0 154 156 | 0 0 155 157 | 0 0 156 158 | 0 0 157 159 | 0 0 158 160 | 0 0 159 161 | 0 0 160 162 | 0 0 161 163 | 0 0 162 164 | 0 0 163 165 | 0 0 164 166 | 0 0 165 167 | 0 0 166 168 | 0 0 167 169 | 0 0 168 170 | 0 0 169 171 | 0 0 170 172 | 0 0 171 173 | 0 0 172 174 | 0 0 173 175 | 0 0 174 176 | 0 0 175 177 | 0 0 176 178 | 0 0 177 179 | 0 0 178 180 | 0 0 179 181 | 0 0 180 182 | 0 0 181 183 | 0 0 182 184 | 0 0 183 185 | 0 0 184 186 | 0 0 185 187 | 0 0 186 188 | 0 0 187 189 | 0 0 188 190 | 0 0 189 191 | 0 0 190 192 | 0 0 191 193 | 0 0 192 194 | 0 0 193 195 | 0 0 194 196 | 0 0 195 197 | 0 0 196 198 | 0 0 197 199 | 0 0 198 200 | 0 0 199 201 | 0 0 200 202 | 0 0 201 203 | 0 0 202 204 | 0 0 203 205 | 0 0 204 206 | 0 0 205 207 | 0 0 206 208 | 0 0 207 209 | 0 0 208 210 | 0 0 209 211 | 0 0 210 212 | 0 0 211 213 | 0 0 212 214 | 0 0 213 215 | 0 0 214 216 | 0 0 215 217 | 0 0 216 218 | 0 0 217 219 | 0 0 218 220 | 0 0 219 221 | 0 0 220 222 | 0 0 221 223 | 0 0 222 224 | 0 0 223 225 | 0 0 224 226 | 0 0 225 227 | 0 0 226 228 | 0 0 227 229 | 0 0 228 230 | 0 0 229 231 | 0 0 230 232 | 0 0 231 233 | 0 0 232 234 | 0 0 233 235 | 0 0 234 236 | 0 0 235 237 | 0 0 236 238 | 0 0 237 239 | 0 0 238 240 | 0 0 239 241 | 0 0 240 242 | 0 0 241 243 | 0 0 242 244 | 0 0 243 245 | 0 0 244 246 | 0 0 245 247 | 0 0 246 248 | 0 0 247 249 | 0 0 248 250 | 0 0 249 251 | 0 0 250 252 | 0 0 251 253 | 0 0 252 254 | 0 0 253 255 | 0 0 254 256 | 0 0 255 257 | 0 0 256 258 | 0 0 257 259 | 0 0 258 260 | 0 0 259 261 | 0 0 260 262 | 0 0 261 263 | 0 0 262 264 | 0 0 263 265 | 0 0 264 266 | 0 0 265 267 | 0 0 266 268 | 0 0 267 269 | 0 0 268 270 | 0 0 269 271 | 0 0 270 272 | 0 0 271 273 | 0 0 272 274 | 0 0 273 275 | 0 0 274 276 | 0 0 275 277 | 0 0 276 278 | 0 0 277 279 | 0 0 278 280 | 0 0 279 281 | 0 0 280 282 | 0 0 281 283 | 0 0 282 284 | 0 0 283 285 | 0 0 284 286 | 0 0 285 287 | 0 0 286 288 | 0 0 287 289 | 0 0 288 290 | 0 0 289 291 | 0 0 290 292 | 0 0 291 293 | 0 0 292 294 | 0 0 293 295 | 0 0 294 296 | 0 0 295 297 | 0 0 296 298 | 0 0 297 299 | 0 0 298 300 | 0 0 299 301 | 0 0 300 302 | 0 0 301 303 | 0 0 302 304 | 0 0 303 305 | 0 0 304 306 | 0 0 305 307 | 0 0 306 308 | 0 0 307 309 | 0 0 308 310 | 0 0 309 311 | 0 0 310 312 | 0 0 311 313 | 0 0 312 314 | 0 0 313 315 | 0 0 314 316 | 0 0 315 317 | 0 0 316 318 | 0 0 317 319 | 0 0 318 320 | 0 0 319 321 | 0 0 320 322 | 0 0 321 323 | 0 0 322 324 | 0 0 323 325 | 0 0 324 326 | 0 0 325 327 | 0 0 326 328 | 0 0 327 329 | 0 0 328 330 | 0 0 329 331 | 0 0 330 332 | 0 0 331 333 | 0 0 332 334 | 0 0 333 335 | 0 0 334 336 | 0 0 335 337 | 0 0 336 338 | 0 0 337 339 | 0 0 338 340 | 0 0 339 341 | 0 0 340 342 | 0 0 341 343 | 0 0 342 344 | 0 0 343 345 | 0 0 344 346 | 0 0 345 347 | 0 0 346 348 | 0 0 347 349 | 0 0 348 350 | 0 0 349 351 | 0 0 350 352 | 0 0 351 353 | 0 0 352 354 | 0 0 353 355 | 0 0 354 356 | 0 0 355 357 | 0 0 356 358 | 0 0 357 359 | 0 0 358 360 | 0 0 359 361 | 0 0 360 362 | 0 0 361 363 | 0 0 362 364 | 0 0 363 365 | 0 0 364 366 | 0 0 365 367 | 0 0 366 368 | 0 0 367 369 | 0 0 368 370 | 0 0 369 371 | 0 0 370 372 | 0 0 371 373 | 0 0 372 374 | 0 0 373 375 | 0 0 374 376 | 0 0 375 377 | 0 0 376 378 | 0 0 377 379 | 0 0 378 380 | 0 0 379 381 | 0 0 380 382 | 0 0 381 383 | 0 0 382 384 | 0 0 383 385 | 0 0 384 386 | 0 0 385 387 | 0 0 386 388 | 0 0 387 389 | 0 0 388 390 | 0 0 389 391 | 0 0 390 392 | 0 0 391 393 | 0 0 392 394 | 0 0 393 395 | 0 0 394 396 | 0 0 395 397 | 0 0 396 398 | 0 0 397 399 | 0 0 398 400 | 0 0 399 401 | 0 0 400 402 | 0 0 401 403 | 0 0 402 404 | 0 0 403 405 | 0 0 404 406 | 0 0 405 407 | 0 0 406 408 | 0 0 407 409 | 0 0 408 410 | 0 0 409 411 | 0 0 410 412 | 0 0 411 413 | 0 0 412 414 | 0 0 413 415 | 0 0 414 416 | 0 0 415 417 | 0 0 416 418 | 0 0 417 419 | 0 0 418 420 | 0 0 419 421 | 0 0 420 422 | 0 0 421 423 | 0 0 422 424 | 0 0 423 425 | 0 0 424 426 | 0 0 425 427 | 0 0 426 428 | 0 0 427 429 | 0 0 428 430 | 0 0 429 431 | 0 0 430 432 | 0 0 431 433 | 0 0 432 434 | 0 0 433 435 | 0 0 434 436 | 0 0 435 437 | 0 0 436 438 | 0 0 437 439 | 0 0 438 440 | 0 0 439 441 | 0 0 440 442 | 0 0 441 443 | 0 0 442 444 | 0 0 443 445 | 0 0 444 446 | 0 0 445 447 | 0 0 446 448 | 0 0 447 449 | 0 0 448 450 | 0 0 449 451 | 0 0 450 452 | 0 0 451 453 | 0 0 452 454 | 0 0 453 455 | 0 0 454 456 | 0 0 455 457 | 0 0 456 458 | 0 0 457 459 | 0 0 458 460 | 0 0 459 461 | 0 0 460 462 | 0 0 461 463 | 0 0 462 464 | 0 0 463 465 | 0 0 464 466 | 0 0 465 467 | 0 0 466 468 | 0 0 467 469 | 0 0 468 470 | 0 0 469 471 | 0 0 470 472 | 0 0 471 473 | 0 0 472 474 | 0 0 473 475 | 0 0 474 476 | 0 0 475 477 | 0 0 476 478 | 0 0 477 479 | 0 0 478 480 | 0 0 479 481 | 0 0 480 482 | 0 0 481 483 | 0 0 482 484 | 0 0 483 485 | 0 0 484 486 | 0 0 485 487 | 0 0 486 488 | 0 0 487 489 | 0 0 488 490 | 0 0 489 491 | 0 0 490 492 | 0 0 491 493 | 0 0 492 494 | 0 0 493 495 | 0 0 494 496 | 0 0 495 497 | 0 0 496 498 | 0 0 497 499 | 0 0 498 500 | 0 0 499 501 | 0 0 500 502 | 0 0 501 503 | 0 0 502 504 | 0 0 503 505 | 0 0 504 506 | 0 0 505 507 | 0 0 506 508 | 0 0 507 509 | 0 0 508 510 | 0 0 509 511 | 0 0 510 512 | 0 0 511 513 | 0 0 512 514 | 0 0 513 515 | 0 0 514 516 | 0 0 515 517 | 0 0 516 518 | 0 0 517 519 | 0 0 518 520 | 0 0 519 521 | 0 0 520 522 | 0 0 521 523 | 0 0 522 524 | 0 0 523 525 | 0 0 524 526 | 0 0 525 527 | 0 0 526 528 | 0 0 527 529 | 0 0 528 530 | 0 0 529 531 | 0 0 530 532 | 0 0 531 533 | 0 0 532 534 | 0 0 533 535 | 0 0 534 536 | 0 0 535 537 | 0 0 536 538 | 0 0 537 539 | 0 0 538 540 | 0 0 539 541 | 0 0 540 542 | 0 0 541 543 | 0 0 542 544 | 0 0 543 545 | 0 0 544 546 | 0 0 545 547 | 0 0 546 548 | 0 0 547 549 | 0 0 548 550 | 0 0 549 551 | 0 0 550 552 | 0 0 551 553 | 0 0 552 554 | 0 0 553 555 | 0 0 554 556 | 0 0 555 557 | 0 0 556 558 | 0 0 557 559 | 0 0 558 560 | 0 0 559 561 | 0 0 560 562 | 0 0 561 563 | 0 0 562 564 | 0 0 563 565 | 0 0 564 566 | 0 0 565 567 | 0 0 566 568 | 0 0 567 569 | 0 0 568 570 | 0 0 569 571 | 0 0 570 572 | 0 0 571 573 | 0 0 572 574 | 0 0 573 575 | 0 0 574 576 | 0 0 575 577 | 0 0 576 578 | 0 0 577 579 | 0 0 578 580 | 0 0 579 581 | 0 0 580 582 | 0 0 581 583 | 0 0 582 584 | 0 0 583 585 | 0 0 584 586 | 0 0 585 587 | 0 0 586 588 | 0 0 587 589 | 0 0 588 590 | 0 0 589 591 | 0 0 590 592 | 0 0 591 593 | 0 0 592 594 | 0 0 593 595 | 0 0 594 596 | 0 0 595 597 | 0 0 596 598 | 0 0 597 599 | 0 0 598 600 | 0 0 599 601 | 0 0 600 602 | 0 0 601 603 | 0 0 602 604 | 0 0 603 605 | 0 0 604 606 | 0 0 605 607 | 0 0 606 608 | 0 0 607 609 | 0 0 608 610 | 0 0 609 611 | 0 0 610 612 | 0 0 611 613 | 0 0 612 614 | 0 0 613 615 | 0 0 614 616 | 0 0 615 617 | 0 0 616 618 | 0 0 617 619 | 0 0 618 620 | 0 0 619 621 | 0 0 620 622 | 0 0 621 623 | 0 0 622 624 | 0 0 623 625 | 0 0 624 626 | 0 0 625 627 | 0 0 626 628 | 0 0 627 629 | 0 0 628 630 | 0 0 629 631 | 0 0 630 632 | 0 0 631 633 | 0 0 632 634 | 0 0 633 635 | 0 0 634 636 | 0 0 635 637 | 0 0 636 638 | 0 0 637 639 | 0 0 638 640 | 0 0 639 641 | 0 0 640 642 | 0 0 641 643 | 0 0 642 644 | 0 0 643 645 | 0 0 644 646 | 0 0 645 647 | 0 0 646 648 | 0 0 647 649 | 0 0 648 650 | 0 0 649 651 | 0 0 650 652 | 0 0 651 653 | 0 0 652 654 | 0 0 653 655 | 0 0 654 656 | 0 0 655 657 | 0 0 656 658 | 0 0 657 659 | 0 0 658 660 | 0 0 659 661 | 0 0 660 662 | 0 0 661 663 | 0 0 662 664 | 0 0 663 665 | 0 0 664 666 | 0 0 665 667 | 0 0 666 668 | 0 0 667 669 | 0 0 668 670 | 0 0 669 671 | 0 0 670 672 | 0 0 671 673 | 0 0 672 674 | 0 0 673 675 | 0 0 674 676 | 0 0 675 677 | 0 0 676 678 | 0 0 677 679 | 0 0 678 680 | 0 0 679 681 | 0 0 680 682 | 0 0 681 683 | 0 0 682 684 | 0 0 683 685 | 0 0 684 686 | 0 0 685 687 | 0 0 686 688 | 0 0 687 689 | 0 0 688 690 | 0 0 689 691 | 0 0 690 692 | 0 0 691 693 | 0 0 692 694 | 0 0 693 695 | 0 0 694 696 | 0 0 695 697 | 0 0 696 698 | 0 0 697 699 | 0 0 698 700 | 0 0 699 701 | 0 0 700 702 | 0 0 701 703 | 0 0 702 704 | 0 0 703 705 | 0 0 704 706 | 0 0 705 707 | 0 0 706 708 | 0 0 707 709 | 0 0 708 710 | 0 0 709 711 | 0 0 710 712 | 0 0 711 713 | 0 0 712 714 | 0 0 713 715 | 0 0 714 716 | 0 0 715 717 | 0 0 716 718 | 0 0 717 719 | 0 0 718 720 | 0 0 719 721 | 0 0 720 722 | 0 0 721 723 | 0 0 722 724 | 0 0 723 725 | 0 0 724 726 | 0 0 725 727 | 0 0 726 728 | 0 0 727 729 | 0 0 728 730 | 0 0 729 731 | 0 0 730 732 | 0 0 731 733 | 0 0 732 734 | 0 0 733 735 | 0 0 734 736 | 0 0 735 737 | 0 0 736 738 | 0 0 737 739 | 0 0 738 740 | 0 0 739 741 | 0 0 740 742 | 0 0 741 743 | 0 0 742 744 | 0 0 743 745 | 0 0 744 746 | 0 0 745 747 | 0 0 746 748 | 0 0 747 749 | 0 0 748 750 | 0 0 749 751 | 0 0 750 752 | 0 0 751 753 | 0 0 752 754 | 0 0 753 755 | 0 0 754 756 | 0 0 755 757 | 0 0 756 758 | 0 0 757 759 | 0 0 758 760 | 0 0 759 761 | 0 0 760 762 | 0 0 761 763 | 0 0 762 764 | 0 0 763 765 | 0 0 764 766 | 0 0 765 767 | 0 0 766 768 | 0 0 767 769 | 0 0 768 770 | 0 0 769 771 | 0 0 770 772 | 0 0 771 773 | 0 0 772 774 | 0 0 773 775 | 0 0 774 776 | 0 0 775 777 | 0 0 776 778 | 0 0 777 779 | 0 0 778 780 | 0 0 779 781 | 0 0 780 782 | 0 0 781 783 | 0 0 782 784 | 0 0 783 785 | 0 0 784 786 | 0 0 785 787 | 0 0 786 788 | 0 0 787 789 | 0 0 788 790 | 0 0 789 791 | 0 0 790 792 | 0 0 791 793 | 0 0 792 794 | 0 0 793 795 | 0 0 794 796 | 0 0 795 797 | 0 0 796 798 | 0 0 797 799 | 0 0 798 800 | 0 0 799 801 | 0 0 800 802 | 0 0 801 803 | 0 0 802 804 | 0 0 803 805 | 0 0 804 806 | 0 0 805 807 | 0 0 806 808 | 0 0 807 809 | 0 0 808 810 | 0 0 809 811 | 0 0 810 812 | 0 0 811 813 | 0 0 812 814 | 0 0 813 815 | 0 0 814 816 | 0 0 815 817 | 0 0 816 818 | 0 0 817 819 | 0 0 818 820 | 0 0 819 821 | 0 0 820 822 | 0 0 821 823 | 0 0 822 824 | 0 0 823 825 | 0 0 824 826 | 0 0 825 827 | 0 0 826 828 | 0 0 827 829 | 0 0 828 830 | 0 0 829 831 | 0 0 830 832 | 0 0 831 833 | 0 0 832 834 | 0 0 833 835 | 0 0 834 836 | 0 0 835 837 | 0 0 836 838 | 0 0 837 839 | 0 0 838 840 | 0 0 839 841 | 0 0 840 842 | 0 0 841 843 | 0 0 842 844 | 0 0 843 845 | 0 0 844 846 | 0 0 845 847 | 0 0 846 848 | 0 0 847 849 | 0 0 848 850 | 0 0 849 851 | 0 0 850 852 | 0 0 851 853 | 0 0 852 854 | 0 0 853 855 | 0 0 854 856 | 0 0 855 857 | 0 0 856 858 | 0 0 857 859 | 0 0 858 860 | 0 0 859 861 | 0 0 860 862 | 0 0 861 863 | 0 0 862 864 | 0 0 863 865 | 0 0 864 866 | 0 0 865 867 | 0 0 866 868 | 0 0 867 869 | 0 0 868 870 | 0 0 869 871 | 0 0 870 872 | 0 0 871 873 | 0 0 872 874 | 0 0 873 875 | 0 0 874 876 | 0 0 875 877 | 0 0 876 878 | 0 0 877 879 | 0 0 878 880 | 0 0 879 881 | 0 0 880 882 | 0 0 881 883 | 0 0 882 884 | 0 0 883 885 | 0 0 884 886 | 0 0 885 887 | 0 0 886 888 | 0 0 887 889 | 0 0 888 890 | 0 0 889 891 | 0 0 890 892 | 0 0 891 893 | 0 0 892 894 | 0 0 893 895 | 0 0 894 896 | 0 0 895 897 | 0 0 896 898 | 0 0 897 899 | 0 0 898 900 | 0 0 899 901 | 0 0 900 902 | 0 0 901 903 | 0 0 902 904 | 0 0 903 905 | 0 0 904 906 | 0 0 905 907 | 0 0 906 908 | 0 0 907 909 | 0 0 908 910 | 0 0 909 911 | 0 0 910 912 | 0 0 911 913 | 0 0 912 914 | 0 0 913 915 | 0 0 914 916 | 0 0 915 917 | 0 0 916 918 | 0 0 917 919 | 0 0 918 920 | 0 0 919 921 | 0 0 920 922 | 0 0 921 923 | 0 0 922 924 | 0 0 923 925 | 0 0 924 926 | 0 0 925 927 | 0 0 926 928 | 0 0 927 929 | 0 0 928 930 | 0 0 929 931 | 0 0 930 932 | 0 0 931 933 | 0 0 932 934 | 0 0 933 935 | 0 0 934 936 | 0 0 935 937 | 0 0 936 938 | 0 0 937 939 | 0 0 938 940 | 0 0 939 941 | 0 0 940 942 | 0 0 941 943 | 0 0 942 944 | 0 0 943 945 | 0 0 944 946 | 0 0 945 947 | 0 0 946 948 | 0 0 947 949 | 0 0 948 950 | 0 0 949 951 | 0 0 950 952 | 0 0 951 953 | 0 0 952 954 | 0 0 953 955 | 0 0 954 956 | 0 0 955 957 | 0 0 956 958 | 0 0 957 959 | 0 0 958 960 | 0 0 959 961 | 0 0 960 962 | 0 0 961 963 | 0 0 962 964 | 0 0 963 965 | 0 0 964 966 | 0 0 965 967 | 0 0 966 968 | 0 0 967 969 | 0 0 968 970 | 0 0 969 971 | 0 0 970 972 | 0 0 971 973 | 0 0 972 974 | 0 0 973 975 | 0 0 974 976 | 0 0 975 977 | 0 0 976 978 | 0 0 977 979 | 0 0 978 980 | 0 0 979 981 | 0 0 980 982 | 0 0 981 983 | 0 0 982 984 | 0 0 983 985 | 0 0 984 986 | 0 0 985 987 | 0 0 986 988 | 0 0 987 989 | 0 0 988 990 | 0 0 989 991 | 0 0 990 992 | 0 0 991 993 | 0 0 992 994 | 0 0 993 995 | 0 0 994 996 | 0 0 995 997 | 0 0 996 998 | 0 0 997 999 | 0 0 998 1000 | 0 0 999 1001 | 0 0 1000 1002 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # tacoxNA 2 | 3 | tacoxDNA (Tools and Converters for oxDNA) is a collection of tools initially developed to help [oxDNA](http://dna.physics.ox.ac.uk/) users. However, it will soon be expanded so as to support additional models. If you use tacoxDNA, please consider citing the following article: 4 | 5 | A. Suma, E. Poppleton, M. Matthies, P. Šulc, F. Romano, A. A. Louis, J. P. K. Doye, C. Micheletti and L. Rovigatti, ["TacoxDNA: A user‐friendly web server for simulations of complex DNA structures, from single strands to origami"](https://doi.org/10.1002/jcc.26029), *J. Comput. Chem.* **40**, 2586 (2019) 6 | 7 | ## Requirements 8 | 9 | * Python 3 (any version should work). If you want to stick to Python 2 check out the corresponding branch. 10 | * `numpy` 11 | 12 | ## Tools 13 | 14 | The sections that follow introduce the tools and their usage. 15 | 16 | * [Generator for twisted and knotted configurations](#generator-for-twisted-and-knotted-configurations) 17 | * [oxDNA-to-LAMMPS converter](#oxdna-to-lammps-converter) 18 | * [LAMMPS-to-oxDNA converter](#lammps-to-oxdna-converter) 19 | * [oxDNA-to-PDB converter](#oxdna-to-pdb-converter) 20 | * [PDB-to-oxDNA converter](#pdb-to-oxdna-converter) 21 | * [cadnano-to-oxDNA converter](#cadnano-to-oxdna-converter) 22 | * [CanDo-to-oxDNA converter](#cando-to-oxdna-converter) 23 | * [Tiamat-to-oxDNA converter](#tiamat-to-oxdna-converter) 24 | * [vHelix-to-oxDNA converter](#vhelix-to-oxdna-converter) 25 | * [rpoly-to-oxDNA converter](#rpoly-to-oxdna-converter) 26 | * [scadnano-to-oxDNA converter](#scadnano-to-oxdna-converter) 27 | 28 | --- 29 | 30 | ## Generator for twisted and knotted configurations 31 | 32 | The `XYZ_oxDNA.py` script generates an oxDNA topology/configuration pair from a file containing a list of coordinates that defines a centerline. 33 | 34 | ### Mandatory arguments 35 | * A centerline file containing a list of coordinates in the format x y z 36 | 37 | ### Optional arguments 38 | * `-c\--closed` 39 | the last bead is connected to the first bead (default) 40 | * `-o\--open` 41 | the last bead is not connected to the first bead 42 | * `-h\--help` 43 | print usage 44 | * `-d\--dsDNA` 45 | the chain is clad with a double-stranded DNA (default) 46 | * `-s\--ssDNA` 47 | the chain is clad with a single-stranded DNA 48 | * `-n\--nicked` 49 | optional argument when -d option is used. One of the two strands of double strand DNA is nicked (not circularized) (not set by default) 50 | * `-p\--supercoiling=SUPERCOILING_DENSITY` 51 | supercoiling density percentage (defaults to 0, with an equilibrium pitch of 10.5 imposed) 52 | * `-w\--writhe=WRITHE_AMOUNT` 53 | topological target writhe to superimpose. When the supercoiling density is zero, this number corresponds to the average writhe. Useful for knots which have an average writhe different from 0 (it defaults to 0) 54 | * `-e\--seed=RNG_SEED` 55 | random seed for DNA sequence (defaults to a random value) 56 | * `-q\--sequence=SEQUENCE` 57 | text file containing a valid DNA sequence (*e.g.* ATCTGA). The length of the sequence should correspond to the number of points in the coordinate file. If not specified, the sequence will be chosen randomly 58 | 59 | ### Output 60 | * An oxDNA topology file (named by suffixing the centerline file with ".top") 61 | * An oxDNA configuration file (named by suffixing the centerline file with ".oxdna") 62 | 63 | --- 64 | 65 | ## oxDNA-to-LAMMPS converter 66 | 67 | The `oxDNA_LAMMPS.py` script takes two mandatory arguments and outputs a single file that can be used as input to run oxDNA simulations [USER-CGDNA](https://lammps.sandia.gov/doc/Packages_details.html#pkg-user-cgdna) LAMMPS package. 68 | 69 | ### Arguments 70 | * An oxDNA topology file 71 | * An oxDNA configuration file 72 | 73 | ### Output 74 | * A file containing the list of nucleotide positions, quaternions, velocities, angular velocities and bonds which can be used as a start file in LAMMPS. The name of the file is just the oxDNA configuration filename, prefixed with "LAMMPS_" 75 | 76 | --- 77 | 78 | ## LAMMPS-to-oxDNA converter 79 | 80 | The `LAMMPS_oxDNA.py` script takes one mandatory argument, one optional argument and outputs two files. 81 | 82 | ### Arguments 83 | * A LAMMPS data file, containing the nucleotide positions, quaternions, velocities, angular momenta and the bond list 84 | * Optionally, a LAMMPS trajectory file with atom data for each time step after the data file name 85 | 86 | ### Output 87 | * An oxDNA topology file (named by suffixing the LAMMPS output file with ".top") 88 | * An oxDNA configuration file (named by suffixing the LAMMPS output file with ".oxdna"). If a trajectory file is also processed, the configuration file will contain the full trajectory data in native oxDNA format. 89 | 90 | --- 91 | 92 | ## oxDNA-to-PDB converter 93 | 94 | The `oxDNA_PDB.py` script takes three mandatory arguments and outputs a single file. Since oxDNA bases has no one-to-one explicit mapping to all-atom representations, the converted structure will most likely require some sort of relaxation procedure before being used as input for all-atom simulation packages. Moreover, when using this script the following points should be taken into account: 95 | 96 | * the phosphate groups of nucleobases at the 5' end of each strand are removed 97 | * a hydrogen is added to each of the 3' and 5' end nucleobases (HO3' and HO5', respectively) 98 | 99 | ### Mandatory arguments 100 | * An oxDNA topology file 101 | * An oxDNA configuration file 102 | * The direction according to which the nucleotides are to be listed in the PDB file. It should be either 35 (for 3' -> 5') or 53 (for 5' -> 3'). Most of the all-atoms tools (*e.g.* GROMACS) assume the 5' -> 3' order. 103 | 104 | ### Optional arguments 105 | * `-H, --hydrogens=[true|false]` 106 | if true, include hydrogen atoms in the PDB file (defaults to true) 107 | * `-u\--uniform-residue-names` 108 | drop the `3` and `5` suffixes from the names of residues that are placed at the strands' ends. It increases the compatibility with some tools (*e.g.* Chimera and Molecular Maya) 109 | * `-o\--one-file-per-strand` 110 | print one PDB file for each strand 111 | * `--rmsf-file` 112 | write rmsf data per residue from the `compute_deviations` command of the [oxDNA Analysis Tools](https://github.com/sulcgroup/oxdna_analysis_tools/) to the output PDB bfactor field 113 | 114 | ### Output 115 | * A [PDB](https://www.cgl.ucsf.edu/chimera/docs/UsersGuide/tutorials/pdbintro.html) file containing the positions of all atoms composing the strand(s) contained in the oxDNA configuration file 116 | 117 | --- 118 | 119 | ## PDB-to-oxDNA converter 120 | 121 | The `PDB_oxDNA.py` script takes two mandatory arguments. Given the sometimes messy nature of PDB files, the script makes some choices during the parsing of the input file. In particular, note the following points: 122 | 123 | * if the PDB file contains more than one MODEL, only the first one will be converted unless the `-m/--models-as-strands` option is given 124 | * if the PDB file contains alternate locations for some (or all) of the atoms, only those marked with either "1" or "A" will be considered. If the PDB file uses a different notation, the script may fail or crash 125 | * sometimes, sugar atoms are marked with asterisks (\*) instead of single quotes ('). In these cases the converter replaces the former with the latter and moves on 126 | 127 | ### Mandatory arguments 128 | * The input PDB file 129 | * The direction according to which the nucleotides are listed in the PDB file. It should be either 35 (for 3' -> 5') or 53 (for 5' -> 3'). 130 | 131 | ### Optional arguments 132 | * `-m, --models-as-strands` 133 | Treat different models as different strands 134 | 135 | ### Output 136 | * An oxDNA topology file (named by suffixing the PDB file with ".top") 137 | * An oxDNA configuration file (named by suffixing the PDB file with ".oxdna") 138 | 139 | --- 140 | 141 | ## cadnano-to-oxDNA converter 142 | 143 | The `cadnano_oxDNA.py` script converts [cadnano](https://cadnano.org/) files into oxDNA configurations. Optionally, it can also output [.oxview files](https://sulcgroup.github.io/oxdna-viewer/) which will contain additional information about base pairing, custom colors and clustered domains. 144 | 145 | Note that the script **does not** support scaffold-less input files. It takes two mandatory arguments. 146 | 147 | ### Mandatory arguments 148 | * The input cadnano file (in json format) 149 | * The lattice type the file was designed with. It should be either *sq* (square) or *he* (hexagonal) 150 | 151 | ### Optional arguments 152 | * `-e\--seed=RNG_SEED` 153 | random seed for DNA sequence (defaults to a random value) 154 | * `-b\--box=VALUE` 155 | the length of the box side (in oxDNA simulation units) where the system will be placed 156 | * `-q\--sequence=SEQUENCE` 157 | text file containing a valid DNA sequence (*e.g.* ATCTGA). If not specified, the sequence will be chosen randomly 158 | * `-p\--print-virt2-nuc` 159 | print the `virt2nuc` file that can be used by the oxDNA's `origami_utils.py` script to convert between cadnano and oxDNA nucleotide indexes 160 | * `-o\--print-oxview` 161 | print a `.oxview` file that can be opened and edited in [oxView](https://sulcgroup.github.io/oxdna-viewer/). Using this option will allow you to keep additional design information not included in the oxDNA files. 162 | 163 | ### Output 164 | * An oxDNA topology file (named by suffixing the cadnano file with ".top") 165 | * An oxDNA configuration file (named by suffixing the cadnano file with ".oxdna") 166 | 167 | --- 168 | 169 | ## CanDo-to-oxDNA converter 170 | 171 | The `CanDo_oxDNA.py` script converts [CanDo](https://cando-dna-origami.org/) files into oxDNA configurations. It takes one mandatory argument. 172 | 173 | ### Mandatory arguments 174 | * The input CanDo file 175 | 176 | ### Optional arguments 177 | * `-b\--box=VALUE` 178 | the length of the box side (in oxDNA simulation units) where the system will be placed (defaults to 100) 179 | * `-f\--print-force-file` 180 | also print a file containing the specifics for a oxDNA-compatible set of external forces that may be useful to relax the system 181 | 182 | ### Output 183 | * An oxDNA topology file (named by suffixing the CanDo file with ".top") 184 | * An oxDNA configuration file (named by suffixing the CanDo file with ".oxdna") 185 | 186 | --- 187 | 188 | ## Tiamat-to-oxDNA converter 189 | 190 | The `Tiamat_oxDNA.py` script converts [Tiamat](http://yanlab.asu.edu/Resources.html) files into oxDNA configurations. It takes one mandatory argument. 191 | 192 | ### Mandatory arguments 193 | * The input Tiamat file (in json format) 194 | 195 | ### Optional arguments 196 | * `-m\--molecule=[DNA|RNA]` 197 | the type of molecule contained in the input file (defaults to DNA) 198 | * `-t\--tiamat-version=[1|2]` 199 | the Tiamat version the input file was generated with. If you are not sure, it's probably 2, the default value 200 | * `-d\--default-base=[A|C|G|T|R|integer]` 201 | some of the bases generated by Tiamat have no associated type. By default, these bases are assigned a random type (either A, C, G or T). By setting this option the user can assign to these bases the same type. Since oxDNA can also use integer numbers as types, these are also supported here 202 | * `-f\--print-force-file` 203 | also print a file containing the specifics for a oxDNA-compatible set of external forces that may be useful to relax the system 204 | * `-o\--print-oxview` 205 | print a `.oxview` file that can be opened and edited in [oxView](https://sulcgroup.github.io/oxdna-viewer/). Using this option will allow you to keep basepair information not included in the oxDNA files. 206 | 207 | ### Output 208 | * An oxDNA topology file (named by suffixing the Tiamat file with ".top") 209 | * An oxDNA configuration file (named by suffixing the Tiamat file with ".oxdna") 210 | 211 | --- 212 | 213 | ## vHelix-to-oxDNA converter 214 | 215 | The `vHelix_oxDNA.py` script converts [vHelix](http://www.vhelix.net/) files into oxDNA configurations. vhelix files are Maya files stored in the MA format. It takes one mandatory argument. 216 | 217 | ### Mandatory arguments 218 | * The input vHelix file 219 | 220 | ### Optional arguments 221 | * `-b\--box=VALUE` 222 | the length of the box side (in oxDNA simulation units) where the system will be placed (defaults to 100) 223 | * `-e\--seed=RNG_SEED` 224 | random seed (defaults to a random value). Random vectors are used whenever the input configuration contains deleted nucleotides. 225 | 226 | ### Output 227 | * An oxDNA topology file (named by suffixing the vHelix file with ".top") 228 | * An oxDNA configuration file (named by suffixing the vHelix file with ".oxdna") 229 | 230 | --- 231 | 232 | ## rpoly-to-oxDNA converter 233 | 234 | The `rpoly_oxDNA.py` script converts routed polyhedra (rpoly) files containing wireframe DNA origami structures automatically generated using the BSCOR package(http://www.vhelix.net/) into oxDNA configurations. It takes one mandatory argument. Optionally, it can output [.oxview files](https://sulcgroup.github.io/oxdna-viewer/) which will also contain basepairs, as well as clusters for each helix. 235 | 236 | ### Mandatory arguments 237 | * The input rpoly file 238 | 239 | ### Optional arguments 240 | * `-e\--seed=RNG_SEED` 241 | random seed for DNA sequence (defaults to a random value) 242 | * `-o\--print-oxview` 243 | print a `.oxview` file that can be opened and edited in [oxView](https://sulcgroup.github.io/oxdna-viewer/). Using this option will allow you to keep additional design information not included in the oxDNA files. 244 | 245 | ### Output 246 | * An oxDNA topology file (named by suffixing the rpoly file with ".top") 247 | * An oxDNA configuration file (named by suffixing the rpoly file with ".oxdna") 248 | 249 | ## scadnano-to-oxDNA converter 250 | 251 | The `scadnano_oxDNA.py` script converts [scadnano](https://github.com/UC-Davis-molecular-computing/scadnano) designs to oxDNA configurations. 252 | 253 | ### Mandatory arguments 254 | * The input scadnano design file 255 | 256 | ### Output 257 | * An oxDNA topology file (named by suffixing the scadnano file with ".top") 258 | * An oxDNA configuration file (named by suffixing the scadnano file with ".oxdna") 259 | 260 | --- 261 | 262 | ## Testing 263 | 264 | tacoxDNA contains a very simple testing suite to verify the working status of the scripts. The `tests` directory contains a directory for each script. Within each directory there is a `run.sh` bash script that performs one or more tests on the specific script. Execute `run_all.sh` to run all tests and get a summary of the results. 265 | 266 | ## Acknowledgements 267 | 268 | * Some of the code has been adapted from the [oxDNA](http://dna.physics.ox.ac.uk/) source 269 | * The vHelix-to-oxDNA converter was provided by Erik Benson 270 | * The source of code of the [pyquaternion lib](https://github.com/KieranWynn/pyquaternion) is included in the source tree 271 | --------------------------------------------------------------------------------