3f93bb2b97119baf71d90dad97a8be00a4372382 braney Wed Oct 8 16:07:53 2014 -0700 fix bug in mapBox placement when passing in negative numbers diff --git src/hg/hgTracks/snakeTrack.c src/hg/hgTracks/snakeTrack.c index 98abfec..110d2d1 100644 --- src/hg/hgTracks/snakeTrack.c +++ src/hg/hgTracks/snakeTrack.c @@ -730,30 +730,55 @@ }; static int snakePalette[] = { 0x1f77b4, 0xff7f0e, 0x2ca02c, 0xd62728, 0x9467bd, 0x8c564b, 0xe377c2, 0x7f7f7f, 0xbcbd22, 0x17becf }; static Color hashColor(char *name) { bits32 hashVal = hashString(name); unsigned int colorInt = snakePalette2[hashVal % (sizeof(snakePalette2)/sizeof(Color))]; return MAKECOLOR_32(((colorInt >> 16) & 0xff),((colorInt >> 8) & 0xff),((colorInt >> 0) & 0xff)); } +static void boundMapBox(struct hvGfx *hvg, int start, int end, int x, int y, int width, int height, + char *track, char *item, char *statusLine, char *directUrl, boolean withHgsid, + char *extra) +// make sure start x and end x position are on the screen +// otherwise the tracking box code gets confused +{ +if (x > insideWidth) + return; + +if (x < 0) + { + width -= -x; + x = 0; + } + +if (x + width > insideWidth) + { + width -= x + width - insideWidth; + } + +mapBoxHgcOrHgGene(hvg, start, end, x, y, width, height, + track, item, statusLine, directUrl, withHgsid, + extra); +} + static void snakeDrawAt(struct track *tg, void *item, struct hvGfx *hvg, int xOff, int y, double scale, MgFont *font, Color color, enum trackVisibility vis) /* Draw a single simple bed item at position. */ { unsigned showSnpWidth = cartOrTdbInt(cart, tg->tdb, SNAKE_SHOW_SNP_WIDTH, SNAKE_DEFAULT_SHOW_SNP_WIDTH); struct linkedFeatures *lf = (struct linkedFeatures *)item; if (tg->visibility == tvFull) calcFullSnake(tg, item); else if (tg->visibility == tvPack) calcPackSnake(tg, item); @@ -911,31 +936,31 @@ if (vis == tvFull) safef(buffer, sizeof buffer, "%d-%d",sf->qStart,sf->qEnd); else safef(buffer, sizeof buffer, "%s:%d-%d",sf->qName,sf->qStart,sf->qEnd); if (sx < insideX) { int olap = insideX - sx; sx = insideX; w -= olap; } char qAddress[4096]; if ((vis == tvFull) || (vis == tvPack) ) { safef(qAddress, sizeof qAddress, "qName=%s&qs=%d&qe=%d&qWidth=%d",sf->qName, qs, qe, winEnd - winStart); - mapBoxHgcOrHgGene(hvg, s, e, sx+1, y, w-2, heightPer, tg->track, + boundMapBox(hvg, s, e, sx+1, y, w-2, heightPer, tg->track, buffer, buffer, NULL, TRUE, qAddress); } hvGfxBox(hvg, sx, y, w, heightPer, color); // now draw the mismatches if we're at high enough resolution if ((isHalSnake && sf->qSequence != NULL) && (winBaseCount < showSnpWidth) && ((vis == tvFull) || (vis == tvPack))) { char *twoBitString = trackDbSetting(tg->tdb, "twoBit"); static struct twoBitFile *tbf = NULL; static char *lastTwoBitString = NULL; static struct dnaSeq *seq = NULL; static char *lastQName = NULL; // sequence for chain snakes is in 2bit files which we cache if (!isHalSnake) @@ -1065,96 +1090,96 @@ { char buffer[1024]; #define MG_ORANGE 0xff0082E6 int color = MG_GRAY; if (lastQEnd != qs) color = MG_ORANGE; // draw the vertical orange bars if there is an insert in the other sequence if ((winBaseCount < showSnpWidth) ) { if ((sf->orientation == 1) && (qs != lastQEnd) && (lastE == s)) { hvGfxLine(hvg, sx, y2 - lineHeight/2 , sx, y2 + lineHeight/2, MG_ORANGE); safef(buffer, sizeof buffer, "%dbp", qs - lastQEnd); - mapBoxHgcOrHgGene(hvg, s, e, sx, y2 - lineHeight/2, 1, lineHeight, tg->track, + boundMapBox(hvg, s, e, sx, y2 - lineHeight/2, 1, lineHeight, tg->track, "foo", buffer, NULL, TRUE, NULL); } else if ((sf->orientation == -1) && (qs != lastQEnd) && (lastS == e)) { hvGfxLine(hvg, ex, y2 - lineHeight/2 , ex, y2 + lineHeight/2, MG_ORANGE); safef(buffer, sizeof buffer, "%dbp", qs - lastQEnd); - mapBoxHgcOrHgGene(hvg, s, e, ex, y2 - lineHeight/2, 1, lineHeight, tg->track, + boundMapBox(hvg, s, e, ex, y2 - lineHeight/2, 1, lineHeight, tg->track, "foo", buffer, NULL, TRUE, NULL); } } // now draw the lines between blocks if ((!((lastX == sx) && (y1 == y2))) && (sf->drawn || ((prevSf != NULL) && (prevSf->drawn))) && (((lastE >= winStart) && (lastE <= winEnd)) || ((s > winStart) && (s < winEnd)))) { if (lastLevel == sf->level) { safef(buffer, sizeof buffer, "%dbp", qs - lastQEnd); if (sf->orientation == -1) { if (lastX != ex) { hvGfxLine(hvg, ex, y1, lastX, y2, color); - mapBoxHgcOrHgGene(hvg, s, e, ex, y1, lastX-ex, 1, tg->track, + boundMapBox(hvg, s, e, ex, y1, lastX-ex, 1, tg->track, "", buffer, NULL, TRUE, NULL); } } else { if (lastX != sx) { hvGfxLine(hvg, lastX, y1, sx, y2, color); - mapBoxHgcOrHgGene(hvg, s, e, lastX, y1, sx-lastX, 1, tg->track, + boundMapBox(hvg, s, e, lastX, y1, sx-lastX, 1, tg->track, "", buffer, NULL, TRUE, NULL); } } } else if (lastLevel > sf->level) { hvGfxLine(hvg, lastX, y1, sx, y2, color); hvGfxLine(hvg, sx, y2, sx, y2 - lineHeight - lineHeight/3, color); char buffer[1024]; safef(buffer, sizeof buffer, "%d-%d %dbp gap",prevSf->qStart,prevSf->qEnd, qs - lastQEnd); - mapBoxHgcOrHgGene(hvg, s, e, sx, y2 - lineHeight - lineHeight/3, 2, lineHeight + lineHeight/3, tg->track, + boundMapBox(hvg, s, e, sx, y2 - lineHeight - lineHeight/3, 2, lineHeight + lineHeight/3, tg->track, "", buffer, NULL, TRUE, NULL); } else { char buffer[1024]; safef(buffer, sizeof buffer, "%d-%d %dbp gap",prevSf->qStart,prevSf->qEnd, qs - lastQEnd); if (sf->orientation == -1) { hvGfxLine(hvg, lastX-1, y1, ex, y2, color); hvGfxLine(hvg, ex, y2, ex, y2 + lineHeight , color); - mapBoxHgcOrHgGene(hvg, s, e, ex-1, y2, 2, lineHeight , tg->track, + boundMapBox(hvg, s, e, ex-1, y2, 2, lineHeight , tg->track, "", buffer, NULL, TRUE, NULL); } else { hvGfxLine(hvg, lastX-1, y1, sx, y2, color); hvGfxLine(hvg, sx, y2, sx, y2 + lineHeight , color); - mapBoxHgcOrHgGene(hvg, s, e, sx-1, y2, 2, lineHeight , tg->track, + boundMapBox(hvg, s, e, sx-1, y2, 2, lineHeight , tg->track, "", buffer, NULL, TRUE, NULL); } } } } tEnd = e; tStart = s; qStart = sf->qStart; if (sf->orientation == -1) lastX = sx; else lastX = ex; lastS = s; lastE = e;