8a0ff4ba63dfd3e13391b2c602a157daaf54d665 kate Thu Mar 1 21:11:27 2012 -0800 Migrate ChipMatrix to refactoring 1 (dataMatrix.js) diff --git src/hg/js/encodeDataMatrix.js src/hg/js/encodeDataMatrix.js index 34685df..692b95b 100644 --- src/hg/js/encodeDataMatrix.js +++ src/hg/js/encodeDataMatrix.js @@ -1,263 +1,260 @@ /* encodeAssayMatrix.js - ENCODE Data Matrix application Pulls experiment table and metadata from server and displays in matrix of assay vs. cell type NOTE: $variables are jQuery objects Formatted: jsbeautify.py -j Syntax checked: jslint indent:4, plusplus: true, continue: true, unparam: true, sloppy: true, browser: true */ /*global $, encodeProject */ $(function () { var requests = [ // requests to server API encodeProject.serverRequests.experiment, encodeProject.serverRequests.dataType, encodeProject.serverRequests.cellType, encodeProject.serverRequests.expId ]; var $matrixTable = $('#matrixTable'); function handleServerData(responses) { // Main actions, called when loading data from server is complete // NOTE: ordering of responses is based on request order var experiments = responses[0], dataTypes = responses[1], cellTypes = responses[2], expIds = responses[3]; var dataGroups, cellTiers, expIdHash; var dataType, cellType; var matrix, dataTypeExps = {}; // hide spinner and show table encodeMatrix.show($matrixTable); // set up structures for data types and their groups // data type labels tucked into their tiers dataGroups = encodeProject.getDataGroups(dataTypes); // set up structures for cell types and their tiers cellTiers = encodeProject.getCellTiers(cellTypes); // use to filter out experiments not in this assembly expIdHash = encodeProject.getExpIdHash(expIds); // gather experiments into matrix // NOTE: dataTypeExps is populated here matrix = makeExperimentMatrix(experiments, expIdHash, dataTypeExps); // fill in table using matrix tableOut($matrixTable, matrix, cellTiers, dataGroups, dataTypeExps); } function makeExperimentMatrix(experiments, expIdHash, dataTypeExps) { // Populate dataType vs. cellType array with counts of experiments var dataType, cellType; var matrix = {}; $.each(experiments, function (i, exp) { // exclude ref genome annotations if (exp.cellType === 'None') { return true; } // exclude experiments lacking an expID (not in this assembly) if (expIdHash[exp.ix] === undefined) { return true; } // count experiments per dataType so we can prune those having none // (the matrix[cellType] indicates this for cell types // so don't need hash for those dataType = exp.dataType; if (dataTypeExps[dataType] === undefined) { - dataTypeExps[dataType] = 1; + dataTypeExps[dataType] = 0; } dataTypeExps[dataType]++; cellType = exp.cellType; if (!matrix[cellType]) { matrix[cellType] = {}; } if (!matrix[cellType][dataType]) { matrix[cellType][dataType] = 0; } matrix[cellType][dataType]++; }); return matrix; } function tableHeaderOut($table, dataGroups, dataTypeExps) { - // Generate table header and add to DOM + // Generate table header and add to document // NOTE: relies on hard-coded classes and ids var $tableHeader, $thead; var maxLen, dataType; // fill in column headers from dataTypes returned by server $tableHeader = $('#columnHeaders'); $thead = $('thead'); // 1st column is row headers // colgroups are needed to support cross-hair hover effect $thead.before('<colgroup></colgroup>'); $.each(dataGroups, function (i, group) { $tableHeader.append('<th class="groupType"><div class="verticalText">' + group.label + '</div></th>'); maxLen = Math.max(maxLen, group.label.length); - $thead.before('<colgroup></colgroup>'); $.each(group.dataTypes, function (i, label) { dataType = encodeProject.getDataTypeByLabel(label); // prune out datatypes with no experiments if (dataTypeExps[dataType.term] !== undefined) { $tableHeader.append('<th class="elementType" title="' + dataType.description + '"><div class="verticalText">' + dataType.label + '</div></th>'); // add colgroup element to support cross-hair hover effect - $thead.before('<colgroup class="dataTypeCol"></colgroup>'); + $thead.before('<colgroup class="experimentCol"></colgroup>'); maxLen = Math.max(maxLen, dataType.label.length); } }); }); // adjust size of headers based on longest label length // empirically len/2 em's is right $('#columnHeaders th').css('height', (String((maxLen/2 + 2)).concat('em'))); $('#columnHeaders th').css('width', '1em'); } function rowAddCells($row, dataGroups, dataTypeExps, matrix, cellType) { // populate a row in the matrix with cells for data groups and data types // null cellType indicates this is a row for a cell group (tier) var $td; - var dataType, url; $.each(dataGroups, function (i, group) { // skip group header $td = $('<td></td>'); $td.addClass('matrixCell'); $row.append($td); $.each(group.dataTypes, function (i, dataTypeLabel) { dataType = encodeProject.getDataTypeByLabel(dataTypeLabel).term; // prune out datatypes with no experiments if (dataTypeExps[dataType] === undefined) { return true; } $td = $('<td></td>'); $td.addClass('matrixCell'); $row.append($td); if (cellType === null) { return true; } if (!matrix[cellType][dataType]) { $td.addClass('todoExperiment'); return true; } // this cell represents experiments that // fill in count, mouseover and selection by click $td.addClass('experiment'); $td.text(matrix[cellType][dataType]); $td.data({ 'dataType' : dataType, 'cellType' : cellType }); $td.mouseover(function() { $(this).attr('title', 'Click to select: ' + encodeProject.getDataType($(this).data().dataType).label + ' ' + ' in ' + $(this).data().cellType +' cells'); }); $td.click(function() { - // TODO: base on preview ? var url = encodeMatrix.getSearchUrl(encodeProject.getAssembly()); // TODO: encapsulate var names url += ('&hgt_mdbVar1=dataType&hgt_mdbVal1=' + $(this).data().dataType + '&hgt_mdbVar2=cell&hgt_mdbVal2=' + $(this).data().cellType + '&hgt_mdbVar3=view&hgt_mdbVal3=Any'); // specifying window name limits open window glut window.open(url, "searchWindow"); }); }); }); } function tableMatrixOut($table, matrix, cellTiers, dataGroups, dataTypeExps) { // Fill in matrix -- // add rows with cell type labels (column 1) and cells for experiments // add sections for each Tier of cell type var maxLen, karyotype, cellType; var $row; $.each(cellTiers, function (i, tier) { //skip bogus 4th tier (not my property ?) if (tier === undefined) { return true; } $row = $('<tr class="matrix"><th class="groupType">' + "Tier " + tier.term + '</th></td></tr>'); rowAddCells($row, dataGroups, dataTypeExps, matrix, null); $table.append($row); - maxLen = 0; + $.each(tier.cellTypes, function (i, term) { if (!term) { return true; } if (!matrix[term]) { return true; } cellType = encodeProject.getCellType(term); // TODO: recognize cancer* // NOTE: coupled to CSS karyotype = cellType.karyotype; if (karyotype !== 'cancer' && karyotype !== 'normal') { karyotype = 'unknown'; } // note karyotype bullet layout requires non-intuitive placement // in code before the span that shows to it's left $row = $('<tr>' + '<th class="elementType">' + '<span style="float:right; text-align: right;" title="karyotype: ' + karyotype + '" class="karyotype ' + karyotype + '">•</span>' + '<span title="' + cellType.description + '"><a href="/cgi-bin/hgEncodeVocab?ra=encode/cv.ra&term=' + cellType.term + '">' + cellType.term + '</a>' + '</th>' ); maxLen = Math.max(maxLen, cellType.term.length); rowAddCells($row, dataGroups, dataTypeExps, matrix, cellType.term); $table.append($row); }); // adjust size of row headers based on longest label length $('tbody th').css('height', '1em'); $('tbody th').css('width', (String((maxLen/2 + 2)).concat('em'))); }); $('body').append($table); } function tableOut($table, matrix, cellTiers, dataGroups, dataTypeExps) { // Create table with rows for each cell types and columns for each data type, // based on matrix tableHeaderOut($table, dataGroups, dataTypeExps); tableMatrixOut($table, matrix, cellTiers, dataGroups, dataTypeExps); encodeMatrix.addTableFloatingHeader($table); encodeMatrix.rotateTableCells($table); encodeMatrix.hoverTableCrossHair($table); } // initialize application encodeMatrix.start($matrixTable); // load data from server and do callback encodeProject.loadAllFromServer(requests, handleServerData); });