@datagrok/helm 2.1.34 → 2.2.1
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/.eslintrc.json +1 -1
- package/CHANGELOG.md +30 -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 +12 -12
- package/src/cell-renderer.ts +21 -153
- package/src/constants.ts +0 -11
- package/src/helm-helper.ts +9 -10
- package/src/helm-monomer-placer.ts +21 -85
- package/src/helm-web-editor.ts +5 -2
- package/src/package-test.ts +6 -2
- package/src/package-utils.ts +150 -0
- package/src/package.ts +96 -100
- package/src/tests/get-monomer-tests.ts +210 -0
- package/src/tests/helm-service-tests.ts +97 -0
- package/src/tests/helm-tests.ts +1 -0
- package/src/tests/properties-widget-tests.ts +4 -2
- package/src/tests/renderers-tests.ts +97 -22
- package/src/types/dojo.ts +3 -0
- package/src/types/index.ts +0 -0
- package/src/utils/dummy-monomer.ts +184 -0
- package/src/utils/get-hovered.ts +104 -0
- package/src/utils/get-monomer.ts +111 -0
- package/src/utils/helm-grid-cell-renderer.ts +199 -0
- package/src/utils/helm-service.ts +130 -0
- package/src/utils/index.ts +7 -7
- package/webpack.config.js +7 -0
- /package/src/tests/{get-molfiles.ts → get-molfiles-tests.ts} +0 -0
|
@@ -0,0 +1,130 @@
|
|
|
1
|
+
import * as grok from 'datagrok-api/grok';
|
|
2
|
+
import * as ui from 'datagrok-api/ui';
|
|
3
|
+
import * as DG from 'datagrok-api/dg';
|
|
4
|
+
|
|
5
|
+
import * as org from 'org';
|
|
6
|
+
import * as scil from 'scil';
|
|
7
|
+
import * as JSDraw2 from 'JSDraw2';
|
|
8
|
+
|
|
9
|
+
import $ from 'cash-dom';
|
|
10
|
+
import {Subject, Unsubscribable} from 'rxjs';
|
|
11
|
+
|
|
12
|
+
import {errInfo} from '@datagrok-libraries/bio/src/utils/err-info';
|
|
13
|
+
import {IMonomerLib} from '@datagrok-libraries/bio/src/types/index';
|
|
14
|
+
import {RenderTask} from '@datagrok-libraries/bio/src/utils/cell-renderer-async-base';
|
|
15
|
+
import {HelmAux, HelmProps, HelmServiceBase} from '@datagrok-libraries/bio/src/viewers/helm-service';
|
|
16
|
+
import {svgToImage} from '@datagrok-libraries/utils/src/svg';
|
|
17
|
+
|
|
18
|
+
import {_package} from '../package';
|
|
19
|
+
|
|
20
|
+
export class HelmService extends HelmServiceBase {
|
|
21
|
+
private readonly hostDiv: HTMLDivElement;
|
|
22
|
+
|
|
23
|
+
private editor!: JSDraw2.Editor;
|
|
24
|
+
private image: HTMLImageElement | null = null;
|
|
25
|
+
|
|
26
|
+
constructor() {
|
|
27
|
+
super(_package.logger);
|
|
28
|
+
|
|
29
|
+
this.hostDiv = ui.box();
|
|
30
|
+
// this.hostDiv.style.display = 'none'; // Disables drawing at all
|
|
31
|
+
this.hostDiv.style.position = 'absolute';
|
|
32
|
+
this.hostDiv.style.left = '0px';
|
|
33
|
+
this.hostDiv.style.right = '0px';
|
|
34
|
+
this.hostDiv.style.width = '0px';
|
|
35
|
+
this.hostDiv.style.height = '0px';
|
|
36
|
+
this.hostDiv.style.visibility = 'hidden';
|
|
37
|
+
document.body.appendChild(this.hostDiv);
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
protected override toLog(): string {
|
|
41
|
+
return `Helm: ${super.toLog()}`;
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
protected override async requestRender(
|
|
45
|
+
key: keyof any | undefined, task: RenderTask<HelmProps, HelmAux>, renderHandler: (aux: HelmAux) => void
|
|
46
|
+
): Promise<[Unsubscribable, number, () => void]> {
|
|
47
|
+
const logPrefix = `${this.toLog()}.requestRender()`;
|
|
48
|
+
this.logger.debug(`${logPrefix}, start, ` + `key: ${key?.toString()}`);
|
|
49
|
+
const emptyCanvasHash: number = 0;
|
|
50
|
+
|
|
51
|
+
if (!this.editor) {
|
|
52
|
+
this.editor = new JSDraw2.Editor(this.hostDiv,
|
|
53
|
+
{width: task.props.width, height: task.props.height, skin: 'w8', viewonly: true});
|
|
54
|
+
}
|
|
55
|
+
const lST = window.performance.now();
|
|
56
|
+
this.editor.options.width = task.props.width;
|
|
57
|
+
this.editor.options.height = task.props.height;
|
|
58
|
+
this.editor.resize(task.props.width, task.props.height);
|
|
59
|
+
const helmStr = task.props.helm;
|
|
60
|
+
if (helmStr) {
|
|
61
|
+
// getMonomerOverrideAndLogAlert(
|
|
62
|
+
// this.monomerLib,
|
|
63
|
+
// getMonomerPatched,
|
|
64
|
+
// () => {
|
|
65
|
+
// this.logger.debug(`${logPrefix}, editor.setData( '${helmStr}' )`);
|
|
66
|
+
// this.editor.setData(helmStr, 'helm');
|
|
67
|
+
// }, this.logger);
|
|
68
|
+
this.logger.debug(`${logPrefix}, editor.setData( '${helmStr}' )`);
|
|
69
|
+
this.editor.setData(helmStr, 'helm');
|
|
70
|
+
}
|
|
71
|
+
if (!helmStr)
|
|
72
|
+
this.editor.reset();
|
|
73
|
+
|
|
74
|
+
const bBox = (this.editor.div.children[0] as SVGSVGElement).getBBox();
|
|
75
|
+
const aux: HelmAux = {
|
|
76
|
+
mol: this.editor.m.clone(false),
|
|
77
|
+
bBox: new DG.Rect(bBox.x, bBox.y, bBox.width + 2, bBox.height + 2) /* adjust for clipping right/bottom */,
|
|
78
|
+
cBox: new DG.Rect(0, 0, task.props.width, task.props.height),
|
|
79
|
+
};
|
|
80
|
+
const lET = window.performance.now();
|
|
81
|
+
|
|
82
|
+
const svgEl = $(this.hostDiv).find('svg').get(0) as unknown as SVGSVGElement;
|
|
83
|
+
const dpr = window.devicePixelRatio;
|
|
84
|
+
|
|
85
|
+
const rST = window.performance.now();
|
|
86
|
+
const renderHandlerInt = (): void => {
|
|
87
|
+
const rET: number = window.performance.now();
|
|
88
|
+
this.logger.debug(`${logPrefix}.renderHandlerInt(), ` +
|
|
89
|
+
`key: ${key?.toString()}, ` +
|
|
90
|
+
`load: ${lET - lST} ms,\n ` + `renderET: ${rET - rST} ms, ` +
|
|
91
|
+
`emptyCanvasHash: ${emptyCanvasHash}`);
|
|
92
|
+
renderHandler(aux);
|
|
93
|
+
};
|
|
94
|
+
|
|
95
|
+
const renderEvent = new Subject();
|
|
96
|
+
const renderSub = renderEvent.subscribe(() => {
|
|
97
|
+
const logPrefixInt = `${logPrefix} on renderEvent`;
|
|
98
|
+
this.logger.debug(`${logPrefixInt}`);
|
|
99
|
+
});
|
|
100
|
+
const trigger = (): void => {
|
|
101
|
+
svgToImage(svgEl, dpr).then((imageEl) => {
|
|
102
|
+
this.image = imageEl;
|
|
103
|
+
renderHandlerInt(); // calls onRendered()
|
|
104
|
+
});
|
|
105
|
+
};
|
|
106
|
+
this.logger.debug(`${logPrefix}, end, ` + `key: ${key?.toString()}`);
|
|
107
|
+
return [renderSub, -1, trigger];
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
protected onRendered(
|
|
111
|
+
key: keyof any | undefined, task: RenderTask<HelmProps, HelmAux>, emptyCanvasHash: number, aux: HelmAux
|
|
112
|
+
): boolean {
|
|
113
|
+
const dpr = window.devicePixelRatio;
|
|
114
|
+
const canvas = ui.canvas(task.props.width, task.props.height);
|
|
115
|
+
try {
|
|
116
|
+
const g = canvas.getContext('2d');
|
|
117
|
+
if (!this.image || !g) return false;
|
|
118
|
+
// g.fillStyle = '#C0C0FF';
|
|
119
|
+
// g.fillRect(0, 0, canvas.width, canvas.height);
|
|
120
|
+
g.drawImage(this.image, 0, 0);
|
|
121
|
+
task.onAfterRender(canvas, aux);
|
|
122
|
+
} finally {
|
|
123
|
+
canvas.remove();
|
|
124
|
+
}
|
|
125
|
+
return true;
|
|
126
|
+
}
|
|
127
|
+
|
|
128
|
+
async reset(): Promise<void> { }
|
|
129
|
+
}
|
|
130
|
+
|
package/src/utils/index.ts
CHANGED
|
@@ -1,5 +1,10 @@
|
|
|
1
1
|
import * as DG from 'datagrok-api/dg';
|
|
2
2
|
|
|
3
|
+
import * as scil from 'scil';
|
|
4
|
+
import * as org from 'org';
|
|
5
|
+
|
|
6
|
+
import {_package} from '../package';
|
|
7
|
+
|
|
3
8
|
import {
|
|
4
9
|
RGROUP_CAP_GROUP_NAME,
|
|
5
10
|
RGROUP_CAP_GROUP_SMILES,
|
|
@@ -39,7 +44,6 @@ export function parseHelm(s: string): string[] {
|
|
|
39
44
|
const sections = split(s, '$');
|
|
40
45
|
s = sections[0];
|
|
41
46
|
const monomers = [];
|
|
42
|
-
//@ts-ignore
|
|
43
47
|
if (!scil.Utils.isNullOrEmpty(s)) {
|
|
44
48
|
const seqs = split(s, '|');
|
|
45
49
|
for (let i = 0; i < seqs.length; ++i) {
|
|
@@ -88,13 +92,11 @@ export function parseHelm(s: string): string[] {
|
|
|
88
92
|
// * used in org.helm.webeditor / scil.helm.Monomers / org.helm.webeditor.Monomers .
|
|
89
93
|
// */
|
|
90
94
|
// export function findMonomers(helmString: string) {
|
|
91
|
-
// //@ts-ignore
|
|
92
95
|
// const types: string[] = Object.keys(org.helm.webeditor.monomerTypeList());
|
|
93
96
|
// const monomerNameList: any[] = [];
|
|
94
97
|
// const monomerNameI: number = 0;
|
|
95
98
|
// const weMonomers = org.helm.webeditor.Monomers;
|
|
96
99
|
// for (let typeI = 0; typeI < types.length; typeI++) {
|
|
97
|
-
// //@ts-ignore
|
|
98
100
|
// const ofTypeMonomers: {} = weMonomers.getMonomerSet(types[typeI]) ?? {};
|
|
99
101
|
// Object.keys(ofTypeMonomers).forEach((key) => {
|
|
100
102
|
// const monomer: any = ofTypeMonomers[key];
|
|
@@ -112,9 +114,9 @@ export function findMonomers(monomerSymbolList: string[]): Set<string> {
|
|
|
112
114
|
const monomers: any = [];
|
|
113
115
|
const monomerNames: any = [];
|
|
114
116
|
for (let i = 0; i < types.length; i++) {
|
|
115
|
-
|
|
117
|
+
// @ts-ignore
|
|
116
118
|
// eslint-disable-next-line new-cap
|
|
117
|
-
monomers.push(new
|
|
119
|
+
monomers.push(new org.helm.webeditor.Monomers.getMonomerSet(types[i]));
|
|
118
120
|
Object.keys(monomers[i]).forEach((k) => {
|
|
119
121
|
monomerNames.push(monomers[i][k].id);
|
|
120
122
|
});
|
|
@@ -210,7 +212,6 @@ function detachAnnotation(s: string) {
|
|
|
210
212
|
|
|
211
213
|
function _detachAppendix(s: string, c: string) {
|
|
212
214
|
let tag = null;
|
|
213
|
-
//@ts-ignore
|
|
214
215
|
if (scil.Utils.endswith(s, c)) {
|
|
215
216
|
let p = s.length - 1;
|
|
216
217
|
while (p > 0) {
|
|
@@ -230,7 +231,6 @@ function _detachAppendix(s: string, c: string) {
|
|
|
230
231
|
}
|
|
231
232
|
|
|
232
233
|
function unescape(s: string) {
|
|
233
|
-
//@ts-ignore
|
|
234
234
|
if (scil.Utils.isNullOrEmpty(s))
|
|
235
235
|
return s;
|
|
236
236
|
|
package/webpack.config.js
CHANGED
|
@@ -2,6 +2,9 @@ const path = require('path');
|
|
|
2
2
|
const packageName = path.parse(require('./package.json').name).name.toLowerCase().replace(/-/g, '');
|
|
3
3
|
|
|
4
4
|
module.exports = {
|
|
5
|
+
cache: {
|
|
6
|
+
type: 'filesystem',
|
|
7
|
+
},
|
|
5
8
|
mode: 'development',
|
|
6
9
|
entry: {
|
|
7
10
|
package: './src/package.ts',
|
|
@@ -36,6 +39,10 @@ module.exports = {
|
|
|
36
39
|
'cash-dom': '$',
|
|
37
40
|
'dayjs': 'dayjs',
|
|
38
41
|
'wu': 'wu',
|
|
42
|
+
'scil': 'scil',
|
|
43
|
+
'org': 'org',
|
|
44
|
+
'dojo': 'dojo',
|
|
45
|
+
'JSDraw2': 'JSDraw2',
|
|
39
46
|
},
|
|
40
47
|
output: {
|
|
41
48
|
filename: '[name].js',
|
|
File without changes
|