David Sehnal 7 年 前
コミット
ce3c3d6493

+ 0 - 0
src/apps/structure-info/density.ts


+ 1 - 1
src/apps/structure-info/helpers.ts

@@ -29,7 +29,7 @@ async function parseCif(data: string|Uint8Array) {
     const comp = CIF.parse(data);
     const parsed = await Run(comp, p => console.log(Progress.format(p)), 250);
     if (parsed.isError) throw parsed;
-    return parsed
+    return parsed.result;
 }
 
 export async function openCif(path: string) {

+ 2 - 2
src/apps/structure-info/index.ts → src/apps/structure-info/model.ts

@@ -22,12 +22,12 @@ import { openCif, downloadCif } from './helpers';
 async function downloadFromPdb(pdb: string) {
     // `https://files.rcsb.org/download/${pdb}.cif`
     const parsed = await downloadCif(`http://www.ebi.ac.uk/pdbe/static/entry/${pdb}_updated.cif`, false);
-    return CIF.schema.mmCIF(parsed.result.blocks[0]);
+    return CIF.schema.mmCIF(parsed.blocks[0]);
 }
 
 async function readPdbFile(path: string) {
     const parsed = await openCif(path);
-    return CIF.schema.mmCIF(parsed.result.blocks[0]);
+    return CIF.schema.mmCIF(parsed.blocks[0]);
 }
 
 export function atomLabel(model: Model, aI: number) {

+ 47 - 0
src/apps/structure-info/volume.ts

@@ -0,0 +1,47 @@
+
+/**
+ * Copyright (c) 2018 mol* contributors, licensed under MIT, See LICENSE file for more info.
+ *
+ * @author David Sehnal <david.sehnal@gmail.com>
+ */
+
+import * as argparse from 'argparse'
+import { VolumeData, parseDensityServerData } from 'mol-model/volume'
+import { downloadCif } from './helpers'
+import CIF from 'mol-io/reader/cif'
+import { DensityServer_Data_Database } from 'mol-io/reader/cif/schema/density-server';
+import { Run } from 'mol-task';
+import { Table } from 'mol-data/db';
+
+type Volume = { source: DensityServer_Data_Database, volume: VolumeData }
+
+async function getVolume(url: string): Promise<Volume> {
+    const cif = await downloadCif(url, false);
+    const data = CIF.schema.densityServer(cif.blocks[1]);
+    return { source: data, volume: await Run(parseDensityServerData(data)) };
+}
+
+function print(volume: Volume) {
+    const { volume_data_3d_info } = volume.source;
+    const row = Table.getRow(volume_data_3d_info, 0);
+    console.log(row);
+}
+
+async function run(url: string) {
+    const volume = await getVolume(url);
+    print(volume);
+}
+
+const parser = new argparse.ArgumentParser({
+addHelp: true,
+description: 'Info about VolumeData from mol-model module'
+});
+parser.addArgument([ '--emdb', '-e' ], {
+    help: 'EMDB id, for example 8116',
+});
+interface Args {
+    emdb?: string
+}
+const args: Args = parser.parseArgs();
+
+run(`https://webchem.ncbr.muni.cz/DensityServer/em/emd-${args.emdb}/cell?detail=1&encoding=cif`);

+ 2 - 2
src/mol-data/db/column.ts

@@ -47,8 +47,8 @@ namespace Column {
         export function Int(defaultValue = 0): Int { return { '@type': 'int', T: defaultValue, valueType: 'int' } };
         export function Float(defaultValue = 0): Float { return { '@type': 'float', T: defaultValue, valueType: 'float' } };
         export function Tensor(space: Tensors.Space, baseType: Int | Float = float): Tensor { return { '@type': 'tensor', T: space.create(), space, valueType: 'tensor', baseType }; }
-        export function Vector(dim: number, baseType: Int | Float = float): Tensor { return Tensor(Tensors.Vector(dim), baseType); }
-        export function Matrix(rows: number, cols: number, baseType: Int | Float = float): Tensor { return Tensor(Tensors.ColumnMajorMatrix(rows, cols), baseType); }
+        export function Vector(dim: number, baseType: Int | Float = float): Tensor { return Tensor(Tensors.Vector(dim, baseType['@type'] === 'int' ? Int32Array : Float64Array), baseType); }
+        export function Matrix(rows: number, cols: number, baseType: Int | Float = float): Tensor { return Tensor(Tensors.ColumnMajorMatrix(rows, cols, baseType['@type'] === 'int' ? Int32Array : Float64Array), baseType); }
 
         export function Aliased<T>(t: Str | Int, defaultValue?: T): Aliased<T> {
             if (typeof defaultValue !== 'undefined') return { ...t, T: defaultValue } as any as Aliased<T>;

+ 4 - 2
src/mol-io/reader/cif.ts

@@ -12,7 +12,8 @@ import { toDatabaseCollection, toDatabase } from './cif/schema'
 import { mmCIF_Schema, mmCIF_Database } from './cif/schema/mmcif'
 import { CCD_Schema, CCD_Database } from './cif/schema/ccd'
 import { BIRD_Schema, BIRD_Database } from './cif/schema/bird'
-import { dic_Schema, dic_Database } from './cif/schema/dic';
+import { dic_Schema, dic_Database } from './cif/schema/dic'
+import { DensityServer_Data_Schema, DensityServer_Data_Database } from './cif/schema/density-server'
 
 export default {
     parse: (data: string|Uint8Array) => typeof data === 'string' ? parseText(data) : parseBinary(data),
@@ -24,7 +25,8 @@ export default {
         mmCIF: (frame: Frame) => toDatabase<mmCIF_Schema, mmCIF_Database>(mmCIF_Schema, frame),
         CCD: (frame: Frame) => toDatabase<CCD_Schema, CCD_Database>(CCD_Schema, frame),
         BIRD: (frame: Frame) => toDatabase<BIRD_Schema, BIRD_Database>(BIRD_Schema, frame),
-        dic: (frame: Frame) => toDatabase<dic_Schema, dic_Database>(dic_Schema, frame)
+        dic: (frame: Frame) => toDatabase<dic_Schema, dic_Database>(dic_Schema, frame),
+        densityServer: (frame: Frame) => toDatabase<DensityServer_Data_Schema, DensityServer_Data_Database>(DensityServer_Data_Schema, frame)
     }
 }
 

+ 6 - 4
src/mol-io/reader/cif/data-model.ts

@@ -78,19 +78,21 @@ export interface Field {
     toFloatArray(params?: Column.ToArrayParams<number>): ReadonlyArray<number>
 }
 
-export function getTensor(category: Category, field: string, space: Tensor.Space, row: number): Tensor.Data {
+export function getTensor(category: Category, field: string, space: Tensor.Space, row: number, zeroIndexed: boolean): Tensor.Data {
     const ret = space.create();
+    const offset = zeroIndexed ? 0 : 1;
+
     if (space.rank === 1) {
         const rows = space.dimensions[0];
         for (let i = 0; i < rows; i++) {
-            const f = category.getField(`${field}[${i + 1}]`);
+            const f = category.getField(`${field}[${i + offset}]`);
             space.set(ret, i, !!f ? f.float(row) : 0.0);
         }
     } else if (space.rank === 2) {
         const rows = space.dimensions[0], cols = space.dimensions[1];
         for (let i = 0; i < rows; i++) {
             for (let j = 0; j < cols; j++) {
-                const f = category.getField(`${field}[${i + 1}][${j + 1}]`);
+                const f = category.getField(`${field}[${i + offset}][${j + offset}]`);
                 space.set(ret, i, j, !!f ? f.float(row) : 0.0);
             }
         }
@@ -99,7 +101,7 @@ export function getTensor(category: Category, field: string, space: Tensor.Space
         for (let i = 0; i < d0; i++) {
             for (let j = 0; j < d1; j++) {
                 for (let k = 0; k < d2; k++) {
-                    const f = category.getField(`${field}[${i + 1}][${j + 1}][${k + 1}]`);
+                    const f = category.getField(`${field}[${i + offset}][${j + offset}][${k + offset}]`);
                     space.set(ret, i, j, k, !!f ? f.float(row) : 0.0);
                 }
             }

+ 7 - 4
src/mol-io/reader/cif/schema.ts

@@ -73,15 +73,18 @@ function createListColumn<T extends number|string>(schema: Column.Schema.List<T>
 
 function createTensorColumn(schema: Column.Schema.Tensor, category: Data.Category, key: string): Column<Tensor.Data> {
     const space = schema.space;
+    const zeroOffset = category.fieldNames.indexOf(`${key}[0]`) >= 0;
+    const fst = zeroOffset ? 0 : 1;
+
     let firstFieldName: string;
     switch (space.rank) {
-        case 1: firstFieldName = `${key}[1]`; break;
-        case 2: firstFieldName = `${key}[1][1]`; break;
-        case 3: firstFieldName = `${key}[1][1][1]`; break;
+        case 1: firstFieldName = `${key}[${fst}]`; break;
+        case 2: firstFieldName = `${key}[${fst}][${fst}]`; break;
+        case 3: firstFieldName = `${key}[${fst}][${fst}][${fst}]`; break;
         default: throw new Error('Tensors with rank > 3 or rank 0 are currently not supported.');
     }
     const first = category.getField(firstFieldName) || Column.Undefined(category.rowCount, schema);
-    const value = (row: number) => Data.getTensor(category, key, space, row);
+    const value = (row: number) => Data.getTensor(category, key, space, row, zeroOffset);
     const toArray: Column<Tensor.Data>['toArray'] = params => ColumnHelpers.createAndFillArray(category.rowCount, value, params)
 
     return {

+ 8 - 0
src/mol-model/volume.ts

@@ -0,0 +1,8 @@
+/**
+ * Copyright (c) 2018 mol* contributors, licensed under MIT, See LICENSE file for more info.
+ *
+ * @author David Sehnal <david.sehnal@gmail.com>
+ */
+
+export * from './volume/data'
+export * from './volume/formats/density-server'

+ 2 - 8
src/mol-model/volume/data.ts

@@ -21,18 +21,12 @@ interface VolumeData {
 }
 
 namespace VolumeData {
-    const _scale = Mat4.zero(), _translate = Mat4.zero(), _perm = Mat4.zero();
+    const _scale = Mat4.zero(), _translate = Mat4.zero();
     export function getGridToCartesianTransform(volume: VolumeData) {
         const { data: { space } } = volume;
         const scale = Mat4.fromScaling(_scale, Vec3.div(Vec3.zero(), Box3D.size(volume.fractionalBox), Vec3.ofArray(space.dimensions)));
         const translate = Mat4.fromTranslation(_translate, volume.fractionalBox.min);
-        const ret = Mat4.mul3(Mat4.zero(), volume.cell.fromFractional, translate, scale);
-
-        const [x, y, z] = space.axisOrderSlowToFast;
-        if (x !== 0 || y !== 1 || z !== 2) {
-            Mat4.mul(ret, Mat4.fromPermutation(_perm, [x, y, z, 3]), ret);
-        }
-        return ret;
+        return Mat4.mul3(Mat4.zero(), volume.cell.fromFractional, translate, scale);
     }
 }