// // Validate a single molecule. // bool Validator::Validate(OpenBabel::OBMol& validationMol) { std::vector<unsigned int> validationFP; bool returnval = false; if (g_debug_output) { std::cerr << "Atoms: " << validationMol.NumAtoms() << std::endl; std::cerr << "Bonds: " << validationMol.NumBonds() << std::endl; } // Create the fingerprint for the validation molecule OpenBabel::OBFingerprint* fpType = OpenBabel::OBFingerprint::FindFingerprint(""); // Acquire the fingerprint of the validation molecule so we can use it for // Tanimoto comparison. fpType->GetFingerprint(&validationMol, validationFP); if (g_debug_output) { std::cerr << "Validation: " << std::endl; foreach_uints(u_it, validationFP) { std::cerr << *u_it << "|"; } std::cerr << std::endl; }
int main(int argc,char **argv) { // Create a test molecule OpenBabel::OBMol mol; OpenBabel::OBAtom* a[5]; a[0] = mol.NewAtom(); a[0]->SetAtomicNum(6); a[0]->SetVector(-0.013, 1.086, 0.008); a[1] = mol.NewAtom(); a[1]->SetAtomicNum(1); a[1]->SetVector( 0.002, -0.004, 0.002); a[2] = mol.NewAtom(); a[2]->SetAtomicNum(9); a[2]->SetVector( 1.300, 1.570, -0.002); a[3] = mol.NewAtom(); a[3]->SetAtomicNum(35); a[3]->SetVector(-0.964, 1.737, -1.585); a[4] = mol.NewAtom(); a[4]->SetAtomicNum(17); a[4]->SetVector(-0.857, 1.667, 1.491); OpenBabel::OBBond* b; for (int i(1); i < 5; ++i) { b = mol.NewBond(); b->SetBegin(a[0]); b->SetEnd(a[i]); b->SetBondOrder(1); } // Run the tests test01(&mol); test02(&mol); test03(&mol); test04(&mol); test05(&mol); test06(&mol); test07(&mol); test08(&mol); test09(&mol); // End return 0; }
extern "C" int write_output_(char *out_filename, double *A, int *n) { std::ofstream ofs(out_filename); OpenBabel::OBConversion ob(NULL, &ofs); OpenBabel::OBAtom atom; OpenBabel::OBMol mol; int i; ob.SetOutFormat("CML"); /* Atom is Iridium */ atom.SetAtomicNum(77); for (i = 0; i < *n; i++) { atom.SetVector(A[i*3], A[i*3+1], A[i*3+2]); mol.AddAtom(atom); } //for (i=0; i < *n; i++) //{ //for (int j=i; j < *n; j++) //{ //mol.AddBond(i+1, j+1, 0); //} //} ob.Write(&mol); ob.CloseOutFile(); }
// Helper function -- handle SMARTS selections // Called by performAction() void SelectExtension::selectSMARTS(GLWidget *widget) { bool ok; QString pattern = QInputDialog::getText(qobject_cast<QWidget*>(parent()), tr("SMARTS Selection"), tr("SMARTS pattern to select"), QLineEdit::Normal, "", &ok); if (ok && !pattern.isEmpty()) { OBSmartsPattern smarts; smarts.Init(pattern.toStdString()); OpenBabel::OBMol obmol = m_molecule->OBMol(); smarts.Match(obmol); // if we have matches, select them if(smarts.NumMatches() != 0) { QList<Primitive *> matchedAtoms; vector< vector <int> > mapList = smarts.GetUMapList(); vector< vector <int> >::iterator i; // a set of matching atoms vector<int>::iterator j; // atom ids in each match for (i = mapList.begin(); i != mapList.end(); ++i) { for (j = i->begin(); j != i->end(); ++j) { matchedAtoms.append(m_molecule->atom(obmol.GetAtom(*j)->GetIdx()-1)); } } widget->clearSelected(); widget->setSelected(matchedAtoms, true); widget->update(); } // end matches } return; }
int spectrophoretest(int argc, char* argv[]) { int defaultchoice = 1; int choice = defaultchoice; if (argc > 1) { if(sscanf(argv[1], "%d", &choice) != 1) { printf("Couldn't parse that input as a number\n"); return -1; } } // Create a test molecule OpenBabel::OBMol mol; OpenBabel::OBAtom* a[5]; a[0] = mol.NewAtom(); a[0]->SetAtomicNum(6); a[0]->SetVector(-0.013, 1.086, 0.008); a[1] = mol.NewAtom(); a[1]->SetAtomicNum(1); a[1]->SetVector( 0.002, -0.004, 0.002); a[2] = mol.NewAtom(); a[2]->SetAtomicNum(9); a[2]->SetVector( 1.300, 1.570, -0.002); a[3] = mol.NewAtom(); a[3]->SetAtomicNum(35); a[3]->SetVector(-0.964, 1.737, -1.585); a[4] = mol.NewAtom(); a[4]->SetAtomicNum(17); a[4]->SetVector(-0.857, 1.667, 1.491); OpenBabel::OBBond* b; for (int i(1); i < 5; ++i) { b = mol.NewBond(); b->SetBegin(a[0]); b->SetEnd(a[i]); b->SetBondOrder(1); } switch(choice) { case 1: test01(&mol); test02(&mol); break; case 2: test03(&mol); test04(&mol); break; case 3: test05(&mol); test06(&mol); break; case 4: test07(&mol); test08(&mol); break; case 5: test09(&mol); break; default: std::cout << "Test number " << choice << " does not exist!\n"; return -1; } return 0; }
int main(int argc, char *argv[]) { if (argc != 2) { // Exit - we expect the name of an input file and output to the standard out std::cerr << "Error: expect one argument - path of input file." << std::endl; return 1; } OpenBabel::OBFormat *inFormat = NULL; OpenBabel::OBConversion conv(&std::cin, &std::cout); OpenBabel::OBMol mol; inFormat = conv.FormatFromExt(argv[1]); conv.SetInFormat(inFormat); std::ifstream in; in.open(argv[1]); conv.Read(&mol, &in); in.close(); // Write out a few parameters. std::cout << "[Formula]\n" << mol.GetSpacedFormula() << std::endl; std::cout << "[Molecular weight]\n" << mol.GetMolWt() << std::endl; // Write out our file formats. std::cout << "[smiles]\n"; conv.SetOutFormat("smi"); conv.Write(&mol); std::cout << "[canonical smiles]\n"; conv.SetOutFormat("can"); conv.Write(&mol); std::cout << "[inchi]\n"; conv.SetOutFormat("inchi"); conv.Write(&mol); std::cout << "[inchikey]\n"; conv.SetOptions("K", conv.OUTOPTIONS); conv.Write(&mol); std::cout << "[XYZ]\n"; conv.SetOutFormat("xyz"); conv.Write(&mol); std::cout << "[end]\n"; std::cout << "[CML]\n"; conv.SetOutFormat("cml"); conv.Write(&mol); std::cout << "[end]\n"; //std::cout << "[SVG]\n"; //conv.SetOutFormat("svg"); //conv.Write(&mol); //std::cout << "[end]\n"; // Let them know we are finished, should be done after all output is complete. std::cout << "[complete]" << std::endl; return 0; }
void ReadFileThread::detectConformers(unsigned int c, const OpenBabel::OBMol &first, const OpenBabel::OBMol ¤t) { if (!c) { // this is the first molecule read m_moleculeFile->setConformerFile(true); addConformer(current); return; } if (!m_moleculeFile->isConformerFile()) return; // as long as we are not sure if this really is a // conformer/trajectory file, add the conformers addConformer(current); // performance: check only certain molecule 1-10,20,50 switch (c) { case 1: case 2: case 3: case 4: case 5: case 6: case 7: case 8: case 9: case 10: case 20: case 50: break; default: return; } if (first.NumAtoms() != current.NumAtoms()) { m_moleculeFile->setConformerFile(false); m_moleculeFile->m_conformers.clear(); return; } for (unsigned int i = 0; i < first.NumAtoms(); ++i) { OpenBabel::OBAtom *firstAtom = first.GetAtom(i+1); OpenBabel::OBAtom *currentAtom = current.GetAtom(i+1); if (firstAtom->GetAtomicNum() != currentAtom->GetAtomicNum()) { m_moleculeFile->setConformerFile(false); m_moleculeFile->m_conformers.clear(); return; } } }
void StereoCenterItem::paint(QPainter *painter, const QStyleOptionGraphicsItem *option, QWidget *widget) { Molecule *mol = molecule(); painter->save(); painter->setPen(Qt::green); if (!mol) { // not connected: default behaviour (draw connectable box) MolInputItem::paint(painter, option, widget); painter->restore(); return; } const QList<Atom*> &atoms = mol->atoms(); OpenBabel::OBMol *obmol = mol->OBMol(); QPointF offset(-5.0, 5.0); #ifdef OPENBABEL2_TRUNK // need to calculate symmetry first std::vector<unsigned int> symmetry_classes; OpenBabel::OBGraphSym graphsym(obmol); graphsym.GetSymmetry(symmetry_classes); //std::vector<unsigned long> atomIds = FindTetrahedralAtoms(obmol, symmetry_classes); std::vector<OpenBabel::StereogenicUnit> units = FindStereogenicUnits(obmol, symmetry_classes); for (unsigned int i = 0; i < units.size(); ++i) { if (units.at(i).type == OpenBabel::OBStereo::Tetrahedral) { OpenBabel::OBAtom *obatom = obmol->GetAtomById(units.at(i).id); painter->drawEllipse(mapFromItem(mol, atoms[obatom->GetIndex()]->pos()), 10, 10); } else if (units.at(i).type == OpenBabel::OBStereo::CisTrans) { OpenBabel::OBBond *obbond = obmol->GetBondById(units.at(i).id); OpenBabel::OBAtom *obatom1 = obbond->GetBeginAtom(); OpenBabel::OBAtom *obatom2 = obbond->GetEndAtom(); painter->drawEllipse(mapFromItem(mol, atoms[obatom1->GetIndex()]->pos()), 10, 10); painter->drawEllipse(mapFromItem(mol, atoms[obatom2->GetIndex()]->pos()), 10, 10); } } #else using OpenBabel::OBMolAtomIter; FOR_ATOMS_OF_MOL(atom, obmol) if (atom->IsChiral()) painter->drawEllipse(mapFromItem(mol, atoms[atom->GetIdx()-1]->pos()), 10, 10); #endif // default behavious (draw the label()) MolInputItem::paint(painter, option, widget); painter->restore(); }
bool CDSpectra::checkForData(Molecule * mol) { OpenBabel::OBMol obmol = mol->OBMol(); OpenBabel::OBElectronicTransitionData *etd = static_cast<OpenBabel::OBElectronicTransitionData*>(obmol.GetData("ElectronicTransitionData")); if (!etd) return false; if ( etd->GetRotatoryStrengthsVelocity().size() == 0 && etd->GetRotatoryStrengthsLength().size() == 0 ) return false; // OK, we have valid data, so store them for later std::vector<double> wavelengths = etd->GetWavelengths(); std::vector<double> rotl = etd->GetRotatoryStrengthsLength(); std::vector<double> rotv = etd->GetRotatoryStrengthsVelocity(); ui.combo_rotatoryType->clear(); if (rotl.size() != 0) ui.combo_rotatoryType->addItem("Length"); if (rotv.size() != 0) ui.combo_rotatoryType->addItem("Velocity"); // Store in member vars m_xList.clear(); m_yList.clear(); for (uint i = 0; i < wavelengths.size(); i++) m_xList.append(wavelengths.at(i)); for (uint i = 0; i < rotl.size(); i++) m_yListLength->append(rotl.at(i)); for (uint i = 0; i < rotv.size(); i++) m_yListVelocity->append(rotv.at(i)); rotatoryTypeChanged(ui.combo_rotatoryType->currentText()); return true; }
OpenBabel::OBMol Schuffenhauer::Rule_1(OpenBabel::OBMol& oldMol) { if (oldMol.GetSSSR().size() <= _ringsToBeRetained) { return oldMol; } OpenBabel::OBMol newMol(oldMol); std::vector<OpenBabel::OBAtom*>::iterator avi; OpenBabel::OBBondIterator bi; OpenBabel::OBAtom* atom; OpenBabel::OBAtom* nbrAtom[2]; for (atom = newMol.BeginAtom(avi); atom; atom = newMol.NextAtom(avi)) { if ((atom->MemberOfRingSize() == 3) && (atom->IsNitrogen() || atom->IsOxygen()) && (atom->MemberOfRingCount() == 1) && (atom->GetHvyValence() == 2)) { nbrAtom[0] = atom->BeginNbrAtom(bi); nbrAtom[1] = atom->NextNbrAtom(bi); if (nbrAtom[0] && nbrAtom[1]) { newMol.DeleteAtom(atom); newMol.GetBond(nbrAtom[0], nbrAtom[1])->SetBondOrder(2); } } } return newMol; }
bool IRSpectra::checkForData(Molecule * mol) { OpenBabel::OBMol obmol = mol->OBMol(); OpenBabel::OBVibrationData *vibrations = static_cast<OpenBabel::OBVibrationData*>(obmol.GetData(OpenBabel::OBGenericDataType::VibrationData)); if (!vibrations) return false; // Setup signals/slots connect(this, SIGNAL(plotDataChanged()), m_dialog, SLOT(regenerateCalculatedSpectra())); connect(ui.cb_labelPeaks, SIGNAL(toggled(bool)), m_dialog, SLOT(regenerateCalculatedSpectra())); connect(ui.spin_scale, SIGNAL(valueChanged(double)), this, SLOT(setScale(double))); connect(ui.spin_FWHM, SIGNAL(valueChanged(double)), m_dialog, SLOT(regenerateCalculatedSpectra())); connect(ui.combo_yaxis, SIGNAL(currentIndexChanged(QString)), this, SLOT(updateYAxis(QString))); // OK, we have valid vibrations, so store them for later vector<double> wavenumbers = vibrations->GetFrequencies(); vector<double> intensities = vibrations->GetIntensities(); // Case where there are no intensities, set all intensities to an arbitrary value, i.e. 1.0 if (wavenumbers.size() > 0 && intensities.size() == 0) { // Warn user QMessageBox::information(m_dialog, tr("No intensities"), tr("The vibration data in the molecule you have loaded does not have any intensity data. Intensities have been set to an arbitrary value for visualization.")); for (uint i = 0; i < wavenumbers.size(); i++) { intensities.push_back(1.0); } } // Normalize intensities into transmittances double maxIntensity=0; for (unsigned int i = 0; i < intensities.size(); i++) { if (intensities.at(i) >= maxIntensity) { maxIntensity = intensities.at(i); } } vector<double> transmittances; for (unsigned int i = 0; i < intensities.size(); i++) { double t = intensities.at(i); t = t / maxIntensity; // Normalize t = 0.97 * t; // Keeps the peaks from extending to the limits of the plot t = 1.0 - t; // Simulate transmittance t *= 100.0; // Convert to percent transmittances.push_back(t); } // Store in member vars m_xList->clear(); m_yList->clear(); for (uint i = 0; i < wavenumbers.size(); i++) { m_xList->append(wavenumbers.at(i)); m_yList->append(transmittances.at(i)); } return true; }
void Geometry::computeGasteigerCharges() { // This is returning zero charges for some reason return; qDebug() << "Geometry::computeGasteigerCharges() not working correctly"; OpenBabel::OBAtom* obAtom(0); OpenBabel::OBMol obMol; obMol.BeginModify(); obMol.UnsetPartialChargesPerceived(); for (int i = 0; i < m_atoms.size(); ++i) { obAtom = obMol.NewAtom(); obAtom->SetAtomicNum(m_atoms[i]->atomicNumber()); obAtom->SetVector(m_coordinates[i].x, m_coordinates[i].y, m_coordinates[i].z); } obMol.SetTotalCharge(m_charge); obMol.SetTotalSpinMultiplicity(m_multiplicity); obMol.EndModify(); OpenBabel::OBMolAtomIter iter(&obMol); for (int i = 0; i < m_atoms.size(); ++i, ++iter) { int index(iter->GetIdx()); qDebug() << "Setting Gasteiger Charge for" << index << "to" << iter->GetPartialCharge(); GasteigerCharge& charge(m_atoms[i]->getProperty<GasteigerCharge>()); charge.setValue(iter->GetPartialCharge()); } }
void FilterCores::Calculate(OpenBabel::OBMol* mol) { // Any rings? OpenBabel::OBAtom* atom; std::vector<OpenBabel::OBAtom*>::iterator i; bool rings(false); for (atom = mol->BeginAtom(i); atom; atom = mol->NextAtom(i)) { if (atom->IsInRing()) { rings = true; break; } } if (rings) { // Make workcopy of original mol OpenBabel::OBMol m = *mol; m.DeleteHydrogens(); // Iteratively remove all endstanding atoms until none are left OpenBabel::OBAtom* atom; std::vector<OpenBabel::OBAtom*>::iterator i; bool endstanding(true); while (endstanding && m.NumAtoms()) { endstanding = false; for (atom = m.BeginAtom(i); atom; atom = m.NextAtom(i)) { if (atom->GetValence() < 2) { if (m.DeleteAtom(atom)) { endstanding = true; break; } } } } if (m.NumAtoms()) _result = 1; else _result = 0; } else { _result = 0; } if ((_minLimit && (_result < _min)) || (_maxLimit && (_result > _max))) { _passed = false; } else { _passed = true; } }
bool DOSSpectra::checkForData(Molecule * mol) { OpenBabel::OBMol obmol = mol->OBMol(); //OpenBabel::OBDOSData *dos = static_cast<OpenBabel::OBDOSData*>(obmol.GetData(OpenBabel::OBGenericDataType::DOSData)); OpenBabel::OBDOSData *dos = static_cast<OpenBabel::OBDOSData*>(obmol.GetData("DOSData")); if (!dos) return false; // OK, we have valid DOS, so store them for later std::vector<double> energies = dos->GetEnergies(); std::vector<double> densities= dos->GetDensities(); if (m_intDOS) delete m_intDOS; m_intDOS = new std::vector<double> (dos->GetIntegration()); if (energies.size() == 0 || energies.size() != densities.size()) return false; // Store in member vars m_numAtoms = mol->numAtoms(); m_fermi = dos->GetFermiEnergy(); ui.label_fermi->setText(QString::number(m_fermi)); m_xList.clear(); m_yList.clear(); bool generateInt = false; if (m_intDOS->size() == 0) generateInt = true; for (uint i = 0; i < energies.size(); i++){ m_xList.append(energies.at(i)); double d = densities.at(i); m_yList.append(d); if (generateInt) { if (i == 0) m_intDOS->push_back(d); else m_intDOS->push_back(m_intDOS->at(i-1) + d); } } setImportedData(m_xList, QList<double>::fromVector(QVector<double>::fromStdVector(*m_intDOS))); return true; }
bool NMRSpectra::checkForData(Molecule * mol) { OpenBabel::OBMol obmol = mol->OBMol(); qDeleteAll(*m_NMRdata); m_NMRdata->clear(); // Test for "NMR Isotropic Shift" in first atom bool hasNMR = false; if (obmol.NumAtoms() > 0) if (obmol.GetFirstAtom()->HasData("NMR Isotropic Shift")) hasNMR = true; if (!hasNMR) return false; // Setup signals/slots connect(this, SIGNAL(plotDataChanged()), m_dialog, SLOT(regenerateCalculatedSpectra())); connect(ui.combo_type, SIGNAL(currentIndexChanged(QString)), this, SLOT(setAtom(QString))); connect(ui.spin_ref, SIGNAL(valueChanged(double)), this, SLOT(setReference(double))); connect(ui.push_resetAxes, SIGNAL(clicked()), this, SLOT(updatePlotAxes())); connect(ui.spin_FWHM, SIGNAL(valueChanged(double)), m_dialog, SLOT(regenerateCalculatedSpectra())); connect(ui.cb_labelPeaks, SIGNAL(toggled(bool)), m_dialog, SLOT(regenerateCalculatedSpectra())); // Extract data from obmol FOR_ATOMS_OF_MOL(atom,obmol) { QString symbol = QString(OpenBabel::etab.GetSymbol(atom->GetAtomicNum())); double shift = QString(atom->GetData("NMR Isotropic Shift")->GetValue().c_str()).toFloat(); QList<double> *list = new QList<double>; if (m_NMRdata->contains(symbol)) { list = m_NMRdata->value(symbol); } else { // Dump symbol into NMR Type list ui.combo_type->addItem(symbol); } list->append(shift); m_NMRdata->insert(symbol, list); }
int main(int argc,char **argv){ if(argc<2){ cout << "Usage: ProgrameName InputFileName"; return 1; } ifstream ifs(argv[1]); if(!ifs){ cout << "Cannot open input file"; return 1; } OpenBabel::OBConversion conv(&ifs, &cout); if(conv.SetInAndOutFormats("mol","sdf")){ OpenBabel::OBMol mol; if(conv.Read(&mol)){ cout << "Mol.wt: "<<mol.GetMolWt()<<endl;//works even with implicit hydrogen mol.AddHydrogens(false,false); //ensure that hydrogens are all explicit cout << "No. of atoms: " << mol.NumAtoms()<<endl; cout << "No. of hvy atoms: " << mol.NumHvyAtoms() << endl; cout << "No. of bonds: " << mol.NumBonds() << endl; double exactMass = 0.0; FOR_ATOMS_OF_MOL(a, mol){ cout << "iterating..."<<endl; exactMass += a->GetExactMass(); }
void GAMESSUKInputDialog::setMolecule(Molecule *molecule) { // Disconnect the old molecule first... if (m_molecule) disconnect(m_molecule, 0, this, 0); m_molecule = molecule; // Set multiplicity to the OB value OpenBabel::OBMol obmol = m_molecule->OBMol(); setMultiplicity(obmol.GetTotalSpinMultiplicity()); // Update the preview text whenever primitives are changed connect(m_molecule, SIGNAL(atomRemoved(Atom *)), this, SLOT(updatePreviewText())); connect(m_molecule, SIGNAL(atomAdded(Atom *)), this, SLOT(updatePreviewText())); connect(m_molecule, SIGNAL(atomUpdated(Atom *)), this, SLOT(updatePreviewText())); // Add atom coordinates updatePreviewText(); }
unsigned int Schuffenhauer::CalculateAcyclicBonds(OpenBabel::OBMol& mol) { unsigned int nbonds(0); OpenBabel::OBAtom* nbratom[2]; OpenBabel::OBBond* bond; std::vector<OpenBabel::OBBond*>::iterator bvi; for (bond = mol.BeginBond(bvi); bond; bond = mol.NextBond(bvi)) { nbratom[0] = bond->GetBeginAtom(); nbratom[1] = bond->GetEndAtom(); if (nbratom[0] && nbratom[1]) { if (!bond->IsInRing() && (nbratom[0]->GetValence() > 1) && (nbratom[1]->GetValence() > 1)) { ++nbonds; } } } return nbonds; }
bool RamanSpectra::checkForData(Molecule * mol) { OpenBabel::OBMol obmol = mol->OBMol(); OpenBabel::OBVibrationData *vibrations = static_cast<OpenBabel::OBVibrationData*>(obmol.GetData(OpenBabel::OBGenericDataType::VibrationData)); if (!vibrations) return false; // OK, we have valid vibrations, so store them for later vector<double> wavenumbers = vibrations->GetFrequencies(); vector<double> intensities = vibrations->GetRamanActivities(); if (wavenumbers.size() == 0 || intensities.size() == 0) return false; /* Case where there are no intensities, set all intensities to an arbitrary value, i.e. 1.0 if (wavenumbers.size() > 0 && intensities.size() == 0) { // Warn user //QMessageBox::information(m_dialog, tr("No intensities"), tr("The vibration data in the molecule you have loaded does not have any intensity data. Intensities have been set to an arbitrary value for visualization.")); for (uint i = 0; i < wavenumbers.size(); i++) { intensities.push_back(1.0); } }*/ // double maxIntensity=0; for (unsigned int i = 0; i < intensities.size(); i++) { if (intensities.at(i) >= maxIntensity) { maxIntensity = intensities.at(i); } } /*vector<double> transmittances;*/ for (unsigned int i = 0; i < intensities.size(); i++) { intensities[i] = intensities.at(i) / maxIntensity; // Normalize } // Store in member vars m_xList.clear(); m_xList_orig.clear(); m_yList.clear(); m_yList_orig.clear(); for (uint i = 0; i < wavenumbers.size(); i++){ double w = wavenumbers.at(i); m_xList.append(w*scale(w)); m_xList_orig.append(w); m_yList.append(intensities.at(i)); m_yList_orig.append(intensities.at(i)); } return true; }
unsigned int Schuffenhauer::CalculateHeteroAtoms(OpenBabel::OBMol& mol, OpenBabel::OBRing* ring, int a = 0) { unsigned int n(0); OpenBabel::OBAtom* atom; std::vector<OpenBabel::OBAtom*>::iterator avi; for (atom = mol.BeginAtom(avi); atom; atom = mol.NextAtom(avi)) { if (ring->IsMember(atom) && (atom->GetAtomicNum() == a)) { ++n; } if (!a && ring->IsMember(atom)) { if ((atom->GetAtomicNum() == 7) || (atom->GetAtomicNum() == 8) || (atom->GetAtomicNum() == 16)) { ++n; } } } return n; }
bool Schuffenhauer::HasLinkerToHeteroAtom(OpenBabel::OBMol& mol, OpenBabel::OBRing* ring) { std::vector<OpenBabel::OBBond*>::iterator bvi; OpenBabel::OBBond* bond; OpenBabel::OBAtom* nbrAtom[2]; for (bond = mol.BeginBond(bvi); bond; bond = mol.NextBond(bvi)) { nbrAtom[0] = bond->GetBeginAtom(); nbrAtom[1] = bond->GetEndAtom(); if ( // Neighbours are real nbrAtom[0] && nbrAtom[1] && // Bond should be acyclic !bond->IsInRing() && // Both atoms have to be ring atoms nbrAtom[0]->IsInRing() && nbrAtom[1]->IsInRing() && // At least one of the atoms should be hetero (nbrAtom[0]->IsHeteroatom() || nbrAtom[1]->IsHeteroatom()) && // One of the atoms, but not both, should be part of this ring ((ring->IsMember(nbrAtom[0]) && !ring->IsMember(nbrAtom[1])) || (ring->IsMember(nbrAtom[1]) && !ring->IsMember(nbrAtom[0]))) ) { return true; } } return false; }
List Factory::convert(Data::Geometry& geometry) { List list; Atoms* atoms(new Atoms()); Bonds* bonds(new Bonds()); list.append(atoms); list.append(bonds); unsigned nAtoms(geometry.nAtoms()); OpenBabel::OBMol obMol; obMol.BeginModify(); AtomMap atomMap; for (unsigned i = 0; i < nAtoms; ++i) { unsigned Z(geometry.atomicNumber(i)); qglviewer::Vec position(geometry.position(i)); Atom* atom(new Atom(geometry.atomicNumber(i))); atom->setPosition(geometry.position(i)); atoms->appendLayer(atom); OpenBabel::OBAtom* obAtom(obMol.NewAtom()); obAtom->SetAtomicNum(Z); obAtom->SetVector(position.x, position.y, position.z); atomMap.insert(obAtom, atom); } obMol.SetTotalCharge(geometry.charge()); obMol.SetTotalSpinMultiplicity(geometry.multiplicity()); obMol.EndModify(); obMol.ConnectTheDots(); obMol.PerceiveBondOrders(); for (OpenBabel::OBMolBondIter obBond(&obMol); obBond; ++obBond) { Atom* begin(atomMap.value(obBond->GetBeginAtom())); Atom* end(atomMap.value(obBond->GetEndAtom())); Bond* bond(new Bond(begin, end)); bond->setOrder(obBond->GetBondOrder()); bonds->appendLayer(bond); } return list; }
bool UVSpectra::checkForData(Molecule * mol) { OpenBabel::OBMol obmol = mol->OBMol(); OpenBabel::OBElectronicTransitionData *etd = static_cast<OpenBabel::OBElectronicTransitionData*>(obmol.GetData("ElectronicTransitionData")); if (!etd) return false; if (etd->GetEDipole().size() == 0) return false; // OK, we have valid data, so store them for later std::vector<double> wavelengths = etd->GetWavelengths(); std::vector<double> edipole= etd->GetEDipole(); // Store in member vars m_xList.clear(); m_yList.clear(); for (uint i = 0; i < wavelengths.size(); i++){ m_xList.append(wavelengths.at(i)); m_yList.append(edipole.at(i)); } return true; }
OpenBabel::OBMol Schuffenhauer::Rule_12(OpenBabel::OBMol& oldMol) { std::vector<OpenBabel::OBRing*> allrings(oldMol.GetSSSR()); if (allrings.size() <= _ringsToBeRetained) { return oldMol; } std::vector<OpenBabel::OBMol> mols; std::vector<unsigned int> rings; for (unsigned int i(0); i < allrings.size(); ++i) { if (HasLinkerToHeteroAtom(oldMol, allrings[i])) { mols.push_back(oldMol); rings.push_back(i); } } std::vector<OpenBabel::OBMol> validMols; for (unsigned int i(0); i < mols.size(); ++i) { mols[i] = RemoveRing(mols[i], allrings, rings[i]); if (!mols[i].Empty()) { validMols.push_back(mols[i]); } } if (validMols.size() == 1) { return validMols[0]; } return oldMol; }
int main(int argc,char **argv) { std::string ifile = ""; OpenBabel::OBSpectrophore::AccuracyOption accuracy = OpenBabel::OBSpectrophore::AngStepSize20; OpenBabel::OBSpectrophore::StereoOption stereo = OpenBabel::OBSpectrophore::NoStereoSpecificProbes; OpenBabel::OBSpectrophore::NormalizationOption normalization = OpenBabel::OBSpectrophore::NoNormalization; double resolution = 3.0; int c; opterr = 0; std::string msg; while ((c = getopt(argc, argv, "ui:n:a:s:r:h")) != -1) { switch (c) { case 'u': showImplementationDetails(argv[0]); exit(1); break; case 'i': if (!isValidValue('i', optarg)) { msg = "Option -i is followed by an invalid argument: "; msg += optarg; showError(msg); exit(1); } else { ifile = optarg; } break; case 'n': if (!isValidValue('n', optarg)) { msg = "Option -n is followed by an invalid argument: "; msg += optarg; showError(msg); exit(1); } else normalization = stringToNormalizationOption(optarg); break; case 'a': if (!isValidValue('a', optarg)) { msg = "Option -a is followed by an invalid argument: "; msg += optarg; showError(msg); exit(1); } else accuracy = stringToAccuracyOption(optarg); break; case 's': if (!isValidValue('s', optarg)) { msg = "Option -s is followed by an invalid argument: "; msg += optarg; showError(msg); exit(1); } else stereo = stringToStereoOption(optarg); break; case 'r': if (!isValidValue('r', optarg)) { msg = "Option -r is followed by an invalid argument: "; msg += optarg; showError(msg); exit(1); } else { resolution = atof(optarg); if (resolution <= 0) { msg = "Resolution -r should be larger than 0.0: "; msg += optarg; showError(msg); exit(1); } } break; case 'h': showHelp(argv[0]); exit(0); break; case '?': if ((optopt == 'i') || (optopt == 'n') || (optopt == 'a') || (optopt == 's') || (optopt == 'r')) { msg = "Option -"; msg += optopt; msg += " requires an argument."; showError(msg); exit(1); } else { msg = "Unknown option -"; msg += optopt; msg += "."; showError(msg); exit(1); } break; default: showError("Unknown option"); exit(1); break; } } // The input file (-i) is the only required option if (ifile.empty()) { msg = "Input file specification is required (option -i)."; showError(msg); exit(1); } OpenBabel::OBConversion obconversion; OpenBabel::OBFormat *format = obconversion.FormatFromExt(ifile.c_str()); if (!format) { msg = "Could not find file format for "; msg += ifile; showError(msg); exit(1); } obconversion.SetInFormat(format); std::ifstream ifs; ifs.open(ifile.c_str()); obconversion.SetInStream(&ifs); // Start calculations OpenBabel::OBMol mol; OpenBabel::OBSpectrophore spec; spec.SetAccuracy(accuracy); spec.SetNormalization(normalization); spec.SetStereo(stereo); spec.SetResolution(resolution); showParameters(spec, ifile); unsigned int count(0); while (obconversion.Read(&mol)) { std::vector<double> result = spec.GetSpectrophore(&mol); if (result.empty()) { std::cerr << "Error calculating Spectrophore from molecule number "; std::cerr << count; std::cerr << " (counting starts at 0)!"; std::cerr << std::endl; } else { std::cout << mol.GetTitle() << "\t"; for (unsigned int i(0); i < result.size(); ++i) { std::cout << result[i] << "\t"; } std::cout << std::endl; } mol.Clear(); ++count; } return 0; }
//*--------------------------------------------------------------------------*// //* MAIN MAIN *// //*--------------------------------------------------------------------------*// int main(int argc, char* argv[]) { // Initialise random number generator srandom(time(NULL)); clock_t t0 = clock(); // Print header printHeader(); // Read options Options uo = parseCommandLine(argc,argv); if(!uo.noHybrid) { if(uo.funcGroupVec[AROM] && uo.funcGroupVec[LIPO]) { uo.funcGroupVec[HYBL] = true; } if(uo.funcGroupVec[HDON] && uo.funcGroupVec[HACC]) { uo.funcGroupVec[HYBH] = true; } } std::cerr << uo.print() << std::endl; if (uo.version) { printHeader(); exit(0); } if (uo.help) { printUsage(); exit(0); } // Db file and pharmacophore out are mandatory elements if (uo.dbInpFile.empty()) { mainErr("Missing database file. This is a required option (-d)."); } if (uo.pharmOutFile.empty() && uo.molOutFile.empty() && uo.scoreOutFile.empty()) { mainErr("No output file defined. So there is actually no use to compute anything at all."); } if ((uo.pharmOutFile.empty() && uo.scoreOutFile.empty()) && !uo.molOutFile.empty()) { mainErr("No file defined to write pharmacophore information."); } if (uo.refInpFile.empty() && uo.pharmOutFile.empty() && uo.molOutFile.empty() && !uo.scoreOutFile.empty()) { mainErr("Only score file requested when no reference is given. Unable to generate this output."); } // Reference variables Pharmacophore refPharm; refPharm.clear(); std::string refId; double refVolume(0.0); int refSize(0); int exclSize(0); // Database variables std::vector<Result*> resList; Pharmacophore dbPharm; std::string dbId; double dbVolume(0.0); int dbSize(0); //---------------------------------------------------------------------------- //...(A).. Process the reference //---------------------------------------------------------------------------- if (!uo.refInpFile.empty()) { //------------------------------------------------------- //...(1).. get reference pharmacophore //------------------------------------------------------- if (uo.refInpType == UNKNOWN) { std::string ext(getExt(uo.refInpFile)); if (ext == ".phar") { uo.refInpType = PHAR; } else { uo.refInpType = MOL; } } if (uo.refInpType == MOL) { OpenBabel::OBMol m; OpenBabel::OBConversion* reader = new OpenBabel::OBConversion(); reader->SetInFormat(reader->FormatFromExt(uo.refInpFile.c_str())); if (!reader->Read(&m, uo.refInpStream)) { mainErr("Unable to read reference molecule"); } calcPharm(&m, &refPharm, uo); refId = m.GetTitle(); delete reader; reader = NULL; } else if (uo.refInpType == PHAR) { PharmacophoreReader* reader = new PharmacophoreReader(); refPharm = reader->read(uo.refInpStream, refId); if (refPharm.empty()) { mainErr("Error reading reference pharmacophore"); } delete reader; reader = NULL; } else { mainErr("Unknown format of reference molecule."); } //------------------------------------------------------- //...(2).. process reference pharmacophore //------------------------------------------------------- if (uo.merge) { pharMerger.merge(refPharm); } refSize = refPharm.size(); for (unsigned int i(0); i < refSize; ++i) { if (refPharm[i].func == EXCL) { // extract overlap with exclusion spheres for (unsigned int j(0); j < refPharm.size(); ++j) { if (refPharm[j].func != EXCL) { refVolume -= VolumeOverlap(refPharm[i], refPharm[j], !uo.noNormal); } } exclSize++; } else { // add point self-overlap refVolume += VolumeOverlap(refPharm[i], refPharm[i], !uo.noNormal); } } if(!uo.isQuiet) { std::cerr << "Reference pharmacophore " << refId << std::endl; std::cerr << " number of points: " << refSize - exclSize << std::endl; std::cerr << " number of exclusion spheres: " << exclSize << std::endl; std::cerr << " totalvolume: " << refVolume << std::endl; } } //---------------------------------------------------------------------------- //...(B).. Process the database file //---------------------------------------------------------------------------- // DB files if (uo.dbInpType == UNKNOWN) { std::string ext(getExt(uo.dbInpFile)); if (ext==".phar") { uo.dbInpType = PHAR; } else { uo.dbInpType = MOL; } } // local storage of the rotation matrix SiMath::Matrix rotMat(3,3,0.0); unsigned int molCount(0); OpenBabel::OBConversion* molReader = NULL; PharmacophoreReader* pharmReader = NULL; if (uo.dbInpType == PHAR) { pharmReader = new PharmacophoreReader(); } else if (uo.dbInpType == MOL) { molReader = new OpenBabel::OBConversion(); molReader->SetInFormat(molReader->FormatFromExt(uo.dbInpFile.c_str())); molReader->SetInStream(uo.dbInpStream); } else { mainErr("Unknown format of db file."); } bool done(false); OpenBabel::OBMol m; while (!done) { dbPharm.clear(); m.Clear(); if (uo.dbInpType == MOL) { if (!molReader->Read(&m)) { done = true; break; } else { calcPharm(&m, &dbPharm, uo); dbId = m.GetTitle(); } } else { if (uo.dbInpStream->eof()) { done = true; break; } else { dbPharm = pharmReader->read(uo.dbInpStream, dbId); } } if (dbPharm.empty()) { continue; } ++molCount; if (!uo.isQuiet ) { if ((molCount % 10) == 0) { std::cerr << "." << std::flush; } if ((molCount % 500) == 0) { std::cerr << molCount << std::endl << std::flush; } } if (uo.merge) { pharMerger.merge(dbPharm); } if (uo.refInpFile.empty()) { if (!(uo.isQuiet)) { printProgress(molCount); } if( !uo.pharmOutFile.empty()) { uo.pharmOutWriter->write(dbPharm, uo.pharmOutStream, dbId); } continue; } //------------------------------------------------------- //...(1).. Alignment //------------------------------------------------------- dbSize = dbPharm.size(); dbVolume = 0.0; for (unsigned int i(0); i < dbSize; ++i) { if (dbPharm[i].func == EXCL) { continue; } dbVolume += VolumeOverlap(dbPharm[i], dbPharm[i], !uo.noNormal); } // Create a result structure Result res; res.refId = refId; res.refVolume = refVolume; res.dbId = dbId; res.dbVolume = dbVolume; res.overlapVolume = 0.0; res.exclVolume = 0.0; res.resMol = m; res.resPharSize = 0; if (uo.scoreOnly) { FunctionMapping funcMap(&refPharm, &dbPharm, uo.epsilon); PharmacophoreMap fMap = funcMap.getNextMap(); double volBest(-9999.999); // loop over all reference points while (!fMap.empty()) { double newVol(0.0); double exclVol(0.0); for (PharmacophoreMap::iterator itP = fMap.begin(); itP != fMap.end(); ++itP) { if ((itP->first)->func == EXCL) { exclVol += VolumeOverlap((itP->first), (itP->second), !uo.noNormal); } else if (((itP->first)->func == (itP->second)->func ) || (((itP->first)->func == HYBH || (itP->first)->func == HDON || (itP->first)->func == HACC) && ((itP->second)->func == HDON || (itP->second)->func == HACC || (itP->second)->func == HYBH)) || (((itP->first)->func == HYBL || (itP->first)->func == AROM || (itP->first)->func == LIPO) && ((itP->second)->func == AROM || (itP->second)->func == LIPO || (itP->second)->func == HYBL))) { newVol += VolumeOverlap((itP->first),(itP->second), !uo.noNormal); } } if ((newVol - exclVol) > volBest) { res.resPhar.clear(); res.resPharSize = 0; for (PharmacophoreMap::iterator itP = fMap.begin(); itP != fMap.end(); ++itP) { // add point to resulting pharmacophore PharmacophorePoint p(itP->second); (res.resPhar).push_back(p); ++res.resPharSize; } res.overlapVolume = newVol; res.exclVolume = exclVol; volBest = newVol - exclVol; } // get the next map fMap.clear(); fMap = funcMap.getNextMap(); } } else { FunctionMapping funcMap(&refPharm, &dbPharm, uo.epsilon); PharmacophoreMap fMap = funcMap.getNextMap(); PharmacophoreMap bestMap; // default solution SolutionInfo best; best.volume = -999.9; // rotor is set to no rotation best.rotor.resize(4); best.rotor = 0.0; best.rotor[0] = 1.0; double bestScore = -1000; int mapSize(fMap.size()); int maxSize = mapSize - 3; while (!fMap.empty()) { int msize = fMap.size(); // add the exclusion spheres to the alignment procedure if (uo.withExclusion) { for (unsigned int i(0); i < refSize ; ++i) { if (refPharm[i].func != EXCL) { continue; } for (unsigned int j(0); j < dbSize; ++j) { if (dbPharm[j].func == EXCL) { continue; } fMap.insert(std::make_pair(&(refPharm[i]), &(dbPharm[j]))); } } } // Only align if the expected score has any chance of being larger // than best score so far if ((msize > maxSize) && (((double) msize / (refSize - exclSize + dbSize - msize)) > bestScore)) { Alignment align(fMap); SolutionInfo r = align.align(!uo.noNormal); if (best.volume < r.volume) { best = r; bestScore = best.volume / (refVolume + dbVolume - best.volume); bestMap = fMap; mapSize = msize; } } else { // Level of mapping site to low break; } if (bestScore > 0.98) { break; } // Get the next map fMap.clear(); fMap = funcMap.getNextMap(); } // Transform the complete pharmacophore and the molecule towards the // best alignment rotMat = quat2Rotation(best.rotor); positionPharmacophore(dbPharm, rotMat, best); positionMolecule(&res.resMol, rotMat, best); // Update result res.info = best; // Compute overlap volume between exlusion spheres and pharmacophore // points for (int i(0); i < refSize; ++i) { if (refPharm[i].func != EXCL) { continue; } for (int j(0); j < dbSize; ++j) { res.exclVolume += VolumeOverlap(refPharm[i], dbPharm[j], !uo.noNormal); } } // make copy of the best map and compute the volume overlap for (PharmacophoreMap::iterator itP = bestMap.begin(); itP != bestMap.end(); ++itP) { if(((itP->first)->func == EXCL) || ((itP->second)->func == EXCL)) { continue; } // compute overlap res.overlapVolume += VolumeOverlap(itP->first, itP->second, !uo.noNormal); // add point to resulting pharmacophore PharmacophorePoint p(itP->second); (res.resPhar).push_back(p); ++res.resPharSize; } } // update scores res.info.volume = res.overlapVolume - res.exclVolume; if (res.info.volume > 0.0) { res.tanimoto = res.info.volume / (res.refVolume + res.dbVolume - res.info.volume); res.tversky_ref = res.info.volume / res.refVolume; res.tversky_db = res.info.volume / res.dbVolume; } switch (uo.rankby) { case TANIMOTO: res.rankbyScore = res.tanimoto; break; case TVERSKY_REF: res.rankbyScore = res.tversky_ref; break; case TVERSKY_DB: res.rankbyScore = res.tversky_db; break; } //------------------------------------------------------- //...(5).. Generate output //------------------------------------------------------- if (uo.cutOff != 0.0) { if (res.rankbyScore < uo.cutOff) { continue; } } if (uo.best != 0) { addBest(res, uo, resList); } else { if (!uo.molOutFile.empty()) { logOut(&res, uo); } if (!uo.pharmOutFile.empty()) { logPharmacophores(&res, uo); } if (!uo.scoreOutFile.empty()) { logScores(&res, uo); } } } if (molReader) { delete molReader; molReader = NULL; } if (pharmReader) { delete pharmReader; pharmReader = NULL; } //---------------------------------------------------------------------------- //...(C).. Process best list (if defined) //---------------------------------------------------------------------------- if (uo.best != 0) { std::vector<Result*>::iterator itR; for (itR = resList.begin(); itR != resList.end(); ++itR) { Result* res(*itR); if (!uo.molOutFile.empty()) { logOut(res, uo); } if (!uo.pharmOutFile.empty()) { logPharmacophores(res, uo); } if (!uo.scoreOutFile.empty()) { logScores(res, uo); } delete res; } } // done processing database if (!uo.isQuiet) { if (uo.refInpFile.empty()) { std::cerr << std::endl; std::cerr << "Processed " << molCount << " molecules"; double tt = (double)(clock() - t0 )/CLOCKS_PER_SEC; std::cerr << " in " << tt << " seconds ("; std::cerr << molCount/tt << " molecules per second)." << std::endl; } else { std::cerr << std::endl; std::cerr << "Processed " << molCount << " molecules" << std::endl; double tt = (double)(clock() - t0 )/CLOCKS_PER_SEC; std::cerr << molCount << " alignments in " << tt << " seconds ("; std::cerr << molCount/tt << " alignments per second)." << std::endl; } } exit(0); }
void FilterBridgeFraction::Calculate(OpenBabel::OBMol* mol) { // Are there rings? OpenBabel::OBAtom* atom; std::vector<OpenBabel::OBAtom*>::iterator i; bool rings(false); for (atom = mol->BeginAtom(i); atom; atom = mol->NextAtom(i)) { if (atom->IsInRing()) { rings = true; break; } } if (rings) { // Make workcopy of original mol OpenBabel::OBMol m = *mol; m.DeleteHydrogens(); unsigned int natoms(m.NumAtoms()); if (!natoms) { _result = 0.0; _passed = false; return; } // Iteratively remove all endstanding atoms until none are left OpenBabel::OBAtom* atom; std::vector<OpenBabel::OBAtom*>::iterator i; bool endstanding(true); while (endstanding && m.NumAtoms()) { endstanding = false; for (atom = m.BeginAtom(i); atom; atom = m.NextAtom(i)) { if (atom->GetValence() < 2) { if (m.DeleteAtom(atom)) { endstanding = true; break; } } } } // Now remove all ring atoms rings = true; while (rings && m.NumAtoms()) { rings = false; for (atom = m.BeginAtom(i); atom; atom = m.NextAtom(i)) { if (atom->IsInRing()) { if (m.DeleteAtom(atom)) { rings = true; break; } } } } _result = (double) m.NumAtoms() / (double) natoms; } else { _result = 0.0; } if ((_minLimit && (_result < _min)) || (_maxLimit && (_result > _max))) { _passed = false; } else { _passed = true; } }
void Molecule::addHydrogens(Atom *a, const QList<unsigned long> &atomIds, const QList<unsigned long> &bondIds) { if (atomIds.size() != bondIds.size()) { qDebug() << "Error, addHydrogens called with atom & bond id lists of different size!"; } // Construct an OBMol, call AddHydrogens and translate the changes OpenBabel::OBMol obmol = OBMol(); if (a) { OpenBabel::OBAtom *obatom = obmol.GetAtom(a->index()+1); // Set implicit valence for unusual elements not handled by OpenBabel // PR#2803076 switch (obatom->GetAtomicNum()) { case 3: case 11: case 19: case 37: case 55: case 85: case 87: obatom->SetImplicitValence(1); obatom->SetHyb(1); obmol.SetImplicitValencePerceived(); break; case 4: case 12: case 20: case 38: case 56: case 88: obatom->SetImplicitValence(2); obatom->SetHyb(2); obmol.SetImplicitValencePerceived(); break; case 84: // Po obatom->SetImplicitValence(2); obatom->SetHyb(3); obmol.SetImplicitValencePerceived(); break; default: // do nothing break; } obmol.AddHydrogens(obatom); } else obmol.AddHydrogens(); // All new atoms in the OBMol must be the additional hydrogens unsigned int numberAtoms = numAtoms(); int j = 0; for (unsigned int i = numberAtoms+1; i <= obmol.NumAtoms(); ++i, ++j) { if (obmol.GetAtom(i)->IsHydrogen()) { OpenBabel::OBAtom *obatom = obmol.GetAtom(i); Atom *atom; if (atomIds.isEmpty()) atom = addAtom(); else if (j < atomIds.size()) atom = addAtom(atomIds.at(j)); else { qDebug() << "Error - not enough unique ids in addHydrogens."; break; } atom->setOBAtom(obatom); // Get the neighbor atom OpenBabel::OBBondIterator iter; OpenBabel::OBAtom *next = obatom->BeginNbrAtom(iter); Bond *bond; if (bondIds.isEmpty()) bond = addBond(); else // Already confirmed by atom ids bond = addBond(bondIds.at(j)); bond->setEnd(Molecule::atom(atom->index())); bond->setBegin(Molecule::atom(next->GetIdx()-1)); } } for (unsigned int i = 1; i <= numberAtoms; ++i) { // Warning -- OB atom index off-by-one here atom(i-1)->setPartialCharge(obmol.GetAtom(i)->GetPartialCharge()); } }
bool extract_thermochemistry(OpenBabel::OBMol &mol, bool bVerbose, int *Nsymm, int Nrotbonds, double dBdT, double *temperature, double *DeltaHf0, double *DeltaHfT, double *DeltaGfT, double *DeltaSfT, double *S0T, double *CVT, double *CPT, std::vector<double> &Scomponents, double *ZPVE) { enum kkTYPE {kkDH, kkDG, kkDS, kkS0, kkCV, kkSt, kkSr, kkSv, kkZP}; typedef struct { std::string term; kkTYPE kk; } energy_unit; double St = 0, Sr = 0, Sv = 0, Sconf = 0, Ssymm = 0; double Rgas = 1.9872041; int RotSymNum = 1; OpenBabel::OBRotationData* rd; rd = (OpenBabel::OBRotationData*)mol.GetData("RotationData"); if (NULL != rd) { RotSymNum = rd->GetSymmetryNumber(); if (bVerbose) { printf("Found symmetry number %d in input file.\n", RotSymNum); } } else if (bVerbose) { printf("Using default symmetry number %d\n", RotSymNum); } if ((*Nsymm > 0) && (*Nsymm != RotSymNum)) { // Rgas in cal/mol K http://en.wikipedia.org/wiki/Gas_constant Ssymm = -Rgas*log((1.0* *Nsymm)/RotSymNum); RotSymNum = *Nsymm; if (bVerbose) { printf("Changing symmetry number to %d\n", RotSymNum); } } else if (*Nsymm == 0) { *Nsymm = RotSymNum; } if (Nrotbonds > 0) { Sconf = Rgas*Nrotbonds*log(3.0); } energy_unit eu[] = { { "zpe", kkZP }, { "DeltaHform", kkDH }, { "DeltaGform", kkDG }, { "DeltaSform", kkDS }, { "S0", kkS0 }, { "cv", kkCV }, { "Strans", kkSt }, { "Srot", kkSr }, { "Svib", kkSv } }; #define NEU (sizeof(eu)/sizeof(eu[0])) int found = 0; std::vector<OpenBabel::OBGenericData*> obdata = mol.GetData(); for(std::vector<OpenBabel::OBGenericData*>::iterator j = obdata.begin(); (j<obdata.end()); ++j) { std::string term = (*j)->GetAttribute(); double value = atof((*j)->GetValue().c_str()); double T = 0; { size_t lh = term.find("("); size_t rh = term.find("K)"); double TT = atof(term.substr(lh+1,rh-lh-1).c_str()); if (0 != TT) { if (0 == T) { T = TT; *temperature = TT; } else { std::cerr << "Different T in the input file, found " << T << " before and now " << TT << ". Output maybe inconsistent." << std::endl; T = TT; } } } for(unsigned int i = 0; (i<NEU); i++) { if (strstr(term.c_str(), eu[i].term.c_str()) != 0) { switch (eu[i].kk) { case kkZP: { *ZPVE = value; } break; case kkDH: if (0 == T) { *DeltaHf0 = value; } else { *DeltaHfT = value; } found ++; break; case kkDG: *DeltaGfT = value - T*(Ssymm+Sconf)/1000; found ++; break; case kkDS: *DeltaSfT = value + Ssymm + Sconf; found ++; break; case kkS0: *S0T = value + Ssymm + Sconf; found ++; break; case kkSt: St = value; found ++; break; case kkSr: Sr = value; found ++; break; case kkSv: Sv = value; found ++; break; case kkCV: *CVT = value; found++; break; default: break; } } } } double P = 16.605/4.184; // Convert pressure to kcal/mol *CPT = *CVT + Rgas + (2*P*dBdT + pow(P*dBdT, 2.0)/Rgas); Scomponents.push_back(St); Scomponents.push_back(Sr); Scomponents.push_back(Sv); Scomponents.push_back(Ssymm); Scomponents.push_back(Sconf); if (bVerbose && (Ssymm != 0)) { printf("Applyied symmetry correction to free energy of %g kcal/mol\n", -(*temperature*Ssymm)/1000); } if (bVerbose && (Sconf != 0)) { printf("Applyied conformational correction to free energy of %g kcal/mol\n", -(*temperature*Sconf)/1000); } return (found == 9); }
//-- bool DataProperty::Satisfy(OpenBabel::OBRing* pRing, const std::string& refTo, std::vector<Class*>& vecSatisfiedClasses, std::string& refValue) { //bool bSatisfied = false; int iPosition = -1; // [rad] if we are default, we automatically satisfy if(!IsDefault()) { if(!SatisfyCommon(vecSatisfiedClasses, iPosition)) { // [rad] this property does not apply refValue = ""; return(false); } } // [rad] go through possible data types.. if(!refTo.compare("RING_SIZE")) { ConvertInt(pRing->Size(), refValue); } else if(!refTo.compare("RING_IS_AROMATIC")) { ConvertBool(pRing->IsAromatic(), refValue); } else if(!refTo.compare("RING_IS_HOMOCYCLIC")) { OpenBabel::OBMol* pMolecule = pRing->GetParent(); OpenBabel::OBAtom* pAtom; bool bHomoCyclic = true; std::vector<int>::iterator iter_path = pRing->_path.begin(); while(iter_path != pRing->_path.end()) { pAtom = pMolecule->GetAtom((*iter_path)); if(pAtom) { if(6 != pAtom->GetAtomicNum()) { bHomoCyclic = false; break; } } iter_path++; } ConvertBool(bHomoCyclic, refValue); } else if(!refTo.compare("RING_IS_HETEROCYCLIC")) { OpenBabel::OBMol* pMolecule = pRing->GetParent(); OpenBabel::OBAtom* pAtom; bool bHeteroCyclic = false; std::vector<int>::iterator iter_path = pRing->_path.begin(); while(iter_path != pRing->_path.end()) { pAtom = pMolecule->GetAtom((*iter_path)); if(pAtom) { if(6 != pAtom->GetAtomicNum()) { bHeteroCyclic = true; break; } } iter_path++; } ConvertBool(bHeteroCyclic, refValue); } else { // [rad] unknown datatype? refValue = ""; return(false); } return(true); }