"Fossies" - the Fresh Open Source Software Archive  

Source code changes of the file "layer2/AtomInfo.cpp" between
pymol-v1.8.6.0.tar.bz2 and pymol-v2.1.0.tar.bz2

About: PyMOL is a Python-enhanced molecular graphics tool. It excels at 3D visualization of proteins, small molecules, density, surfaces, and trajectories. It also includes molecular editing, ray tracing, and movies. Open Source version.

AtomInfo.cpp  (pymol-v1.8.6.0.tar.bz2):AtomInfo.cpp  (pymol-v2.1.0.tar.bz2)
skipping to change at line 587 skipping to change at line 587
} }
break; break;
} }
break; break;
} }
return false; return false;
} }
int AtomInfoKnownPolymerResName(const char *resn) int AtomInfoKnownPolymerResName(const char *resn)
{ {
return AtomInfoKnownProteinResName(resn) ||
AtomInfoKnownNucleicResName(resn);
}
int AtomInfoKnownNucleicResName(const char *resn)
{
if (resn[0] == 'D') {
// Deoxy ribonucleotide
++resn;
}
switch (resn[0]) {
case 'A':
case 'C':
case 'G':
case 'I':
case 'T':
case 'U':
if (!resn[1])
return true;
}
return false;
}
int AtomInfoKnownProteinResName(const char *resn)
{
switch (resn[0]) { switch (resn[0]) {
case 'A': case 'A':
switch (resn[1]) { switch (resn[1]) {
case 0: /* A*/
return true;
break;
case 'L': case 'L':
switch (resn[2]) { switch (resn[2]) {
case 'A': /* ALA */ case 'A': /* ALA */
return true; return true;
break; break;
} }
break; break;
case 'R': case 'R':
switch (resn[2]) { switch (resn[2]) {
case 'G': /* ARG */ case 'G': /* ARG */
skipping to change at line 621 skipping to change at line 645
break; break;
case 'N': /* ASN */ case 'N': /* ASN */
return true; return true;
break; break;
} }
break; break;
} }
break; break;
case 'C': case 'C':
switch (resn[1]) { switch (resn[1]) {
case 0: /* C */
return true;
case 'Y': case 'Y':
switch (resn[2]) { switch (resn[2]) {
case 'S': /* CYS */ case 'S': /* CYS */
case 'X': /* CYX */ case 'X': /* CYX */
return true; return true;
break; break;
} }
break; break;
} }
break; break;
case 'D':
switch (resn[1]) {
case 'G': /* DG */
switch (resn[2]) {
case 0:
return true;
break;
}
case 'C': /* DC */
switch (resn[2]) {
case 0:
return true;
break;
}
case 'T': /* DT */
switch (resn[2]) {
case 0:
return true;
break;
}
case 'A': /* DA */
switch (resn[2]) {
case 0:
return true;
break;
}
case 'U': /* DU */
switch (resn[2]) {
case 0:
return true;
break;
}
case 'I': /* DI */
switch (resn[2]) {
case 0:
return true;
break;
}
}
break;
case 'G': case 'G':
switch (resn[1]) { switch (resn[1]) {
case 0: /* G */
return true;
break;
case 'L': case 'L':
switch (resn[2]) { switch (resn[2]) {
case 'N': /* GLN */ case 'N': /* GLN */
return true; return true;
break; break;
case 'U': /* GLU */ case 'U': /* GLU */
return true; return true;
break; break;
case 'Y': /* GLY */ case 'Y': /* GLY */
return true; return true;
skipping to change at line 705 skipping to change at line 684
switch (resn[2]) { switch (resn[2]) {
case 'S': /* HIS */ case 'S': /* HIS */
case 'D': /* HID */ case 'D': /* HID */
case 'E': /* HIE */ case 'E': /* HIE */
case 'P': /* HIP */ case 'P': /* HIP */
return true; return true;
break; break;
} }
break; break;
} }
break;
case 'I': case 'I':
switch (resn[1]) { switch (resn[1]) {
case 'L': case 'L':
switch (resn[2]) { switch (resn[2]) {
case 'E': /* ILE */ case 'E': /* ILE */
return true; return true;
break; break;
} }
} }
break; break;
skipping to change at line 787 skipping to change at line 767
switch (resn[2]) { switch (resn[2]) {
case 'R': /* SER */ case 'R': /* SER */
return true; return true;
break; break;
} }
break; break;
} }
break; break;
case 'T': case 'T':
switch (resn[1]) { switch (resn[1]) {
case 0: /* T */
return true;
case 'H': case 'H':
switch (resn[2]) { switch (resn[2]) {
case 'R': /* THR */ case 'R': /* THR */
return true; return true;
break; break;
} }
break; break;
case 'R': case 'R':
switch (resn[2]) { switch (resn[2]) {
case 'P': /* TRP */ case 'P': /* TRP */
skipping to change at line 812 skipping to change at line 790
break; break;
case 'Y': case 'Y':
switch (resn[2]) { switch (resn[2]) {
case 'R': /* TYR */ case 'R': /* TYR */
return true; return true;
break; break;
} }
break; break;
} }
break; break;
case 'U':
switch (resn[1]) {
case 0: /* U */
return true;
break;
}
break;
case 'V': case 'V':
switch (resn[1]) { switch (resn[1]) {
case 'A': case 'A':
switch (resn[2]) { switch (resn[2]) {
case 'L': /* VAL */ case 'L': /* VAL */
return true; return true;
break; break;
} }
break; break;
} }
skipping to change at line 853 skipping to change at line 824
// return false if buffer too small // return false if buffer too small
bool AtomResiFromResv(char *resi, size_t size, int resv, char inscode) { bool AtomResiFromResv(char *resi, size_t size, int resv, char inscode) {
if (inscode > ' ') if (inscode > ' ')
return snprintf(resi, size, "%d%c", resv, inscode) < size; return snprintf(resi, size, "%d%c", resv, inscode) < size;
return snprintf(resi, size, "%d", resv) < size; return snprintf(resi, size, "%d", resv) < size;
} }
/*========================================================================*/ /*========================================================================*/
PyObject *AtomInfoAsPyList(PyMOLGlobals * G, const AtomInfoType * I) PyObject *AtomInfoAsPyList(PyMOLGlobals * G, const AtomInfoType * I)
{ {
#ifdef _PYMOL_NOPY
return NULL;
#else
PyObject *result = NULL; PyObject *result = NULL;
result = PyList_New(48); result = PyList_New(48);
int version = SettingGetGlobal_f(G, cSetting_pse_export_version) * 1000; int version = SettingGetGlobal_f(G, cSetting_pse_export_version) * 1000;
char resi[8]; char resi[8];
// at some point, change this to !version || ... // at some point, change this to !version || ...
if (version >= 1810) { if (version >= 1810) {
resi[0] = I->inscode; resi[0] = I->inscode;
skipping to change at line 922 skipping to change at line 890
const float anisou_stack[] {0.f, 0.f, 0.f, 0.f, 0.f, 0.f}; const float anisou_stack[] {0.f, 0.f, 0.f, 0.f, 0.f, 0.f};
const float * anisou = I->anisou ? I->anisou : anisou_stack; const float * anisou = I->anisou ? I->anisou : anisou_stack;
for (int i = 0; i < 6; ++i) { for (int i = 0; i < 6; ++i) {
PyList_SetItem(result, 41 + i, PyFloat_FromDouble(anisou[i])); PyList_SetItem(result, 41 + i, PyFloat_FromDouble(anisou[i]));
} }
PyList_SetItem(result, 47, PyString_FromString(LexStr(G, I->custom))); PyList_SetItem(result, 47, PyString_FromString(LexStr(G, I->custom)));
return (PConvAutoNone(result)); return (PConvAutoNone(result));
#endif
} }
int AtomInfoFromPyList(PyMOLGlobals * G, AtomInfoType * I, PyObject * list) int AtomInfoFromPyList(PyMOLGlobals * G, AtomInfoType * I, PyObject * list)
{ {
#ifdef _PYMOL_NOPY
return 0;
#else
int ok = true; int ok = true;
int tmp_int; int tmp_int;
ov_size ll = 0; ov_size ll = 0;
OrthoLineType temp = ""; OrthoLineType temp = "";
#define PCONVPYSTRTOLEXIDX(i, n) { \ #define PCONVPYSTRTOLEXIDX(i, n) { \
ok = CPythonVal_PConvPyStrToStr_From_List(G, list, i, temp, sizeof(OrthoLineTy pe)); \ ok = CPythonVal_PConvPyStrToStr_From_List(G, list, i, temp, sizeof(OrthoLineTy pe)); \
n = LexIdx(G, temp); } n = LexIdx(G, temp); }
if(ok) if(ok)
skipping to change at line 1060 skipping to change at line 1024
float u[6]; float u[6];
for (int i = 0; ok && i < 6; ++i) for (int i = 0; ok && i < 6; ++i)
ok = CPythonVal_PConvPyFloatToFloat_From_List(G, list, 41 + i, u + i); ok = CPythonVal_PConvPyFloatToFloat_From_List(G, list, 41 + i, u + i);
if(ok && (u[0] || u[1] || u[2] || u[3] || u[4] || u[5])) if(ok && (u[0] || u[1] || u[2] || u[3] || u[4] || u[5]))
memcpy(I->get_anisou(), u, 6 * sizeof(float)); memcpy(I->get_anisou(), u, 6 * sizeof(float));
} }
if(ok && (ll > 47)) { if(ok && (ll > 47)) {
PCONVPYSTRTOLEXIDX(47, I->custom); PCONVPYSTRTOLEXIDX(47, I->custom);
} }
return (ok); return (ok);
#endif
} }
void AtomInfoCopy(PyMOLGlobals * G, const AtomInfoType * src, AtomInfoType * dst , int copy_properties) void AtomInfoCopy(PyMOLGlobals * G, const AtomInfoType * src, AtomInfoType * dst , int copy_properties)
{ {
/* copy, handling resource management issues... */ /* copy, handling resource management issues... */
*dst = *src; *dst = *src;
dst->selEntry = 0; dst->selEntry = 0;
if(src->unique_id && src->has_setting) { if(src->unique_id && src->has_setting) {
dst->unique_id = AtomInfoGetNewUniqueID(G); dst->unique_id = AtomInfoGetNewUniqueID(G);
skipping to change at line 1288 skipping to change at line 1251
if(matchFlag && ((!flag1) || flag1[ai1 - atInfo1])) { if(matchFlag && ((!flag1) || flag1[ai1 - atInfo1])) {
if(c < 100) { if(c < 100) {
if((c < 10) && ai1->elem[1]) /* try to keep halogens 3 or under */ if((c < 10) && ai1->elem[1]) /* try to keep halogens 3 or under */
sprintf(name, "%2s%1d", ai1->elem, c); sprintf(name, "%2s%1d", ai1->elem, c);
else else
sprintf(name, "%1s%02d", ai1->elem, c); sprintf(name, "%1s%02d", ai1->elem, c);
} else { } else {
sprintf(name, "%1d%1s%02d", c / 100, ai1->elem, c % 100); sprintf(name, "%1d%1s%02d", c / 100, ai1->elem, c % 100);
} }
name[4] = 0; /* just is case we go over */
LexAssign(G, ai1->name, name); LexAssign(G, ai1->name, name);
result++; result++;
c = c + 1; c = c + 1;
} else { } else {
ai1++; ai1++;
b++; b++;
} }
} }
return result; return result;
} }
skipping to change at line 1903 skipping to change at line 1865
{"lawrencium", "Lr", 1.80, 262.110000}, {"lawrencium", "Lr", 1.80, 262.110000},
{"rutherfordium", "Rf", 1.80, 261.110000}, {"rutherfordium", "Rf", 1.80, 261.110000},
{"dubnium", "Db", 1.80, 262.110000}, {"dubnium", "Db", 1.80, 262.110000},
{"seaborgium", "Sg", 1.80, 266.120000}, {"seaborgium", "Sg", 1.80, 266.120000},
{"bohrium", "Bh", 1.80, 264.120000}, {"bohrium", "Bh", 1.80, 264.120000},
{"hassium", "Hs", 1.80, 269.130000}, {"hassium", "Hs", 1.80, 269.130000},
{"meitnerium", "Mt", 1.80, 268.140000}, {"meitnerium", "Mt", 1.80, 268.140000},
{"darmstadtium", "Ds", 1.80, 281.000000}, {"darmstadtium", "Ds", 1.80, 281.000000},
{"roentgenium", "Rg", 1.80, 281.000000}, {"roentgenium", "Rg", 1.80, 281.000000},
{"copernicium", "Cn", 1.80, 285.000000}, {"copernicium", "Cn", 1.80, 285.000000},
{"nihonium", "Nh", 1.80, 286.000000},
{"flerovium", "Fl", 1.80, 289.000000},
{"moscovium", "Mc", 1.80, 290.000000},
{"livermorium", "Lv", 1.80, 293.000000},
{"tennessine", "Ts", 1.80, 294.000000},
{"oganesson", "Og", 1.80, 294.000000},
{NULL, NULL, 0.00, 0.000000} {NULL, NULL, 0.00, 0.000000}
}; };
const int ElementTableSize = sizeof(ElementTable) / sizeof(ElementTable[0]) - 1; const int ElementTableSize = sizeof(ElementTable) / sizeof(ElementTable[0]) - 1;
/* /*
* Assign atomic color, or G->AtomInfo->CColor in case of carbon. * Assign atomic color, or G->AtomInfo->CColor in case of carbon.
*/ */
void AtomInfoAssignColors(PyMOLGlobals * G, AtomInfoType * at1) void AtomInfoAssignColors(PyMOLGlobals * G, AtomInfoType * at1)
{ {
skipping to change at line 2072 skipping to change at line 2040
if ((wc = WordCompare(G, at1->resn, at2->resn, true))) return wc; if ((wc = WordCompare(G, at1->resn, at2->resn, true))) return wc;
if (at1->discrete_state != at2->discrete_state) return (at1->discrete_state < at2->discrete_state) ? -1 : 1; if (at1->discrete_state != at2->discrete_state) return (at1->discrete_state < at2->discrete_state) ? -1 : 1;
// if this looks like a "bulk" het group with no residue number, then don't // if this looks like a "bulk" het group with no residue number, then don't
// compare by name/alt/priority (affects mmCIF with cif_use_auth=0) // compare by name/alt/priority (affects mmCIF with cif_use_auth=0)
if (!ignore_rank && !at1->resv && at1->hetatm) if (!ignore_rank && !at1->resv && at1->hetatm)
goto rank_compare; goto rank_compare;
if (at1->priority != at2->priority) return (at1->priority < at2->priority) ? - 1 : 1; if (at1->priority != at2->priority) return (at1->priority < at2->priority) ? - 1 : 1;
// empty alt code goes last: 'A' < 'B' < '' // Changed (PyMOL 2.1): name before alt
if ((wc = AtomInfoNameCompare(G, at1->name, at2->name))) return wc;
// Changed (PyMOL 2.1): empty alt goes first: '' < 'A' < 'B'
if (at1->alt[0] != at2->alt[0]) { if (at1->alt[0] != at2->alt[0]) {
if (!at2->alt[0]) return -1;
if (!at1->alt[0]) return 1;
return (at1->alt[0] < at2->alt[0]) ? -1 : 1; return (at1->alt[0] < at2->alt[0]) ? -1 : 1;
} }
if ((wc = AtomInfoNameCompare(G, at1->name, at2->name))) return wc;
rank_compare: rank_compare:
if (!ignore_rank && at1->rank != at2->rank) return (at1->rank < at2->rank) ? - 1 : 1; if (!ignore_rank && at1->rank != at2->rank) return (at1->rank < at2->rank) ? - 1 : 1;
return 0; return 0;
} }
int AtomInfoCompare(PyMOLGlobals * G, const AtomInfoType * at1, const AtomInfoTy pe * at2) int AtomInfoCompare(PyMOLGlobals * G, const AtomInfoType * at1, const AtomInfoTy pe * at2)
{ {
return AtomInfoCompare(G, at1, at2, false, false); return AtomInfoCompare(G, at1, at2, false, false);
} }
skipping to change at line 2107 skipping to change at line 2074
int AtomInfoCompareIgnoreRank(PyMOLGlobals * G, const AtomInfoType * at1, const AtomInfoType * at2) int AtomInfoCompareIgnoreRank(PyMOLGlobals * G, const AtomInfoType * at1, const AtomInfoType * at2)
{ {
return AtomInfoCompare(G, at1, at2, false, true); return AtomInfoCompare(G, at1, at2, false, true);
} }
int AtomInfoCompareIgnoreHet(PyMOLGlobals * G, const AtomInfoType * at1, const A tomInfoType * at2) int AtomInfoCompareIgnoreHet(PyMOLGlobals * G, const AtomInfoType * at1, const A tomInfoType * at2)
{ {
return AtomInfoCompare(G, at1, at2, true, false); return AtomInfoCompare(G, at1, at2, true, false);
} }
/*
* Function only used for matching atoms of two aligned residues.
*
* Changed (PyMOL 2.1):
* Consider alt codes to be equal if at least one is empty.
* Otherwise, alt-code (C-alpha) atoms can't be aligned to non-alt atoms
* (also affects morphing).
*/
int AtomInfoNameOrder(PyMOLGlobals * G, const AtomInfoType * at1, const AtomInfo Type * at2) int AtomInfoNameOrder(PyMOLGlobals * G, const AtomInfoType * at1, const AtomInfo Type * at2)
{ {
int result; int result;
if(at1->alt[0] == at2->alt[0]) { if(at1->alt[0] == at2->alt[0] || !at1->alt[0] || !at2->alt[0]) {
if(at1->priority == at2->priority) { if(at1->priority == at2->priority) {
result = AtomInfoNameCompare(G, at1->name, at2->name); result = AtomInfoNameCompare(G, at1->name, at2->name);
} else if(at1->priority < at2->priority) { } else if(at1->priority < at2->priority) {
result = -1; result = -1;
} else { } else {
result = 1; result = 1;
} }
} else if((!at2->alt[0]) || (at1->alt[0] && ((at1->alt[0] < at2->alt[0])))) { } else if(at1->alt[0] < at2->alt[0]) {
result = -1; result = -1;
} else { } else {
result = 1; result = 1;
} }
return (result); return (result);
} }
int AtomInfoSameResidue(PyMOLGlobals * G, const AtomInfoType * at1, const AtomIn foType * at2) int AtomInfoSameResidue(PyMOLGlobals * G, const AtomInfoType * at1, const AtomIn foType * at2)
{ {
return ( return (
skipping to change at line 2371 skipping to change at line 2346
if (lookup.empty()) { if (lookup.empty()) {
for (int i = 0; i < ElementTableSize; i++) for (int i = 0; i < ElementTableSize; i++)
lookup[ElementTable[i].symbol] = i; lookup[ElementTable[i].symbol] = i;
lookup["Q"] = cAN_H; lookup["Q"] = cAN_H;
lookup["D"] = cAN_H; lookup["D"] = cAN_H;
} }
// check second letter for lower case // check second letter for lower case
if (isupper(symbol[1])) { if (isupper(symbol[1]) && strcmp(symbol, "LP") != 0) {
UtilNCopy(titleized, symbol, 4); UtilNCopy(titleized, symbol, 4);
titleized[1] = tolower(symbol[1]); titleized[1] = tolower(symbol[1]);
symbol = titleized; symbol = titleized;
} }
// find in lookup dictionary // find in lookup dictionary
auto it = lookup.find(symbol); auto it = lookup.find(symbol);
if (it != lookup.end()) { if (it != lookup.end()) {
return it->second; return it->second;
skipping to change at line 2439 skipping to change at line 2414
// elem from protons (except for LP, assume protons=0 if uninitialized) // elem from protons (except for LP, assume protons=0 if uninitialized)
if(!*e && I->protons > 0) { if(!*e && I->protons > 0) {
atomicnumber2elem(e, I->protons); atomicnumber2elem(e, I->protons);
} }
// elem from name // elem from name
if(!*e) { /* try to guess atomic type from name */ if(!*e) { /* try to guess atomic type from name */
n = LexStr(G, I->name); n = LexStr(G, I->name);
while(((*n) >= '0') && ((*n) <= '9') && (*(n + 1))) while(((*n) >= '0') && ((*n) <= '9') && (*(n + 1)))
n++; n++;
while((((*n) >= 'A') && ((*n) <= 'Z')) || (((*n) >= 'a') && ((*n) <= 'z'))) strncpy(e, n, cElemNameLen);
{
*(e++) = *(n++);
}
*e = 0;
e = I->elem;
switch (*e) { switch (*e) {
case '\0':
break;
case 'C': case 'C':
if(*(e + 1) == 'A') { if(*(e + 1) == 'A') {
if(!WordMatchExact(G, G->lex_const.CA, I->resn, true) if(!WordMatchExact(G, G->lex_const.CA, I->resn, true)
&& (!WordMatchExact(G, "CA+", LexStr(G, I->resn), true))) && (!WordMatchExact(G, "CA+", LexStr(G, I->resn), true)))
/* CA intpreted as carbon, not calcium */
*(e + 1) = 0; *(e + 1) = 0;
} else if(!((*(e + 1) == 'a') || /* CA intpreted as carbon, not calcium * / } else if(!((*(e + 1) == 'a') || /* CA intpreted as carbon, not calcium * /
(*(e + 1) == 'l') || (*(e + 1) == 'L') || (*(e + 1) == 'l') || (*(e + 1) == 'L') ||
(*(e + 1) == 'u') || (*(e + 1) == 'U') || (*(e + 1) == 'u') || (*(e + 1) == 'U') ||
(*(e + 1) == 'o') || (*(e + 1) == 'O') || (*(e + 1) == 'o') || (*(e + 1) == 'O') ||
(*(e + 1) == 's') || (*(e + 1) == 'S') || (*(e + 1) == 's') || (*(e + 1) == 'S') ||
(*(e + 1) == 'r') || (*(e + 1) == 'R') (*(e + 1) == 'r') || (*(e + 1) == 'R')
)) ))
*(e + 1) = 0; *(e + 1) = 0;
break; break;
skipping to change at line 2490 skipping to change at line 2464
*(e + 1) = 0; *(e + 1) = 0;
break; break;
case 'O': case 'O':
if(!((*(e + 1) == 's'))) if(!((*(e + 1) == 's')))
*(e + 1) = 0; *(e + 1) = 0;
break; break;
case 'Q': case 'Q':
*(e + 1) = 0; *(e + 1) = 0;
break; break;
default:
break;
} }
if(*(e + 1)) if(*(e + 1) && (e[1] != 'P' || e[0] != 'L'))
*(e + 1) = tolower(*(e + 1)); *(e + 1) = tolower(*(e + 1));
} }
// priority // priority
n = LexStr(G, I->name); n = LexStr(G, I->name);
while((*n >= '0') && (*n <= '9') && (*(n + 1))) while((*n >= '0') && (*n <= '9') && (*(n + 1)))
n++; n++;
if(toupper(*n) != I->elem[0]) { if(toupper(*n) != I->elem[0]) {
pri = 1000; /* unconventional atom name -- make no assignmen ts */ pri = 1000; /* unconventional atom name -- make no assignmen ts */
} else if(SettingGetGlobal_b(G, cSetting_pdb_standard_order)) { } else if(SettingGetGlobal_b(G, cSetting_pdb_standard_order)) {
skipping to change at line 2825 skipping to change at line 2797
bt1->id != bt2->id || bt1->id != bt2->id ||
bt1->unique_id != bt2->unique_id || bt1->unique_id != bt2->unique_id ||
bt1->stereo != bt2->stereo || bt1->stereo != bt2->stereo ||
bt1->has_setting != bt2->has_setting); bt1->has_setting != bt2->has_setting);
} }
void atomicnumber2elem(char * dst, int protons) { void atomicnumber2elem(char * dst, int protons) {
if (protons > -1 && protons < ElementTableSize) if (protons > -1 && protons < ElementTableSize)
strncpy(dst, ElementTable[protons].symbol, cElemNameLen); strncpy(dst, ElementTable[protons].symbol, cElemNameLen);
} }
/*
* Get a string representation of the stereo configuration. Either
* R/S chirality, if set, or the SDF odd/even parity, if set.
*/
const char * AtomInfoGetStereoAsStr(const AtomInfoType * ai) {
switch (ai->mmstereo) {
case 1 /* MMSTEREO_CHIRALITY_R */: return "R";
case 2 /* MMSTEREO_CHIRALITY_S */: return "S";
}
switch (ai->stereo) {
case SDF_CHIRALITY_ODD: return "odd";
case SDF_CHIRALITY_EVEN: return "even";
}
if (ai->mmstereo || ai->stereo) {
return "?";
}
return "";
}
/*
* Set stereochemistry. Valid are: R, S, N[one], E[ven], O[dd]
*/
void AtomInfoSetStereo(AtomInfoType * ai, const char * stereo) {
switch (toupper(stereo[0])) {
case 'R': ai->mmstereo = 1; ai->stereo = 0; break; // MMSTEREO_CHIRALITY_R
case 'S': ai->mmstereo = 2; ai->stereo = 0; break; // MMSTEREO_CHIRALITY_S
case 'E': ai->mmstereo = 0; ai->stereo = SDF_CHIRALITY_EVEN; break;
case 'O': ai->mmstereo = 0; ai->stereo = SDF_CHIRALITY_ODD; break;
case 'N': case 0: ai->mmstereo = ai->stereo = 0; break;
default: ai->mmstereo = ai->stereo = 3; break;
}
}
/*
* Get column aligned (left space padded) PDB residue name
*
* resn: output buffer
*/
void AtomInfoGetAlignedPDBResidueName(PyMOLGlobals * G,
const AtomInfoType * ai,
ResName & resn)
{
sprintf(resn, "%3.4s", LexStr(G, ai->resn));
if(SettingGetGlobal_b(G, cSetting_pdb_truncate_residue_name)) {
resn[3] = 0; /* enforce 3-letter residue name in PDB files */
}
}
/*
* Get column aligned (left space padded) PDB atom name
*
* resn: space padded residue name
* name: output buffer
*/
void AtomInfoGetAlignedPDBAtomName(PyMOLGlobals * G,
const AtomInfoType * ai,
const ResName & resn,
AtomName & name)
{
int literal = SettingGetGlobal_b(G, cSetting_pdb_literal_names);
int reformat = SettingGetGlobal_i(G, cSetting_pdb_reformat_names_mode);
// default is "literal=0" and "reformat=0" (no reformatting)
const char * ai_name = LexStr(G, ai->name);
auto ai_name_len = strlen(ai_name);
bool start_column_1 = false;
UtilNCopy(name, ai_name, 5);
if(!ai->name) {
if(!ai->elem[1])
sprintf(name, " %s", ai->elem);
else
sprintf(name, "%s", ai->elem);
} else if(!literal) {
if(ai_name_len < 4) { /* atom name less than length 4 */
if(!isdigit(name[0])) { /* doesn't start with a number */
if((toupper(ai->elem[0]) == toupper(name[0])) && ((!ai->elem[1]) || /* s
ymbol len = 1 */
(toupper(ai->elem[1]) == toupper(name[1])))) { /* matched l
en 2 */
/* starts with corrent atomic symbol, so */
if(!ai->elem[1]) { /* symbol len = 1 */
switch (reformat) {
case 1: /* pdb with internal pdb */
case 3: /* pdb with internal iupac */
if((ai->elem[0] == 'H') && ai_name_len > 2) {
AtomInfoGetPDB3LetHydroName(G, resn, ai_name, name);
break;
}
default: /* otherwise, start in column 1 */
start_column_1 = true;
break;
}
}
} else { /* name doesn't start with atomic symbol */
/* then just place it in column 1 as usual */
start_column_1 = true;
}
} else { /* name starts with a number */
switch (reformat) {
case 2: /* make Amber compliant */
if((ai->elem[0] == name[1]) &&
((!ai->elem[1]) || (toupper(ai->elem[1]) == toupper(name[2])))) {
/* rotate the name to place atom symbol in column 0 to comply with A
mber PDB format */
name[3] = name[0];
name[0] = ' ';
}
break;
}
} /* just stick it in column 0 and hope for the be
st */
} else { /* if name is length 4 */
if((ai->elem[0] == name[0]) && ((!ai->elem[1]) || /* symbol len = 1 */
(toupper(ai->elem[1]) == toupper(name[
1])))) { /* matched len 2 */
/* name starts with the atomic symbol */
if((!ai->elem[1]) && (ai->elem[0])) { /* but if element is one letter.
.. */
switch (reformat) {
case 1: /* retaining PDB compliance throughout, or */
case 3: /* saving as PDB compliant, but use IUPAC within
PyMOL */
if(isdigit(name[3])) { /* and last character is a number */
/* rotate the name to place atom symbol in column 1 to comply with
PDB format */
name[0] = ai_name[3];
name[1] = ai_name[0];
name[2] = ai_name[1];
name[3] = ai_name[2];
name[4] = 0;
}
break;
}
}
} else { /* name does not start with the symbol... */
if(reformat == 2) { /* AMBER compliance mode */
if(isdigit(name[0])) {
if((ai->elem[0] == name[1]) &&
((!(ai->elem[1])) || (toupper(ai->elem[1]) == toupper(name[2]))))
{
/* rotate the name to place atom symbol in column 0 to comply with
Amber PDB format */
name[0] = ai_name[1];
name[1] = ai_name[2];
name[2] = ai_name[3];
name[3] = ai_name[0];
name[4] = 0;
}
}
}
}
}
} else { /* LITERAL mode: preserve what was in the origin
al PDB as best PyMOL can
this should enable people to open and save am
ber pdb files without issues */
if (ai_name_len < 4 && !(ai->elem[1] && /* elem len = 2 */
toupper(ai->elem[0]) == toupper(name[0]) &&
toupper(ai->elem[1]) == toupper(name[1]))) {
start_column_1 = true;
}
}
if (start_column_1) {
name[0] = ' ';
UtilNCopy(name + 1, ai_name, 4);
}
name[4] = 0;
}
 End of changes. 27 change blocks. 
83 lines changed or deleted 54 lines changed or added

Home  |  About  |  Features  |  All  |  Newest  |  Dox  |  Diffs  |  RSS Feeds  |  Screenshots  |  Comments  |  Imprint  |  Privacy  |  HTTP(S)