d3752edc12da1bf08427946150f564dbdd5d2254 angie Thu Oct 24 13:55:51 2019 -0700 bigDbSnp track handler code - initial commit. refs #23283 * dnautil: Added trimRefAltLeft to get left-justified trimming (a la VCF not HGVS). * bigBedClick: do hReplaceGbdb up front in parseDetailsTablUrls instead of waiting until endpoint. * trackDbCustom.c: consolidating type-handling for wig/bigWig vs. bigBed-based big*. diff --git src/lib/dnautil.c src/lib/dnautil.c index 9ee6d78..cf82e9e 100644 --- src/lib/dnautil.c +++ src/lib/dnautil.c @@ -1200,49 +1200,81 @@ char aaUC = toupper(aa); int ix; for (ix = 0; ix < ArraySize(aminoAcidTable); ix++) { if (aaUC == aminoAcidTable[ix].letter) { // safencpy(...3) is required here because aminoAcidTable.abbreviation is char[3] not [4] safencpy(abbrBuf, abbrBufSize, aminoAcidTable[ix].abbreviation, 3); abbrBuf[0] = toupper(abbrBuf[0]); return; } } safef(abbrBuf, abbrBufSize, "?%c?", aa); } -void trimRefAlt(char *ref, char *alt, uint *pStart, uint *pEnd, int *pRefLen, int *pAltLen) +void trimRefAltDir(char *ref, char *alt, uint *pStart, uint *pEnd, int *pRefLen, int *pAltLen, + boolean leftJustify) /* If ref and alt have identical bases at beginning and/or end, trim those & update all params. */ { -int trimStart = 0; -while (ref[trimStart] != '\0' && alt[trimStart] != '\0' && ref[trimStart] == alt[trimStart]) - trimStart++; +int trimStart = 0, trimEnd = 0; int refLen = strlen(ref); int altLen = strlen(alt); -int iR = refLen - 1, iA = altLen - 1, trimEnd = 0; +if (leftJustify) + { + // first trim end, then start + while (refLen > 0 && altLen > 0 && ref[refLen-1] == alt[altLen-1]) + { + (*pEnd)--; + refLen--; + altLen--; + ref[refLen] = 0; + alt[altLen] = 0; + } + while (ref[trimStart] != '\0' && alt[trimStart] != '\0' && ref[trimStart] == alt[trimStart]) + trimStart++; + } +else + { + // first trim start, then end + while (ref[trimStart] != '\0' && alt[trimStart] != '\0' && ref[trimStart] == alt[trimStart]) + trimStart++; + int iR = refLen - 1, iA = altLen - 1; while (iR >= trimStart && iA >= trimStart && ref[iR] == alt[iA]) { iR--; iA--; trimEnd++; } + } if (trimEnd) { *pEnd -= trimEnd; refLen -= trimEnd; altLen -= trimEnd; ref[refLen] = '\0'; alt[altLen] = '\0'; } if (trimStart) { *pStart += trimStart; refLen -= trimStart; altLen -= trimStart; memmove(ref, ref+trimStart, refLen+1); memmove(alt, alt+trimStart, altLen+1); } *pRefLen = refLen; *pAltLen = altLen; } + +void trimRefAlt(char *ref, char *alt, uint *pStart, uint *pEnd, int *pRefLen, int *pAltLen) +/* If ref and alt have identical bases at beginning and/or end, trim those & update all params. */ +{ +trimRefAltDir(ref, alt, pStart, pEnd, pRefLen, pAltLen, FALSE); +} + +void trimRefAltLeft(char *ref, char *alt, uint *pStart, uint *pEnd, int *pRefLen, int *pAltLen) +/* If ref and alt have identical bases at beginning and/or end, trim those starting on the right + * so we get the leftmost representation & update all params. */ +{ +trimRefAltDir(ref, alt, pStart, pEnd, pRefLen, pAltLen, TRUE); +}