Skip to content
Snippets Groups Projects
Commit a843ec04 authored by Julian Späth's avatar Julian Späth
Browse files

Merge branch 'connect-to-new-backend' into 'master'

Use new backend

See merge request covid-19/frontend!16
parents 977c2103 06144161
No related branches found
No related tags found
No related merge requests found
import {Injectable} from '@angular/core'; import {Injectable} from '@angular/core';
import {ProteinGroup} from './pages/protein-network'; import {Protein} from './pages/protein-network';
import {Subject} from 'rxjs'; import {Subject} from 'rxjs';
@Injectable({ @Injectable({
...@@ -7,30 +7,30 @@ import {Subject} from 'rxjs'; ...@@ -7,30 +7,30 @@ import {Subject} from 'rxjs';
}) })
export class AnalysisService { export class AnalysisService {
private selectedProteins = new Map<string, ProteinGroup>(); private selectedProteins = new Map<string, Protein>();
private selectSubject = new Subject<{protein: ProteinGroup, selected: boolean}>(); private selectSubject = new Subject<{protein: Protein, selected: boolean}>();
constructor() { constructor() {
} }
addProtein(protein: ProteinGroup) { addProtein(protein: Protein) {
if (!this.inSelection(protein)) { if (!this.inSelection(protein)) {
this.selectedProteins.set(`${protein.groupId}`, protein); this.selectedProteins.set(`${protein.proteinAc}`, protein);
this.selectSubject.next({protein, selected: true}); this.selectSubject.next({protein, selected: true});
} }
} }
inSelection(protein: ProteinGroup): boolean { inSelection(protein: Protein): boolean {
return this.selectedProteins.has(`${protein.groupId}`); return this.selectedProteins.has(protein.proteinAc);
} }
removeProtein(protein: ProteinGroup) { removeProtein(protein: Protein) {
if (this.selectedProteins.delete(`${protein.groupId}`)) { if (this.selectedProteins.delete(`${protein.proteinAc}`)) {
this.selectSubject.next({protein, selected: false}); this.selectSubject.next({protein, selected: false});
} }
} }
getSelection(): ProteinGroup[] { getSelection(): Protein[] {
return Array.from(this.selectedProteins.values()); return Array.from(this.selectedProteins.values());
} }
...@@ -38,7 +38,7 @@ export class AnalysisService { ...@@ -38,7 +38,7 @@ export class AnalysisService {
return this.selectedProteins.size; return this.selectedProteins.size;
} }
subscribe(cb: (protein: ProteinGroup, selected: boolean) => void) { subscribe(cb: (protein: Protein, selected: boolean) => void) {
this.selectSubject.subscribe((event) => { this.selectSubject.subscribe((event) => {
cb(event.protein, event.selected); cb(event.protein, event.selected);
}); });
......
...@@ -7,7 +7,7 @@ import {HomePageComponent} from './pages/home-page/home-page.component'; ...@@ -7,7 +7,7 @@ import {HomePageComponent} from './pages/home-page/home-page.component';
export const routes: Routes = [ export const routes: Routes = [
{ path: '', component: HomePageComponent }, { path: '', component: HomePageComponent },
{ path: 'explorer', component: ExplorerPageComponent}, { path: 'explorer', component: ExplorerPageComponent},
{ path: 'explorer/:proteinGroup', component: ExplorerPageComponent}, { path: 'explorer/:protein', component: ExplorerPageComponent},
{ path: 'about', component: AboutPageComponent } { path: 'about', component: AboutPageComponent }
]; ];
......
...@@ -16,7 +16,7 @@ ...@@ -16,7 +16,7 @@
</thead> </thead>
<tbody> <tbody>
<tr *ngFor="let p of analysis.getSelection()"> <tr *ngFor="let p of analysis.getSelection()">
<td>{{p.name}}</td> <td>{{p.proteinAc}}</td>
<td> <td>
<button (click)="analysis.removeProtein(p)" class="button is-small is-danger"> <button (click)="analysis.removeProtein(p)" class="button is-small is-danger">
<i class="fa fa-trash"></i> <i class="fa fa-trash"></i>
......
<div class="content"> <div class="content">
<ng-select [items]="queryItems" bindLabel="name" [virtualScroll]="true" class="custom" <ng-select [items]="queryItems" bindLabel="proteinAc" [virtualScroll]="true" class="custom"
placeholder="Search..." (change)="select($event)"> placeholder="Search..." (change)="select($event)">
</ng-select> </ng-select>
</div> </div>
import { Component, Input, Output, EventEmitter } from '@angular/core'; import { Component, Input, Output, EventEmitter } from '@angular/core';
import {Protein} from '../../pages/protein-network';
@Component({ @Component({
selector: 'app-query-component', selector: 'app-query-component',
...@@ -8,12 +9,11 @@ import { Component, Input, Output, EventEmitter } from '@angular/core'; ...@@ -8,12 +9,11 @@ import { Component, Input, Output, EventEmitter } from '@angular/core';
export class QueryComponent { export class QueryComponent {
@Output() selectProtein: EventEmitter<string> = new EventEmitter(); @Output() selectProtein: EventEmitter<Protein> = new EventEmitter();
@Input() queryItems: any[]; @Input() queryItems: Protein[];
select(protein) { select(protein) {
console.log(protein); this.selectProtein.emit(protein);
this.selectProtein.emit('pg_' + protein.groupId);
} }
} }
...@@ -24,7 +24,7 @@ ...@@ -24,7 +24,7 @@
<div class="level-item has-text-centered"> <div class="level-item has-text-centered">
<div> <div>
<p class="heading">Protein Groups</p> <p class="heading">Protein Groups</p>
<p class="title">{{ proteinData.proteinGroups.length }}</p> <p class="title">{{ proteinData.proteins.length }}</p>
</div> </div>
</div> </div>
<div class="level-item has-text-centered"> <div class="level-item has-text-centered">
...@@ -70,11 +70,11 @@ ...@@ -70,11 +70,11 @@
<div class="content"> <div class="content">
<p><b>Baits</b></p> <p><b>Baits</b></p>
<div class="bait-frame"> <div class="bait-frame">
<div *ngFor="let bait of baitProteins"> <div *ngFor="let bait of viralProteinCheckboxes">
<label class="checkbox"> <label class="checkbox">
<input type="checkbox" class="checkbox" [ngModel]="bait.checked" <input type="checkbox" class="checkbox" [ngModel]="bait.checked"
(ngModelChange)="bait.checked = $event; filterNodes()"> (ngModelChange)="bait.checked = $event; filterNodes()">
Bait {{ bait.data.name }} Bait {{ bait.data.effectId }}
</label> </label>
</div> </div>
</div> </div>
...@@ -139,13 +139,12 @@ ...@@ -139,13 +139,12 @@
<div class="card-content"> <div class="card-content">
<div *ngIf="showDetails" class="content"> <div *ngIf="showDetails" class="content">
<p><b>Protein Group:</b> {{ proteinGroup }}</p> <p><b>Protein Group:</b> {{ currentProteinAc }}</p>
<p><b>Gene Name(s):</b> <span *ngFor="let geneName of geneNames"> {{ geneName }}</span></p> <p><b>Gene Name(s):</b> <span *ngFor="let geneName of geneNames"> {{ geneName }}</span></p>
<p><b>Protein Name(s):</b> <span *ngFor="let proteinName of proteinNames"> {{ proteinName }}</span></p> <p><b>Protein Name(s):</b> <span *ngFor="let proteinName of proteinNames"> {{ proteinName }}</span></p>
<p align="row"><b>Protein AC(s):</b> <p><b>Protein AC(s):</b>
<a href="https://www.uniprot.org/uniprot/{{proteinAC}}" target="_blank" <a href="https://www.uniprot.org/uniprot/{{proteinAc}}" target="_blank" *ngFor="let proteinAc of proteinAcs">
*ngFor="let proteinAC of proteinACs"> {{ proteinAc }}
{{ proteinAC }}
</a> </a>
</p> </p>
</div> </div>
...@@ -170,8 +169,8 @@ ...@@ -170,8 +169,8 @@
<figure class="image"> <figure class="image">
<img src="assets/boxplot.png" alt="Boxplots"> <img src="assets/boxplot.png" alt="Boxplots">
</figure> </figure>
<button class="button" *ngIf="!inSelection(proteinGroup)" (click)="addToSelection(proteinGroup)">Select for analysis</button> <button class="button" *ngIf="!inSelection(currentProteinAc)" (click)="addToSelection(currentProteinAc)">Select for analysis</button>
<button class="button" *ngIf="inSelection(proteinGroup)" (click)="removeFromSelection(proteinGroup)">Remove from analysis</button> <button class="button" *ngIf="inSelection(currentProteinAc)" (click)="removeFromSelection(currentProteinAc)">Remove from analysis</button>
</div> </div>
</div> </div>
</div> </div>
......
import {AfterViewInit, Component, ElementRef, OnInit, ViewChild, Output, EventEmitter} from '@angular/core'; import {AfterViewInit, Component, ElementRef, OnInit, ViewChild, Output, EventEmitter} from '@angular/core';
import {ActivatedRoute, Router} from '@angular/router'; import {ActivatedRoute, Router} from '@angular/router';
import {Effect, ProteinGroup, ProteinNetwork} from '../protein-network'; import {Effect, Protein, ProteinNetwork} from '../protein-network';
import {HttpClient} from '@angular/common/http'; import {HttpClient} from '@angular/common/http';
import {ApiService} from '../../api.service'; import {ApiService} from '../../api.service';
import {AnalysisService} from '../../analysis.service'; import {AnalysisService} from '../../analysis.service';
...@@ -15,36 +15,31 @@ declare var vis: any; ...@@ -15,36 +15,31 @@ declare var vis: any;
export class ExplorerPageComponent implements OnInit, AfterViewInit { export class ExplorerPageComponent implements OnInit, AfterViewInit {
public showDetails = false; public showDetails = false;
public groupId = ''; public currentProteinAc = '';
public geneNames: Array<string> = []; public geneNames: Array<string> = [];
public proteinGroup = '';
public proteinNames: Array<string> = []; public proteinNames: Array<string> = [];
public proteinACs: Array<string> = []; public proteinAcs: Array<string> = [];
public baitProteins: Array<{ checked: boolean; data: Effect }> = []; public viralProteinCheckboxes: Array<{ checked: boolean; data: Effect }> = [];
public proteinData: ProteinNetwork; public proteinData: ProteinNetwork;
public filteredProteins = []; public filteredProteins = [];
public proteinGroups: any; public proteins: any;
public effects: any; public effects: any;
public edges: any; public edges: any;
private network: any; private network: any;
private nodeData: { nodes: any, edges: any } = {nodes: null, edges: null}; private nodeData: { nodes: any, edges: any } = {nodes: null, edges: null};
private networkData: any = [];
private seed = 1; // TODO: Remove this private seed = 1; // TODO: Remove this
private dumpPositions = false; private dumpPositions = false;
public physicsEnabled = false; public physicsEnabled = false;
public queryItems = []; public queryItems = [];
public showAnalysisDialog = false; public showAnalysisDialog = false;
@ViewChild('network', {static: false}) networkEl: ElementRef; @ViewChild('network', {static: false}) networkEl: ElementRef;
constructor(private http: HttpClient, constructor(private http: HttpClient,
...@@ -54,39 +49,39 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit { ...@@ -54,39 +49,39 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit {
public analysis: AnalysisService) { public analysis: AnalysisService) {
this.geneNames.push('IFI16'); this.geneNames.push('IFI16');
this.proteinNames.push('Gamma-interface-inducible protein 16'); this.proteinNames.push('Gamma-interface-inducible protein 16');
this.proteinACs.push('Q16666'); this.proteinAcs.push('Q16666');
this.route.queryParams.subscribe(async (params) => { this.route.queryParams.subscribe(async (params) => {
this.dumpPositions = params.dumpPositions; this.dumpPositions = params.dumpPositions;
this.physicsEnabled = !!this.dumpPositions; this.physicsEnabled = !!this.dumpPositions;
const proteinGroup = params.proteinGroup; const protein = params.protein;
if (!proteinGroup) { if (!protein) {
// In this case, the URL is just `/explorer` // In this case, the URL is just `/explorer`
// Therefore, we do not show a modal // Therefore, we do not show a modal
this.showDetails = false; this.showDetails = false;
return; return;
} }
// In this case, the URL is `/explorer/<proteinGroup>` // In this case, the URL is `/explorer/<protein>`
if (this.proteinGroup === proteinGroup) { if (this.currentProteinAc === protein) {
// The protein group is the same as before, so we do not need to do anything // The protein group is the same as before, so we do not need to do anything
// TODO Also highlight node when reloading the page/sharing the URL // TODO Also highlight node when reloading the page/sharing the URL
return; return;
} }
// We have a new proteinGroup id, so we need to load it and show the modal... // We have a new protein id, so we need to load it and show the modal...
this.proteinGroup = proteinGroup; this.currentProteinAc = protein;
// TODO: Perform call here for 'proteinGroup'... // TODO: Perform call here for 'protein'...
// this.zoomToNode(proteinGroup) // this.zoomToNode(protein)
this.showDetails = true; this.showDetails = true;
}); });
this.analysis.subscribe((protein, selected) => { this.analysis.subscribe((protein, selected) => {
const nodeId = `pg_${protein.groupId}`; const nodeId = `pg_${protein.proteinAc}`;
if (selected) { if (selected) {
const node = this.nodeData.nodes.get(nodeId); const node = this.nodeData.nodes.get(nodeId);
if (node) { if (node) {
...@@ -119,14 +114,14 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit { ...@@ -119,14 +114,14 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit {
private async getNetwork() { private async getNetwork() {
const data: any = await this.api.getNetwork(); const data: any = await this.api.getNetwork();
this.proteinGroups = data.proteinGroups; this.proteins = data.proteins;
this.effects = data.effects; this.effects = data.effects;
this.edges = data.edges; this.edges = data.edges;
} }
public reset(event) { public reset(event) {
const checked = event.target.checked; const checked = event.target.checked;
this.baitProteins.forEach(item => item.checked = checked); this.viralProteinCheckboxes.forEach(item => item.checked = checked);
this.filterNodes(); this.filterNodes();
} }
...@@ -139,14 +134,10 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit { ...@@ -139,14 +134,10 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit {
}); });
} }
public getGroupId() { public async openSummary(protein: Protein, zoom: boolean) {
return this.groupId; await this.router.navigate(['explorer'], {queryParams: {protein: protein.proteinAc}});
}
public async openSummary(groupId: string, zoom: boolean) {
await this.router.navigate(['explorer'], {queryParams: {proteinGroup: groupId}});
if (zoom) { if (zoom) {
this.zoomToNode(this.proteinGroup); this.zoomToNode(`pg_${protein.proteinAc}`);
} }
} }
...@@ -157,7 +148,7 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit { ...@@ -157,7 +148,7 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit {
private async createNetwork() { private async createNetwork() {
await this.getNetwork(); await this.getNetwork();
this.proteinData = new ProteinNetwork(this.proteinGroups, this.effects, this.edges); this.proteinData = new ProteinNetwork(this.proteins, this.effects, this.edges);
if (!this.dumpPositions) { if (!this.dumpPositions) {
await this.proteinData.loadPositions(this.http); await this.proteinData.loadPositions(this.http);
} }
...@@ -165,7 +156,7 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit { ...@@ -165,7 +156,7 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit {
// Populate baits // Populate baits
this.proteinData.effects.forEach((effect) => { this.proteinData.effects.forEach((effect) => {
this.baitProteins.push({ this.viralProteinCheckboxes.push({
checked: false, checked: false,
data: effect, data: effect,
}); });
...@@ -198,7 +189,12 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit { ...@@ -198,7 +189,12 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit {
console.log(id); console.log(id);
if (id.length > 0) { if (id.length > 0) {
console.log('clicked node:', id); console.log('clicked node:', id);
this.openSummary(id[0], false); if (id[0].startsWith('pg_')) {
const protein = this.proteinData.getProtein(id[0].substr(3));
this.openSummary(protein, false);
} else {
this.closeSummary();
}
} }
}); });
...@@ -209,11 +205,11 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit { ...@@ -209,11 +205,11 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit {
this.network.stabilize(); this.network.stabilize();
} }
if (this.proteinGroup) { if (this.currentProteinAc) {
this.zoomToNode(this.proteinGroup); this.zoomToNode(`pg_${this.currentProteinAc}`);
} }
this.filteredProteins = this.proteinGroups; this.filteredProteins = this.proteins;
this.fillQueryItems(); this.fillQueryItems();
} }
...@@ -225,13 +221,13 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit { ...@@ -225,13 +221,13 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit {
const removeIds = new Set<string>(); const removeIds = new Set<string>();
const addNodes = new Map<string, Node>(); const addNodes = new Map<string, Node>();
const showAll = !this.baitProteins.find((eff) => eff.checked); const showAll = !this.viralProteinCheckboxes.find((eff) => eff.checked);
console.log(showAll); console.log(showAll);
const connectedProteinGroupIds = new Set<number>(); const connectedProteinAcs = new Set<string>();
this.baitProteins.forEach((bait) => { this.viralProteinCheckboxes.forEach((bait) => {
const nodeId = `eff_${bait.data.name}`; const nodeId = `eff_${bait.data.effectId}`;
const found = visibleIds.has(nodeId); const found = visibleIds.has(nodeId);
if ((bait.checked || showAll) && !found) { if ((bait.checked || showAll) && !found) {
const node = this.mapEffectToNode(bait.data); const node = this.mapEffectToNode(bait.data);
...@@ -242,21 +238,21 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit { ...@@ -242,21 +238,21 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit {
removeIds.add(nodeId); removeIds.add(nodeId);
} }
if (bait.checked || showAll) { if (bait.checked || showAll) {
bait.data.proteinGroups.forEach((pg) => { bait.data.proteins.forEach((pg) => {
connectedProteinGroupIds.add(pg.id); connectedProteinAcs.add(pg.proteinAc);
}); });
} }
}); });
this.filteredProteins = []; this.filteredProteins = [];
for (const proteinGroup of this.proteinData.proteinGroups) { for (const protein of this.proteinData.proteins) {
const nodeId = `pg_${proteinGroup.groupId}`; const nodeId = `pg_${protein.proteinAc}`;
const contains = connectedProteinGroupIds.has(proteinGroup.id); const contains = connectedProteinAcs.has(protein.proteinAc);
const found = visibleIds.has(nodeId); const found = visibleIds.has(nodeId);
if (contains) { if (contains) {
this.filteredProteins.push(proteinGroup); this.filteredProteins.push(protein);
} }
if (contains && !found) { if (contains && !found) {
const node = this.mapProteinGroupToNode(proteinGroup); const node = this.mapProteinToNode(protein);
// this.nodeData.nodes.add(node); // this.nodeData.nodes.add(node);
addNodes.set(node.id, node); addNodes.set(node.id, node);
...@@ -279,24 +275,24 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit { ...@@ -279,24 +275,24 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit {
}); });
} }
private mapProteinGroupToNode(proteinGroup: ProteinGroup): any { private mapProteinToNode(protein: Protein): any {
let color = '#e2b600'; let color = '#e2b600';
if (this.analysis.inSelection(proteinGroup)) { if (this.analysis.inSelection(protein)) {
color = '#c42eff'; color = '#c42eff';
} }
return { return {
id: `pg_${proteinGroup.groupId}`, id: `pg_${protein.proteinAc}`,
label: `${proteinGroup.name}`, label: `${protein.proteinAc}`,
size: 10, font: '5px', color, shape: 'ellipse', shadow: false, size: 10, font: '5px', color, shape: 'ellipse', shadow: false,
x: proteinGroup.x, x: protein.x,
y: proteinGroup.y y: protein.y
}; };
} }
private mapEffectToNode(effect: Effect): any { private mapEffectToNode(effect: Effect): any {
return { return {
id: `eff_${effect.name}`, id: `eff_${effect.effectId}`,
label: `${effect.name}`, label: `${effect.effectId}`,
size: 10, color: '#118AB2', shape: 'box', shadow: true, font: {color: '#FFFFFF'}, size: 10, color: '#118AB2', shape: 'box', shadow: true, font: {color: '#FFFFFF'},
x: effect.x, x: effect.x,
y: effect.y y: effect.y
...@@ -304,15 +300,15 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit { ...@@ -304,15 +300,15 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit {
} }
private mapEdge(edge: any): any { private mapEdge(edge: any): any {
return {from: `pg_${edge.groupId}`, to: `eff_${edge.effectName}`, color: {color: '#afafaf', highlight: '#854141'}}; return {from: `pg_${edge.proteinAc}`, to: `eff_${edge.effectId}`, color: {color: '#afafaf', highlight: '#854141'}};
} }
private mapDataToNodes(data: ProteinNetwork): { nodes: any[], edges: any[] } { private mapDataToNodes(data: ProteinNetwork): { nodes: any[], edges: any[] } {
const nodes = []; const nodes = [];
const edges = []; const edges = [];
for (const proteinGroup of data.proteinGroups) { for (const protein of data.proteins) {
nodes.push(this.mapProteinGroupToNode(proteinGroup)); nodes.push(this.mapProteinToNode(protein));
} }
for (const effect of data.effects) { for (const effect of data.effects) {
...@@ -338,30 +334,27 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit { ...@@ -338,30 +334,27 @@ export class ExplorerPageComponent implements OnInit, AfterViewInit {
// Selection // Selection
// TODO: Improve usage of group ids, revise this after models have been changed to just protein // TODO: Improve usage of group ids, revise this after models have been changed to just protein
inSelection(groupIdStr: string): boolean { inSelection(proteinAc: string): boolean {
if (!this.proteinData || !groupIdStr) { if (!this.proteinData || !proteinAc) {
return false; return false;
} }
const groupId = Number(groupIdStr.split('_')[1]); const protein = this.proteinData.getProtein(proteinAc);
const protein = this.proteinData.getProteinGroup(groupId);
return this.analysis.inSelection(protein); return this.analysis.inSelection(protein);
} }
addToSelection(groupIdStr: string) { addToSelection(proteinAc: string) {
if (!groupIdStr) { if (!this.proteinData || !proteinAc) {
return; return false;
} }
const groupId = Number(groupIdStr.split('_')[1]); const protein = this.proteinData.getProtein(proteinAc);
const protein = this.proteinData.getProteinGroup(groupId);
this.analysis.addProtein(protein); this.analysis.addProtein(protein);
} }
removeFromSelection(groupIdStr: string) { removeFromSelection(proteinAc: string) {
if (!groupIdStr) { if (!this.proteinData || !proteinAc) {
return; return false;
} }
const groupId = Number(groupIdStr.split('_')[1]); const protein = this.proteinData.getProtein(proteinAc);
const protein = this.proteinData.getProteinGroup(groupId);
this.analysis.removeProtein(protein); this.analysis.removeProtein(protein);
} }
......
import {HttpClient} from '@angular/common/http'; import {HttpClient} from '@angular/common/http';
export interface ProteinGroup { export interface Protein {
id: number;
name: string; name: string;
groupId: number; proteinAc: string;
effects?: Effect[]; effects?: Effect[];
x?: number; x?: number;
y?: number; y?: number;
} }
export interface Effect { export interface Effect {
id: number; effectId: string;
name: string; effectName: string;
proteinGroups?: ProteinGroup[]; datasetName: string;
virusName: string;
proteins?: Protein[];
x?: number; x?: number;
y?: number; y?: number;
} }
export interface Edge { export interface Edge {
groupId: number; proteinAc: string;
effectName: string; effectId: string;
} }
export class ProteinNetwork { export class ProteinNetwork {
constructor(public proteinGroups: ProteinGroup[], public effects: Effect[], public edges: Edge[]) { constructor(public proteins: Protein[], public effects: Effect[], public edges: Edge[]) {
} }
public async loadPositions(http: HttpClient) { public async loadPositions(http: HttpClient) {
const nodePositions = await http.get(`assets/positions/network.json`).toPromise(); const nodePositions = await http.get(`assets/positions/network.json`).toPromise();
this.proteinGroups.forEach((node) => { this.proteins.forEach((node) => {
const nodePosition = nodePositions[`pg_${node.groupId}`]; const nodePosition = nodePositions[`pg_${node.proteinAc}`];
if (nodePosition) { if (nodePosition) {
node.x = nodePosition.x; node.x = nodePosition.x;
node.y = nodePosition.y; node.y = nodePosition.y;
} }
}); });
this.effects.forEach((node) => { this.effects.forEach((node) => {
const nodePosition = nodePositions[`eff_${node.name}`]; const nodePosition = nodePositions[`eff_${node.effectId}`];
if (nodePosition) { if (nodePosition) {
node.x = nodePosition.x; node.x = nodePosition.x;
node.y = nodePosition.y; node.y = nodePosition.y;
...@@ -45,27 +46,27 @@ export class ProteinNetwork { ...@@ -45,27 +46,27 @@ export class ProteinNetwork {
}); });
} }
public getProteinGroup(id: number): ProteinGroup { public getProtein(ac: string): Protein {
return this.proteinGroups.find((pg) => pg.groupId === id); return this.proteins.find((p) => p.proteinAc === ac);
} }
public getEffect(name: string): Effect { public getEffect(name: string): Effect {
return this.effects.find((eff) => eff.name === name); return this.effects.find((eff) => eff.effectId === name);
} }
public linkNodes() { public linkNodes() {
this.proteinGroups.forEach((pg) => { this.proteins.forEach((pg) => {
pg.effects = []; pg.effects = [];
}); });
this.effects.forEach((eff) => { this.effects.forEach((eff) => {
eff.proteinGroups = []; eff.proteins = [];
}); });
this.edges.forEach((edge) => { this.edges.forEach((edge) => {
const proteinGroup = this.getProteinGroup(edge.groupId); const proteinGroup = this.getProtein(edge.proteinAc);
const effect = this.getEffect(edge.effectName); const effect = this.getEffect(edge.effectId);
if (proteinGroup && effect) { if (proteinGroup && effect) {
proteinGroup.effects.push(effect); proteinGroup.effects.push(effect);
effect.proteinGroups.push(proteinGroup); effect.proteins.push(proteinGroup);
} }
}); });
} }
......
This diff is collapsed.
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment