diff --git a/browser/src/GenePage/GenePage.tsx b/browser/src/GenePage/GenePage.tsx index 15be9baa8..fdab3431d 100644 --- a/browser/src/GenePage/GenePage.tsx +++ b/browser/src/GenePage/GenePage.tsx @@ -528,6 +528,7 @@ const GenePage = ({ datasetId, gene, geneId }: Props) => { {hasCodingExons && gene.chrom !== 'M' && gene.pext && ( { +}: GeneTranscriptsTrack) => { const transcriptsTrack = useRef(null) + const gtexTissues = GTEX_TISSUES[getTopLevelDataset(datasetId)] + const isTissueExpressionAvailable = gene.reference_genome === 'GRCh37' const [showTissueExpressionModal, setShowTissueExpressionModal] = useState(false) const maxMeanExpression = isTissueExpressionAvailable ? max( - gene.transcripts.map((transcript: any) => - mean(Object.values(transcript.gtex_tissue_expression)) + // @ts-ignore + gene.transcripts.map((transcript: Transcript) => + mean(transcript.gtex_tissue_expression!.map((tissue) => tissue.value)) ) ) : undefined @@ -146,10 +150,7 @@ const GeneTranscriptsTrack = ({ // @ts-expect-error TS(2322) FIXME: Type '{ children: Element; tooltip: string; }' is ... Remove this comment to see the full error message tooltip={`Mean expression across all tissues = ${meanExpression.toFixed( 2 - )} TPM\nMost expressed in ${ - // @ts-expect-error TS(2538) FIXME: Type 'undefined' cannot be used as an index type. - GTEX_TISSUE_NAMES[tissueMostExpressedIn] - } (${ + )} TPM\nMost expressed in ${gtexTissues[tissueMostExpressedIn].fullName} (${ // @ts-expect-error TS(2532) FIXME: Object is possibly 'undefined'. maxExpression.toFixed(2) } TPM)`} diff --git a/browser/src/GenePage/TissueExpressionTrack.tsx b/browser/src/GenePage/TissueExpressionTrack.tsx index b83a13efa..c44ec8b1e 100644 --- a/browser/src/GenePage/TissueExpressionTrack.tsx +++ b/browser/src/GenePage/TissueExpressionTrack.tsx @@ -9,12 +9,15 @@ import { Track } from '@gnomad/region-viewer' import { RegionsPlot } from '@gnomad/track-regions' import { Badge, Button, Modal, SearchInput, Select, TooltipAnchor } from '@gnomad/ui' -import { GTEX_TISSUE_COLORS, GTEX_TISSUE_NAMES } from '../gtex' +import { Transcript } from '../TranscriptPage/TranscriptPage' + +import { GTEX_TISSUES } from '../gtex' import InfoButton from '../help/InfoButton' import { logButtonClick } from '../analytics' import TranscriptsTissueExpression from './TranscriptsTissueExpression' +import { DatasetId, getTopLevelDataset } from '@gnomad/dataset-metadata/metadata' const getPlotRegions = (expressionRegions: any, getValueForRegion: any) => { const roundedRegions = expressionRegions.map((region: any) => ({ @@ -67,6 +70,7 @@ const TRACK_HEIGHT = 20 const heightScale = scaleLinear().domain([0, 1]).range([0, TRACK_HEIGHT]).clamp(true) type PextRegionsPlotProps = { + datasetId: DatasetId color: string regions: { start: number @@ -145,8 +149,13 @@ const NotExpressedMessage = styled.div` color: gray; font-size: 10px; ` +type ExpressedTissue = { + tissue: string + value: number +} -type OwnIndividualTissueTrackProps = { +type IndividualTissueTrackProps = { + datasetId: DatasetId exons: { start: number stop: number @@ -155,9 +164,7 @@ type OwnIndividualTissueTrackProps = { start: number stop: number mean?: number - tissues: { - [key: string]: number - } + tissues: ExpressedTissue[] }[] maxTranscriptExpressionInTissue: number maxMeanTranscriptExpressionInAnyTissue: number @@ -169,12 +176,8 @@ type OwnIndividualTissueTrackProps = { } } -// @ts-expect-error TS(2456) FIXME: Type alias 'IndividualTissueTrackProps' circularly... Remove this comment to see the full error message -type IndividualTissueTrackProps = OwnIndividualTissueTrackProps & - typeof IndividualTissueTrack.defaultProps - -// @ts-expect-error TS(7022) FIXME: 'IndividualTissueTrack' implicitly has type 'any' ... Remove this comment to see the full error message const IndividualTissueTrack = ({ + datasetId, exons, expressionRegions, maxTranscriptExpressionInTissue, @@ -183,11 +186,17 @@ const IndividualTissueTrack = ({ tissue, transcriptWithMaxExpressionInTissue, }: IndividualTissueTrackProps) => { - const isExpressed = expressionRegions.some((region: any) => region.tissues[tissue] !== 0) + const gtexTissuesForDataset = GTEX_TISSUES[getTopLevelDataset(datasetId)] + const isExpressed = expressionRegions.some( + (region: any) => + region.tissues.find((tissueObject: ExpressedTissue) => tissueObject.tissue === tissue) + .value !== 0 + ) + return ( {GTEX_TISSUE_NAMES[tissue]}} + renderLeftPanel={() => {gtexTissuesForDataset[tissue].fullName}} renderRightPanel={({ width }: any) => width > 36 && ( @@ -216,7 +225,7 @@ const IndividualTissueTrack = ({ transcriptWithMaxExpressionInTissue.transcript_version })` : // @ts-expect-error TS(7053) FIXME: Element implicitly has an 'any' type because expre... Remove this comment to see the full error message - `Gene is not expressed in ${GTEX_TISSUE_NAMES[tissue]}` + `Gene is not expressed in ${gtexTissuesForDataset[tissue].fullName}` } > @@ -249,9 +258,15 @@ const IndividualTissueTrack = ({ return ( r.tissues[tissue])} + color={gtexTissuesForDataset[tissue].color} + regions={getPlotRegions( + expressionRegions, + (r: any) => + r.tissues.find((tissueObject: ExpressedTissue) => tissueObject.tissue === tissue) + .value + )} scalePosition={scalePosition} width={width} /> @@ -310,7 +325,8 @@ const RightPanel = styled.div` margin-top: 1.25em; ` -type OwnTissueExpressionTrackProps = { +type TissueExpressionTrackProps = { + datasetId: DatasetId exons: { start: number stop: number @@ -320,29 +336,18 @@ type OwnTissueExpressionTrackProps = { stop: number mean?: number tissues: { - [key: string]: number - } - }[] - flags: string[] - transcripts: { - transcript_id: string - transcript_version: string - exons: { - feature_type: string - start: number - stop: number + tissue: string + value: number }[] }[] + flags: string[] + transcripts: Transcript[] preferredTranscriptId?: string preferredTranscriptDescription?: string | React.ReactNode } -// @ts-expect-error TS(2456) FIXME: Type alias 'TissueExpressionTrackProps' circularly... Remove this comment to see the full error message -type TissueExpressionTrackProps = OwnTissueExpressionTrackProps & - typeof TissueExpressionTrack.defaultProps - -// @ts-expect-error TS(7022) FIXME: 'TissueExpressionTrack' implicitly has type 'any' ... Remove this comment to see the full error message const TissueExpressionTrack = ({ + datasetId, exons, expressionRegions, flags, @@ -356,55 +361,72 @@ const TissueExpressionTrack = ({ const [tissueFilterText, setTissueFilterText] = useState('') const mainTrack = useRef() + const gtexTissuesInDataset = GTEX_TISSUES[getTopLevelDataset(datasetId)] + const [sortTissuesBy, setSortTissuesBy] = useState('alphabetical') - const expressionByTissue = Object.keys(GTEX_TISSUE_NAMES).reduce((acc, tissueId) => { - let maxTranscriptExpressionInTissue = 0 - let transcriptWithMaxExpressionInTissue = null - transcripts.forEach((transcript: any) => { - const expressionInTissue = transcript.gtex_tissue_expression[tissueId] - if (expressionInTissue > maxTranscriptExpressionInTissue) { - maxTranscriptExpressionInTissue = expressionInTissue - transcriptWithMaxExpressionInTissue = transcript - } - }) + type ExpressionByTissueDetails = { + maxTranscriptExpressionInTissue: number + meanTranscriptExpressionInTissue: number + transcriptWithMaxExpressionInTissue: string + } + type ExpressionByTissue = Record - const meanTranscriptExpressionInTissue = mean( - transcripts.map((transcript: any) => transcript.gtex_tissue_expression[tissueId]) - ) + const expressionByTissue: ExpressionByTissue = Object.keys(gtexTissuesInDataset).reduce( + (acc, tissueId) => { + let maxTranscriptExpressionInTissue = 0 + let transcriptWithMaxExpressionInTissue = null - return { - ...acc, - [tissueId]: { - maxTranscriptExpressionInTissue, - meanTranscriptExpressionInTissue, - transcriptWithMaxExpressionInTissue, - }, - } - }, {}) + transcripts.forEach((transcript: Transcript) => { + const expressionInTissue = transcript.gtex_tissue_expression!.find( + (tissue) => tissue.tissue === tissueId + )!.value + + if (expressionInTissue! > maxTranscriptExpressionInTissue) { + maxTranscriptExpressionInTissue = expressionInTissue! + transcriptWithMaxExpressionInTissue = transcript + } + }) + + const meanTranscriptExpressionInTissue = mean( + transcripts.map( + (transcript: Transcript) => + transcript.gtex_tissue_expression!.find((tissue) => tissue.tissue === tissueId)!.value + ) + ) + + return { + ...acc, + [tissueId]: { + maxTranscriptExpressionInTissue, + meanTranscriptExpressionInTissue, + transcriptWithMaxExpressionInTissue, + }, + } + }, + {} + ) const maxMeanTranscriptExpressionInAnyTissue = max( - Object.values(expressionByTissue).map((v: any) => v.meanTranscriptExpressionInTissue) + Object.values(expressionByTissue).map((v) => v.meanTranscriptExpressionInTissue) ) let tissues if (sortTissuesBy === 'mean-expression') { - tissues = Object.entries(GTEX_TISSUE_NAMES) - .sort((t1: any, t2: any) => { - // @ts-expect-error TS(7053) FIXME: Element implicitly has an 'any' type because expre... Remove this comment to see the full error message + tissues = Object.entries(gtexTissuesInDataset) + .sort((t1, t2) => { const t1Expression = expressionByTissue[t1[0]].meanTranscriptExpressionInTissue - // @ts-expect-error TS(7053) FIXME: Element implicitly has an 'any' type because expre... Remove this comment to see the full error message const t2Expression = expressionByTissue[t2[0]].meanTranscriptExpressionInTissue if (t1Expression === t2Expression) { - return t1[1].localeCompare(t2[1]) + return t1[1].fullName.localeCompare(t2[1].fullName) } return t2Expression - t1Expression }) .map((t: any) => t[0]) } else { - tissues = Object.entries(GTEX_TISSUE_NAMES) - .sort((t1: any, t2: any) => t1[1].localeCompare(t2[1])) - .map((t: any) => t[0]) + tissues = Object.entries(gtexTissuesInDataset) + .sort((t1, t2) => t1[1].fullName.localeCompare(t2[1].fullName)) + .map((t) => t[0]) } const isExpressed = expressionRegions.some((region: any) => region.mean !== 0) @@ -549,6 +571,7 @@ const TissueExpressionTrack = ({ {(tissueFilterText ? tissues.filter(tissuePredicate(tissueFilterText)) : tissues).map( (tissue: any) => ( transcript.exons.some((exon: any) => exon.feature_type === 'CDS') -type OwnTranscriptsTissueExpressionProps = { - transcripts: { - transcript_id: string - transcript_version: string - exons: { - feature_type: string - start: number - stop: number - }[] - }[] +type TranscriptsTissueExpressionProps = { + datasetId: DatasetId + transcripts: Transcript[] + // transcripts: { + // transcript_id: string + // transcript_version: string + // exons: { + // feature_type: string + // start: number + // stop: number + // }[] + // }[] includeNonCodingTranscripts: boolean preferredTranscriptId?: string preferredTranscriptDescription?: string | React.ReactNode defaultSortTissuesBy?: 'alphabetical' | 'mean-expression' } -export type GtexTissueExpression = { - adipose_subcutaneous: number - adipose_visceral_omentum: number - adrenal_gland: number - artery_aorta: number - artery_coronary: number - artery_tibial: number - bladder: number - brain_amygdala: number - brain_anterior_cingulate_cortex_ba24: number - brain_caudate_basal_ganglia: number - brain_cerebellar_hemisphere: number - brain_cerebellum: number - brain_cortex: number - brain_frontal_cortex_ba9: number - brain_hippocampus: number - brain_hypothalamus: number - brain_nucleus_accumbens_basal_ganglia: number - brain_putamen_basal_ganglia: number - brain_spinal_cord_cervical_c_1: number - brain_substantia_nigra: number - breast_mammary_tissue: number - cells_ebv_transformed_lymphocytes: number - cells_transformed_fibroblasts?: number - cells_cultured_fibroblasts?: number - cervix_ectocervix: number - cervix_endocervix: number - colon_sigmoid: number - colon_transverse: number - esophagus_gastroesophageal_junction: number - esophagus_mucosa: number - esophagus_muscularis: number - fallopian_tube: number - heart_atrial_appendage: number - heart_left_ventricle: number - kidney_cortex: number - liver: number - lung: number - minor_salivary_gland: number - muscle_skeletal: number - nerve_tibial: number - ovary: number - pancreas: number - pituitary: number - prostate: number - skin_not_sun_exposed_suprapubic: number - skin_sun_exposed_lower_leg: number - small_intestine_terminal_ileum: number - spleen: number - stomach: number - testis: number - thyroid: number - uterus: number - vagina: number - whole_blood: number +export type TissueExpression = { + tissue: string + value: number } -// @ts-expect-error TS(2456) FIXME: Type alias 'TranscriptsTissueExpressionProps' circ... Remove this comment to see the full error message -type TranscriptsTissueExpressionProps = OwnTranscriptsTissueExpressionProps & - typeof TranscriptsTissueExpression.defaultProps +export type GtexTissueExpression = TissueExpression[] -// @ts-expect-error TS(7022) FIXME: 'TranscriptsTissueExpression' implicitly has type ... Remove this comment to see the full error message const TranscriptsTissueExpression = ({ + datasetId, transcripts, includeNonCodingTranscripts, preferredTranscriptId, @@ -106,12 +55,27 @@ const TranscriptsTissueExpression = ({ }: TranscriptsTissueExpressionProps) => { const [sortTranscriptsBy, setSortTranscriptsBy] = useState('default') + // TODO: really I should calc this ONCE early on (like at the top level of all these components, and just pass it down to everywhere + // + // + console.log('wha') + console.log(datasetId) + console.log(getTopLevelDataset(datasetId)) + + const gtexTissuesForDataset = GTEX_TISSUES[getTopLevelDataset(datasetId)] + let renderedTranscripts = sortTranscriptsBy === 'default' ? sortedTranscripts(transcripts, preferredTranscriptId) : [...transcripts].sort((t1, t2) => { - const t1Expression = t1.gtex_tissue_expression[sortTranscriptsBy] || 0 - const t2Expression = t2.gtex_tissue_expression[sortTranscriptsBy] || 0 + const t1Expression = + t1.gtex_tissue_expression.find( + (tissue: TissueExpression) => tissue.tissue === sortTranscriptsBy + ).value || 0 + const t2Expression = + t2.gtex_tissue_expression.find( + (tissue: TissueExpression) => tissue.tissue === sortTranscriptsBy + ).value || 0 if (t1Expression === t2Expression) { return t1.transcript_id.localeCompare(t2.transcript_id) @@ -123,31 +87,36 @@ const TranscriptsTissueExpression = ({ const [sortTissuesBy, setSortTissuesBy] = useState(defaultSortTissuesBy) let tissues if (sortTissuesBy === 'mean-expression') { - const meanExpressionByTissue = Object.keys(GTEX_TISSUE_NAMES).reduce( + const meanExpressionByTissue: Record = Object.keys( + gtexTissuesForDataset + ).reduce( (acc, tissueId) => ({ ...acc, [tissueId]: mean( - transcripts.map((transcript: any) => transcript.gtex_tissue_expression[tissueId] || 0) + transcripts.map( + (transcript: any) => + transcript.gtex_tissue_expression.find( + (tissue: TissueExpression) => tissue.tissue === tissueId + ).value || 0 + ) ), }), {} ) - tissues = Object.entries(GTEX_TISSUE_NAMES) - .sort((t1: any, t2: any) => { - // @ts-expect-error TS(7053) FIXME: Element implicitly has an 'any' type because expre... Remove this comment to see the full error message + tissues = Object.entries(gtexTissuesForDataset) + .sort((t1, t2) => { const t1Expression = meanExpressionByTissue[t1[0]] - // @ts-expect-error TS(7053) FIXME: Element implicitly has an 'any' type because expre... Remove this comment to see the full error message const t2Expression = meanExpressionByTissue[t2[0]] if (t1Expression === t2Expression) { - return t1[1].localeCompare(t2[1]) + return t1[1].fullName.localeCompare(t2[1].fullName) } return t2Expression - t1Expression }) .map((t: any) => t[0]) } else { - tissues = Object.entries(GTEX_TISSUE_NAMES) - .sort((t1: any, t2: any) => t1[1].localeCompare(t2[1])) - .map((t: any) => t[0]) + tissues = Object.entries(gtexTissuesForDataset) + .sort((t1, t2) => t1[1].fullName.localeCompare(t2[1].fullName)) + .map((t) => t[0]) } if (!includeNonCodingTranscripts) { @@ -167,10 +136,10 @@ const TranscriptsTissueExpression = ({ > - {Object.entries(GTEX_TISSUE_NAMES).map(([tissueId, tissueName]) => { + {Object.entries(gtexTissuesForDataset).map(([tissueId, tissueDetails]) => { return ( ) })} @@ -194,6 +163,7 @@ const TranscriptsTissueExpression = ({ {preferredTranscriptDescription &&

* {preferredTranscriptDescription}

} { if (regions.length === 0) { @@ -120,46 +123,49 @@ const margin = { top: 45, } -type OwnTranscriptsTissueExpressionPlotProps = { - tissues?: string[] - transcripts: { - transcript_id: string - transcript_version: string - gtex_tissue_expression: { - [key: string]: number - } - }[] +type TranscriptsTissueExpressionPlotProps = { + datasetId: DatasetId + tissues?: AllGtexTissues[] + transcripts: Transcript[] starredTranscriptId?: string } -// @ts-expect-error TS(2456) FIXME: Type alias 'TranscriptsTissueExpressionPlotProps' ... Remove this comment to see the full error message -type TranscriptsTissueExpressionPlotProps = OwnTranscriptsTissueExpressionPlotProps & - typeof TranscriptsTissueExpressionPlot.defaultProps - -// @ts-expect-error TS(7022) FIXME: 'TranscriptsTissueExpressionPlot' implicitly has t... Remove this comment to see the full error message const TranscriptsTissueExpressionPlot = ({ + datasetId, tissues, transcripts, starredTranscriptId, }: TranscriptsTissueExpressionPlotProps) => { - const renderedTissues = ['Mean', 'Median', ...tissues] + const renderedTissues: (AllGtexTissues | 'Mean' | 'Median')[] = ['Mean', 'Median', ...tissues!] + + console.log('hmmm') + console.log(datasetId) + console.log(getTopLevelDataset(datasetId)) + + const gtexTissuesForDataset = GTEX_TISSUES[getTopLevelDataset(datasetId)] + + const transcriptsWithMeanAndMedianExpression = transcripts.map((transcript) => { + const gtexTissueExpressionObject = transcript.gtex_tissue_expression!.reduce((acc, tissue) => { + acc[tissue.tissue] = tissue.value + return acc + }, {} as Record) + + const expressionValues = transcript.gtex_tissue_expression!.map((tissue) => tissue.value) - const transcriptsWithMeanAndMedianExpresion = transcripts.map((transcript: any) => { - const expressionValues = Object.values(transcript.gtex_tissue_expression) return { ...transcript, gtex_tissue_expression: { - ...transcript.gtex_tissue_expression, - // @ts-expect-error TS(2345) FIXME: Argument of type 'unknown[]' is not assignable to ... Remove this comment to see the full error message + ...gtexTissueExpressionObject, Mean: mean(expressionValues), - // @ts-expect-error TS(2345) FIXME: Argument of type 'unknown[]' is not assignable to ... Remove this comment to see the full error message Median: median(expressionValues), }, } }) const maxTissueExpression = max( - transcripts.flatMap((transcript: any) => Object.values(transcript.gtex_tissue_expression)) + transcripts.flatMap((transcript: Transcript) => + transcript.gtex_tissue_expression!.map((tissue) => tissue.value) + ) ) // @ts-expect-error TS(2345) FIXME: Argument of type '(string | number | undefined)[]'... Remove this comment to see the full error message @@ -201,7 +207,7 @@ const TranscriptsTissueExpressionPlot = ({ ) const yScale = scaleBand() - .domain(transcriptsWithMeanAndMedianExpresion.map((t: any) => t.transcript_id)) + .domain(transcriptsWithMeanAndMedianExpression.map((t: any) => t.transcript_id)) .range([0, plotHeight]) .padding(padding) @@ -210,7 +216,6 @@ const TranscriptsTissueExpressionPlot = ({ const halfYPadding = (yScale.step() * yScale.paddingInner()) / 2 const transcriptLabels = transcripts.reduce( - // @ts-expect-error TS(7006) FIXME: Parameter 'acc' implicitly has an 'any' type. (acc, transcript) => ({ ...acc, [transcript.transcript_id]: `${transcript.transcript_id}.${transcript.transcript_version}`, @@ -288,7 +293,10 @@ const TranscriptsTissueExpressionPlot = ({ scale={xAxisScale} stroke="#333" // @ts-expect-error TS(7053) FIXME: Element implicitly has an 'any' type because expre... Remove this comment to see the full error message - tickFormat={(t) => GTEX_TISSUE_NAMES[t] || t} + tickFormat={(t) => { + console.log(t) + return gtexTissuesForDataset[t] ? gtexTissuesForDataset[t].fullName : t + }} tickLabelProps={(value) => ({ dx: '-0.25em', dy: '0.25em', @@ -301,7 +309,7 @@ const TranscriptsTissueExpressionPlot = ({ tickLength={3} /> - {transcriptsWithMeanAndMedianExpresion.map((transcript: any) => ( + {transcriptsWithMeanAndMedianExpression.map((transcript) => ( t1[1].localeCompare(t2[1])) - .map((t: any) => t[0]), - starredTranscriptId: null, -} +// TranscriptsTissueExpressionPlot.defaultProps = { +// tissues: Object.entries(GTEX_TISSUE_NAMES) +// .sort((t1: any, t2: any) => t1[1].localeCompare(t2[1])) +// .map((t: any) => t[0]), +// starredTranscriptId: null, +// } export default TranscriptsTissueExpressionPlot diff --git a/browser/src/GenePage/sortedTranscripts.ts b/browser/src/GenePage/sortedTranscripts.ts index f0e825e8b..812fbb4c9 100644 --- a/browser/src/GenePage/sortedTranscripts.ts +++ b/browser/src/GenePage/sortedTranscripts.ts @@ -1,24 +1,26 @@ import { mean } from 'd3-array' +import { Transcript } from '../TranscriptPage/TranscriptPage' -const sortedTranscripts = (transcripts: any, firstTranscriptId: any) => { +const sortedTranscripts = (transcripts: Transcript[], firstTranscriptId: string | undefined) => { return [...transcripts].sort((t1, t2) => { // Sort specified transcript first // Then sort transcripts by mean expression and transcript ID - if (t1.transcript_id === firstTranscriptId) { - return -1 - } - if (t2.transcript_id === firstTranscriptId) { - return 1 + + if (firstTranscriptId) { + if (t1.transcript_id === firstTranscriptId) { + return -1 + } + if (t2.transcript_id === firstTranscriptId) { + return 1 + } } - const t1Mean = mean(Object.values(t1.gtex_tissue_expression || {})) - const t2Mean = mean(Object.values(t2.gtex_tissue_expression || {})) + const t1Mean = mean(t1.gtex_tissue_expression!.map((tissue) => tissue.value)) || 0 + const t2Mean = mean(t2.gtex_tissue_expression!.map((tissue) => tissue.value)) || 0 if (t1Mean === t2Mean) { return t1.transcript_id.localeCompare(t2.transcript_id) } - - // @ts-expect-error TS(2532) FIXME: Object is possibly 'undefined'. return t2Mean - t1Mean }) } diff --git a/browser/src/gtex.ts b/browser/src/gtex.ts index aa5f2b99b..9bc3c2bc9 100644 --- a/browser/src/gtex.ts +++ b/browser/src/gtex.ts @@ -1,113 +1,326 @@ -export const GTEX_TISSUE_NAMES = { - adipose_subcutaneous: 'Adipose - Subcutaneous', - adipose_visceral_omentum: 'Adipose - Visceral (Omentum)', - adrenal_gland: 'Adrenal Gland', - artery_aorta: 'Artery - Aorta', - artery_coronary: 'Artery - Coronary', - artery_tibial: 'Artery - Tibial', - bladder: 'Bladder', - brain_amygdala: 'Brain - Amygdala', - brain_anterior_cingulate_cortex_ba24: 'Brain - Anterior cingulate cortex (BA24)', - brain_caudate_basal_ganglia: 'Brain - Caudate (basal ganglia)', - brain_cerebellar_hemisphere: 'Brain - Cerebellar Hemisphere', - brain_cerebellum: 'Brain - Cerebellum', - brain_cortex: 'Brain - Cortex', - brain_frontal_cortex_ba9: 'Brain - Frontal Cortex (BA9)', - brain_hippocampus: 'Brain - Hippocampus', - brain_hypothalamus: 'Brain - Hypothalamus', - brain_nucleus_accumbens_basal_ganglia: 'Brain - Nucleus accumbens (basal ganglia)', - brain_putamen_basal_ganglia: 'Brain - Putamen (basal ganglia)', - brain_spinal_cord_cervical_c_1: 'Brain - Spinal cord (cervical c-1)', - brain_substantia_nigra: 'Brain - Substantia nigra', - breast_mammary_tissue: 'Breast - Mammary Tissue', - cells_ebv_transformed_lymphocytes: 'Cells - EBV-transformed lymphocytes', - // cells_transformed_fibroblasts: 'Cells - Transformed fibroblasts', - cells_cultured_fibroblasts: 'Cells - Cultured fibroblasts', - cervix_ectocervix: 'Cervix - Ectocervix', - cervix_endocervix: 'Cervix - Endocervix', - colon_sigmoid: 'Colon - Sigmoid', - colon_transverse: 'Colon - Transverse', - esophagus_gastroesophageal_junction: 'Esophagus - Gastroesophageal Junction', - esophagus_mucosa: 'Esophagus - Mucosa', - esophagus_muscularis: 'Esophagus - Muscularis', - fallopian_tube: 'Fallopian Tube', - heart_atrial_appendage: 'Heart - Atrial Appendage', - heart_left_ventricle: 'Heart - Left Ventricle', - kidney_cortex: 'Kidney - Cortex', - liver: 'Liver', - lung: 'Lung', - minor_salivary_gland: 'Minor Salivary Gland', - muscle_skeletal: 'Muscle - Skeletal', - nerve_tibial: 'Nerve - Tibial', - ovary: 'Ovary', - pancreas: 'Pancreas', - pituitary: 'Pituitary', - prostate: 'Prostate', - skin_not_sun_exposed_suprapubic: 'Skin - Not Sun Exposed (Suprapubic)', - skin_sun_exposed_lower_leg: 'Skin - Sun Exposed (Lower leg)', - small_intestine_terminal_ileum: 'Small Intestine - Terminal Ileum', - spleen: 'Spleen', - stomach: 'Stomach', - testis: 'Testis', - thyroid: 'Thyroid', - uterus: 'Uterus', - vagina: 'Vagina', - whole_blood: 'Whole Blood', +import { TopLevelDataset } from '@gnomad/dataset-metadata/metadata' + +const SHARED_GTEX_TISSUES = { + adipose_subcutaneous: { + fullName: 'Adipose - Subcutaneous', + color: '#FF6600', + }, + adipose_visceral_omentum: { + fullName: 'Adipose - Visceral (Omentum)', + color: '#FFAA00', + }, + adrenal_gland: { + fullName: 'Adrenal Gland', + color: '#33DD33', + }, + artery_aorta: { + fullName: 'Artery - Aorta', + color: '#FF5555', + }, + artery_coronary: { + fullName: 'Artery - Coronary', + color: '#FFAA99', + }, + artery_tibial: { + fullName: 'Artery - Tibial', + color: '#FF0000', + }, + bladder: { + fullName: 'Bladder', + color: '#AA0000', + }, + brain_amygdala: { + fullName: 'Brain - Amygdala', + color: '#EEEE00', + }, + brain_anterior_cingulate_cortex_ba24: { + fullName: 'Brain - Anterior cingulate cortex (BA24)', + color: '#EEEE00', + }, + brain_caudate_basal_ganglia: { + fullName: 'Brain - Caudate (basal ganglia)', + color: '#EEEE00', + }, + brain_cerebellar_hemisphere: { + fullName: 'Brain - Cerebellar Hemisphere', + color: '#EEEE00', + }, + brain_cerebellum: { + fullName: 'Brain - Cerebellum', + color: '#EEEE00', + }, + brain_cortex: { + fullName: 'Brain - Cortex', + color: '#EEEE00', + }, + brain_frontal_cortex_ba9: { + fullName: 'Brain - Frontal Cortex (BA9)', + color: '#EEEE00', + }, + brain_hippocampus: { + fullName: 'Brain - Hippocampus', + color: '#EEEE00', + }, + brain_hypothalamus: { + fullName: 'Brain - Hypothalamus', + color: '#EEEE00', + }, + brain_nucleus_accumbens_basal_ganglia: { + fullName: 'Brain - Nucleus accumbens (basal ganglia)', + color: '#EEEE00', + }, + brain_putamen_basal_ganglia: { + fullName: 'Brain - Putamen (basal ganglia)', + color: '#EEEE00', + }, + brain_spinal_cord_cervical_c_1: { + fullName: 'Brain - Spinal cord (cervical c-1)', + color: '#EEEE00', + }, + brain_substantia_nigra: { + fullName: 'Brain - Substantia nigra', + color: '#EEEE00', + }, + breast_mammary_tissue: { + fullName: 'Breast - Mammary Tissue', + color: '#33CCCC', + }, + cells_ebv_transformed_lymphocytes: { + fullName: 'Cells - EBV-transformed lymphocytes', + color: '#CC66FF', + }, + cervix_ectocervix: { + fullName: 'Cervix - Ectocervix', + color: '#FFCCCC', + }, + cervix_endocervix: { + fullName: 'Cervix - Endocervix', + color: '#CCAADD', + }, + colon_sigmoid: { + fullName: 'Colon - Sigmoid', + color: '#EEBB77', + }, + colon_transverse: { + fullName: 'Colon - Transverse', + color: '#CC9955', + }, + esophagus_gastroesophageal_junction: { + fullName: 'Esophagus - Gastroesophageal Junction', + color: '#8B7355', + }, + esophagus_mucosa: { + fullName: 'Esophagus - Mucosa', + color: '#552200', + }, + esophagus_muscularis: { + fullName: 'Esophagus - Muscularis', + color: '#BB9988', + }, + fallopian_tube: { + fullName: 'Fallopian Tube', + color: '#FFCCCC', + }, + heart_atrial_appendage: { + fullName: 'Heart - Atrial Appendage', + color: '#9900FF', + }, + heart_left_ventricle: { + fullName: 'Heart - Left Ventricle', + color: '#660099', + }, + kidney_cortex: { + fullName: 'Kidney - Cortex', + color: '#22FFDD', + }, + liver: { + fullName: 'Liver', + color: '#AABB66', + }, + lung: { + fullName: 'Lung', + color: '#99FF00', + }, + minor_salivary_gland: { + fullName: 'Minor Salivary Gland', + color: '#99BB88', + }, + muscle_skeletal: { + fullName: 'Muscle - Skeletal', + color: '#AAAAFF', + }, + nerve_tibial: { + fullName: 'Nerve - Tibial', + color: '#FFD700', + }, + ovary: { + fullName: 'Ovary', + color: '#FFAAFF', + }, + pancreas: { + fullName: 'Pancreas', + color: '#995522', + }, + pituitary: { + fullName: 'Pituitary', + color: '#AAFF99', + }, + prostate: { + fullName: 'Prostate', + color: '#DDDDDD', + }, + skin_not_sun_exposed_suprapubic: { + fullName: 'Skin - Not Sun Exposed (Suprapubic)', + color: '#0000FF', + }, + skin_sun_exposed_lower_leg: { + fullName: 'Skin - Sun Exposed (Lower leg)', + color: '#7777FF', + }, + small_intestine_terminal_ileum: { + fullName: 'Small Intestine - Terminal Ileum', + color: '#555522', + }, + spleen: { + fullName: 'Spleen', + color: '#778855', + }, + stomach: { + fullName: 'Stomach', + color: '#FFDD99', + }, + testis: { + fullName: 'Testis', + color: '#AAAAAA', + }, + thyroid: { + fullName: 'Thyroid', + color: '#006600', + }, + uterus: { + fullName: 'Uterus', + color: '#FF66FF', + }, + vagina: { + fullName: 'Vagina', + color: '#FF5599', + }, + whole_blood: { + fullName: 'Whole Blood', + color: '#FF00BB', + }, +} + +type SharedTissues = keyof typeof SHARED_GTEX_TISSUES + +type TissueDetail = { + fullName: string + color: string +} + +const V2_SPECIFIC_GTEX_TISSUES = { + cells_transformed_fibroblasts: { + fullName: 'Cells - Transformed fibroblasts', + color: '#AAEEFF', + }, +} + +type V2GtexTissues = SharedTissues | keyof typeof V2_SPECIFIC_GTEX_TISSUES + +const V2_GTEX_TISSUES: Record = { + ...SHARED_GTEX_TISSUES, + ...V2_SPECIFIC_GTEX_TISSUES, +} + +const V4_SPECIFIC_GTEX_TISSUES = { + cells_cultured_fibroblasts: { + fullName: 'Cells - Cultured fibroblasts', + color: '#AAEEFF', + }, + colon_transverse_mixed_cell: { + fullName: 'Colon - Transverse mixed cell', + color: '#CC9955', + }, + colon_transverse_mucosa: { + fullName: 'Colon - Transverse mucosa', + color: '#CC9955', + }, + colon_transverse_muscularis: { + fullName: 'Colon - Transverse muscularis', + color: '#CC9955', + }, + kidney_medulla: { + fullName: 'Kidney - Medulla', + color: '#33FFC2', + }, + liver_hepatocyte: { + fullName: 'Liver - Hepatocyte', + color: '#AABB66', + }, + liver_mixed_cell: { + fullName: 'Liver - Mixed cell', + color: '#AABB66', + }, + liver_portal_tract: { + fullName: 'Liver - Portal tract', + color: '#AABB66', + }, + pancreas_acini: { + fullName: 'Pancreas - Acini', + color: '#995522', + }, + pancreas_islets: { + fullName: 'Pancreas - Islets', + color: '#995522', + }, + pancreas_mixed_cell: { + fullName: 'Pancreas - Mixed cell', + color: '#995522', + }, + small_intestine_terminal_ileum_lymphoid_aggregate: { + fullName: 'Small Intestine - Terminal ileum lymphoid aggregate', + color: '#555522', + }, + small_intestine_terminal_ileum_mixed_cell: { + fullName: 'Small intestine - Terminal ileum mixed cell', + color: '#555522', + }, + stomach_mixed_cell: { + fullName: 'Stomach - Mixed cell', + color: '#FFDD99', + }, + stomach_mucosa: { + fullName: 'Stomach - Mucosa', + color: '#FFDD99', + }, + stomach_muscularis: { + fullName: 'Stomach - Muscularis', + color: '#FFDD99', + }, +} + +type V4GtexTissues = SharedTissues | keyof typeof V4_SPECIFIC_GTEX_TISSUES + +export type AllGtexTissues = + | SharedTissues + | keyof typeof V2_SPECIFIC_GTEX_TISSUES + | keyof typeof V4_SPECIFIC_GTEX_TISSUES + +const V4_GTEX_TISSUES: Record = { + ...SHARED_GTEX_TISSUES, + ...V4_SPECIFIC_GTEX_TISSUES, } -export const GTEX_TISSUE_COLORS = { - adipose_subcutaneous: '#FF6600', - adipose_visceral_omentum: '#FFAA00', - adrenal_gland: '#33DD33', - artery_aorta: '#FF5555', - artery_coronary: '#FFAA99', - artery_tibial: '#FF0000', - bladder: '#AA0000', - brain_amygdala: '#EEEE00', - brain_anterior_cingulate_cortex_ba24: '#EEEE00', - brain_caudate_basal_ganglia: '#EEEE00', - brain_cerebellar_hemisphere: '#EEEE00', - brain_cerebellum: '#EEEE00', - brain_cortex: '#EEEE00', - brain_frontal_cortex_ba9: '#EEEE00', - brain_hippocampus: '#EEEE00', - brain_hypothalamus: '#EEEE00', - brain_nucleus_accumbens_basal_ganglia: '#EEEE00', - brain_putamen_basal_ganglia: '#EEEE00', - brain_spinal_cord_cervical_c_1: '#EEEE00', - brain_substantia_nigra: '#EEEE00', - breast_mammary_tissue: '#33CCCC', - cells_ebv_transformed_lymphocytes: '#CC66FF', - // cells_transformed_fibroblasts: '#AAEEFF', - cells_cultured_fibroblasts: '#AAEEFF', - cervix_ectocervix: '#FFCCCC', - cervix_endocervix: '#CCAADD', - colon_sigmoid: '#EEBB77', - colon_transverse: '#CC9955', - esophagus_gastroesophageal_junction: '#8B7355', - esophagus_mucosa: '#552200', - esophagus_muscularis: '#BB9988', - fallopian_tube: '#FFCCCC', - heart_atrial_appendage: '#9900FF', - heart_left_ventricle: '#660099', - kidney_cortex: '#22FFDD', - liver: '#AABB66', - lung: '#99FF00', - minor_salivary_gland: '#99BB88', - muscle_skeletal: '#AAAAFF', - nerve_tibial: '#FFD700', - ovary: '#FFAAFF', - pancreas: '#995522', - pituitary: '#AAFF99', - prostate: '#DDDDDD', - skin_not_sun_exposed_suprapubic: '#0000FF', - skin_sun_exposed_lower_leg: '#7777FF', - small_intestine_terminal_ileum: '#555522', - spleen: '#778855', - stomach: '#FFDD99', - testis: '#AAAAAA', - thyroid: '#006600', - uterus: '#FF66FF', - vagina: '#FF5599', - whole_blood: '#FF00BB', +export const GTEX_TISSUES: { + v2: Record + v4: Record + default: Record + v3: Record + ExAC: Record +} = { + v2: V2_GTEX_TISSUES, + v4: V4_GTEX_TISSUES, + default: SHARED_GTEX_TISSUES, + v3: SHARED_GTEX_TISSUES, + ExAC: SHARED_GTEX_TISSUES, }