diff --git a/src/apps/structure-info/density.ts b/src/apps/structure-info/density.ts deleted file mode 100644 index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..0000000000000000000000000000000000000000 diff --git a/src/apps/structure-info/helpers.ts b/src/apps/structure-info/helpers.ts index 45fb1c0322837fbf02d7ced63000c1e9f2fc3f2d..94095a99055759cdbab8d9b2c677345632520848 100644 --- a/src/apps/structure-info/helpers.ts +++ b/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) { diff --git a/src/apps/structure-info/index.ts b/src/apps/structure-info/model.ts similarity index 98% rename from src/apps/structure-info/index.ts rename to src/apps/structure-info/model.ts index 93b84cb096bb82196e6658cfd56d2bd9d12f3c59..8ab4ad1dbf361bdda44c7d36492d95e616ca126a 100644 --- a/src/apps/structure-info/index.ts +++ b/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) { diff --git a/src/apps/structure-info/volume.ts b/src/apps/structure-info/volume.ts new file mode 100644 index 0000000000000000000000000000000000000000..e3b4b2e1efdba2514a0f052feea69932ac21f2cd --- /dev/null +++ b/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`); \ No newline at end of file diff --git a/src/mol-data/db/column.ts b/src/mol-data/db/column.ts index 1b0f46ce483df2f61039f0ae9d8612e927cdc130..355c1c365a7ba7f51c1cf41f7ede0d691f25d48c 100644 --- a/src/mol-data/db/column.ts +++ b/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>; diff --git a/src/mol-io/reader/cif.ts b/src/mol-io/reader/cif.ts index 93c30be9a53b8069dfe6dccc0744b900b764944c..440be38553cb525327fd6e376bbd0f29490f4203 100644 --- a/src/mol-io/reader/cif.ts +++ b/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) } } diff --git a/src/mol-io/reader/cif/data-model.ts b/src/mol-io/reader/cif/data-model.ts index 8182d0fca61359721a06f525aa672b7faa404717..4a090d35163ec693de14ff65e0c4e559a6dbaf89 100644 --- a/src/mol-io/reader/cif/data-model.ts +++ b/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); } } diff --git a/src/mol-io/reader/cif/schema.ts b/src/mol-io/reader/cif/schema.ts index c0f7e1d20c8ef614911b68cff79680662bab1d63..c7710132f758dc4ec0509b0f2089c9f336289544 100644 --- a/src/mol-io/reader/cif/schema.ts +++ b/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 { diff --git a/src/mol-model/volume.ts b/src/mol-model/volume.ts index e69de29bb2d1d6434b8b29ae775ad8c2e48c5391..aa8cf1ce46056532d4723f8c3584de3842c4e484 100644 --- a/src/mol-model/volume.ts +++ b/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' \ No newline at end of file diff --git a/src/mol-model/volume/data.ts b/src/mol-model/volume/data.ts index 628f4fe6b57b48c3b33833e09790c8671089c58c..19826278bb33abda9b02a791c90066cb287cda9a 100644 --- a/src/mol-model/volume/data.ts +++ b/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); } }