RNA.h

Go to the documentation of this file.
00001 #ifndef SimTK_MOLMODEL_RNA_H_
00002 #define SimTK_MOLMODEL_RNA_H_
00003 
00004 /* -------------------------------------------------------------------------- *
00005  *                      SimTK Core: SimTK Molmodel                            *
00006  * -------------------------------------------------------------------------- *
00007  * This is part of the SimTK Core biosimulation toolkit originating from      *
00008  * Simbios, the NIH National Center for Physics-Based Simulation of           *
00009  * Biological Structures at Stanford, funded under the NIH Roadmap for        *
00010  * Medical Research, grant U54 GM072970. See https://simtk.org.               *
00011  *                                                                            *
00012  * Portions copyright (c) 2007 Stanford University and the Authors.           *
00013  * Authors: Michael Sherman, Christopher Bruns                                *
00014  * Contributors: Samuel Flores                                                *
00015  *                                                                            *
00016  * Permission is hereby granted, free of charge, to any person obtaining a    *
00017  * copy of this software and associated documentation files (the "Software"), *
00018  * to deal in the Software without restriction, including without limitation  *
00019  * the rights to use, copy, modify, merge, publish, distribute, sublicense,   *
00020  * and/or sell copies of the Software, and to permit persons to whom the      *
00021  * Software is furnished to do so, subject to the following conditions:       *
00022  *                                                                            *
00023  * The above copyright notice and this permission notice shall be included in *
00024  * all copies or substantial portions of the Software.                        *
00025  *                                                                            *
00026  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR *
00027  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,   *
00028  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL    *
00029  * THE AUTHORS, CONTRIBUTORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,    *
00030  * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR      *
00031  * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE  *
00032  * USE OR OTHER DEALINGS IN THE SOFTWARE.                                     *
00033  * -------------------------------------------------------------------------- */
00034 
00035 
00036 #include "molmodel/internal/common.h"
00037 #include "molmodel/internal/Compound.h"
00038 
00039 namespace SimTK {
00040 
00041 // RiboseCore leaves 4 bond centers open:
00042 // 1) inboard center at O5* atom, for binding 5' phosphate
00043 // 2) 
00044 class SimTK_MOLMODEL_EXPORT RiboseCore : public BiopolymerResidue {
00045 public:
00046     RiboseCore(const String& name, const String& tlc, char olc) 
00047         : BiopolymerResidue(name, tlc, olc)
00048     {
00049         setBaseAtom(BivalentAtom("O5*", Element::Oxygen(), 120.90*Deg2Rad));
00050 
00051         bondAtom(AliphaticCarbon("C5*"), "O5*/bond2", 0.1423, 180*Deg2Rad);
00052         bondAtom(AliphaticHydrogen("H5*1"), "C5*/bond4");
00053         bondAtom(AliphaticHydrogen("H5*2"), "C5*/bond3");
00054 
00055         bondAtom(AliphaticCarbon("C4*"), "C5*/bond2", 0.1510); // length from (Gelbin et al 1996)
00056         bondAtom(AliphaticHydrogen("H4*"), "C4*/bond4");
00057 
00058         bondAtom(BivalentAtom("O4*", Element::Oxygen(), 112.0*Deg2Rad), "C4*/bond2", 0.1453);
00059 
00060         bondAtom(AliphaticCarbon("C3*"), "C4*/bond3", 0.1524);
00061         bondAtom(AliphaticHydrogen("H3*"), "C3*/bond4");
00062 
00063         bondAtom(BivalentAtom("O3*", Element::Oxygen(), 119.7*Deg2Rad), "C3*/bond2", 0.1423);
00064  
00065         bondAtom(AliphaticCarbon("C2*"), "C3*/bond3", 0.1525);
00066         bondAtom(AliphaticHydrogen("H2*"), "C2*/bond3");
00067 
00068         bondAtom(AliphaticCarbon("C1*"), "C2*/bond2", 0.1528);
00069         bondAtom(AliphaticHydrogen("H1*"), "C1*/bond4");
00070 
00071         addRingClosingBond("C1*/bond2", "O4*/bond2", 0.1414);
00072 
00073         // Ring strain reduces ring bond angles
00074         setDefaultBondAngle(109.6*Deg2Rad, "C1*", "O4*", "C4*"); 
00075         setDefaultBondAngle(105.5*Deg2Rad, "O4*", "C4*", "C3*"); 
00076         setDefaultBondAngle(102.7*Deg2Rad, "C4*", "C3*", "C2*"); 
00077         setDefaultBondAngle(101.5*Deg2Rad, "C3*", "C2*", "C1*"); 
00078         setDefaultBondAngle(106.4*Deg2Rad, "C2*", "C1*", "O4*");
00079 
00080         nameBondCenter("bondO5", "O5*/bond1");
00081         nameBondCenter("bondO3", "O3*/bond2");
00082         nameBondCenter("bondC1", "C1*/bond3");
00083 
00084         // RNA backbone dihedral angles
00085         // defineDihedralAngle("alpha", "bondO5", ""); // TODO requires phosphate
00086         //defineDihedralAngle("beta", "bondO5", "C5*/bond2");
00087         //defineDihedralAngle("gamma", "O5*", "C5*", "C4*", "C3*");
00088         //defineDihedralAngle("delta", "C5*", "C4*", "C3*", "C2*");
00089         //defineDihedralAngle("epsilon", "bondO3", "C3*/bond1");
00090         // TODO zeta requires next phosphate
00091 
00092         // ribose ring dihedral angles
00093         defineDihedralAngle( "nu0", "C4*", "O4*", "C1*", "C2*" );
00094         defineDihedralAngle( "nu1", "O4*", "C1*", "C2*", "C3*" );
00095         defineDihedralAngle( "nu2", "C1*", "C2*", "C3*", "C4*" );
00096         defineDihedralAngle( "nu3", "C2*", "C3*", "C4*", "O4*" );
00097         defineDihedralAngle( "nu4", "C3*", "C4*", "O4*", "C1*" );
00098 
00099         // Guestimated from Figure 2 of 
00100         // Schneider, B; Moravek, Z; and Berman, H.M. (2004)
00101         // "RNA conformational classes"
00102         // Nucleic Acids Research 32(5): 1666-1677
00103         // setDefaultDihedralAngle("alpha", -60*Deg2Rad);
00104         //setDefaultDihedralAngle("beta", 180*Deg2Rad);
00105         //setDefaultDihedralAngle("gamma", 60*Deg2Rad);
00106         //setDefaultDihedralAngle("delta", 80*Deg2Rad);
00107         //setDefaultDihedralAngle("epsilon", 190*Deg2Rad);
00108         // setDefaultDihedralAngle("zeta", -70*Deg2Rad);
00109 
00110         // nu angles selected from resdue U52 of 1EHZ
00111         setDefaultDihedralAngle("nu0", 2.2*Deg2Rad);
00112         setDefaultDihedralAngle("nu1", -24.5*Deg2Rad);
00113         setDefaultDihedralAngle("nu2", 35.8*Deg2Rad);
00114         setDefaultDihedralAngle("nu3", -35.9*Deg2Rad); // same bond as delta, different reference atoms
00115         setDefaultDihedralAngle("nu4", 21.6*Deg2Rad);
00116 
00117         nameBondCenter("bondNext", "bondO3");
00118         nameBondCenter("bondPrevious", "bondO5");
00119 
00120         setDefaultInboardBondLength(0.16100);
00121 
00122         // alternate atom names
00123         nameAtom("O5'", "O5*");
00124         nameAtom("C5'", "C5*");
00125         nameAtom("H5'", "H5*1");
00126         nameAtom("H5''", "H5*2");
00127         nameAtom("C4'", "C4*");
00128         nameAtom("H4'", "H4*");
00129         nameAtom("O4'", "O4*");
00130         nameAtom("C3'", "C3*");
00131         nameAtom("H3'", "H3*");
00132         nameAtom("O3'", "O3*");
00133         nameAtom("C2'", "C2*");
00134         nameAtom("H2'", "H2*");
00135         nameAtom("C1'", "C1*");
00136         nameAtom("H1'", "H1*");
00137     }
00138 
00139 };
00140 
00141 
00143 class SimTK_MOLMODEL_EXPORT FivePrimeRnaHydroxylGroup : public BiopolymerResidue
00144 {
00145 public:
00146     FivePrimeRnaHydroxylGroup(String name, String threeLetterCode = "Unk", char oneLetterCode = '?') 
00147     : BiopolymerResidue(name, threeLetterCode, oneLetterCode)
00148     {
00149         instantiateBiotypes();
00150         
00151         setBaseAtom( UnivalentAtom("H5T", Element::Hydrogen()) );
00152         
00153         nameBondCenter("bondNext", "H5T/bond");
00154 
00155         setBiotypeIndex( "H5T", Biotype::get("Hydroxyl, RNA", "H5T", SimTK::Ordinality::Initial).getIndex() );
00156     }
00157     
00158     static void instantiateBiotypes() 
00159     {
00160         if ( ! Biotype::exists("Hydroxyl, RNA", "H5T", SimTK::Ordinality::Initial) )
00161             Biotype::defineBiotype(Element::Hydrogen(), 1, "Hydroxyl, RNA", "H5T", SimTK::Ordinality::Initial);
00162         
00163         // This oxygen biotype should get applied to the 5' oxygen of the nucleotide this hydroxyl attaches to
00164         if ( ! Biotype::exists("Hydroxyl, RNA", "O5*", SimTK::Ordinality::Initial) )
00165             Biotype::defineBiotype(Element::Oxygen(), 2, "Hydroxyl, RNA", "O5*", SimTK::Ordinality::Initial);
00166     }
00167     
00168 };
00169 
00170 
00172 class SimTK_MOLMODEL_EXPORT FivePrimeRnaPhosphateGroup : public BiopolymerResidue
00173 {
00174 public:
00175     FivePrimeRnaPhosphateGroup(String name, String threeLetterCode = "Unk", char oneLetterCode = '?') 
00176     : BiopolymerResidue(name, threeLetterCode, oneLetterCode)
00177     {
00178         instantiateBiotypes();
00179         
00180         setBaseAtom( QuadrivalentAtom("P", Element::Phosphorus()) );
00181         
00182         bondAtom(UnivalentAtom("OP1", Element::Oxygen()), "P/bond4", 0.14800);
00183         bondAtom(UnivalentAtom("OP2", Element::Oxygen()), "P/bond3", 0.14800);
00184         bondAtom(UnivalentAtom("OP3", Element::Oxygen()), "P/bond2", 0.14800);
00185         
00186         nameBondCenter("bondNext", "P/bond1");
00187 
00188         setBiotypeIndex( "P", Biotype::get("Phosphate, RNA", "P", SimTK::Ordinality::Initial).getIndex() );
00189         setBiotypeIndex( "OP1", Biotype::get("Phosphate, RNA", "OP", SimTK::Ordinality::Initial).getIndex() );
00190         setBiotypeIndex( "OP2", Biotype::get("Phosphate, RNA", "OP", SimTK::Ordinality::Initial).getIndex() );
00191         setBiotypeIndex( "OP3", Biotype::get("Phosphate, RNA", "OP", SimTK::Ordinality::Initial).getIndex() );
00192     }
00193     
00194     static void instantiateBiotypes() 
00195     {
00196         if ( ! Biotype::exists("Phosphate, RNA", "P", SimTK::Ordinality::Initial) )
00197             Biotype::defineBiotype(Element::Phosphorus(), 4, "Phosphate, RNA", "P", SimTK::Ordinality::Initial);
00198         if ( ! Biotype::exists("Phosphate, RNA", "OP", SimTK::Ordinality::Initial) )
00199             Biotype::defineBiotype(Element::Oxygen(), 1, "Phosphate, RNA", "OP", SimTK::Ordinality::Initial);
00200     }
00201     
00202 };
00203 
00204 
00205 // Phosphodiester linkage between two RNA nucleotides
00206 class SimTK_MOLMODEL_EXPORT RnaPhosphodiesterLinkage : public BiopolymerResidue
00207 {
00208 public:
00209     RnaPhosphodiesterLinkage(String name, String threeLetterCode = "Unk", char oneLetterCode = '?') 
00210         : BiopolymerResidue(name, threeLetterCode, oneLetterCode)
00211     {
00212         instantiateBiotypes();
00213 
00214         // TODO - set bond angles: 102.6 between ether oxygens, 119.9 between lone oxygen, 108.23 between mismatched pairs
00215         setBaseAtom( QuadrivalentAtom("P", Element::Phosphorus() 
00216                    ,  104.0*Deg2Rad // 03'-P-O5' from Gelbin et al
00217                    ,  107.9*Deg2Rad // 03'-P-OP? from Gelbin et al
00218                    ,  107.9*Deg2Rad // 03'-P-OP? from Gelbin et al
00219                    , -108.15*Deg2Rad // to make OP1-P-OP2 angle 119.6
00220                    ,  108.15*Deg2Rad // to make OP1-P-OP2 angle 119.6
00221                    ) );
00222 
00223         bondAtom(UnivalentAtom("OP1", Element::Oxygen()), "P/bond4", 0.14800);
00224         bondAtom(UnivalentAtom("OP2", Element::Oxygen()), "P/bond3", 0.14800);
00225 
00226         nameBondCenter("bondPrevious", "P/bond1");
00227         nameBondCenter("bondNext", "P/bond2");
00228 
00229         setDefaultInboardBondLength(0.16100);
00230 
00231         addCompoundSynonym("Phosphodiester, RNA");
00232 
00233         setBiotypeIndex("P", Biotype::get("Phosphodiester, RNA", "P").getIndex() );
00234         setBiotypeIndex("OP1", Biotype::get("Phosphodiester, RNA", "OP").getIndex() );
00235         setBiotypeIndex("OP2", Biotype::get("Phosphodiester, RNA", "OP").getIndex() );
00236     }
00237     
00238     
00239     static void instantiateBiotypes() 
00240     {
00241         if ( ! Biotype::exists("Phosphodiester, RNA", "P") )
00242             Biotype::defineBiotype(Element::Phosphorus(), 4, "Phosphodiester, RNA", "P");
00243         if ( ! Biotype::exists("Phosphodiester, RNA", "OP") )
00244             Biotype::defineBiotype(Element::Oxygen(), 1, "Phosphodiester, RNA", "OP");
00245     }
00246 };
00247 
00248 
00250 class SimTK_MOLMODEL_EXPORT ThreePrimeRnaHydroxylGroup : public BiopolymerResidue
00251 {
00252 public:
00253     ThreePrimeRnaHydroxylGroup(String name, String threeLetterCode = "Unk", char oneLetterCode = '?') 
00254     : BiopolymerResidue(name, threeLetterCode, oneLetterCode)
00255     {
00256         instantiateBiotypes();
00257         
00258         setBaseAtom( UnivalentAtom("H3T", Element::Hydrogen()) );
00259         
00260         nameBondCenter("bondNext", "H3T/bond");
00261 
00262         setBiotypeIndex( "H3T", Biotype::get("Hydroxyl, RNA", "H3T", SimTK::Ordinality::Final).getIndex() );
00263     }
00264     
00265     static void instantiateBiotypes() 
00266     {
00267         if ( ! Biotype::exists("Hydroxyl, RNA", "H3T", SimTK::Ordinality::Final) )
00268             Biotype::defineBiotype(Element::Hydrogen(), 1, "Hydroxyl, RNA", "H3T", SimTK::Ordinality::Final);
00269         
00270         // This oxygen biotype should get applied to the 3' oxygen of the nucleotide this hydroxyl attaches to
00271         if ( ! Biotype::exists("Hydroxyl, RNA", "O3*", SimTK::Ordinality::Final) )
00272             Biotype::defineBiotype(Element::Oxygen(), 2, "Hydroxyl, RNA", "O3*", SimTK::Ordinality::Final);
00273     }
00274     
00275 };
00276 
00278 class SimTK_MOLMODEL_EXPORT ThreePrimeRnaPhosphateGroup : public BiopolymerResidue
00279 {
00280 public:
00281     ThreePrimeRnaPhosphateGroup(String name, String threeLetterCode = "Unk", char oneLetterCode = '?') 
00282     : BiopolymerResidue(name, threeLetterCode, oneLetterCode)
00283     {
00284         instantiateBiotypes();
00285         
00286         setBaseAtom( QuadrivalentAtom("P", Element::Phosphorus()) );
00287         
00288         bondAtom(UnivalentAtom("OP1", Element::Oxygen()), "P/bond4", 0.14800);
00289         bondAtom(UnivalentAtom("OP2", Element::Oxygen()), "P/bond3", 0.14800);
00290         bondAtom(UnivalentAtom("OP3", Element::Oxygen()), "P/bond2", 0.14800);
00291         
00292         nameBondCenter("bondNext", "P/bond1");
00293 
00294         setBiotypeIndex( "P", Biotype::get("Phosphate, RNA", "P", SimTK::Ordinality::Final).getIndex() );
00295         setBiotypeIndex( "OP1", Biotype::get("Phosphate, RNA", "OP", SimTK::Ordinality::Final).getIndex() );
00296         setBiotypeIndex( "OP2", Biotype::get("Phosphate, RNA", "OP", SimTK::Ordinality::Final).getIndex() );
00297         setBiotypeIndex( "OP3", Biotype::get("Phosphate, RNA", "OP", SimTK::Ordinality::Final).getIndex() );
00298     }
00299     
00300     static void instantiateBiotypes() 
00301     {
00302         if ( ! Biotype::exists("Phosphate, RNA", "P", SimTK::Ordinality::Final) )
00303             Biotype::defineBiotype(Element::Phosphorus(), 4, "Phosphate, RNA", "P", SimTK::Ordinality::Final);
00304         if ( ! Biotype::exists("Phosphate, RNA", "OP", SimTK::Ordinality::Final) )
00305             Biotype::defineBiotype(Element::Oxygen(), 1, "Phosphate, RNA", "OP", SimTK::Ordinality::Final);
00306     }
00307     
00308 };
00309 
00310 
00311 // Nucleoside has sugar and base but not phosphate
00312 class SimTK_MOLMODEL_EXPORT RibonucleosideResidue : public RiboseCore {
00313 public:
00314     RibonucleosideResidue(String name, String threeLetterCode = "Unk", char oneLetterCode = '?')
00315         : RiboseCore(name, threeLetterCode, oneLetterCode)
00316     {
00317         // 2' hydroxyl group present in RNA but not in DNA
00318         bondAtom(BivalentAtom("O2*", Element::Oxygen(), 108.50*Deg2Rad), "C2*/bond4", 0.1413, -60*Deg2Rad);
00319         bondAtom(UnivalentAtom("2HO*", Element::Hydrogen()), "O2*/bond2", 0.0960);
00320 
00321         // alternate atom name
00322         nameAtom("O2'", "O2*");
00323         nameAtom("HO2'", "2HO*");
00324     }
00325 };
00326 
00327 // Nucleotide has sugar and base and phosphate
00328 class SimTK_MOLMODEL_EXPORT RibonucleotideResidue : public RibonucleosideResidue {
00329 public:
00330     // Factory method
00331     static RibonucleotideResidue create(char oneLetterCode);
00332     static RibonucleotideResidue create(const PdbResidue& pdbResidue);
00333 
00334     RibonucleotideResidue(String name, String threeLetterCode = "Unk", char oneLetterCode = '?')
00335         : RibonucleosideResidue(name, threeLetterCode, oneLetterCode)
00336     {
00337         defineDihedralAngle("beta", "O5*/bond1", "C5*/bond2");
00338         setDefaultDihedralAngle("beta", 173.0*Deg2Rad); //  A-RNA (Schneider et al 2004)
00339 
00340         defineDihedralAngle("gamma", "C5*/bond1", "C4*/bond3");
00341         setDefaultDihedralAngle("gamma", 54.0*Deg2Rad); //  A-RNA (Schneider et al 2004)
00342 
00343         defineDihedralAngle("delta", "C4*/bond1", "C3*/bond2");
00344         setDefaultDihedralAngle("delta", 80.0*Deg2Rad); //  A-RNA (Schneider et al 2004)
00345 
00346         defineDihedralAngle("epsilon", "C3*/bond1", "O3*/bond2");
00347         setDefaultDihedralAngle("epsilon", 210.0*Deg2Rad); //  A-RNA (Schneider et al 2004)
00348 
00349         nameBondCenter("bondBase", "C1*/bond3");
00350     }
00351 
00352 
00353     class Adenylate;
00354     class Cytidylate;
00355     class Guanylate;
00356     class Uridylate;
00357     
00358     // Modified residues from tRNA
00359     class TwoNMethylGuanylate;
00360 };
00361 
00362 
00363 // PurineBaseCore represents the atoms in common among purine bases such as Adenine and Guanine
00364 class PurineBaseCore : public Compound {
00365 public:
00366     PurineBaseCore()
00367     {
00368         setBaseAtom( TrivalentAtom("N9",  Element::Nitrogen(), 125.8*Deg2Rad, 128.8*Deg2Rad));
00369 
00370         bondAtom( TrivalentAtom("C8",  Element::Carbon(),   113.9*Deg2Rad, 123.05*Deg2Rad),  "N9/bond3", 0.13710, 180*Deg2Rad,   BondMobility::Rigid );
00371 
00372         bondAtom( UnivalentAtom("H8",  Element::Hydrogen()),                                 "C8/bond3",  0.10800 );
00373         bondAtom(  BivalentAtom("N7",  Element::Nitrogen(), 103.8*Deg2Rad),                  "C8/bond2",  0.13040, 0*Deg2Rad,    BondMobility::Rigid );
00374         bondAtom( TrivalentAtom("C5",  Element::Carbon(),   110.4*Deg2Rad, 132.40*Deg2Rad),  "N7/bond2",  0.13910, 0*Deg2Rad,    BondMobility::Rigid );
00375         
00376         bondAtom( TrivalentAtom("C4",  Element::Carbon(),   126.2*Deg2Rad, 106.2*Deg2Rad),   "N9/bond2",  0.13740, 0*Deg2Rad,    BondMobility::Rigid );
00377 
00378         addRingClosingBond("C5/bond2",                                                       "C4/bond3",  0.13700, 0*Deg2Rad,    BondMobility::Rigid );
00379 
00380         // 114.30 is average between amber angle for guanine(111.30) and adenine(117.30)
00381         bondAtom( TrivalentAtom("C6",  Element::Carbon(), 114.30*Deg2Rad, 122.85*Deg2Rad),   "C5/bond3",  0.14040, 180*Deg2Rad,  BondMobility::Rigid );
00382 
00383         bondAtom(  BivalentAtom("N3",  Element::Nitrogen(), 118.60*Deg2Rad),                 "C4/bond2",  0.13540, 180*Deg2Rad,  BondMobility::Rigid );
00384         bondAtom( TrivalentAtom("C2",  Element::Carbon()),                                   "N3/bond2",  0.13240, 0*Deg2Rad,    BondMobility::Rigid );
00385 
00386         // Two bond centers open, inboard (N9), and C6
00387         nameBondCenter("bondC6", "C6/bond3");
00388         nameBondCenter("bondC2", "C2/bond3");
00389     }
00390 };
00391 
00392 
00393 class AdenineBase : public PurineBaseCore
00394 {
00395 public:
00396     AdenineBase()
00397     {
00398         // Lone pair on N1
00399         bondAtom(  BivalentAtom("N1",  Element::Nitrogen(), 118.60*Deg2Rad), "C6/bond2",  0.13390, 0*Deg2Rad, BondMobility::Rigid );
00400         addRingClosingBond("N1/bond2",                                       "C2/bond2",  0.13240, 0*Deg2Rad, BondMobility::Rigid);
00401 
00402         // Hydrogen on C2
00403         bondAtom( UnivalentAtom("H2",  Element::Hydrogen()),                 "bondC2",    0.10800,            BondMobility::Rigid );
00404 
00405         // Amine on C6
00406         bondAtom( TrivalentAtom("N6",  Element::Nitrogen()),                 "bondC6",    0.13400, 0*Deg2Rad, BondMobility::Rigid );
00407         bondAtom( UnivalentAtom("H61", Element::Hydrogen()),                 "N6/bond2",  0.10100,            BondMobility::Rigid );
00408         bondAtom( UnivalentAtom("H62", Element::Hydrogen()),                 "N6/bond3",  0.10100,            BondMobility::Rigid );
00409     }
00410 };
00411 
00412 class GuanineBase : public PurineBaseCore
00413 {
00414 public:
00415     GuanineBase()
00416     {
00417         // Hydrogen on N1
00418         bondAtom( TrivalentAtom("N1",  Element::Nitrogen(), 125.20*Deg2Rad, 116.8*Deg2Rad), "C6/bond2",  0.13880, 0*Deg2Rad, BondMobility::Rigid );
00419         bondAtom(UnivalentAtom("H1", Element::Hydrogen()),   "N1/bond3", 0.10100, BondMobility::Rigid);
00420         addRingClosingBond("N1/bond2",                       "C2/bond2",  0.13240, 0*Deg2Rad, BondMobility::Rigid);
00421 
00422         // Amine on C2
00423         bondAtom( TrivalentAtom("N2",  Element::Nitrogen()), "bondC2",    0.13400, 0*Deg2Rad, BondMobility::Rigid );
00424         bondAtom( UnivalentAtom("H21", Element::Hydrogen()), "N2/bond2",  0.10100,            BondMobility::Rigid );
00425         bondAtom( UnivalentAtom("H22", Element::Hydrogen()), "N2/bond3",  0.10100,            BondMobility::Rigid );
00426 
00427         // Carbonyl on C6
00428         bondAtom( UnivalentAtom("O6",  Element::Oxygen()),   "bondC6",    0.12290,            BondMobility::Rigid );
00429 
00430     }
00431 };
00432 
00433 class TwoNMethylGuanineBaseGroup : public PurineBaseCore
00434 {
00435 public:
00436     TwoNMethylGuanineBaseGroup() {
00437         addCompoundSynonym("Guanosine"); // for resolving biotypes KLUDGE
00438         // TODO
00439     }
00440 };
00441 
00442 
00443 // PyrimidineBaseCore represents the atoms in common among pyrimidine bases such as Cytosine, Uracil, and Thymine
00444 class PyrimidineBaseCore : public Compound {
00445 public:
00446     PyrimidineBaseCore()
00447     {
00448     }
00449 };
00450 
00451 
00452 class CytosineBase : public PyrimidineBaseCore
00453 {
00454 public:
00455     CytosineBase()
00456     {
00457         setBaseAtom( TrivalentAtom("N1",  Element::Nitrogen(), 125.8*Deg2Rad, 128.8*Deg2Rad));
00458 
00459         bondAtom( TrivalentAtom("C2", Element::Carbon(), 118.6*Deg2Rad, 120.9*Deg2Rad),  "N1/bond2", 0.1383, 180*Deg2Rad,   BondMobility::Rigid );
00460         bondAtom( UnivalentAtom("O2", Element::Oxygen()), "C2/bond3", 0.1229, 0*Deg2Rad, BondMobility::Rigid);
00461 
00462         bondAtom( BivalentAtom("N3", Element::Nitrogen(), 120.5*Deg2Rad), "C2/bond2", 0.1358, 0*Deg2Rad, BondMobility::Rigid);
00463 
00464         bondAtom( TrivalentAtom("C4", Element::Carbon(), 121.5*Deg2Rad, 119.3*Deg2Rad), "N3/bond2", 0.1339, 0*Deg2Rad, BondMobility::Rigid);
00465         bondAtom( TrivalentAtom("N4", Element::Nitrogen(), 120.0*Deg2Rad, 120.0*Deg2Rad), "C4/bond3", 0.1340, 0*Deg2Rad, BondMobility::Rigid);
00466         bondAtom( UnivalentAtom("H41", Element::Hydrogen()), "N4/bond2", 0.1010, 0*Deg2Rad, BondMobility::Rigid);
00467         bondAtom( UnivalentAtom("H42", Element::Hydrogen()), "N4/bond3", 0.1010, 0*Deg2Rad, BondMobility::Rigid);
00468 
00469         bondAtom( TrivalentAtom("C5", Element::Carbon(), 117.0*Deg2Rad, 119.70*Deg2Rad), "C4/bond2", 0.1433, 0*Deg2Rad, BondMobility::Rigid);
00470         bondAtom( UnivalentAtom("H5", Element::Hydrogen()), "C5/bond3", 0.1080, 0*Deg2Rad, BondMobility::Rigid);
00471 
00472         bondAtom( TrivalentAtom("C6", Element::Carbon(), 121.20*Deg2Rad, 119.70*Deg2Rad), "C5/bond2", 0.1350, 0*Deg2Rad, BondMobility::Rigid);
00473         bondAtom( UnivalentAtom("H6", Element::Hydrogen()), "C6/bond3", 0.1080, 0*Deg2Rad, BondMobility::Rigid);
00474 
00475         addRingClosingBond("C6/bond2", "N1/bond3", 0.1365, 0*Deg2Rad, BondMobility::Rigid);
00476     }
00477 };
00478 
00479 class UracilBase : public PyrimidineBaseCore
00480 {
00481 public:
00482     UracilBase()
00483     {
00484         setBaseAtom( TrivalentAtom("N1",  Element::Nitrogen(), 125.8*Deg2Rad, 128.8*Deg2Rad));
00485 
00486         bondAtom( TrivalentAtom("C2", Element::Carbon(), 118.6*Deg2Rad, 120.9*Deg2Rad),  "N1/bond2", 0.1383, 180*Deg2Rad,   BondMobility::Rigid );
00487         bondAtom( UnivalentAtom("O2", Element::Oxygen()), "C2/bond3", 0.1229, 0*Deg2Rad, BondMobility::Rigid);
00488 
00489         bondAtom(TrivalentAtom("N3", Element::Nitrogen(), 126.4*Deg2Rad, 116.8*Deg2Rad), "C2/bond2", 0.1358, 0*Deg2Rad, BondMobility::Rigid);
00490         bondAtom(UnivalentAtom("H3", Element::Hydrogen()), "N3/bond3", 0.1010, 0*Deg2Rad, BondMobility::Rigid);
00491 
00492         bondAtom( TrivalentAtom("C4", Element::Carbon(), 114.0*Deg2Rad, 120.6*Deg2Rad),  "N3/bond2", 0.1388, 0*Deg2Rad,   BondMobility::Rigid );
00493         bondAtom( UnivalentAtom("O4", Element::Oxygen()), "C4/bond3", 0.1229, 0*Deg2Rad, BondMobility::Rigid);
00494 
00495         bondAtom( TrivalentAtom("C5", Element::Carbon(), 120.7*Deg2Rad, 119.70*Deg2Rad), "C4/bond2", 0.1444, 0*Deg2Rad, BondMobility::Rigid);
00496         bondAtom( UnivalentAtom("H5", Element::Hydrogen()), "C5/bond3", 0.1080, 0*Deg2Rad, BondMobility::Rigid);
00497 
00498         bondAtom( TrivalentAtom("C6", Element::Carbon(), 121.20*Deg2Rad, 119.70*Deg2Rad), "C5/bond2", 0.1350, 0*Deg2Rad, BondMobility::Rigid);
00499         bondAtom( UnivalentAtom("H6", Element::Hydrogen()), "C6/bond3", 0.1080, 0*Deg2Rad, BondMobility::Rigid);
00500 
00501         addRingClosingBond("C6/bond2", "N1/bond3", 0.1365, 0*Deg2Rad, BondMobility::Rigid);
00502     }
00503 };
00504 
00505 // TODO - these should not be classes, e.g. Adenylate should be an instance of RibonucleotideResidue
00506 class  RibonucleotideResidue::Adenylate : public RibonucleotideResidue {
00507 public:
00508     Adenylate() : RibonucleotideResidue("adenylate", "A  ", 'A') 
00509     {
00510         bondCompound("base", AdenineBase(), "bondBase", 0.14750, 200*Deg2Rad, BondMobility::Torsion);
00511         inheritAtomNames("base");
00512 
00513         defineDihedralAngle("chi", "O4*", "C1*", "N9", "C4");
00514         setDefaultDihedralAngle("chi", 199.0*Deg2Rad);
00515 
00516         addCompoundSynonym("Adenosine"); // for resolving biotypes
00517     }
00518 };
00519 
00520 class  RibonucleotideResidue::Guanylate : public RibonucleotideResidue {
00521 public:
00522     Guanylate() : RibonucleotideResidue("guanylate", "G  ", 'G') 
00523     {
00524         bondCompound("base", GuanineBase(), "bondBase", 0.14710, 200*Deg2Rad, BondMobility::Torsion);
00525         inheritAtomNames("base");
00526 
00527         defineDihedralAngle("chi", "O4*", "C1*", "N9", "C4");
00528         setDefaultDihedralAngle("chi", 199.0*Deg2Rad);
00529 
00530         addCompoundSynonym("Guanosine"); // for resolving biotypes
00531     }
00532 };
00533 
00534 class  RibonucleotideResidue::Cytidylate : public RibonucleotideResidue {
00535 public:
00536     Cytidylate() : RibonucleotideResidue("cytidylate", "C  ", 'C') 
00537     {
00538         bondCompound("base", CytosineBase(), "bondBase", 0.14710, 200*Deg2Rad, BondMobility::Torsion);
00539         inheritAtomNames("base");
00540 
00541         defineDihedralAngle("chi", "O4*", "C1*", "N1", "C2");
00542         setDefaultDihedralAngle("chi", 199.0*Deg2Rad);
00543 
00544         addCompoundSynonym("Cytidine"); // for resolving biotypes
00545     }
00546 };
00547 
00548 class  RibonucleotideResidue::Uridylate : public RibonucleotideResidue {
00549 public:
00550     Uridylate() : RibonucleotideResidue("uridylate", "U  ", 'U') 
00551     {
00552         bondCompound("base", UracilBase(), "bondBase", 0.14710, 200*Deg2Rad, BondMobility::Torsion);
00553         inheritAtomNames("base");
00554 
00555         defineDihedralAngle("chi", "O4*", "C1*", "N1", "C2");
00556         setDefaultDihedralAngle("chi", 199.0*Deg2Rad);
00557 
00558         addCompoundSynonym("Uridine"); // for resolving biotypes
00559     }
00560 };
00561 
00562 
00563 class TwoNMethylGuanidineGroup : public Compound {
00564 public:
00565     TwoNMethylGuanidineGroup()
00566     {
00567         instantiateBiotypes();
00568 
00569         setPdbResidueName("2MG");
00570 
00571         setCompoundName("TwoNMethylGuanidineGroup");
00572 
00573         setBaseAtom( TrivalentAtom("N9", Element::Nitrogen(), 127.767*Deg2Rad, 112.885*Deg2Rad) );
00574 
00575         bondAtom( TrivalentAtom("C8", Element::Carbon(), 113.564*Deg2Rad, 120.934*Deg2Rad), "N9/bond2", 0.13740, 180.00*Deg2Rad, BondMobility::Rigid );
00576         bondAtom( BivalentAtom("N7", Element::Nitrogen(), 104.422*Deg2Rad), "C8/bond2", 0.12800, 0.02*Deg2Rad, BondMobility::Rigid );
00577         bondAtom( TrivalentAtom("C5", Element::Carbon(), 130.918*Deg2Rad, 112.885*Deg2Rad), "N7/bond2", 0.13760, 179.54*Deg2Rad, BondMobility::Rigid );
00578         bondAtom( TrivalentAtom("C6", Element::Carbon(), 131.213*Deg2Rad, 109.672*Deg2Rad), "C5/bond2", 0.14350, -0.17*Deg2Rad, BondMobility::Rigid );
00579         bondAtom( UnivalentAtom("O6", Element::Oxygen()), "C6/bond2", 0.11940 );
00580         bondAtom( TrivalentAtom("N1", Element::Nitrogen(), 126.495*Deg2Rad, 113.649*Deg2Rad), "C6/bond3", 0.14150, 0.32*Deg2Rad, BondMobility::Rigid );
00581         bondAtom( TrivalentAtom("C2", Element::Carbon(), 116.091*Deg2Rad, 123.417*Deg2Rad), "N1/bond2", 0.13620, 178.30*Deg2Rad, BondMobility::Rigid );
00582         bondAtom( TrivalentAtom("N2", Element::Nitrogen(), 116.703*Deg2Rad, 120.926*Deg2Rad), "C2/bond2", 0.13550, 20.71*Deg2Rad, BondMobility::Rigid );
00583         bondAtom( UnivalentAtom("1H2", Element::Hydrogen()), "N2/bond2", 0.09940 );
00584         bondAtom( QuadrivalentAtom("C10", Element::Carbon()), "N2/bond3", 0.14490, 176.13*Deg2Rad, BondMobility::Torsion );
00585         bondAtom( UnivalentAtom("H20", Element::Hydrogen()), "C10/bond2", 0.10810 );
00586         bondAtom( UnivalentAtom("H21", Element::Hydrogen()), "C10/bond3", 0.10850 );
00587         bondAtom( UnivalentAtom("H22", Element::Hydrogen()), "C10/bond4", 0.10790 );
00588         bondAtom( BivalentAtom("N3", Element::Nitrogen(), 112.885*Deg2Rad), "C2/bond3", 0.12910, 0.73*Deg2Rad, BondMobility::Rigid );
00589         bondAtom( TrivalentAtom("C4", Element::Carbon(), 109.368*Deg2Rad, 104.422*Deg2Rad), "N3/bond2", 0.13560, -119.37*Deg2Rad, BondMobility::Rigid );
00590         bondAtom( UnivalentAtom("H1", Element::Hydrogen()), "N1/bond3", 0.09980 );
00591         bondAtom( UnivalentAtom("H8", Element::Hydrogen()), "C8/bond3", 0.10710 );
00592 
00593         addRingClosingBond( "C4/bond2", "N9/bond3", 0.15);
00594         addRingClosingBond( "C4/bond3", "C5/bond3", 0.15);
00595 
00596         setBiotypeIndex( "N9", Biotype::get("TwoNMethylGuanidineGroup", "N9").getIndex());
00597         setBiotypeIndex( "C8", Biotype::get("TwoNMethylGuanidineGroup", "C8").getIndex());
00598         setBiotypeIndex( "N7", Biotype::get("TwoNMethylGuanidineGroup", "N7").getIndex());
00599         setBiotypeIndex( "C5", Biotype::get("TwoNMethylGuanidineGroup", "C5").getIndex());
00600         setBiotypeIndex( "C6", Biotype::get("TwoNMethylGuanidineGroup", "C6").getIndex());
00601         setBiotypeIndex( "O6", Biotype::get("TwoNMethylGuanidineGroup", "O6").getIndex());
00602         setBiotypeIndex( "N1", Biotype::get("TwoNMethylGuanidineGroup", "N1").getIndex());
00603         setBiotypeIndex( "C2", Biotype::get("TwoNMethylGuanidineGroup", "C2").getIndex());
00604         setBiotypeIndex( "N2", Biotype::get("TwoNMethylGuanidineGroup", "N2").getIndex());
00605         setBiotypeIndex( "1H2", Biotype::get("TwoNMethylGuanidineGroup", "1H2").getIndex());
00606         setBiotypeIndex( "C10", Biotype::get("TwoNMethylGuanidineGroup", "C10").getIndex());
00607         setBiotypeIndex( "H20", Biotype::get("TwoNMethylGuanidineGroup", "H20").getIndex());
00608         setBiotypeIndex( "H21", Biotype::get("TwoNMethylGuanidineGroup", "H21").getIndex());
00609         setBiotypeIndex( "H22", Biotype::get("TwoNMethylGuanidineGroup", "H22").getIndex());
00610         setBiotypeIndex( "N3", Biotype::get("TwoNMethylGuanidineGroup", "N3").getIndex());
00611         setBiotypeIndex( "C4", Biotype::get("TwoNMethylGuanidineGroup", "C4").getIndex());
00612         setBiotypeIndex( "H1", Biotype::get("TwoNMethylGuanidineGroup", "H1").getIndex());
00613         setBiotypeIndex( "H8", Biotype::get("TwoNMethylGuanidineGroup", "H8").getIndex());
00614 
00615         setDefaultDihedralAngle(0.020*Deg2Rad, "C5", "N7", "C8", "N9");
00616         setDefaultDihedralAngle(179.544*Deg2Rad, "C6", "C5", "N7", "C8");
00617         setDefaultDihedralAngle(-0.165*Deg2Rad, "O6", "C6", "C5", "N7");
00618         setDefaultDihedralAngle(-179.886*Deg2Rad, "N1", "C6", "C5", "N7");
00619         setDefaultDihedralAngle(0.318*Deg2Rad, "C2", "N1", "C6", "C5");
00620         setDefaultDihedralAngle(178.303*Deg2Rad, "N2", "C2", "N1", "C6");
00621         setDefaultDihedralAngle(20.715*Deg2Rad, "1H2", "N2", "C2", "N1");
00622         setDefaultDihedralAngle(173.145*Deg2Rad, "C10", "N2", "C2", "N1");
00623         setDefaultDihedralAngle(176.133*Deg2Rad, "H20", "C10", "N2", "C2");
00624         setDefaultDihedralAngle(-63.298*Deg2Rad, "H21", "C10", "N2", "C2");
00625         setDefaultDihedralAngle(57.486*Deg2Rad, "H22", "C10", "N2", "C2");
00626         setDefaultDihedralAngle(-0.550*Deg2Rad, "N3", "C2", "N1", "C6");
00627         setDefaultDihedralAngle(0.727*Deg2Rad, "C4", "N3", "C2", "N1");
00628         setDefaultDihedralAngle(176.522*Deg2Rad, "H1", "N1", "C6", "C5");
00629     } // end constructor TwoNMethylGuanidineGroup 
00630 
00631     static void instantiateBiotypes() {
00632         if (! Biotype::exists("TwoNMethylGuanidineGroup", "N9") )
00633             Biotype::defineBiotype(Element::Nitrogen(), 3, "TwoNMethylGuanidineGroup", "N9"); 
00634         if (! Biotype::exists("TwoNMethylGuanidineGroup", "C8") )
00635             Biotype::defineBiotype(Element::Carbon(), 3, "TwoNMethylGuanidineGroup", "C8"); 
00636         if (! Biotype::exists("TwoNMethylGuanidineGroup", "N7") )
00637             Biotype::defineBiotype(Element::Nitrogen(), 2, "TwoNMethylGuanidineGroup", "N7"); 
00638         if (! Biotype::exists("TwoNMethylGuanidineGroup", "C5") )
00639             Biotype::defineBiotype(Element::Carbon(), 3, "TwoNMethylGuanidineGroup", "C5"); 
00640         if (! Biotype::exists("TwoNMethylGuanidineGroup", "C6") )
00641             Biotype::defineBiotype(Element::Carbon(), 3, "TwoNMethylGuanidineGroup", "C6"); 
00642         if (! Biotype::exists("TwoNMethylGuanidineGroup", "O6") )
00643             Biotype::defineBiotype(Element::Oxygen(), 1, "TwoNMethylGuanidineGroup", "O6"); 
00644         if (! Biotype::exists("TwoNMethylGuanidineGroup", "N1") )
00645             Biotype::defineBiotype(Element::Nitrogen(), 3, "TwoNMethylGuanidineGroup", "N1"); 
00646         if (! Biotype::exists("TwoNMethylGuanidineGroup", "C2") )
00647             Biotype::defineBiotype(Element::Carbon(), 3, "TwoNMethylGuanidineGroup", "C2"); 
00648         if (! Biotype::exists("TwoNMethylGuanidineGroup", "N2") )
00649             Biotype::defineBiotype(Element::Nitrogen(), 3, "TwoNMethylGuanidineGroup", "N2"); 
00650         if (! Biotype::exists("TwoNMethylGuanidineGroup", "1H2") )
00651             Biotype::defineBiotype(Element::Hydrogen(), 1, "TwoNMethylGuanidineGroup", "1H2"); 
00652         if (! Biotype::exists("TwoNMethylGuanidineGroup", "C10") )
00653             Biotype::defineBiotype(Element::Carbon(), 4, "TwoNMethylGuanidineGroup", "C10"); 
00654         if (! Biotype::exists("TwoNMethylGuanidineGroup", "H20") )
00655             Biotype::defineBiotype(Element::Hydrogen(), 1, "TwoNMethylGuanidineGroup", "H20"); 
00656         if (! Biotype::exists("TwoNMethylGuanidineGroup", "H21") )
00657             Biotype::defineBiotype(Element::Hydrogen(), 1, "TwoNMethylGuanidineGroup", "H21"); 
00658         if (! Biotype::exists("TwoNMethylGuanidineGroup", "H22") )
00659             Biotype::defineBiotype(Element::Hydrogen(), 1, "TwoNMethylGuanidineGroup", "H22"); 
00660         if (! Biotype::exists("TwoNMethylGuanidineGroup", "N3") )
00661             Biotype::defineBiotype(Element::Nitrogen(), 2, "TwoNMethylGuanidineGroup", "N3"); 
00662         if (! Biotype::exists("TwoNMethylGuanidineGroup", "C4") )
00663             Biotype::defineBiotype(Element::Carbon(), 3, "TwoNMethylGuanidineGroup", "C4"); 
00664         if (! Biotype::exists("TwoNMethylGuanidineGroup", "H1") )
00665             Biotype::defineBiotype(Element::Hydrogen(), 1, "TwoNMethylGuanidineGroup", "H1"); 
00666         if (! Biotype::exists("TwoNMethylGuanidineGroup", "H8") )
00667             Biotype::defineBiotype(Element::Hydrogen(), 1, "TwoNMethylGuanidineGroup", "H8"); 
00668     } // end instantiateBiotypes
00669 
00670 }; // end class TwoNMethylGuanidineGroup 
00671 
00672 
00673 class  RibonucleotideResidue::TwoNMethylGuanylate : public RibonucleotideResidue {
00674 public:
00675     TwoNMethylGuanylate() : RibonucleotideResidue("2-N-methyl-guanylate", "2MG", 'X') 
00676     {
00677         bondCompound("base", TwoNMethylGuanidineGroup(), "bondBase", 0.14750, 200*Deg2Rad, BondMobility::Torsion);
00678         inheritAtomNames("base");
00679 
00680         defineDihedralAngle("chi", "O4*", "C1*", "N9", "C4");
00681         setDefaultDihedralAngle("chi", 210*Deg2Rad);
00682 
00683         addCompoundSynonym("TwoNMethylGuanidineGroup"); // for resolving biotypes
00684         
00685         setBiotypeIndex( "N9", Biotype::get("TwoNMethylGuanidineGroup", "N9").getIndex());
00686         setBiotypeIndex( "C8", Biotype::get("TwoNMethylGuanidineGroup", "C8").getIndex());
00687         setBiotypeIndex( "N7", Biotype::get("TwoNMethylGuanidineGroup", "N7").getIndex());
00688         setBiotypeIndex( "C5", Biotype::get("TwoNMethylGuanidineGroup", "C5").getIndex());
00689         setBiotypeIndex( "C6", Biotype::get("TwoNMethylGuanidineGroup", "C6").getIndex());
00690         setBiotypeIndex( "O6", Biotype::get("TwoNMethylGuanidineGroup", "O6").getIndex());
00691         setBiotypeIndex( "N1", Biotype::get("TwoNMethylGuanidineGroup", "N1").getIndex());
00692         setBiotypeIndex( "C2", Biotype::get("TwoNMethylGuanidineGroup", "C2").getIndex());
00693         setBiotypeIndex( "N2", Biotype::get("TwoNMethylGuanidineGroup", "N2").getIndex());
00694         setBiotypeIndex( "1H2", Biotype::get("TwoNMethylGuanidineGroup", "1H2").getIndex());
00695         setBiotypeIndex( "C10", Biotype::get("TwoNMethylGuanidineGroup", "C10").getIndex());
00696         setBiotypeIndex( "H20", Biotype::get("TwoNMethylGuanidineGroup", "H20").getIndex());
00697         setBiotypeIndex( "H21", Biotype::get("TwoNMethylGuanidineGroup", "H21").getIndex());
00698         setBiotypeIndex( "H22", Biotype::get("TwoNMethylGuanidineGroup", "H22").getIndex());
00699         setBiotypeIndex( "N3", Biotype::get("TwoNMethylGuanidineGroup", "N3").getIndex());
00700         setBiotypeIndex( "C4", Biotype::get("TwoNMethylGuanidineGroup", "C4").getIndex());
00701         setBiotypeIndex( "H1", Biotype::get("TwoNMethylGuanidineGroup", "H1").getIndex());
00702         setBiotypeIndex( "H8", Biotype::get("TwoNMethylGuanidineGroup", "H8").getIndex());
00703         
00704     }
00705 };
00706 
00707 
00708 
00709 
00710 
00711 
00712 class  RNA : public Biopolymer {
00713 public:
00714 
00715     RNA(const PdbStructure& pdbStructure) 
00716     {
00717         // Assume first chain of first model is wanted
00718         const PdbChain& pdbChain = pdbStructure.getModel(Pdb::ModelIndex(0)).getChain(Pdb::ChainIndex(0));
00719         initializeFromPdbChain(pdbChain);
00720     }
00721 
00722     RNA(const PdbChain& pdbChain)
00723     {
00724         initializeFromPdbChain(pdbChain);
00725     }
00730     RNA(const Sequence& seq, int useCappingHydroxyls= 1) 
00731     {
00732         String previousResidueName;
00733         Biotype::initializePopularBiotypes();
00734 
00735         // TODO - create 5' end cap
00736         for (int resi = 0; resi < (int)seq.size(); ++resi)
00737         {
00738             
00739             RibonucleotideResidue residue = RibonucleotideResidue::create(seq[resi]);
00740             residue.assignBiotypes();
00741 
00742             residue.setPdbResidueNumber(resi + 1);
00743 
00744             // Name residue subcompound after its number in the sequence
00745             // name must be unique within the protein
00746             String residueName(resi);
00747 
00748             // Cap the 3' end with a hydroxyl group
00749             if ((resi == seq.size() - 1) && (useCappingHydroxyls)) {
00750                 residue.bondCompound(
00751                         "3PrimeHydroxyl", 
00752                         ThreePrimeRnaHydroxylGroup(residueName, residue.getPdbResidueName(), 'X'), 
00753                         "bondNext", 
00754                         0.0960);
00755                 residue.inheritAtomNames("3PrimeHydroxyl");
00756                 // Oxygen biotype must be changed for the amber atom types to come out correctly
00757                 if ( (residue.hasAtom("O3*")) && ( Biotype::exists("Hydroxyl, RNA", "O3*", SimTK::Ordinality::Final)) )
00758                     residue.setBiotypeIndex( "O3*", Biotype::get("Hydroxyl, RNA", "O3*", SimTK::Ordinality::Final).getIndex() );
00759             }
00760 
00761             if (resi == 0) {
00762                 // first residue needs end cap
00763                 residue.convertInboardBondCenterToOutboard();
00764 
00765                 if (useCappingHydroxyls) { // 5' hydroxyl
00766                     residue.bondCompound(
00767                             "5PrimeHydroxyl", 
00768                             FivePrimeRnaHydroxylGroup(residueName, residue.getPdbResidueName(), 'X'), 
00769                             "bondPrevious", 
00770                             0.0960);
00771                     residue.inheritAtomNames("5PrimeHydroxyl");
00772                     if ( (residue.hasAtom("O5*")) && ( Biotype::exists("Hydroxyl, RNA", "O5*", SimTK::Ordinality::Initial)) )
00773                         residue.setBiotypeIndex( "O5*", Biotype::get("Hydroxyl, RNA", "O5*", SimTK::Ordinality::Initial).getIndex() );
00774                 }
00775 
00776                 else { // 5' phosphate
00777                     residue.bondCompound(
00778                             "5PrimePhosphate", 
00779                             FivePrimeRnaPhosphateGroup(residueName, residue.getPdbResidueName(), 'X'), 
00780                             "bondPrevious");
00781                     residue.inheritAtomNames("5PrimePhosphate");
00782                 }
00783                 
00784                 appendResidue( residueName, residue );
00785             }
00786             else {
00787                 // non-first residue needs phosphodiester linkage
00788                 RnaPhosphodiesterLinkage po2(residueName, residue.getPdbResidueName(), 'X');
00789                 po2.bondCompound("nucleoside", residue, "bondNext");
00790                 po2.inheritAtomNames("nucleoside");
00791                 po2.nameBondCenter("bondNext", "nucleoside/bondNext");
00792                 
00793                 po2.setPdbResidueNumber(resi + 1);
00794                 
00795                 po2.defineDihedralAngle("alpha", "bondPrevious", "O5*/bond2");
00796                 po2.setDefaultDihedralAngle("alpha", 295.0*Deg2Rad); // A-RNA (Schneider et al 2004)
00797 
00798                 appendResidue( residueName, po2 );
00799 
00800                 // Define zeta angle
00801                 String zetaName = String("zeta") + String(resi - 1);
00802                 defineDihedralAngle(zetaName, previousResidueName + "/O3*/bond1", residueName + "/P/bond2");
00803                 setDefaultDihedralAngle(zetaName, 287.0*Deg2Rad); // (Schneider et al 2004)
00804             }
00805 
00806             previousResidueName = residueName;
00807         }
00808     }
00821     RNA setRNABondMobility (BondMobility::Mobility  mobility, int startResidue, int  endResidue){
00822         for (int q =startResidue; q<=endResidue; q++) {
00823             (updResidue(Compound::Index(q))).setCompoundBondMobility(mobility);
00824             if (q>startResidue) {
00825                 std::stringstream ss1;
00826                 ss1<<q-1<<"/O3*";
00827                 std::stringstream ss2;
00828                 ss2<<q<<"/P";
00829                 setBondMobility(mobility ,ss1.str() ,ss2.str()  ); 
00830             } 
00831         }
00832     return *this;
00833 
00834     }
00835 
00836 private:
00837     void initializeFromPdbChain(const PdbChain& pdbChain) 
00838     {
00839         // TODO end caps
00840         for (Pdb::ResidueIndex r(0); r < (Pdb::ResidueIndex)pdbChain.getNResidues(); ++r) 
00841         {
00842             const PdbResidue& pdbResidue = pdbChain.getResidue(r);
00843             String residueName = pdbResidue.getName() + String(pdbResidue.getPdbResidueNumber());
00844             if (pdbResidue.getInsertionCode() != ' ') // include unusual insertion codes in residue name
00845                 residueName += pdbResidue.getInsertionCode();
00846             appendResidue(residueName, RibonucleotideResidue::create(pdbResidue));
00847         }
00848     }
00849 };
00850 
00851 
00852 } // namespace SimTK
00853 
00854 #endif // SimTK_MOLMODEL_RNA_H_

Generated on Fri Sep 26 07:44:15 2008 for SimTKcore by  doxygen 1.5.6