8cb0eb5850ff9883a1a278c1607998f0a6046bcb max Thu Aug 4 08:56:32 2016 -0700 adding internal ability to draw multiple highlights. refs #14951. There is no way to set these currently in the UI, as this would be a whole project of its own. Also, in multi-exon mode, it will only draw the first region, if multiple ones are defined. diff --git src/hg/hgTracks/hgTracks.c src/hg/hgTracks/hgTracks.c index 216be7e..d7916a8 100644 --- src/hg/hgTracks/hgTracks.c +++ src/hg/hgTracks/hgTracks.c @@ -2085,65 +2085,79 @@ static void rAddToTrackHash(struct hash *trackHash, struct track *trackList) /* Add list and any children of list to hash. */ { struct track *track; for (track = trackList; track != NULL; track = track->next) { hashAddUnique(trackHash, track->track, track); rAddToTrackHash(trackHash, track->subtracks); } } struct highlightVar // store highlight information { +struct highlightVar *next; char *db; char *chrom; long chromStart; long chromEnd; char *hexColor; }; struct highlightVar *parseHighlightInfo() -// Parse highlight info from cart var -// db.chrom:start-end#hexColor +// Parse highlight info from cart var to a linked list of highlightVar structs +// db.chrom:start-end#hexColor|db.chrom:start-end#hexColor|... { -struct highlightVar *h = NULL; +struct highlightVar *hlList = NULL; char *highlightDef = cartOptionalString(cart, "highlight"); if(highlightDef) { + char *hlArr[256]; + int hlCount = chopByChar(cloneString(highlightDef), '|', hlArr, ArraySize(hlArr)); + int i; + for (i=0; i<hlCount; i++) + { + char *oneHl = hlArr[i]; + struct highlightVar *h; AllocVar(h); - h->db = cloneNextWordByDelimiter(&highlightDef,'.'); - h->chrom = cloneNextWordByDelimiter(&highlightDef,':'); + h->db = cloneNextWordByDelimiter(&oneHl,'.'); + h->chrom = cloneNextWordByDelimiter(&oneHl,':'); // long to handle virt chrom coordinates - h->chromStart = atol(cloneNextWordByDelimiter(&highlightDef,'-')); - h->chromEnd = atol(cloneNextWordByDelimiter(&highlightDef,'#')); + h->chromStart = atol(cloneNextWordByDelimiter(&oneHl,'-')); + h->chromEnd = atol(cloneNextWordByDelimiter(&oneHl,'#')); h->chromStart--; // Not zero based if (highlightDef && *highlightDef != '\0') - h->hexColor = cloneString(highlightDef); + h->hexColor = cloneString(oneHl); + slAddHead(&hlList, h); + } + slReverse(&hlList); } -return h; +return hlList; } -void highlightRegion(struct cart *cart, struct hvGfx *hvg, int imagePixelHeight) -// Highlights a region in the image. Only done if theImgBox is not defined. +static void highlightRegions(struct cart *cart, struct hvGfx *hvg, int imagePixelHeight) +// Highlights regions in the image. Only done if theImgBox is not defined. // Thus it is done for ps/pdf and view image but the hgTracks image is highlighted via js { -struct highlightVar *h = parseHighlightInfo(); +struct highlightVar *hlList = parseHighlightInfo(); -if(h && theImgBox == NULL) // Only highlight region when imgBox is not used. (pdf and show-image) +if(hlList && theImgBox == NULL) // Only highlight region when imgBox is not used. (pdf and show-image) + { + struct highlightVar *h; + for (h=hlList; h; h=h->next) { if (virtualSingleChrom()) // DISGUISE VMODE { if ((h->db && sameString(h->db, database)) && (h->chrom && sameString(h->chrom,chromName))) { char position[1024]; safef(position, sizeof position, "%s:%ld-%ld", h->chrom, h->chromStart, h->chromEnd); char *newPosition = undisguisePosition(position); // UN-DISGUISE VMODE if (startsWith("virt:", newPosition)) { parseVPosition(newPosition, &h->chrom, &h->chromStart, &h->chromEnd); } } } @@ -2164,30 +2178,31 @@ if (width < 2) width = 2; // Default color to light blue, but if setting has color, use it. unsigned int hexColor = MAKECOLOR_32(170, 255, 255); if (h->hexColor) { long rgb = strtol(h->hexColor,NULL,16); // Big and little Endians hexColor = MAKECOLOR_32( ((rgb>>16)&0xff), ((rgb>>8)&0xff), (rgb&0xff) ); } hvGfxBox(hvg, fullInsideX + startPixels, 0, width, imagePixelHeight, hexColor); } } } +} struct hash *makeGlobalTrackHash(struct track *trackList) /* Create a global track hash and returns a pointer to it. */ { trackHash = newHash(8); rAddToTrackHash(trackHash, trackList); return trackHash; } //void domAddMenu(char *afterMenuId, char *newMenuId, char *label) ///* Append a new drop down menu after a given menu, by changing the DOM with jquery */ //{ //printf("$('#%s').last().after('<li class=\"menuparent\" id=\"%s\"><span>%s</span>" // "<ul style=\"display: none; visibility: hidden;\"></ul></li>');\n", // afterMenuId, newMenuId, label); @@ -4653,31 +4668,31 @@ hvgSide = hvGfxOpenPng(pixWidth, pixHeight, pngTnSide.forCgi, transparentImage); // Also add the side image theSideImg = imgBoxImageAdd(theImgBox,pngTnSide.forHtml,NULL,pixWidth, pixHeight,FALSE); hvgSide->rc = revCmplDisp; initColors(hvgSide); } } hvg->rc = revCmplDisp; initColors(hvg); /* Start up client side map. */ hPrintf("<MAP id='map' Name=%s>\n", mapName); if (theImgBox == NULL) // imageV2 highlighting is done by javascript. This does pdf and view-image highlight - highlightRegion(cart, hvg, imagePixelHeight); + highlightRegions(cart, hvg, imagePixelHeight); for (window=windows; window; window=window->next) { /* Find colors to draw in. */ findTrackColors(hvg, window->trackList); } // Good to go ahead and add all imgTracks regardless of buttons, left label, centerLabel, etc. if (theImgBox) { if (rulerMode != tvHide) { curImgTrack = imgBoxTrackFindOrAdd(theImgBox,NULL,RULER_TRACK_NAME,rulerMode,FALSE, IMG_FIXEDPOS); // No tdb, no centerLbl, not reorderable