Skip to content
Snippets Groups Projects
Commit a09e0d48 authored by David Sehnal's avatar David Sehnal
Browse files

wip, custom props

parent b53203e5
No related branches found
No related tags found
No related merge requests found
...@@ -11,7 +11,7 @@ import { Structure, Element } from '../structure' ...@@ -11,7 +11,7 @@ import { Structure, Element } from '../structure'
import { Model } from '../model' import { Model } from '../model'
import P from '../query/properties' import P from '../query/properties'
interface Context { export interface CifExportContext {
structure: Structure, structure: Structure,
model: Model model: Model
} }
...@@ -53,7 +53,7 @@ const atom_site_fields: CifField<Element.Location>[] = [ ...@@ -53,7 +53,7 @@ const atom_site_fields: CifField<Element.Location>[] = [
]; ];
function copy_mmCif_cat(name: keyof mmCIF_Schema) { function copy_mmCif_cat(name: keyof mmCIF_Schema) {
return ({ model }: Context) => { return ({ model }: CifExportContext) => {
if (model.sourceData.kind !== 'mmCIF') return CifCategory.Empty; if (model.sourceData.kind !== 'mmCIF') return CifCategory.Empty;
const table = model.sourceData.data[name]; const table = model.sourceData.data[name];
if (!table || !table._rowCount) return CifCategory.Empty; if (!table || !table._rowCount) return CifCategory.Empty;
...@@ -61,12 +61,12 @@ function copy_mmCif_cat(name: keyof mmCIF_Schema) { ...@@ -61,12 +61,12 @@ function copy_mmCif_cat(name: keyof mmCIF_Schema) {
}; };
} }
function _entity({ model, structure }: Context): CifCategory { function _entity({ model, structure }: CifExportContext): CifCategory {
const keys = Structure.getEntityKeys(structure); const keys = Structure.getEntityKeys(structure);
return CifCategory.ofTable('entity', model.entities.data, keys); return CifCategory.ofTable('entity', model.entities.data, keys);
} }
function _atom_site({ structure }: Context): CifCategory { function _atom_site({ structure }: CifExportContext): CifCategory {
return { return {
data: structure, data: structure,
name: 'atom_site', name: 'atom_site',
...@@ -104,7 +104,7 @@ export function encode_mmCIF_categories(encoder: CifWriter.Encoder, structure: S ...@@ -104,7 +104,7 @@ export function encode_mmCIF_categories(encoder: CifWriter.Encoder, structure: S
if (models.length !== 1) throw 'Can\'t export stucture composed from multiple models.'; if (models.length !== 1) throw 'Can\'t export stucture composed from multiple models.';
const model = models[0]; const model = models[0];
const ctx: Context[] = [{ structure, model }]; const ctx: CifExportContext[] = [{ structure, model }];
for (const cat of Categories) { for (const cat of Categories) {
encoder.writeCategory(cat, ctx); encoder.writeCategory(cat, ctx);
......
...@@ -24,6 +24,7 @@ import { getSequence } from './mmcif/sequence'; ...@@ -24,6 +24,7 @@ import { getSequence } from './mmcif/sequence';
import { sortAtomSite } from './mmcif/sort'; import { sortAtomSite } from './mmcif/sort';
import { mmCIF_Database, mmCIF_Schema } from 'mol-io/reader/cif/schema/mmcif'; import { mmCIF_Database, mmCIF_Schema } from 'mol-io/reader/cif/schema/mmcif';
import { Element } from '../../../structure' import { Element } from '../../../structure'
import { CustomProperties } from '../properties/custom';
import mmCIF_Format = Format.mmCIF import mmCIF_Format = Format.mmCIF
type AtomSite = mmCIF_Database['atom_site'] type AtomSite = mmCIF_Database['atom_site']
...@@ -184,6 +185,7 @@ function createModel(format: mmCIF_Format, atom_site: AtomSite, previous?: Model ...@@ -184,6 +185,7 @@ function createModel(format: mmCIF_Format, atom_site: AtomSite, previous?: Model
sourceData: format, sourceData: format,
modelNum: format.data.atom_site.pdbx_PDB_model_num.value(0), modelNum: format.data.atom_site.pdbx_PDB_model_num.value(0),
entities, entities,
symmetry: getSymmetry(format),
atomicHierarchy, atomicHierarchy,
sequence: getSequence(format.data, entities, atomicHierarchy, modifiedResidueNameMap), sequence: getSequence(format.data, entities, atomicHierarchy, modifiedResidueNameMap),
atomicConformation: getConformation(atom_site), atomicConformation: getConformation(atom_site),
...@@ -193,7 +195,9 @@ function createModel(format: mmCIF_Format, atom_site: AtomSite, previous?: Model ...@@ -193,7 +195,9 @@ function createModel(format: mmCIF_Format, atom_site: AtomSite, previous?: Model
secondaryStructure: getSecondaryStructureMmCif(format.data, atomicHierarchy), secondaryStructure: getSecondaryStructureMmCif(format.data, atomicHierarchy),
modifiedResidueNameMap modifiedResidueNameMap
}, },
symmetry: getSymmetry(format) customProperties: new CustomProperties(),
_staticPropertyData: Object.create(null),
_dynamicPropertyData: Object.create(null)
}; };
} }
......
...@@ -10,6 +10,8 @@ import { LinkType } from '../../types' ...@@ -10,6 +10,8 @@ import { LinkType } from '../../types'
import { findEntityIdByAsymId, findAtomIndexByLabelName } from './util' import { findEntityIdByAsymId, findAtomIndexByLabelName } from './util'
import { Column } from 'mol-data/db' import { Column } from 'mol-data/db'
// TODO: add dynamic property descriptor for this?
export interface StructConn { export interface StructConn {
getResidueEntries(residueAIndex: number, residueBIndex: number): ReadonlyArray<StructConn.Entry> getResidueEntries(residueAIndex: number, residueBIndex: number): ReadonlyArray<StructConn.Entry>
getAtomEntries(atomIndex: number): ReadonlyArray<StructConn.Entry> getAtomEntries(atomIndex: number): ReadonlyArray<StructConn.Entry>
...@@ -100,7 +102,7 @@ export namespace StructConn { ...@@ -100,7 +102,7 @@ export namespace StructConn {
export const PropName = '__StructConn__'; export const PropName = '__StructConn__';
export function fromModel(model: Model): StructConn | undefined { export function fromModel(model: Model): StructConn | undefined {
if (model.properties[PropName]) return model.properties[PropName]; if (model._staticPropertyData[PropName]) return model._staticPropertyData[PropName];
if (model.sourceData.kind !== 'mmCIF') return; if (model.sourceData.kind !== 'mmCIF') return;
const { struct_conn } = model.sourceData.data; const { struct_conn } = model.sourceData.data;
...@@ -189,7 +191,7 @@ export namespace StructConn { ...@@ -189,7 +191,7 @@ export namespace StructConn {
} }
const ret = new StructConnImpl(entries); const ret = new StructConnImpl(entries);
model.properties[PropName] = ret; model._staticPropertyData[PropName] = ret;
return ret; return ret;
} }
} }
...@@ -230,7 +232,7 @@ export namespace ComponentBond { ...@@ -230,7 +232,7 @@ export namespace ComponentBond {
export const PropName = '__ComponentBond__'; export const PropName = '__ComponentBond__';
export function fromModel(model: Model): ComponentBond | undefined { export function fromModel(model: Model): ComponentBond | undefined {
if (model.properties[PropName]) return model.properties[PropName]; if (model._staticPropertyData[PropName]) return model._staticPropertyData[PropName];
if (model.sourceData.kind !== 'mmCIF') return if (model.sourceData.kind !== 'mmCIF') return
const { chem_comp_bond } = model.sourceData.data; const { chem_comp_bond } = model.sourceData.data;
...@@ -269,7 +271,7 @@ export namespace ComponentBond { ...@@ -269,7 +271,7 @@ export namespace ComponentBond {
entry.add(nameA, nameB, ord, flags); entry.add(nameA, nameB, ord, flags);
} }
model.properties[PropName] = compBond; model._staticPropertyData[PropName] = compBond;
return compBond; return compBond;
} }
} }
\ No newline at end of file
...@@ -11,6 +11,7 @@ import { AtomicHierarchy, AtomicConformation } from './properties/atomic' ...@@ -11,6 +11,7 @@ import { AtomicHierarchy, AtomicConformation } from './properties/atomic'
import { ModelSymmetry } from './properties/symmetry' import { ModelSymmetry } from './properties/symmetry'
import { CoarseHierarchy, CoarseConformation } from './properties/coarse' import { CoarseHierarchy, CoarseConformation } from './properties/coarse'
import { Entities } from './properties/common'; import { Entities } from './properties/common';
import { CustomProperties } from './properties/custom';
import { SecondaryStructure } from './properties/seconday-structure'; import { SecondaryStructure } from './properties/seconday-structure';
//import from_gro from './formats/gro' //import from_gro from './formats/gro'
...@@ -35,15 +36,21 @@ interface Model extends Readonly<{ ...@@ -35,15 +36,21 @@ interface Model extends Readonly<{
atomicHierarchy: AtomicHierarchy, atomicHierarchy: AtomicHierarchy,
atomicConformation: AtomicConformation, atomicConformation: AtomicConformation,
/** Various parts of the code can "cache" custom properties here */
properties: { properties: {
// secondary structure provided by the input file
readonly secondaryStructure: SecondaryStructure, readonly secondaryStructure: SecondaryStructure,
// maps modified residue name to its parent // maps modified residue name to its parent
readonly modifiedResidueNameMap: Map<string, string>, readonly modifiedResidueNameMap: Map<string, string>
[customName: string]: any
}, },
// TODO: separate properties to "static" (propagated with trajectory) and "dynamic" (computed for each frame separately) customProperties: CustomProperties,
/**
* Not to be accessed directly, each custom property descriptor
* defines property accessors that use this field to store the data.
*/
_staticPropertyData: { [name: string]: any },
_dynamicPropertyData: { [name: string]: any },
coarseHierarchy: CoarseHierarchy, coarseHierarchy: CoarseHierarchy,
coarseConformation: CoarseConformation coarseConformation: CoarseConformation
......
/**
* Copyright (c) 2018 mol* contributors, licensed under MIT, See LICENSE file for more info.
*
* @author David Sehnal <david.sehnal@gmail.com>
*/
export * from './custom/descriptor'
export * from './custom/collection'
\ No newline at end of file
/**
* Copyright (c) 2018 mol* contributors, licensed under MIT, See LICENSE file for more info.
*
* @author David Sehnal <david.sehnal@gmail.com>
*/
import { PropertyDescriptor } from './descriptor'
export class CustomProperties {
private _list: PropertyDescriptor[] = [];
private _set = new Set<PropertyDescriptor>();
get all(): ReadonlyArray<PropertyDescriptor> {
return this._list;
}
add(desc: PropertyDescriptor) {
this._list.push(desc);
this._set.add(desc);
}
has(desc: PropertyDescriptor): boolean {
return this._set.has(desc);
}
}
\ No newline at end of file
/**
* Copyright (c) 2018 mol* contributors, licensed under MIT, See LICENSE file for more info.
*
* @author David Sehnal <david.sehnal@gmail.com>
*/
import { CifWriter } from 'mol-io/writer/cif'
import { CifExportContext } from '../../../export/mmcif';
interface PropertyDescriptor {
readonly isStatic: boolean,
readonly name: string,
/** Given a structure, returns a list of category providers used for export. */
getCifCategories: (ctx: CifExportContext) => CifWriter.Category.Provider[]
}
export { PropertyDescriptor }
\ No newline at end of file
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment