@datagrok/peptides 1.21.5 → 1.21.7
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +8 -0
- package/dist/package-test.js +1 -1
- package/dist/package-test.js.map +1 -1
- package/dist/package.js +1 -1
- package/dist/package.js.map +1 -1
- package/package.json +1 -1
- package/src/demo/fasta.ts +25 -5
- package/src/model.ts +72 -22
- package/src/package.ts +4 -5
- package/src/peptideUtils.ts +5 -0
- package/src/tests/benchmarks.ts +4 -4
- package/src/tests/core.ts +1 -1
- package/src/tests/misc.ts +1 -1
- package/src/tests/model.ts +3 -1
- package/src/tests/table-view.ts +1 -1
- package/src/tests/viewers.ts +1 -1
- package/src/tests/widgets.ts +4 -4
- package/src/viewers/logo-summary.ts +5 -1
- package/src/viewers/sar-viewer.ts +21 -1
- package/test-console-output-1.log +69 -5975
- package/test-record-1.mp4 +0 -0
package/package.json
CHANGED
package/src/demo/fasta.ts
CHANGED
|
@@ -7,15 +7,33 @@ import * as C from '../utils/constants';
|
|
|
7
7
|
import {scaleActivity} from '../utils/misc';
|
|
8
8
|
import {ALIGNMENT, ALPHABET, NOTATION, TAGS as bioTAGS} from '@datagrok-libraries/bio/src/utils/macromolecule';
|
|
9
9
|
import {PeptidesModel} from '../model';
|
|
10
|
-
import {delay} from '@datagrok-libraries/utils/src/test';
|
|
10
|
+
import {awaitCheck, delay} from '@datagrok-libraries/utils/src/test';
|
|
11
|
+
import {MCLSettings} from '../utils/types';
|
|
11
12
|
|
|
12
13
|
export async function macromoleculeSarFastaDemoUI(): Promise<void> {
|
|
13
14
|
grok.shell.windows.showContextPanel = true;
|
|
14
15
|
const alignedSequenceCol = 'AlignedSequence';
|
|
15
16
|
const simpleActivityColName = 'IC50';
|
|
16
17
|
const simpleTable = DG.DataFrame.fromCsv(await _package.files.readAsText('aligned.csv'));
|
|
17
|
-
|
|
18
|
-
|
|
18
|
+
simpleTable.name = 'Simple peptides';
|
|
19
|
+
if (!simpleTable.id)
|
|
20
|
+
simpleTable.id = `Simple-peptides-analysis-table-id-${Math.random()}-${Date.now()}`;
|
|
21
|
+
const view = grok.shell.addTableView(simpleTable);
|
|
22
|
+
await delay(50);
|
|
23
|
+
const grid = view.grid;
|
|
24
|
+
await new Promise((res) => {
|
|
25
|
+
let timer: any = null;
|
|
26
|
+
const sub = grid?.onAfterDrawContent?.subscribe(() => {
|
|
27
|
+
if (timer)
|
|
28
|
+
clearTimeout(timer);
|
|
29
|
+
sub.unsubscribe();
|
|
30
|
+
res(undefined);
|
|
31
|
+
});
|
|
32
|
+
timer = setTimeout(() => {
|
|
33
|
+
sub.unsubscribe();
|
|
34
|
+
res(undefined);
|
|
35
|
+
}, 3000);
|
|
36
|
+
});
|
|
19
37
|
const simpleActivityCol = simpleTable.getCol(simpleActivityColName);
|
|
20
38
|
const simpleAlignedSeqCol = simpleTable.getCol(alignedSequenceCol);
|
|
21
39
|
simpleAlignedSeqCol.semType = DG.SEMTYPE.MACROMOLECULE;
|
|
@@ -28,7 +46,9 @@ export async function macromoleculeSarFastaDemoUI(): Promise<void> {
|
|
|
28
46
|
sequenceCol: simpleAlignedSeqCol,
|
|
29
47
|
clustersCol,
|
|
30
48
|
});
|
|
49
|
+
const mclSettings = new MCLSettings();
|
|
50
|
+
mclSettings.threshold = 94;
|
|
31
51
|
const model: PeptidesModel = await startAnalysis(simpleActivityCol, alignedCol, null, simpleTable, simpleScaledCol,
|
|
32
|
-
C.SCALING_METHODS.MINUS_LG) as PeptidesModel;
|
|
33
|
-
model.modifyWebLogoSelection({monomerOrCluster: 'D', positionOrClusterType: '13'});
|
|
52
|
+
C.SCALING_METHODS.MINUS_LG, {addMCL: true, useEmbeddingsClusters: true, mclSettings: mclSettings}) as PeptidesModel;
|
|
53
|
+
// model.modifyWebLogoSelection({monomerOrCluster: 'D', positionOrClusterType: '13'});
|
|
34
54
|
}
|
package/src/model.ts
CHANGED
|
@@ -146,11 +146,15 @@ export class PeptidesModel {
|
|
|
146
146
|
get analysisView(): DG.TableView {
|
|
147
147
|
if (this._analysisView === undefined) {
|
|
148
148
|
this._analysisView = this.id ? wu(grok.shell.tableViews).find(({dataFrame}) => dataFrame?.getTag(DG.TAGS.ID) === this.id) : undefined;
|
|
149
|
-
|
|
149
|
+
|
|
150
|
+
if (!this._analysisView && (grok.shell.v as any)?.preview instanceof DG.TableView && (grok.shell.v as any)?.preview?.dataFrame === this.df)
|
|
151
|
+
this._analysisView = (grok.shell.v as any)!.preview as any as DG.TableView;
|
|
152
|
+
|
|
153
|
+
if (!this._analysisView)
|
|
150
154
|
this._analysisView = grok.shell.addTableView(this.df);
|
|
151
155
|
}
|
|
152
156
|
|
|
153
|
-
if (this.df.getTag(C.TAGS.MULTIPLE_VIEWS) !== '1' && !this._layoutEventInitialized)
|
|
157
|
+
if (this.df.getTag(C.TAGS.MULTIPLE_VIEWS) !== '1' && !this._layoutEventInitialized && !grok.shell.isInDemo)
|
|
154
158
|
grok.shell.v = this._analysisView;
|
|
155
159
|
|
|
156
160
|
|
|
@@ -369,8 +373,37 @@ export class PeptidesModel {
|
|
|
369
373
|
// this is important bit. settings are written by startAnalysis function or other viewers, but separate viewers will not init the peptides model
|
|
370
374
|
if (settings)
|
|
371
375
|
model.init(settings);
|
|
376
|
+
|
|
377
|
+
let wasEmptySelectionBefore = true;
|
|
378
|
+
model.subs.push(DG.debounce(dataFrame.onSelectionChanged, 10).subscribe((_) => {
|
|
379
|
+
//clear all selections if user cleared the selection.
|
|
380
|
+
if (wasEmptySelectionBefore || dataFrame.selection.anyTrue || !model._analysisView || !document.contains(model._analysisView.root) ||
|
|
381
|
+
model._analysisView.dataFrame !== dataFrame || !model.positionColumns) {
|
|
382
|
+
wasEmptySelectionBefore = !dataFrame?.selection?.anyTrue;
|
|
383
|
+
return;
|
|
384
|
+
}
|
|
385
|
+
model.webLogoSelection = initSelection(model.positionColumns!);
|
|
386
|
+
const mpViewer = model.findViewer(VIEWER_TYPE.SEQUENCE_VARIABILITY_MAP) as MonomerPosition | null;
|
|
387
|
+
if (mpViewer != null) {
|
|
388
|
+
mpViewer.invariantMapSelection = initSelection(model.positionColumns!);
|
|
389
|
+
mpViewer.mutationCliffsSelection = initSelection(model.positionColumns!);
|
|
390
|
+
}
|
|
391
|
+
const mprViewer = model.findViewer(VIEWER_TYPE.MOST_POTENT_RESIDUES) as MostPotentResidues | null;
|
|
392
|
+
if (mprViewer != null)
|
|
393
|
+
mprViewer.mutationCliffsSelection = initSelection(model.positionColumns!);
|
|
394
|
+
const lstViewer = model.findViewer(VIEWER_TYPE.LOGO_SUMMARY_TABLE) as LogoSummaryTable | null;
|
|
395
|
+
if (lstViewer != null) {
|
|
396
|
+
lstViewer.initClusterSelection({notify: true});
|
|
397
|
+
lstViewer.render();
|
|
398
|
+
}
|
|
399
|
+
wasEmptySelectionBefore = true;
|
|
400
|
+
//model.fireBitsetChanged();
|
|
401
|
+
}));
|
|
372
402
|
}
|
|
373
|
-
|
|
403
|
+
|
|
404
|
+
const model = dataFrame.temp[PeptidesModel.modelName] as PeptidesModel;
|
|
405
|
+
|
|
406
|
+
return model;
|
|
374
407
|
}
|
|
375
408
|
|
|
376
409
|
/**
|
|
@@ -403,7 +436,7 @@ export class PeptidesModel {
|
|
|
403
436
|
* @return {DG.Accordion | null} - Accordion with analysis info based on current selection
|
|
404
437
|
*/
|
|
405
438
|
createAccordion(): DG.Accordion | null {
|
|
406
|
-
const trueModel: PeptidesModel | undefined =
|
|
439
|
+
const trueModel: PeptidesModel | undefined = this.df?.temp[PeptidesModel.modelName];
|
|
407
440
|
if (!trueModel)
|
|
408
441
|
return null;
|
|
409
442
|
|
|
@@ -428,41 +461,43 @@ export class PeptidesModel {
|
|
|
428
461
|
const selectedClusters: string = (trueLSTViewer === null ? [] :
|
|
429
462
|
trueLSTViewer.clusterSelection[CLUSTER_TYPE.ORIGINAL].concat(trueLSTViewer.clusterSelection[CLUSTER_TYPE.CUSTOM]))
|
|
430
463
|
.join(', ');
|
|
431
|
-
|
|
432
|
-
|
|
433
|
-
|
|
464
|
+
const htmlTextEl = (t: string): HTMLElement => {
|
|
465
|
+
const el = ui.divText(t);
|
|
466
|
+
el.innerHTML = t;
|
|
467
|
+
return el;
|
|
434
468
|
}
|
|
469
|
+
if (selectedClusters.length !== 0)
|
|
470
|
+
selectionDescription.push(htmlTextEl(`<b>Logo Summary Table</b> clusters: ${selectedClusters}`));
|
|
435
471
|
|
|
436
472
|
// Monomer-Position viewer selection overview
|
|
437
473
|
const trueMPViewer = trueModel.findViewer(VIEWER_TYPE.SEQUENCE_VARIABILITY_MAP) as MonomerPosition | null;
|
|
438
474
|
const selectedMonomerPositions = getSelectionString(trueMPViewer?.invariantMapSelection ?? {});
|
|
439
475
|
const selectedMutationCliffs = getSelectionString(trueMPViewer?.mutationCliffsSelection ?? {});
|
|
440
|
-
if (selectedMonomerPositions.length !== 0 || selectedMutationCliffs.length !== 0)
|
|
441
|
-
|
|
476
|
+
// if (selectedMonomerPositions.length !== 0 || selectedMutationCliffs.length !== 0)
|
|
477
|
+
// selectionDescription.push(ui.h1('Sequence Variabily Map viewer selection'));
|
|
442
478
|
|
|
443
479
|
|
|
444
480
|
if (selectedMonomerPositions.length !== 0)
|
|
445
|
-
selectionDescription.push(
|
|
481
|
+
selectionDescription.push(htmlTextEl(`<b>Invariant map</b>: ${selectedMonomerPositions}`));
|
|
446
482
|
|
|
447
483
|
|
|
448
484
|
if (selectedMutationCliffs.length !== 0)
|
|
449
|
-
selectionDescription.push(
|
|
485
|
+
selectionDescription.push(htmlTextEl(`<b>Mutation cliffs</b>: ${selectedMutationCliffs}`));
|
|
450
486
|
|
|
451
487
|
|
|
452
488
|
// Most Potent Residues viewer selection overview
|
|
453
489
|
const trueMPRViewer = trueModel.findViewer(VIEWER_TYPE.MOST_POTENT_RESIDUES) as MostPotentResidues | null;
|
|
454
490
|
const selectedMPRMonomerPositions = getSelectionString(trueMPRViewer?.mutationCliffsSelection ?? {});
|
|
455
|
-
if (selectedMPRMonomerPositions.length !== 0)
|
|
456
|
-
selectionDescription.push(
|
|
457
|
-
selectionDescription.push(ui.divText(`Selected monomer-positions: ${selectedMPRMonomerPositions}`));
|
|
458
|
-
}
|
|
491
|
+
if (selectedMPRMonomerPositions.length !== 0)
|
|
492
|
+
selectionDescription.push(htmlTextEl(`<b>Most potent residues</b>: ${selectedMPRMonomerPositions}`));
|
|
459
493
|
|
|
460
494
|
// WebLogo selection overview
|
|
461
495
|
const selectedMonomers = getSelectionString(trueModel.webLogoSelection);
|
|
462
|
-
if (selectedMonomers.length !== 0)
|
|
463
|
-
selectionDescription.push(
|
|
464
|
-
|
|
465
|
-
|
|
496
|
+
if (selectedMonomers.length !== 0)
|
|
497
|
+
selectionDescription.push(htmlTextEl(`<b>WebLogo</b>: ${selectedMonomers}`));
|
|
498
|
+
|
|
499
|
+
if (selectionDescription.length !== 0)
|
|
500
|
+
selectionDescription.unshift(ui.h1('Selection Sources'));
|
|
466
501
|
|
|
467
502
|
const descritionsHost = ui.div(ui.divV(selectionDescription));
|
|
468
503
|
acc.addTitle(ui.divV([
|
|
@@ -836,15 +871,23 @@ export class PeptidesModel {
|
|
|
836
871
|
|
|
837
872
|
const selection = this.df.selection;
|
|
838
873
|
const filter = this.df.filter;
|
|
839
|
-
|
|
874
|
+
let prevTimer: any = null;
|
|
840
875
|
const showAccordion = (): void => {
|
|
841
876
|
try {
|
|
877
|
+
if (prevTimer != null) {
|
|
878
|
+
clearTimeout(prevTimer);
|
|
879
|
+
prevTimer = null;
|
|
880
|
+
}
|
|
842
881
|
const acc = this.createAccordion();
|
|
843
882
|
if (acc === null)
|
|
844
883
|
return;
|
|
845
884
|
|
|
846
|
-
|
|
885
|
+
// these shinanigans are needed to prevent frozen custom accordion from sticking
|
|
847
886
|
grok.shell.o = acc.root;
|
|
887
|
+
prevTimer = setTimeout(() => {
|
|
888
|
+
if (grok.shell.o != acc.root)
|
|
889
|
+
grok.shell.o = acc.root;
|
|
890
|
+
}, 1500);
|
|
848
891
|
} catch (e) {
|
|
849
892
|
console.error(e);
|
|
850
893
|
}
|
|
@@ -1134,6 +1177,8 @@ export class PeptidesModel {
|
|
|
1134
1177
|
};
|
|
1135
1178
|
const logoSummaryTable = await this.df.plot
|
|
1136
1179
|
.fromType(VIEWER_TYPE.LOGO_SUMMARY_TABLE, viewerProperties) as LogoSummaryTable;
|
|
1180
|
+
if (grok.shell.isInDemo)
|
|
1181
|
+
this.analysisView.addViewer(logoSummaryTable);
|
|
1137
1182
|
this.analysisView.dockManager.dock(logoSummaryTable, DG.DOCK_TYPE.RIGHT, null, VIEWER_TYPE.LOGO_SUMMARY_TABLE);
|
|
1138
1183
|
|
|
1139
1184
|
logoSummaryTable.viewerGrid.invalidate();
|
|
@@ -1173,6 +1218,9 @@ export class PeptidesModel {
|
|
|
1173
1218
|
};
|
|
1174
1219
|
const monomerPosition = await this.df.plot
|
|
1175
1220
|
.fromType(VIEWER_TYPE.SEQUENCE_VARIABILITY_MAP, viewerProperties) as MonomerPosition;
|
|
1221
|
+
// for browse mode, we need to add viewer to the analysis view before docking. remove with release of 1.25
|
|
1222
|
+
if (grok.shell.isInDemo)
|
|
1223
|
+
this.analysisView.addViewer(monomerPosition);
|
|
1176
1224
|
const mostPotentResidues = this.findViewer(VIEWER_TYPE.MOST_POTENT_RESIDUES) as MostPotentResidues | null;
|
|
1177
1225
|
const dm = this.analysisView.dockManager;
|
|
1178
1226
|
const [dockType, refNode, ratio] = mostPotentResidues === null ? [DG.DOCK_TYPE.DOWN, null, undefined] :
|
|
@@ -1195,6 +1243,8 @@ export class PeptidesModel {
|
|
|
1195
1243
|
};
|
|
1196
1244
|
const mostPotentResidues =
|
|
1197
1245
|
await this.df.plot.fromType(VIEWER_TYPE.MOST_POTENT_RESIDUES, viewerProperties) as MostPotentResidues;
|
|
1246
|
+
if (grok.shell.isInDemo)
|
|
1247
|
+
this.analysisView.addViewer(mostPotentResidues);
|
|
1198
1248
|
const monomerPosition = this.findViewer(VIEWER_TYPE.SEQUENCE_VARIABILITY_MAP) as MonomerPosition | null;
|
|
1199
1249
|
const dm = this.analysisView.dockManager;
|
|
1200
1250
|
const [dockType, refNode, ratio] = monomerPosition === null ? [DG.DOCK_TYPE.DOWN, null, undefined] :
|
|
@@ -1327,7 +1377,7 @@ export class PeptidesModel {
|
|
|
1327
1377
|
minClusterSize: mclParams.minClusterSize,
|
|
1328
1378
|
} satisfies MCLSerializableOptions);
|
|
1329
1379
|
|
|
1330
|
-
const tv = grok.shell.getTableView(this.df.name);
|
|
1380
|
+
const tv = this.analysisView ?? grok.shell.getTableView(this.df.name);
|
|
1331
1381
|
if (tv) {
|
|
1332
1382
|
const func = DG.Func.find({package: 'EDA', name: 'markovClusteringViewer'})[0];
|
|
1333
1383
|
if (!func)
|
package/src/package.ts
CHANGED
|
@@ -36,8 +36,7 @@ export async function initPeptides(): Promise<void> {
|
|
|
36
36
|
try {
|
|
37
37
|
monomerWorks ??= new MonomerWorks(await grok.functions.call('Bio:getBioLib'));
|
|
38
38
|
treeHelper ??= await getTreeHelper();
|
|
39
|
-
await PeptideUtils.
|
|
40
|
-
await PeptideUtils.loadMonomerLib();
|
|
39
|
+
await PeptideUtils.loadComponents();
|
|
41
40
|
} catch (e) {
|
|
42
41
|
grok.log.error(e as string);
|
|
43
42
|
}
|
|
@@ -178,9 +177,9 @@ export function manualAlignment(_monomer: string): DG.Widget {
|
|
|
178
177
|
}
|
|
179
178
|
|
|
180
179
|
// --- Demo ---
|
|
181
|
-
//name:
|
|
182
|
-
//description:
|
|
183
|
-
//meta.demoPath: Bioinformatics |
|
|
180
|
+
//name: Peptide SAR
|
|
181
|
+
//description: Peptide SAR Analysis demo on peptide sequences in FASTA format
|
|
182
|
+
//meta.demoPath: Bioinformatics | Peptide SAR
|
|
184
183
|
//meta.demoSkip: GROK-14320
|
|
185
184
|
export async function macromoleculeSarFastaDemo(): Promise<void> {
|
|
186
185
|
return await macromoleculeSarFastaDemoUI();
|
package/src/peptideUtils.ts
CHANGED
|
@@ -20,6 +20,11 @@ export class PeptideUtils {
|
|
|
20
20
|
this._secHelper ??= await getSeqHelper();
|
|
21
21
|
}
|
|
22
22
|
|
|
23
|
+
public static async loadComponents(): Promise<void> {
|
|
24
|
+
await this.loadSeqHelper();
|
|
25
|
+
await this.loadMonomerLib();
|
|
26
|
+
}
|
|
27
|
+
|
|
23
28
|
public static async loadMonomerLib(): Promise<void> {
|
|
24
29
|
this._monomerLibHelper ??= await getMonomerLibHelper();
|
|
25
30
|
await this._monomerLibHelper.awaitLoaded();
|
package/src/tests/benchmarks.ts
CHANGED
|
@@ -17,7 +17,7 @@ const benchmarkDatasetSizes = [5, 50, 100, 200];
|
|
|
17
17
|
|
|
18
18
|
category('Benchmarks: Mutation Cliffs', () => {
|
|
19
19
|
before(async () => {
|
|
20
|
-
await PeptideUtils.
|
|
20
|
+
await PeptideUtils.loadComponents();
|
|
21
21
|
});
|
|
22
22
|
for (const size of benchmarkDatasetSizes)
|
|
23
23
|
test(`${size}k sequences`, async () => await mutationCliffsBenchmark(size), {timeout: 300000});
|
|
@@ -25,7 +25,7 @@ category('Benchmarks: Mutation Cliffs', () => {
|
|
|
25
25
|
|
|
26
26
|
category('Benchmarks: Cluster stats', () => {
|
|
27
27
|
before(async () => {
|
|
28
|
-
await PeptideUtils.
|
|
28
|
+
await PeptideUtils.loadComponents();
|
|
29
29
|
});
|
|
30
30
|
for (const size of benchmarkDatasetSizes) {
|
|
31
31
|
test(`${size}k sequences`, async () => {
|
|
@@ -49,7 +49,7 @@ category('Benchmarks: Cluster stats', () => {
|
|
|
49
49
|
|
|
50
50
|
category('Benchmarks: Monomer-Position stats', () => {
|
|
51
51
|
before(async () => {
|
|
52
|
-
await PeptideUtils.
|
|
52
|
+
await PeptideUtils.loadComponents();
|
|
53
53
|
});
|
|
54
54
|
for (const size of benchmarkDatasetSizes) {
|
|
55
55
|
test(`${size}k sequences`, async () => {
|
|
@@ -78,7 +78,7 @@ category('Benchmarks: Monomer-Position stats', () => {
|
|
|
78
78
|
|
|
79
79
|
category('Benchmarks: Analysis start', () => {
|
|
80
80
|
before(async () => {
|
|
81
|
-
await PeptideUtils.
|
|
81
|
+
await PeptideUtils.loadComponents();
|
|
82
82
|
});
|
|
83
83
|
for (const size of benchmarkDatasetSizes) {
|
|
84
84
|
test(`${size}k sequences`, async () => {
|
package/src/tests/core.ts
CHANGED
|
@@ -15,7 +15,7 @@ import {PeptideUtils} from '../peptideUtils';
|
|
|
15
15
|
category('Core', () => {
|
|
16
16
|
const alignedSequenceCol = 'AlignedSequence';
|
|
17
17
|
before(async () => {
|
|
18
|
-
await PeptideUtils.
|
|
18
|
+
await PeptideUtils.loadComponents();
|
|
19
19
|
});
|
|
20
20
|
let model: PeptidesModel | null = null;
|
|
21
21
|
test('Start analysis: simple', async () => {
|
package/src/tests/misc.ts
CHANGED
|
@@ -14,7 +14,7 @@ category('Algorithms', () => {
|
|
|
14
14
|
let targetCol: type.RawColumn;
|
|
15
15
|
|
|
16
16
|
before(async () => {
|
|
17
|
-
await PeptideUtils.
|
|
17
|
+
await PeptideUtils.loadComponents();
|
|
18
18
|
|
|
19
19
|
activityCol = DG.Column.fromList('int', 'test', [1, 2, 5]).getRawData();
|
|
20
20
|
monomerColumns = [
|
package/src/tests/model.ts
CHANGED
|
@@ -63,8 +63,10 @@ category('Model: Settings', () => {
|
|
|
63
63
|
};
|
|
64
64
|
|
|
65
65
|
before(async () => {
|
|
66
|
-
await PeptideUtils.
|
|
66
|
+
await PeptideUtils.loadComponents();
|
|
67
67
|
df = DG.DataFrame.fromCsv(await _package.files.readAsText('tests/HELM_small.csv'));
|
|
68
|
+
df.name = 'HELM_small';
|
|
69
|
+
//df.id ??= `HELM_small-${Date.now()}`;
|
|
68
70
|
activityCol = df.getCol(TEST_COLUMN_NAMES.ACTIVITY);
|
|
69
71
|
sequenceCol = df.getCol(TEST_COLUMN_NAMES.SEQUENCE);
|
|
70
72
|
sequenceCol.semType = DG.SEMTYPE.MACROMOLECULE;
|
package/src/tests/table-view.ts
CHANGED
|
@@ -27,7 +27,7 @@ category('Table view', () => {
|
|
|
27
27
|
const secondCluster = {monomerOrCluster: '1', positionOrClusterType: CLUSTER_TYPE.ORIGINAL, count: 3};
|
|
28
28
|
|
|
29
29
|
before(async () => {
|
|
30
|
-
await PeptideUtils.
|
|
30
|
+
await PeptideUtils.loadComponents();
|
|
31
31
|
|
|
32
32
|
df = DG.DataFrame.fromCsv(await _package.files.readAsText('tests/HELM_small.csv'));
|
|
33
33
|
activityCol = df.getCol(TEST_COLUMN_NAMES.ACTIVITY);
|
package/src/tests/viewers.ts
CHANGED
|
@@ -18,7 +18,7 @@ category('Viewers: Basic', () => {
|
|
|
18
18
|
let df: DG.DataFrame;
|
|
19
19
|
|
|
20
20
|
before(async () => {
|
|
21
|
-
await PeptideUtils.
|
|
21
|
+
await PeptideUtils.loadComponents();
|
|
22
22
|
|
|
23
23
|
df = DG.DataFrame.fromCsv(await _package.files.readAsText('tests/HELM_small.csv'));
|
|
24
24
|
await delay(500);
|
package/src/tests/widgets.ts
CHANGED
|
@@ -26,7 +26,7 @@ category('Widgets: Settings', () => {
|
|
|
26
26
|
let scaledActivityCol: DG.Column<number>;
|
|
27
27
|
|
|
28
28
|
before(async () => {
|
|
29
|
-
await PeptideUtils.
|
|
29
|
+
await PeptideUtils.loadComponents();
|
|
30
30
|
|
|
31
31
|
df = DG.DataFrame.fromCsv(await _package.files.readAsText('tests/HELM_small.csv'));
|
|
32
32
|
activityCol = df.getCol(TEST_COLUMN_NAMES.ACTIVITY);
|
|
@@ -73,7 +73,7 @@ category('Widgets: Distribution panel', () => {
|
|
|
73
73
|
let scaledActivityCol: DG.Column<number>;
|
|
74
74
|
|
|
75
75
|
before(async () => {
|
|
76
|
-
await PeptideUtils.
|
|
76
|
+
await PeptideUtils.loadComponents();
|
|
77
77
|
|
|
78
78
|
df = DG.DataFrame.fromCsv(await _package.files.readAsText('tests/HELM_small.csv'));
|
|
79
79
|
activityCol = df.getCol(TEST_COLUMN_NAMES.ACTIVITY);
|
|
@@ -114,7 +114,7 @@ category('Widgets: Mutation cliffs', () => {
|
|
|
114
114
|
let scaledActivityCol: DG.Column<number>;
|
|
115
115
|
|
|
116
116
|
before(async () => {
|
|
117
|
-
await PeptideUtils.
|
|
117
|
+
await PeptideUtils.loadComponents();
|
|
118
118
|
|
|
119
119
|
df = DG.DataFrame.fromCsv(await _package.files.readAsText('tests/HELM_small.csv'));
|
|
120
120
|
activityCol = df.getCol(TEST_COLUMN_NAMES.ACTIVITY);
|
|
@@ -159,7 +159,7 @@ category('Widgets: Actions', () => {
|
|
|
159
159
|
let scaledActivityCol: DG.Column<number>;
|
|
160
160
|
|
|
161
161
|
before(async () => {
|
|
162
|
-
await PeptideUtils.
|
|
162
|
+
await PeptideUtils.loadComponents();
|
|
163
163
|
|
|
164
164
|
df = DG.DataFrame.fromCsv(await _package.files.readAsText('tests/HELM_small.csv'));
|
|
165
165
|
await df.meta.detectSemanticTypes();
|
|
@@ -714,8 +714,12 @@ export class LogoSummaryTable extends DG.JsViewer implements ILogoSummaryTable {
|
|
|
714
714
|
});
|
|
715
715
|
grid.root.addEventListener('mouseleave', (_ev) => this.model.unhighlight());
|
|
716
716
|
DG.debounce(grid.onCurrentCellChanged, 500).subscribe((gridCell) => {
|
|
717
|
-
if (!gridCell.isTableCell)
|
|
717
|
+
if (!gridCell.isTableCell || gridCell.gridRow === -1) {
|
|
718
|
+
this.initClusterSelection({notify: false});
|
|
719
|
+
this.model.fireBitsetChanged(VIEWER_TYPE.LOGO_SUMMARY_TABLE);
|
|
720
|
+
grid.invalidate();
|
|
718
721
|
return;
|
|
722
|
+
}
|
|
719
723
|
|
|
720
724
|
|
|
721
725
|
try {
|
|
@@ -882,6 +882,16 @@ export class MonomerPosition extends SARViewer {
|
|
|
882
882
|
try {
|
|
883
883
|
if (!gridCell || !gridCell.dart || !gridCell?.cell?.column?.name || this._monomerMetaColumns.has(gridCell.cell.column.name))
|
|
884
884
|
return;
|
|
885
|
+
if (gridCell.gridRow === -1) {
|
|
886
|
+
if (this.mode === SELECTION_MODE.INVARIANT_MAP)
|
|
887
|
+
this._invariantMapSelection = initSelection(this.positionColumns);
|
|
888
|
+
else
|
|
889
|
+
this._mutationCliffsSelection = initSelection(this.positionColumns);
|
|
890
|
+
|
|
891
|
+
this.model.fireBitsetChanged(VIEWER_TYPE.SEQUENCE_VARIABILITY_MAP);
|
|
892
|
+
grid.invalidate();
|
|
893
|
+
}
|
|
894
|
+
|
|
885
895
|
if (!this.keyPressed)
|
|
886
896
|
return;
|
|
887
897
|
|
|
@@ -920,7 +930,10 @@ export class MonomerPosition extends SARViewer {
|
|
|
920
930
|
setTimeout(() => grid?.invalidate(), 300);
|
|
921
931
|
} finally {
|
|
922
932
|
this.keyPressed = false;
|
|
923
|
-
|
|
933
|
+
if (gridCell.tableColumn?.name && gridCell.grid)
|
|
934
|
+
this.currentGridCell = DG.GridCell.fromColumnRow(gridCell.grid, gridCell.tableColumn.name, gridCell.gridRow);
|
|
935
|
+
else
|
|
936
|
+
this.currentGridCell = null;
|
|
924
937
|
}
|
|
925
938
|
});
|
|
926
939
|
grid.root.addEventListener('keydown', (ev) => {
|
|
@@ -1265,6 +1278,13 @@ export class MostPotentResidues extends SARViewer {
|
|
|
1265
1278
|
});
|
|
1266
1279
|
DG.debounce(grid.onCurrentCellChanged, 500).subscribe((gridCell: DG.GridCell) => {
|
|
1267
1280
|
try {
|
|
1281
|
+
if (gridCell.gridRow === -1) {
|
|
1282
|
+
this._mutationCliffsSelection = initSelection(this.positionColumns);
|
|
1283
|
+
this.model.fireBitsetChanged(VIEWER_TYPE.MOST_POTENT_RESIDUES);
|
|
1284
|
+
grid.invalidate();
|
|
1285
|
+
return;
|
|
1286
|
+
}
|
|
1287
|
+
|
|
1268
1288
|
if ((this.keyPressed && mprDf.currentCol.name !== C.COLUMNS_NAMES.MEAN_DIFFERENCE) || !this.keyPressed)
|
|
1269
1289
|
return;
|
|
1270
1290
|
|