@judah-silva/rnacanvas 0.0.6 → 0.0.8

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/dist/index.d.mts CHANGED
@@ -8,7 +8,16 @@ import { Mesh, TransformNode, Scene, Matrix, Nullable, Quaternion, Observer, Eng
8
8
  declare class Residue extends Group<MeshObject> {
9
9
  constructor(name: string);
10
10
  addChild(child: MeshObject): void;
11
+ /**
12
+ * Checks if the residue has a mesh with the given uuid
13
+ * @param uuid
14
+ */
11
15
  hasMesh(uuid: string): boolean;
16
+ /**
17
+ * Cretes a material with the given color and sets it to the mesh
18
+ * @param color String in the format of #RRGGBB
19
+ */
20
+ colorResidue(color: string): void;
12
21
  }
13
22
 
14
23
  /**
@@ -358,7 +367,7 @@ type MotifMesh = Record<string, any>;
358
367
  * @returns {Promise<Motif>}
359
368
  * @async
360
369
  */
361
- declare function getMotif(motifName: string, motifMesh: MotifMesh, motifColorHex?: string): Promise<Motif>;
370
+ declare function getMotif(motifName: string, motifMesh: MotifMesh, motifColorHex?: string, includeAtoms?: boolean): Promise<Motif>;
362
371
 
363
372
  /**
364
373
  * Copyright (c) 2025 RNA3DS Lab CSUMB.
@@ -372,7 +381,7 @@ declare function getMotif(motifName: string, motifMesh: MotifMesh, motifColorHex
372
381
  * @param nucleotideData {number[][]}
373
382
  * @returns Object of { vertices: number[][], indices: number[][] }
374
383
  */
375
- declare function getPoints(nucleotideData: number[][]): {
384
+ declare function getPoints(nucleotideData: number[][], includeAtoms: boolean): {
376
385
  vertices: number[][];
377
386
  indices: number[][];
378
387
  };
@@ -413,6 +422,7 @@ interface CanvasProps {
413
422
  rendererBackgroundColor?: string;
414
423
  rendererSizeIsWindow?: boolean;
415
424
  cameraPositionZ?: number;
425
+ showRMSD?: boolean;
416
426
  motifProps: MotifProps[];
417
427
  customEventProps?: AnyEventProps[];
418
428
  }
@@ -432,7 +442,7 @@ interface CanvasProps {
432
442
  * @function Canvas {JSX.Element}
433
443
  * @returns {JSX.Element}
434
444
  */
435
- declare function Canvas({ rendererHeight, rendererWidth, rendererBackgroundColor, rendererSizeIsWindow, cameraPositionZ, motifProps, customEventProps, }: CanvasProps): JSX.Element;
445
+ declare function Canvas({ rendererHeight, rendererWidth, rendererBackgroundColor, rendererSizeIsWindow, cameraPositionZ, showRMSD, motifProps, customEventProps, }: CanvasProps): JSX.Element;
436
446
 
437
447
  /**
438
448
  * Copyright (c) 2025 RNA3DS Lab CSUMB.
package/dist/index.d.ts CHANGED
@@ -8,7 +8,16 @@ import { Mesh, TransformNode, Scene, Matrix, Nullable, Quaternion, Observer, Eng
8
8
  declare class Residue extends Group<MeshObject> {
9
9
  constructor(name: string);
10
10
  addChild(child: MeshObject): void;
11
+ /**
12
+ * Checks if the residue has a mesh with the given uuid
13
+ * @param uuid
14
+ */
11
15
  hasMesh(uuid: string): boolean;
16
+ /**
17
+ * Cretes a material with the given color and sets it to the mesh
18
+ * @param color String in the format of #RRGGBB
19
+ */
20
+ colorResidue(color: string): void;
12
21
  }
13
22
 
14
23
  /**
@@ -358,7 +367,7 @@ type MotifMesh = Record<string, any>;
358
367
  * @returns {Promise<Motif>}
359
368
  * @async
360
369
  */
361
- declare function getMotif(motifName: string, motifMesh: MotifMesh, motifColorHex?: string): Promise<Motif>;
370
+ declare function getMotif(motifName: string, motifMesh: MotifMesh, motifColorHex?: string, includeAtoms?: boolean): Promise<Motif>;
362
371
 
363
372
  /**
364
373
  * Copyright (c) 2025 RNA3DS Lab CSUMB.
@@ -372,7 +381,7 @@ declare function getMotif(motifName: string, motifMesh: MotifMesh, motifColorHex
372
381
  * @param nucleotideData {number[][]}
373
382
  * @returns Object of { vertices: number[][], indices: number[][] }
374
383
  */
375
- declare function getPoints(nucleotideData: number[][]): {
384
+ declare function getPoints(nucleotideData: number[][], includeAtoms: boolean): {
376
385
  vertices: number[][];
377
386
  indices: number[][];
378
387
  };
@@ -413,6 +422,7 @@ interface CanvasProps {
413
422
  rendererBackgroundColor?: string;
414
423
  rendererSizeIsWindow?: boolean;
415
424
  cameraPositionZ?: number;
425
+ showRMSD?: boolean;
416
426
  motifProps: MotifProps[];
417
427
  customEventProps?: AnyEventProps[];
418
428
  }
@@ -432,7 +442,7 @@ interface CanvasProps {
432
442
  * @function Canvas {JSX.Element}
433
443
  * @returns {JSX.Element}
434
444
  */
435
- declare function Canvas({ rendererHeight, rendererWidth, rendererBackgroundColor, rendererSizeIsWindow, cameraPositionZ, motifProps, customEventProps, }: CanvasProps): JSX.Element;
445
+ declare function Canvas({ rendererHeight, rendererWidth, rendererBackgroundColor, rendererSizeIsWindow, cameraPositionZ, showRMSD, motifProps, customEventProps, }: CanvasProps): JSX.Element;
436
446
 
437
447
  /**
438
448
  * Copyright (c) 2025 RNA3DS Lab CSUMB.
package/dist/index.js CHANGED
@@ -312,7 +312,10 @@ var Residue = class extends Group {
312
312
  child.setParent(this);
313
313
  this._children.add(child);
314
314
  }
315
- // Temporary function to find if Residue contains mesh with uuid
315
+ /**
316
+ * Checks if the residue has a mesh with the given uuid
317
+ * @param uuid
318
+ */
316
319
  hasMesh(uuid) {
317
320
  let found = false;
318
321
  this._children.forEach((child) => {
@@ -322,6 +325,15 @@ var Residue = class extends Group {
322
325
  });
323
326
  return found;
324
327
  }
328
+ /**
329
+ * Cretes a material with the given color and sets it to the mesh
330
+ * @param color String in the format of #RRGGBB
331
+ */
332
+ colorResidue(color) {
333
+ this._children.forEach((child) => {
334
+ child.createAndSetMaterial(color);
335
+ });
336
+ }
325
337
  };
326
338
 
327
339
  // src/3D/MeshObject.ts
@@ -838,10 +850,10 @@ async function parseAtomCoords(meshObject) {
838
850
  }
839
851
 
840
852
  // src/3D/utils/GetPoints.ts
841
- function getPoints(nucleotideData) {
853
+ function getPoints(nucleotideData, includeAtoms) {
842
854
  const vertices = [];
843
855
  const indices = [];
844
- for (let i = 1; i < nucleotideData.length; i += 2) {
856
+ for (let i = includeAtoms ? 1 : 0; i < nucleotideData.length; i += 2) {
845
857
  vertices.push(nucleotideData[i]);
846
858
  indices.push(nucleotideData[i + 1]);
847
859
  }
@@ -849,10 +861,10 @@ function getPoints(nucleotideData) {
849
861
  }
850
862
 
851
863
  // src/3D/utils/GetMotif.ts
852
- async function getMotif(motifName, motifMesh, motifColorHex = "0xcc2900") {
864
+ async function getMotif(motifName, motifMesh, motifColorHex = "0xcc2900", includeAtoms = true) {
853
865
  const motif = new Motif(`${motifName}_motif`);
854
866
  for (const [key] of Object.entries(motifMesh)) {
855
- const { vertices, indices } = getPoints(motifMesh[key]);
867
+ const { vertices, indices } = getPoints(motifMesh[key], includeAtoms);
856
868
  const residue = new Residue("residue");
857
869
  const backboneMesh = new MeshObject(`backbone_${key}`);
858
870
  backboneMesh.applyVertexData(vertices[0], indices[0]);
@@ -865,7 +877,7 @@ async function getMotif(motifName, motifMesh, motifColorHex = "0xcc2900") {
865
877
  motif.addChild(residue);
866
878
  }
867
879
  motif.userData.fileName = motifName;
868
- motif.userData.atomInfo = await parseAtomCoords(motifMesh);
880
+ if (includeAtoms) motif.userData.atomInfo = await parseAtomCoords(motifMesh);
869
881
  return motif;
870
882
  }
871
883
 
@@ -1134,6 +1146,7 @@ function Canvas({
1134
1146
  rendererBackgroundColor = "#040a20",
1135
1147
  rendererSizeIsWindow = false,
1136
1148
  cameraPositionZ = 1e3,
1149
+ showRMSD = true,
1137
1150
  motifProps,
1138
1151
  customEventProps
1139
1152
  }) {
@@ -1244,7 +1257,7 @@ function Canvas({
1244
1257
  element.rotate(axisVec, angle);
1245
1258
  }
1246
1259
  });
1247
- setScoreRMSD(calculateRMSD(Array.from(selectedMotifMeshState.current), motifs));
1260
+ if (showRMSD) setScoreRMSD(calculateRMSD(Array.from(selectedMotifMeshState.current), motifs));
1248
1261
  }
1249
1262
  }
1250
1263
  }
@@ -1289,7 +1302,7 @@ function Canvas({
1289
1302
  element.rotate(event.rotationAxis, angle);
1290
1303
  }
1291
1304
  });
1292
- setScoreRMSD(calculateRMSD(Array.from(selectedMotifMeshState.current), motifs));
1305
+ if (showRMSD) setScoreRMSD(calculateRMSD(Array.from(selectedMotifMeshState.current), motifs));
1293
1306
  }
1294
1307
  function onKeyboardTranslate(event) {
1295
1308
  if (event.translationDirection.equals(Vec3.Zero)) {
@@ -1367,7 +1380,7 @@ function Canvas({
1367
1380
  }
1368
1381
  });
1369
1382
  updateGlow();
1370
- setScoreRMSD(calculateRMSD(Array.from(selectedMotifMeshState.current), motifs));
1383
+ if (showRMSD) setScoreRMSD(calculateRMSD(Array.from(selectedMotifMeshState.current), motifs));
1371
1384
  }, [selectedMotifIds]);
1372
1385
  (0, import_react.useEffect)(() => {
1373
1386
  const unsubscribe = CanvasDataManager.subscribe("lockedMotifIds" /* LOCKED_MOTIF_IDS */, () => {
@@ -1385,23 +1398,27 @@ function Canvas({
1385
1398
  hardLockedMotifIds = CanvasDataManager.hardLockedMotifIds;
1386
1399
  }, [CanvasDataManager.hardLockedMotifIds]);
1387
1400
  (0, import_react.useEffect)(() => {
1401
+ if (!showRMSD) return;
1388
1402
  const unsubscribe = CanvasDataManager.subscribe("scoreRMSD" /* SCORE_RMSD */, () => {
1389
1403
  setScoreRMSD(CanvasDataManager.scoreRMSD);
1390
1404
  });
1391
1405
  return () => unsubscribe();
1392
1406
  }, []);
1393
1407
  (0, import_react.useEffect)(() => {
1408
+ if (!showRMSD) return;
1394
1409
  if (CanvasDataManager.scoreRMSD !== scoreRMSD) {
1395
1410
  CanvasDataManager.setScoreRMSD(scoreRMSD);
1396
1411
  }
1397
1412
  }, [scoreRMSD]);
1398
1413
  (0, import_react.useEffect)(() => {
1414
+ if (!showRMSD) return;
1399
1415
  const unsubscribe = CanvasDataManager.subscribe("kabschRMSD" /* KABSCH_RMSD */, () => {
1400
1416
  setKabschRMSD(CanvasDataManager.kabschRMSD);
1401
1417
  });
1402
1418
  return () => unsubscribe();
1403
1419
  }, []);
1404
1420
  (0, import_react.useEffect)(() => {
1421
+ if (!showRMSD) return;
1405
1422
  if (CanvasDataManager.kabschRMSD !== kabschRMSD) {
1406
1423
  CanvasDataManager.setKabschRMSD(kabschRMSD);
1407
1424
  } else if (CanvasDataManager.kabschRMSD.length !== motifs.length) {
@@ -1426,7 +1443,7 @@ function Canvas({
1426
1443
  );
1427
1444
  }
1428
1445
  if (motifs.length > 0) {
1429
- setKabschRMSD(calculateAllKabschRMSD(motifs));
1446
+ if (showRMSD) setKabschRMSD(calculateAllKabschRMSD(motifs));
1430
1447
  if (scene.current.children.size !== motifs.length) {
1431
1448
  const positions = calculatePositions(motifs.length);
1432
1449
  motifs.forEach((motifMesh, index) => {
package/dist/index.mjs CHANGED
@@ -255,7 +255,10 @@ var Residue = class extends Group {
255
255
  child.setParent(this);
256
256
  this._children.add(child);
257
257
  }
258
- // Temporary function to find if Residue contains mesh with uuid
258
+ /**
259
+ * Checks if the residue has a mesh with the given uuid
260
+ * @param uuid
261
+ */
259
262
  hasMesh(uuid) {
260
263
  let found = false;
261
264
  this._children.forEach((child) => {
@@ -265,6 +268,15 @@ var Residue = class extends Group {
265
268
  });
266
269
  return found;
267
270
  }
271
+ /**
272
+ * Cretes a material with the given color and sets it to the mesh
273
+ * @param color String in the format of #RRGGBB
274
+ */
275
+ colorResidue(color) {
276
+ this._children.forEach((child) => {
277
+ child.createAndSetMaterial(color);
278
+ });
279
+ }
268
280
  };
269
281
 
270
282
  // src/3D/MeshObject.ts
@@ -781,10 +793,10 @@ async function parseAtomCoords(meshObject) {
781
793
  }
782
794
 
783
795
  // src/3D/utils/GetPoints.ts
784
- function getPoints(nucleotideData) {
796
+ function getPoints(nucleotideData, includeAtoms) {
785
797
  const vertices = [];
786
798
  const indices = [];
787
- for (let i = 1; i < nucleotideData.length; i += 2) {
799
+ for (let i = includeAtoms ? 1 : 0; i < nucleotideData.length; i += 2) {
788
800
  vertices.push(nucleotideData[i]);
789
801
  indices.push(nucleotideData[i + 1]);
790
802
  }
@@ -792,10 +804,10 @@ function getPoints(nucleotideData) {
792
804
  }
793
805
 
794
806
  // src/3D/utils/GetMotif.ts
795
- async function getMotif(motifName, motifMesh, motifColorHex = "0xcc2900") {
807
+ async function getMotif(motifName, motifMesh, motifColorHex = "0xcc2900", includeAtoms = true) {
796
808
  const motif = new Motif(`${motifName}_motif`);
797
809
  for (const [key] of Object.entries(motifMesh)) {
798
- const { vertices, indices } = getPoints(motifMesh[key]);
810
+ const { vertices, indices } = getPoints(motifMesh[key], includeAtoms);
799
811
  const residue = new Residue("residue");
800
812
  const backboneMesh = new MeshObject(`backbone_${key}`);
801
813
  backboneMesh.applyVertexData(vertices[0], indices[0]);
@@ -808,7 +820,7 @@ async function getMotif(motifName, motifMesh, motifColorHex = "0xcc2900") {
808
820
  motif.addChild(residue);
809
821
  }
810
822
  motif.userData.fileName = motifName;
811
- motif.userData.atomInfo = await parseAtomCoords(motifMesh);
823
+ if (includeAtoms) motif.userData.atomInfo = await parseAtomCoords(motifMesh);
812
824
  return motif;
813
825
  }
814
826
 
@@ -1077,6 +1089,7 @@ function Canvas({
1077
1089
  rendererBackgroundColor = "#040a20",
1078
1090
  rendererSizeIsWindow = false,
1079
1091
  cameraPositionZ = 1e3,
1092
+ showRMSD = true,
1080
1093
  motifProps,
1081
1094
  customEventProps
1082
1095
  }) {
@@ -1187,7 +1200,7 @@ function Canvas({
1187
1200
  element.rotate(axisVec, angle);
1188
1201
  }
1189
1202
  });
1190
- setScoreRMSD(calculateRMSD(Array.from(selectedMotifMeshState.current), motifs));
1203
+ if (showRMSD) setScoreRMSD(calculateRMSD(Array.from(selectedMotifMeshState.current), motifs));
1191
1204
  }
1192
1205
  }
1193
1206
  }
@@ -1232,7 +1245,7 @@ function Canvas({
1232
1245
  element.rotate(event.rotationAxis, angle);
1233
1246
  }
1234
1247
  });
1235
- setScoreRMSD(calculateRMSD(Array.from(selectedMotifMeshState.current), motifs));
1248
+ if (showRMSD) setScoreRMSD(calculateRMSD(Array.from(selectedMotifMeshState.current), motifs));
1236
1249
  }
1237
1250
  function onKeyboardTranslate(event) {
1238
1251
  if (event.translationDirection.equals(Vec3.Zero)) {
@@ -1310,7 +1323,7 @@ function Canvas({
1310
1323
  }
1311
1324
  });
1312
1325
  updateGlow();
1313
- setScoreRMSD(calculateRMSD(Array.from(selectedMotifMeshState.current), motifs));
1326
+ if (showRMSD) setScoreRMSD(calculateRMSD(Array.from(selectedMotifMeshState.current), motifs));
1314
1327
  }, [selectedMotifIds]);
1315
1328
  useEffect(() => {
1316
1329
  const unsubscribe = CanvasDataManager.subscribe("lockedMotifIds" /* LOCKED_MOTIF_IDS */, () => {
@@ -1328,23 +1341,27 @@ function Canvas({
1328
1341
  hardLockedMotifIds = CanvasDataManager.hardLockedMotifIds;
1329
1342
  }, [CanvasDataManager.hardLockedMotifIds]);
1330
1343
  useEffect(() => {
1344
+ if (!showRMSD) return;
1331
1345
  const unsubscribe = CanvasDataManager.subscribe("scoreRMSD" /* SCORE_RMSD */, () => {
1332
1346
  setScoreRMSD(CanvasDataManager.scoreRMSD);
1333
1347
  });
1334
1348
  return () => unsubscribe();
1335
1349
  }, []);
1336
1350
  useEffect(() => {
1351
+ if (!showRMSD) return;
1337
1352
  if (CanvasDataManager.scoreRMSD !== scoreRMSD) {
1338
1353
  CanvasDataManager.setScoreRMSD(scoreRMSD);
1339
1354
  }
1340
1355
  }, [scoreRMSD]);
1341
1356
  useEffect(() => {
1357
+ if (!showRMSD) return;
1342
1358
  const unsubscribe = CanvasDataManager.subscribe("kabschRMSD" /* KABSCH_RMSD */, () => {
1343
1359
  setKabschRMSD(CanvasDataManager.kabschRMSD);
1344
1360
  });
1345
1361
  return () => unsubscribe();
1346
1362
  }, []);
1347
1363
  useEffect(() => {
1364
+ if (!showRMSD) return;
1348
1365
  if (CanvasDataManager.kabschRMSD !== kabschRMSD) {
1349
1366
  CanvasDataManager.setKabschRMSD(kabschRMSD);
1350
1367
  } else if (CanvasDataManager.kabschRMSD.length !== motifs.length) {
@@ -1369,7 +1386,7 @@ function Canvas({
1369
1386
  );
1370
1387
  }
1371
1388
  if (motifs.length > 0) {
1372
- setKabschRMSD(calculateAllKabschRMSD(motifs));
1389
+ if (showRMSD) setKabschRMSD(calculateAllKabschRMSD(motifs));
1373
1390
  if (scene.current.children.size !== motifs.length) {
1374
1391
  const positions = calculatePositions(motifs.length);
1375
1392
  motifs.forEach((motifMesh, index) => {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@judah-silva/rnacanvas",
3
- "version": "0.0.6",
3
+ "version": "0.0.8",
4
4
  "description": "A 3D Canvas for displaying and interacting with custom RNA models. Powered by BabylonJS.",
5
5
  "license": "MIT",
6
6
  "main": "./dist/index.js",