03d6935afd1f21e64a308f28fe738cd22c0c5b25
chmalee
  Mon Feb 9 14:05:16 2026 -0800
hgGateway: rename category labels in the 'recents' section. external hub clicks on cards no longer remain selected after clicking. GenArk and native dbs are handled the same for UI purposes, refs #34078

diff --git src/hg/js/hgGateway.js src/hg/js/hgGateway.js
index 3889fc2d98f..902abde49e2 100644
--- src/hg/js/hgGateway.js
+++ src/hg/js/hgGateway.js
@@ -329,32 +329,32 @@
                                          title: hub.longLabel
 				     });
 	text.onclick = function() {hgGateway.onClickHubName(hub.hubUrl, hub.taxId, hub.defaultDb, hub.name);};
         svg.appendChild(text);
     }
 
     function drawHubs(svg, hubList, yIn) {
         // Add a label for each hub in hubList, with a separator line below and
         // "Hub Genomes" link instead of a tree.
         var y = yIn;
         var hub, i, textX, textY, lineX1, lineY, lineX2;
         var countNonCurated = 0;
         if (hubList && hubList.length) {
             for (i = 0;  i < hubList.length;  i++) {
                 hub = hubList[i];
-                // is this a curated assembly hub? If so, don't list it
-                if (!(hub.hubUrl.startsWith("/gbdb") && ! hub.hubUrl.startsWith("/gbdb/genark"))) {
+                // Skip UCSC-hosted hubs (native and GenArk) under /gbdb
+                if (!hub.hubUrl.startsWith("/gbdb")) {
                     addHubLabel(svg, hub, y);
                     y += cfg.labelLineHeight;
                     countNonCurated++;
                 }
             }
             if (countNonCurated) {
                 textX = cfg.labelRightX + cfg.speciesLineOffsetX;
                 textY = (yIn + y - cfg.labelLineHeight) / 2;
                 addTrackHubsLink(svg, textX, textY);
                 lineX1 = cfg.hubLineOffset;
                 lineY = y - cfg.halfTextHeight;
                 lineX2 = cfg.containerWidth - cfg.speciesLineOffsetX;
                 addLine(svg, lineX1, lineY, lineX2, lineY);
                 y += cfg.labelLineHeight;
             }
@@ -1116,36 +1116,36 @@
 
     function addHubsToList(hubList) {
         // Render connected hubs into the connected hubs section
         // Only show the section if there are non-curated hubs to display
         var $title = $('#connectedHubsTitle');
         var $section = $('#connectedHubsSection');
         var $panel = $('#connectedHubsList');
 
         if (!hubList || hubList.length === 0) {
             // No hubs, hide the section
             $title.hide();
             $section.hide();
             return;
         }
 
-        // Filter out curated assembly hubs (those in /gbdb but not /gbdb/genark)
-        // and convert hub objects to card-compatible format
+        // Filter out UCSC-hosted hubs (native and GenArk) under /gbdb
+        // and convert remaining hub objects to card-compatible format
         var displayHubs = [];
         hubList.forEach(function(hub) {
-            // Skip curated assembly hubs (same logic as drawHubs)
-            if (hub.hubUrl.startsWith("/gbdb") && !hub.hubUrl.startsWith("/gbdb/genark")) {
+            // Skip UCSC-hosted hubs (native and GenArk) under /gbdb
+            if (hub.hubUrl.startsWith("/gbdb")) {
                 return;
             }
             // Convert hub object to card-compatible format
             var hubItem = {
                 label: hub.shortLabel + ' (' + hub.assemblyCount + ' assembl' +
                        (hub.assemblyCount === 1 ? 'y' : 'ies') + ')',
                 genome: hub.defaultDb,
                 category: 'Assembly Hub',
                 hubUrl: hub.hubUrl,
                 taxId: hub.taxId,
                 db: hub.defaultDb,
                 hubName: hub.name,
                 longLabel: hub.longLabel
             };
             displayHubs.push(hubItem);
@@ -1486,65 +1486,69 @@
             if (!isGenomeAtFrontOfRecents(dbForRecents)) {
                 // Construct a descriptive label that includes the db/accession for identification
                 var label = uiState.genomeLabel || uiState.genome;
                 if (label && dbForRecents && label.indexOf(dbForRecents) < 0) {
                     // Add the db/accession to the label if not already present
                     label = label + ' (' + dbForRecents + ')';
                 }
                 var recentItem = {
                     db: dbForRecents,
                     genome: uiState.genome,
                     label: label,
                     taxId: uiState.taxId
                 };
                 if (uiState.hubUrl) {
                     recentItem.hubUrl = uiState.hubUrl;
-                    // For hub genomes, add category for proper detection when re-selected
-                    if (dbForRecents.startsWith('GCA_') || dbForRecents.startsWith('GCF_')) {
-                        recentItem.category = "UCSC GenArk";
+                    if (uiState.hubUrl.startsWith("/gbdb")) {
+                        recentItem.category = "UCSC Curated";
+                    } else {
+                        recentItem.category = "Assembly Hub";
                     }
+                } else {
+                    recentItem.category = "UCSC Curated";
                 }
                 addRecentGenome(recentItem);
             }
             displayRecentGenomesInPanel();
         } else {
             console.log('handleSetDb ignoring: ' + trackHubSkipHubName(jsonData.db) +
                         ' !== ' + trackHubSkipHubName(uiState.db));
         }
     }
 
     function handleSetTaxId(jsonData) {
         // Handle the server's response to the setTaxId cartJson command.
         if (checkJsonData(jsonData, 'handleSetTaxId') && jsonData.taxId === uiState.taxId) {
             // Update uiState with new values and update the page:
             _.assign(uiState, jsonData);
             updateFindPositionSection(uiState);
             // Save to recent genomes only if not already at the front (autocompleteCat.js may have just added it)
             // Use db without hub prefix for consistent key comparison
             var dbForRecents = trackHubSkipHubName(uiState.db);
             if (!isGenomeAtFrontOfRecents(dbForRecents)) {
                 // Construct a descriptive label that includes the db for identification
                 var label = uiState.genomeLabel || uiState.genome;
                 if (label && dbForRecents && label.indexOf(dbForRecents) < 0) {
                     // Add the db to the label if not already present
                     label = label + ' (' + dbForRecents + ')';
                 }
                 addRecentGenome({
                     db: dbForRecents,
                     genome: uiState.genome,
                     label: label,
-                    taxId: uiState.taxId
+                    taxId: uiState.taxId,
+                    category: "UCSC Curated"
                 });
             }
             displayRecentGenomesInPanel();
         } else {
             console.log('handleSetTaxId ignoring: ' + jsonData.taxId +
                         ' !== ' + uiState.taxId);
         }
     }
 
     // UI Event Handlers
 
     function clearWatermarkInput($input, watermark) {
         // Note: it is not necessary to re-.Watermark if we upgrade the plugin to version >= 3.1
         $input.css('color', 'black');
         $input.val('').Watermark(watermark ,'#686868');
@@ -1823,72 +1827,73 @@
         $panel.empty();
 
         if (!items || items.length === 0) {
             if (emptyMessage) {
                 $panel.html('<div class="recentGenomesEmpty">' + emptyMessage + '</div>');
             }
             return;
         }
 
         var clickHandler = onCardClick || setDbFromAutocomplete;
 
         // Render each item as a card (vertical layout)
         items.forEach(function(item) {
             var $card = $('<div class="recentGenomeCard"></div>');
             var label = item.label || item.shortLabel || item.value || item.genome || item.commonName;
-            var genome = item.genome || item.db || '';
+            var genome = trackHubSkipHubName(item.genome || item.db || '');
 
             $card.append('<div class="recentGenomeLabel">' + escapeHtml(label) + '</div>');
             if (genome && label.indexOf(genome) < 0) {
                 $card.append('<div class="recentGenomeDb">' + escapeHtml(genome) + '</div>');
             }
 
-            // Add category as small label
-            if (item.category) {
-                var shortCategory = item.category;
-                if (shortCategory.indexOf('UCSC Genome Browser') >= 0) {
-                    shortCategory = 'UCSC';
-                } else if (shortCategory.indexOf('GenArk') >= 0) {
-                    shortCategory = 'GenArk';
-                } else if (shortCategory.indexOf('Assembly Hub') >= 0) {
-                    shortCategory = 'Hub';
+            // Add category label: "External" for assembly hubs, "UCSC Curated" for everything else.
+            // The indexOf check handles both the new "Assembly Hub" category from handleSetDb
+            // and legacy localStorage entries from addHubsToList or older code.
+            var shortCategory;
+            if (item.category && item.category.indexOf('Assembly Hub') >= 0) {
+                shortCategory = 'External';
+            } else {
+                shortCategory = 'UCSC Curated';
             }
             $card.append('<div class="recentGenomeCategory">' + escapeHtml(shortCategory) + '</div>');
-            }
 
             // Store item data for click handler
             $card.data('item', item);
             $card.on('click', function() {
                 var clickedItem = $(this).data('item');
                 clickHandler(clickedItem);
                 // Highlight selected card in this panel
                 $panel.find('.recentGenomeCard').removeClass('selected');
                 $(this).addClass('selected');
             });
 
             $panel.append($card);
         });
     }
 
     function displayRecentGenomesInPanel() {
         // Display recent genomes in the panel on page load and after genome selection
         var recentGenomes = getRecentGenomes();
         // Show the section (hidden by default in HTML)
         $('#recentGenomesTitle').show();
         $('#recentGenomesSection').show();
         var emptyMessage = 'Search for a genome above, or click a popular species icon';
         renderGenomeCards(recentGenomes, $('#recentGenomesList'), emptyMessage);
+        // Clear any selected state from connected hub cards (selection was transient,
+        // the genome is now reflected in the recent genomes panel)
+        $('#connectedHubsList .recentGenomeCard').removeClass('selected');
     }
 
     function escapeHtml(text) {
         // Simple HTML escape for display
         if (!text) return '';
         return String(text)
             .replace(/&/g, '&amp;')
             .replace(/</g, '&lt;')
             .replace(/>/g, '&gt;')
             .replace(/"/g, '&quot;');
     }
 
     function init() {
         // Boot up the page; initialize elements and install event handlers.
         var searchObj = {};