Skip to content
Snippets Groups Projects
Commit bd1b07ad authored by Alexander Rose's avatar Alexander Rose
Browse files

removed gaussian density calc from unit

parent ef32f877
No related branches found
No related tags found
No related merge requests found
......@@ -7,7 +7,7 @@
import { SymmetryOperator } from 'mol-math/geometry/symmetry-operator'
import { Model } from '../model'
import { GridLookup3D, Lookup3D, DensityData } from 'mol-math/geometry'
import { GridLookup3D, Lookup3D } from 'mol-math/geometry'
import { IntraUnitLinks, computeIntraUnitBonds } from './unit/links'
import { CoarseElements, CoarseSphereConformation, CoarseGaussianConformation } from '../model/properties/coarse';
import { ValueRef } from 'mol-util';
......@@ -18,9 +18,6 @@ import { IntMap, SortedArray } from 'mol-data/int';
import { hash2, hashFnv32a } from 'mol-data/util';
import { getAtomicPolymerElements, getCoarsePolymerElements, getAtomicGapElements, getCoarseGapElements } from './util/polymer';
import { getNucleotideElements } from './util/nucleotide';
import { GaussianDensityProps, computeUnitGaussianDensityCached } from './unit/gaussian-density';
import { RuntimeContext } from 'mol-task';
import { WebGLContext } from 'mol-gl/webgl/context';
/**
* A building block of a structure that corresponds to an atomic or
......@@ -191,10 +188,6 @@ namespace Unit {
return this.model.atomicHierarchy.residueAtomSegments.index[this.elements[elementIndex]];
}
async computeGaussianDensity(props: GaussianDensityProps, ctx: RuntimeContext, webgl?: WebGLContext) {
return computeUnitGaussianDensityCached(this, props, this.props.gaussianDensities, ctx, webgl);
}
constructor(id: number, invariantId: number, model: Model, elements: StructureElement.Set, conformation: SymmetryOperator.ArrayMapping<ElementIndex>, props: AtomicProperties) {
this.id = id;
this.invariantId = invariantId;
......@@ -215,7 +208,6 @@ namespace Unit {
polymerElements: ValueRef<SortedArray<ElementIndex> | undefined>
gapElements: ValueRef<SortedArray<ElementIndex> | undefined>
nucleotideElements: ValueRef<SortedArray<ElementIndex> | undefined>
gaussianDensities: Map<string, DensityData>
}
function AtomicProperties(): AtomicProperties {
......@@ -226,7 +218,6 @@ namespace Unit {
polymerElements: ValueRef.create(void 0),
gapElements: ValueRef.create(void 0),
nucleotideElements: ValueRef.create(void 0),
gaussianDensities: new Map()
};
}
......@@ -280,10 +271,6 @@ namespace Unit {
return this.kind === Kind.Spheres ? this.model.coarseConformation.spheres : this.model.coarseConformation.gaussians;
}
async computeGaussianDensity(props: GaussianDensityProps, ctx: RuntimeContext, webgl?: WebGLContext): Promise<DensityData> {
return computeUnitGaussianDensityCached(this as Unit.Spheres | Unit.Gaussians, props, this.props.gaussianDensities, ctx, webgl); // TODO get rid of casting
}
constructor(id: number, invariantId: number, model: Model, kind: K, elements: StructureElement.Set, conformation: SymmetryOperator.ArrayMapping<ElementIndex>, props: CoarseProperties) {
this.kind = kind;
this.id = id;
......@@ -299,7 +286,6 @@ namespace Unit {
interface CoarseProperties {
lookup3d: ValueRef<Lookup3D | undefined>,
gaussianDensities: Map<string, DensityData>
polymerElements: ValueRef<SortedArray<ElementIndex> | undefined>
gapElements: ValueRef<SortedArray<ElementIndex> | undefined>
}
......@@ -307,7 +293,6 @@ namespace Unit {
function CoarseProperties(): CoarseProperties {
return {
lookup3d: ValueRef.create(void 0),
gaussianDensities: new Map(),
polymerElements: ValueRef.create(void 0),
gapElements: ValueRef.create(void 0),
};
......
/**
* Copyright (c) 2018 mol* contributors, licensed under MIT, See LICENSE file for more info.
*
* @author Alexander Rose <alexander.rose@weirdbyte.de>
*/
import { Unit, StructureElement, ElementIndex } from 'mol-model/structure';
import { GaussianDensity } from 'mol-math/geometry/gaussian-density';
import { Task, RuntimeContext } from 'mol-task';
import { DensityData } from 'mol-math/geometry';
import { ParamDefinition as PD } from 'mol-util/param-definition';
import { GaussianDensityTexture } from 'mol-math/geometry/gaussian-density/gpu';
import { Texture } from 'mol-gl/webgl/texture';
import { WebGLContext } from 'mol-gl/webgl/context';
import { PhysicalSizeTheme } from 'mol-theme/size/physical';
export const GaussianDensityParams = {
resolution: PD.Numeric(1, { min: 0.1, max: 10, step: 0.1 }),
radiusOffset: PD.Numeric(0, { min: 0, max: 10, step: 0.1 }),
smoothness: PD.Numeric(1.5, { min: 0.5, max: 2.5, step: 0.1 }),
useGpu: PD.Boolean(false),
ignoreCache: PD.Boolean(false),
}
export const DefaultGaussianDensityProps = PD.getDefaultValues(GaussianDensityParams)
export type GaussianDensityProps = typeof DefaultGaussianDensityProps
function getConformation(unit: Unit) {
switch (unit.kind) {
case Unit.Kind.Atomic: return unit.model.atomicConformation
case Unit.Kind.Spheres: return unit.model.coarseConformation.spheres
case Unit.Kind.Gaussians: return unit.model.coarseConformation.gaussians
}
}
function getConformationAndRadius(unit: Unit) {
const conformation = getConformation(unit)
const { elements } = unit
const position = {
indices: elements,
x: conformation.x,
y: conformation.y,
z: conformation.z
}
const l = StructureElement.create(unit)
const sizeTheme = PhysicalSizeTheme({}, {})
const radius = (index: number) => {
l.element = index as ElementIndex
return sizeTheme.size(l)
}
return { position, radius }
}
export function computeUnitGaussianDensity(unit: Unit, props: GaussianDensityProps, webgl?: WebGLContext) {
const { position, radius } = getConformationAndRadius(unit)
return Task.create('Gaussian Density', async ctx => {
return await GaussianDensity(ctx, position, unit.lookup3d.boundary.box, radius, props, webgl);
});
}
export function computeUnitGaussianDensityTexture(unit: Unit, props: GaussianDensityProps, webgl: WebGLContext, texture?: Texture) {
const { position, radius } = getConformationAndRadius(unit)
return Task.create('Gaussian Density', async ctx => {
return await GaussianDensityTexture(ctx, webgl, position, unit.lookup3d.boundary.box, radius, props, texture);
});
}
export async function computeUnitGaussianDensityCached(unit: Unit, props: GaussianDensityProps, cache: Map<string, DensityData>, ctx: RuntimeContext, webgl?: WebGLContext) {
const key = `${props.radiusOffset}|${props.resolution}|${props.smoothness}`
let density = cache.get(key)
if (density && !props.ignoreCache) return density
density = await computeUnitGaussianDensity(unit, props, webgl).runInContext(ctx)
if (!props.ignoreCache) cache.set(key, density)
return density
}
\ No newline at end of file
......@@ -11,12 +11,12 @@ import { StructureElementIterator } from './util/element';
import { EmptyLoci } from 'mol-model/loci';
import { Vec3 } from 'mol-math/linear-algebra';
import { UnitsPointsVisual, UnitsPointsParams } from '../units-visual';
import { GaussianDensityProps, GaussianDensityParams } from 'mol-model/structure/structure/unit/gaussian-density';
import { ParamDefinition as PD } from 'mol-util/param-definition';
import { Points } from 'mol-geo/geometry/points/points';
import { PointsBuilder } from 'mol-geo/geometry/points/points-builder';
import { VisualContext } from 'mol-repr/visual';
import { Theme } from 'mol-theme/theme';
import { computeUnitGaussianDensity, GaussianDensityParams, GaussianDensityProps } from './util/gaussian';
export const GaussianDensityPointParams = {
...UnitsPointsParams,
......@@ -26,7 +26,7 @@ export const GaussianDensityPointParams = {
export type GaussianDensityPointParams = typeof GaussianDensityPointParams
export async function createGaussianDensityPoint(ctx: VisualContext, unit: Unit, structure: Structure, theme: Theme, props: GaussianDensityProps, points?: Points) {
const { transform, field: { space, data } } = await unit.computeGaussianDensity(props, ctx.runtime, ctx.webgl)
const { transform, field: { space, data } } = await computeUnitGaussianDensity(unit, props, ctx.webgl).runInContext(ctx.runtime)
const { dimensions, get } = space
const [ xn, yn, zn ] = dimensions
......
......@@ -4,7 +4,7 @@
* @author Alexander Rose <alexander.rose@weirdbyte.de>
*/
import { Structure, StructureElement } from 'mol-model/structure';
import { Structure } from 'mol-model/structure';
import { VisualUpdateState } from '../../util';
import { ParamDefinition as PD } from 'mol-util/param-definition';
import { DirectVolume } from 'mol-geo/geometry/direct-volume/direct-volume';
......@@ -14,56 +14,9 @@ import { ComplexVisual, ComplexDirectVolumeVisual, ComplexDirectVolumeParams } f
import { EmptyLoci } from 'mol-model/loci';
import { NullLocation } from 'mol-model/location';
import { LocationIterator } from 'mol-geo/util/location-iterator';
import { WebGLContext } from 'mol-gl/webgl/context';
import { Texture } from 'mol-gl/webgl/texture';
import { GaussianDensityTexture } from 'mol-math/geometry/gaussian-density/gpu';
import { Task } from 'mol-task';
import { OrderedSet } from 'mol-data/int';
import { PhysicalSizeTheme } from 'mol-theme/size/physical';
import { computeStructureGaussianDensityTexture, GaussianDensityTextureProps, GaussianDensityTextureParams } from './util/gaussian';
function getConformationAndRadius(structure: Structure) {
const n = structure.elementCount
const xs = new Float32Array(n)
const ys = new Float32Array(n)
const zs = new Float32Array(n)
const rs = new Float32Array(n)
const l = StructureElement.create()
const sizeTheme = PhysicalSizeTheme({}, {})
let m = 0
for (let i = 0, il = structure.units.length; i < il; ++i) {
const unit = structure.units[i]
const { elements } = unit
const { x, y, z } = unit.conformation
l.unit = unit
for (let j = 0, jl = elements.length; j < jl; ++j) {
const eI = elements[j]
xs[m + j] = x(eI)
ys[m + j] = y(eI)
zs[m + j] = z(eI)
l.element = eI
rs[m + j] = sizeTheme.size(l)
}
m += elements.length
}
const position = { indices: OrderedSet.ofRange(0, n), x: xs, y: ys, z: zs }
const radius = (index: number) => rs[index]
return { position, radius }
}
// TODO calculate by combining unit volumes
function computeStructureGaussianDensityTexture(structure: Structure, props: PD.Values<GaussianDensityVolumeParams>, webgl: WebGLContext, texture?: Texture) {
const { position, radius } = getConformationAndRadius(structure)
return Task.create('Gaussian Density', async ctx => {
return await GaussianDensityTexture(ctx, webgl, position, structure.lookup3d.boundary.box, radius, props, texture);
});
}
async function createGaussianDensityVolume(ctx: VisualContext, structure: Structure, theme: Theme, props: PD.Values<GaussianDensityVolumeParams>, directVolume?: DirectVolume): Promise<DirectVolume> {
async function createGaussianDensityVolume(ctx: VisualContext, structure: Structure, theme: Theme, props: GaussianDensityTextureProps, directVolume?: DirectVolume): Promise<DirectVolume> {
const { runtime, webgl } = ctx
if (webgl === undefined) throw new Error('createGaussianDensityVolume requires `webgl` object in VisualContext')
......@@ -77,9 +30,7 @@ async function createGaussianDensityVolume(ctx: VisualContext, structure: Struct
export const GaussianDensityVolumeParams = {
...ComplexDirectVolumeParams,
resolution: PD.Numeric(1, { min: 0.1, max: 10, step: 0.1 }),
radiusOffset: PD.Numeric(0, { min: 0, max: 10, step: 0.1 }),
smoothness: PD.Numeric(1.5, { min: 0.5, max: 2.5, step: 0.1 }),
...GaussianDensityTextureParams
}
export type GaussianDensityVolumeParams = typeof GaussianDensityVolumeParams
......
......@@ -9,16 +9,16 @@ import { UnitsVisual } from '../representation';
import { VisualUpdateState } from '../../util';
import { UnitsMeshVisual, UnitsMeshParams } from '../units-visual';
import { StructureElementIterator, getElementLoci, markElement } from './util/element';
import { GaussianDensityProps, GaussianDensityParams } from 'mol-model/structure/structure/unit/gaussian-density';
import { ParamDefinition as PD } from 'mol-util/param-definition';
import { Mesh } from 'mol-geo/geometry/mesh/mesh';
import { computeMarchingCubesMesh } from 'mol-geo/util/marching-cubes/algorithm';
import { VisualContext } from 'mol-repr/visual';
import { Theme } from 'mol-theme/theme';
import { GaussianDensityProps, computeUnitGaussianDensity, GaussianDensityParams } from './util/gaussian';
async function createGaussianSurfaceMesh(ctx: VisualContext, unit: Unit, structure: Structure, theme: Theme, props: GaussianDensityProps, mesh?: Mesh): Promise<Mesh> {
const { smoothness } = props
const { transform, field, idField } = await unit.computeGaussianDensity(props, ctx.runtime, ctx.webgl)
const { transform, field, idField } = await computeUnitGaussianDensity(unit, props, ctx.webgl).runInContext(ctx.runtime)
const params = {
isoLevel: Math.exp(-smoothness),
......
......@@ -9,16 +9,16 @@ import { UnitsVisual } from '../representation';
import { VisualUpdateState } from '../../util';
import { UnitsLinesVisual, UnitsLinesParams } from '../units-visual';
import { StructureElementIterator, getElementLoci, markElement } from './util/element';
import { GaussianDensityProps, GaussianDensityParams } from 'mol-model/structure/structure/unit/gaussian-density';
import { ParamDefinition as PD } from 'mol-util/param-definition';
import { Lines } from 'mol-geo/geometry/lines/lines';
import { computeMarchingCubesLines } from 'mol-geo/util/marching-cubes/algorithm';
import { VisualContext } from 'mol-repr/visual';
import { Theme } from 'mol-theme/theme';
import { GaussianDensityProps, GaussianDensityParams, computeUnitGaussianDensity } from './util/gaussian';
async function createGaussianWireframe(ctx: VisualContext, unit: Unit, structure: Structure, theme: Theme, props: GaussianDensityProps, lines?: Lines): Promise<Lines> {
const { smoothness } = props
const { transform, field, idField } = await unit.computeGaussianDensity(props, ctx.runtime)
const { transform, field, idField } = await computeUnitGaussianDensity(unit, props, ctx.webgl).runInContext(ctx.runtime)
const params = {
isoLevel: Math.exp(-smoothness),
......
......@@ -3,3 +3,127 @@
*
* @author Alexander Rose <alexander.rose@weirdbyte.de>
*/
import { Unit, StructureElement, ElementIndex, Structure } from 'mol-model/structure';
import { GaussianDensity } from 'mol-math/geometry/gaussian-density';
import { Task, RuntimeContext } from 'mol-task';
import { DensityData } from 'mol-math/geometry';
import { ParamDefinition as PD } from 'mol-util/param-definition';
import { GaussianDensityTexture } from 'mol-math/geometry/gaussian-density/gpu';
import { Texture } from 'mol-gl/webgl/texture';
import { WebGLContext } from 'mol-gl/webgl/context';
import { PhysicalSizeTheme } from 'mol-theme/size/physical';
import { OrderedSet } from 'mol-data/int';
export const GaussianDensityParams = {
resolution: PD.Numeric(1, { min: 0.1, max: 10, step: 0.1 }),
radiusOffset: PD.Numeric(0, { min: 0, max: 10, step: 0.1 }),
smoothness: PD.Numeric(1.5, { min: 0.5, max: 2.5, step: 0.1 }),
useGpu: PD.Boolean(false),
ignoreCache: PD.Boolean(false),
}
export const DefaultGaussianDensityProps = PD.getDefaultValues(GaussianDensityParams)
export type GaussianDensityProps = typeof DefaultGaussianDensityProps
function getConformation(unit: Unit) {
switch (unit.kind) {
case Unit.Kind.Atomic: return unit.model.atomicConformation
case Unit.Kind.Spheres: return unit.model.coarseConformation.spheres
case Unit.Kind.Gaussians: return unit.model.coarseConformation.gaussians
}
}
function getUnitConformationAndRadius(unit: Unit) {
const conformation = getConformation(unit)
const { elements } = unit
const position = {
indices: elements,
x: conformation.x,
y: conformation.y,
z: conformation.z
}
const l = StructureElement.create(unit)
const sizeTheme = PhysicalSizeTheme({}, {})
const radius = (index: number) => {
l.element = index as ElementIndex
return sizeTheme.size(l)
}
return { position, radius }
}
export function computeUnitGaussianDensity(unit: Unit, props: GaussianDensityProps, webgl?: WebGLContext) {
const { position, radius } = getUnitConformationAndRadius(unit)
return Task.create('Gaussian Density', async ctx => {
return await GaussianDensity(ctx, position, unit.lookup3d.boundary.box, radius, props, webgl);
});
}
export function computeUnitGaussianDensityTexture(unit: Unit, props: GaussianDensityProps, webgl: WebGLContext, texture?: Texture) {
const { position, radius } = getUnitConformationAndRadius(unit)
return Task.create('Gaussian Density', async ctx => {
return await GaussianDensityTexture(ctx, webgl, position, unit.lookup3d.boundary.box, radius, props, texture);
});
}
export async function computeUnitGaussianDensityCached(unit: Unit, props: GaussianDensityProps, cache: Map<string, DensityData>, ctx: RuntimeContext, webgl?: WebGLContext) {
const key = `${props.radiusOffset}|${props.resolution}|${props.smoothness}`
let density = cache.get(key)
if (density && !props.ignoreCache) return density
density = await computeUnitGaussianDensity(unit, props, webgl).runInContext(ctx)
if (!props.ignoreCache) cache.set(key, density)
return density
}
//
function getStructureConformationAndRadius(structure: Structure) {
const n = structure.elementCount
const xs = new Float32Array(n)
const ys = new Float32Array(n)
const zs = new Float32Array(n)
const rs = new Float32Array(n)
const l = StructureElement.create()
const sizeTheme = PhysicalSizeTheme({}, {})
let m = 0
for (let i = 0, il = structure.units.length; i < il; ++i) {
const unit = structure.units[i]
const { elements } = unit
const { x, y, z } = unit.conformation
l.unit = unit
for (let j = 0, jl = elements.length; j < jl; ++j) {
const eI = elements[j]
xs[m + j] = x(eI)
ys[m + j] = y(eI)
zs[m + j] = z(eI)
l.element = eI
rs[m + j] = sizeTheme.size(l)
}
m += elements.length
}
const position = { indices: OrderedSet.ofRange(0, n), x: xs, y: ys, z: zs }
const radius = (index: number) => rs[index]
return { position, radius }
}
export const GaussianDensityTextureParams = {
resolution: PD.Numeric(1, { min: 0.1, max: 10, step: 0.1 }),
radiusOffset: PD.Numeric(0, { min: 0, max: 10, step: 0.1 }),
smoothness: PD.Numeric(1.5, { min: 0.5, max: 2.5, step: 0.1 }),
}
export const DefaultGaussianDensityTextureProps = PD.getDefaultValues(GaussianDensityTextureParams)
export type GaussianDensityTextureProps = typeof DefaultGaussianDensityTextureProps
// TODO calculate by combining unit volumes
export function computeStructureGaussianDensityTexture(structure: Structure, props: GaussianDensityTextureProps, webgl: WebGLContext, texture?: Texture) {
const { position, radius } = getStructureConformationAndRadius(structure)
return Task.create('Gaussian Density', async ctx => {
return await GaussianDensityTexture(ctx, webgl, position, structure.lookup3d.boundary.box, radius, props, texture);
});
}
\ 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