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

added transperancy-from-bundle, improved overpaint

parent 8b76c095
No related branches found
No related tags found
No related merge requests found
...@@ -52,7 +52,7 @@ export const DefaultPluginSpec: PluginSpec = { ...@@ -52,7 +52,7 @@ export const DefaultPluginSpec: PluginSpec = {
PluginSpec.Action(StateTransforms.Representation.ExplodeStructureRepresentation3D), PluginSpec.Action(StateTransforms.Representation.ExplodeStructureRepresentation3D),
PluginSpec.Action(StateTransforms.Representation.UnwindStructureAssemblyRepresentation3D), PluginSpec.Action(StateTransforms.Representation.UnwindStructureAssemblyRepresentation3D),
PluginSpec.Action(StateTransforms.Representation.OverpaintStructureRepresentation3DFromScript), PluginSpec.Action(StateTransforms.Representation.OverpaintStructureRepresentation3DFromScript),
PluginSpec.Action(StateTransforms.Representation.TransparencyStructureRepresentation3D), PluginSpec.Action(StateTransforms.Representation.TransparencyStructureRepresentation3DFromScript),
PluginSpec.Action(StateTransforms.Volume.VolumeFromCcp4), PluginSpec.Action(StateTransforms.Volume.VolumeFromCcp4),
PluginSpec.Action(StateTransforms.Representation.VolumeRepresentation3D), PluginSpec.Action(StateTransforms.Representation.VolumeRepresentation3D),
......
...@@ -4,50 +4,9 @@ ...@@ -4,50 +4,9 @@
* @author Alexander Rose <alexander.rose@weirdbyte.de> * @author Alexander Rose <alexander.rose@weirdbyte.de>
*/ */
import { Structure, StructureSelection, QueryContext, StructureElement } from '../../../mol-model/structure'; import { Structure } from '../../../mol-model/structure';
import { Color } from '../../../mol-util/color';
import { Overpaint } from '../../../mol-theme/overpaint';
import { parseMolScript } from '../../../mol-script/language/parser';
import { transpileMolScript } from '../../../mol-script/script/mol-script/symbols';
import { compile } from '../../../mol-script/runtime/query/compiler';
import { Transparency } from '../../../mol-theme/transparency';
import { ComputedSecondaryStructure } from '../../../mol-model-props/computed/secondary-structure'; import { ComputedSecondaryStructure } from '../../../mol-model-props/computed/secondary-structure';
type Script = { language: string, expression: string }
function scriptToLoci(structure: Structure, script: Script) {
const parsed = parseMolScript(script.expression)
if (parsed.length === 0) throw new Error('No query')
const query = transpileMolScript(parsed[0])
const compiled = compile<StructureSelection>(query)
const result = compiled(new QueryContext(structure))
return StructureSelection.toLoci2(result)
}
export function getStructureOverpaintFromScript(structure: Structure, scriptLayers: { script: Script, color: Color, clear: boolean }[], alpha: number): Overpaint {
const layers: Overpaint.Layer[] = []
for (let i = 0, il = scriptLayers.length; i < il; ++i) {
const { script, color, clear } = scriptLayers[i]
layers.push({ loci: scriptToLoci(structure, script), color, clear })
}
return { layers, alpha }
}
export function getStructureOverpaintFromBundle(structure: Structure, bundleLayers: { bundle: StructureElement.Bundle, color: Color, clear: boolean }[], alpha: number): Overpaint {
const layers: Overpaint.Layer[] = []
for (let i = 0, il = bundleLayers.length; i < il; ++i) {
const { bundle, color, clear } = bundleLayers[i]
const loci = StructureElement.Bundle.toLoci(bundle, structure.root)
layers.push({ loci, color, clear })
}
return { layers, alpha }
}
export function getStructureTransparency(structure: Structure, script: Script, value: number, variant: Transparency.Variant): Transparency {
return { loci: scriptToLoci(structure, script), value, variant }
}
/** /**
* Attaches ComputedSecondaryStructure property when unavailable in sourceData * Attaches ComputedSecondaryStructure property when unavailable in sourceData
*/ */
......
...@@ -29,8 +29,8 @@ import { unwindStructureAssembly, explodeStructure } from '../animation/helpers' ...@@ -29,8 +29,8 @@ import { unwindStructureAssembly, explodeStructure } from '../animation/helpers'
import { Color } from '../../../mol-util/color'; import { Color } from '../../../mol-util/color';
import { Overpaint } from '../../../mol-theme/overpaint'; import { Overpaint } from '../../../mol-theme/overpaint';
import { Transparency } from '../../../mol-theme/transparency'; import { Transparency } from '../../../mol-theme/transparency';
import { getStructureOverpaintFromScript, getStructureOverpaintFromBundle, getStructureTransparency } from './helpers';
import { BaseGeometry } from '../../../mol-geo/geometry/base'; import { BaseGeometry } from '../../../mol-geo/geometry/base';
import { Script } from '../../../mol-script/script';
export { StructureRepresentation3D } export { StructureRepresentation3D }
export { StructureRepresentation3DHelpers } export { StructureRepresentation3DHelpers }
...@@ -39,7 +39,8 @@ export { ExplodeStructureRepresentation3D } ...@@ -39,7 +39,8 @@ export { ExplodeStructureRepresentation3D }
export { UnwindStructureAssemblyRepresentation3D } export { UnwindStructureAssemblyRepresentation3D }
export { OverpaintStructureRepresentation3DFromScript } export { OverpaintStructureRepresentation3DFromScript }
export { OverpaintStructureRepresentation3DFromBundle } export { OverpaintStructureRepresentation3DFromBundle }
export { TransparencyStructureRepresentation3D } export { TransparencyStructureRepresentation3DFromScript }
export { TransparencyStructureRepresentation3DFromBundle }
export { VolumeRepresentation3D } export { VolumeRepresentation3D }
namespace StructureRepresentation3DHelpers { namespace StructureRepresentation3DHelpers {
...@@ -334,12 +335,12 @@ const OverpaintStructureRepresentation3DFromScript = PluginStateTransform.BuiltI ...@@ -334,12 +335,12 @@ const OverpaintStructureRepresentation3DFromScript = PluginStateTransform.BuiltI
to: SO.Molecule.Structure.Representation3DState, to: SO.Molecule.Structure.Representation3DState,
params: { params: {
layers: PD.ObjectList({ layers: PD.ObjectList({
script: PD.ScriptExpression({ language: 'mol-script', expression: '(sel.atom.all)' }), script: PD.Script(Script('(sel.atom.all)', 'mol-script')),
color: PD.Color(ColorNames.blueviolet), color: PD.Color(ColorNames.blueviolet),
clear: PD.Boolean(false) clear: PD.Boolean(false)
}, e => `${e.clear ? 'Clear' : Color.toRgbString(e.color)}`, { }, e => `${e.clear ? 'Clear' : Color.toRgbString(e.color)}`, {
defaultValue: [{ defaultValue: [{
script: { language: 'mol-script', expression: '(sel.atom.all)' }, script: Script('(sel.atom.all)', 'mol-script'),
color: ColorNames.blueviolet, color: ColorNames.blueviolet,
clear: false clear: false
}] }]
...@@ -352,7 +353,7 @@ const OverpaintStructureRepresentation3DFromScript = PluginStateTransform.BuiltI ...@@ -352,7 +353,7 @@ const OverpaintStructureRepresentation3DFromScript = PluginStateTransform.BuiltI
}, },
apply({ a, params }) { apply({ a, params }) {
const structure = a.data.source.data const structure = a.data.source.data
const overpaint = getStructureOverpaintFromScript(structure, params.layers, params.alpha) const overpaint = Overpaint.ofScript(params.layers, params.alpha, structure)
return new SO.Molecule.Structure.Representation3DState({ return new SO.Molecule.Structure.Representation3DState({
state: { overpaint }, state: { overpaint },
...@@ -366,7 +367,7 @@ const OverpaintStructureRepresentation3DFromScript = PluginStateTransform.BuiltI ...@@ -366,7 +367,7 @@ const OverpaintStructureRepresentation3DFromScript = PluginStateTransform.BuiltI
const newStructure = a.data.source.data const newStructure = a.data.source.data
if (newStructure !== oldStructure) return StateTransformer.UpdateResult.Recreate if (newStructure !== oldStructure) return StateTransformer.UpdateResult.Recreate
const oldOverpaint = b.data.state.overpaint! const oldOverpaint = b.data.state.overpaint!
const newOverpaint = getStructureOverpaintFromScript(newStructure, newParams.layers, newParams.alpha) const newOverpaint = Overpaint.ofScript(newParams.layers, newParams.alpha, newStructure)
if (oldParams.alpha === newParams.alpha && Overpaint.areEqual(oldOverpaint, newOverpaint)) return StateTransformer.UpdateResult.Unchanged if (oldParams.alpha === newParams.alpha && Overpaint.areEqual(oldOverpaint, newOverpaint)) return StateTransformer.UpdateResult.Unchanged
b.data.state.overpaint = newOverpaint b.data.state.overpaint = newOverpaint
...@@ -403,7 +404,7 @@ const OverpaintStructureRepresentation3DFromBundle = PluginStateTransform.BuiltI ...@@ -403,7 +404,7 @@ const OverpaintStructureRepresentation3DFromBundle = PluginStateTransform.BuiltI
}, },
apply({ a, params }) { apply({ a, params }) {
const structure = a.data.source.data const structure = a.data.source.data
const overpaint = getStructureOverpaintFromBundle(structure, params.layers, params.alpha) const overpaint = Overpaint.ofBundle(params.layers, params.alpha, structure)
return new SO.Molecule.Structure.Representation3DState({ return new SO.Molecule.Structure.Representation3DState({
state: { overpaint }, state: { overpaint },
...@@ -417,7 +418,7 @@ const OverpaintStructureRepresentation3DFromBundle = PluginStateTransform.BuiltI ...@@ -417,7 +418,7 @@ const OverpaintStructureRepresentation3DFromBundle = PluginStateTransform.BuiltI
const newStructure = a.data.source.data const newStructure = a.data.source.data
if (newStructure !== oldStructure) return StateTransformer.UpdateResult.Recreate if (newStructure !== oldStructure) return StateTransformer.UpdateResult.Recreate
const oldOverpaint = b.data.state.overpaint! const oldOverpaint = b.data.state.overpaint!
const newOverpaint = getStructureOverpaintFromBundle(newStructure, newParams.layers, newParams.alpha) const newOverpaint = Overpaint.ofBundle(newParams.layers, newParams.alpha, newStructure)
if (oldParams.alpha === newParams.alpha && Overpaint.areEqual(oldOverpaint, newOverpaint)) return StateTransformer.UpdateResult.Unchanged if (oldParams.alpha === newParams.alpha && Overpaint.areEqual(oldOverpaint, newOverpaint)) return StateTransformer.UpdateResult.Unchanged
b.data.state.overpaint = newOverpaint b.data.state.overpaint = newOverpaint
...@@ -427,14 +428,14 @@ const OverpaintStructureRepresentation3DFromBundle = PluginStateTransform.BuiltI ...@@ -427,14 +428,14 @@ const OverpaintStructureRepresentation3DFromBundle = PluginStateTransform.BuiltI
} }
}); });
type TransparencyStructureRepresentation3D = typeof TransparencyStructureRepresentation3D type TransparencyStructureRepresentation3DFromScript = typeof TransparencyStructureRepresentation3DFromScript
const TransparencyStructureRepresentation3D = PluginStateTransform.BuiltIn({ const TransparencyStructureRepresentation3DFromScript = PluginStateTransform.BuiltIn({
name: 'transparency-structure-representation-3d', name: 'transparency-structure-representation-3d-from-script',
display: 'Transparency 3D Representation', display: 'Transparency 3D Representation',
from: SO.Molecule.Structure.Representation3D, from: SO.Molecule.Structure.Representation3D,
to: SO.Molecule.Structure.Representation3DState, to: SO.Molecule.Structure.Representation3DState,
params: { params: {
script: PD.ScriptExpression({ language: 'mol-script', expression: '(sel.atom.all)' }), script: PD.Script(Script('(sel.atom.all)', 'mol-script')),
value: PD.Numeric(0.75, { min: 0, max: 1, step: 0.01 }, { label: 'Transparency' }), value: PD.Numeric(0.75, { min: 0, max: 1, step: 0.01 }, { label: 'Transparency' }),
variant: PD.Select('single', [['single', 'Single-layer'], ['multi', 'Multi-layer']]) variant: PD.Select('single', [['single', 'Single-layer'], ['multi', 'Multi-layer']])
} }
...@@ -444,7 +445,7 @@ const TransparencyStructureRepresentation3D = PluginStateTransform.BuiltIn({ ...@@ -444,7 +445,7 @@ const TransparencyStructureRepresentation3D = PluginStateTransform.BuiltIn({
}, },
apply({ a, params }) { apply({ a, params }) {
const structure = a.data.source.data const structure = a.data.source.data
const transparency = getStructureTransparency(structure, params.script, params.value, params.variant) const transparency = Transparency.ofScript(params.script, params.value, params.variant, structure)
return new SO.Molecule.Structure.Representation3DState({ return new SO.Molecule.Structure.Representation3DState({
state: { transparency }, state: { transparency },
...@@ -457,7 +458,47 @@ const TransparencyStructureRepresentation3D = PluginStateTransform.BuiltIn({ ...@@ -457,7 +458,47 @@ const TransparencyStructureRepresentation3D = PluginStateTransform.BuiltIn({
const structure = b.data.info as Structure const structure = b.data.info as Structure
if (a.data.source.data !== structure) return StateTransformer.UpdateResult.Recreate if (a.data.source.data !== structure) return StateTransformer.UpdateResult.Recreate
const oldTransparency = b.data.state.transparency! const oldTransparency = b.data.state.transparency!
const newTransparency = getStructureTransparency(structure, newParams.script, newParams.value, newParams.variant) const newTransparency = Transparency.ofScript(newParams.script, newParams.value, newParams.variant, structure)
if (Transparency.areEqual(oldTransparency, newTransparency)) return StateTransformer.UpdateResult.Unchanged
b.data.state.transparency = newTransparency
b.data.source = a
b.label = `Transparency (${newTransparency.value})`
return StateTransformer.UpdateResult.Updated
}
});
type TransparencyStructureRepresentation3DFromBundle = typeof TransparencyStructureRepresentation3DFromBundle
const TransparencyStructureRepresentation3DFromBundle = PluginStateTransform.BuiltIn({
name: 'transparency-structure-representation-3d-from-bundle',
display: 'Transparency 3D Representation',
from: SO.Molecule.Structure.Representation3D,
to: SO.Molecule.Structure.Representation3DState,
params: {
bundle: PD.Value<StructureElement.Bundle>(StructureElement.Bundle.Empty),
value: PD.Numeric(0.75, { min: 0, max: 1, step: 0.01 }, { label: 'Transparency' }),
variant: PD.Select('single', [['single', 'Single-layer'], ['multi', 'Multi-layer']])
}
})({
canAutoUpdate() {
return true;
},
apply({ a, params }) {
const structure = a.data.source.data
const transparency = Transparency.ofBundle(params.bundle, params.value, params.variant, structure)
return new SO.Molecule.Structure.Representation3DState({
state: { transparency },
initialState: { transparency: Transparency.Empty },
info: structure,
source: a
}, { label: `Transparency (${transparency.value})` })
},
update({ a, b, newParams, oldParams }) {
const structure = b.data.info as Structure
if (a.data.source.data !== structure) return StateTransformer.UpdateResult.Recreate
const oldTransparency = b.data.state.transparency!
const newTransparency = Transparency.ofBundle(newParams.bundle, newParams.value, newParams.variant, structure)
if (Transparency.areEqual(oldTransparency, newTransparency)) return StateTransformer.UpdateResult.Unchanged if (Transparency.areEqual(oldTransparency, newTransparency)) return StateTransformer.UpdateResult.Unchanged
b.data.state.transparency = newTransparency b.data.state.transparency = newTransparency
......
...@@ -6,7 +6,8 @@ ...@@ -6,7 +6,8 @@
import { Loci } from '../mol-model/loci'; import { Loci } from '../mol-model/loci';
import { Color } from '../mol-util/color'; import { Color } from '../mol-util/color';
import { Structure } from '../mol-model/structure'; import { Structure, StructureElement } from '../mol-model/structure';
import { Script } from '../mol-script/script';
export { Overpaint } export { Overpaint }
...@@ -36,4 +37,23 @@ namespace Overpaint { ...@@ -36,4 +37,23 @@ namespace Overpaint {
} }
return { layers, alpha: overpaint.alpha } return { layers, alpha: overpaint.alpha }
} }
export function ofScript(scriptLayers: { script: Script, color: Color, clear: boolean }[], alpha: number, structure: Structure): Overpaint {
const layers: Overpaint.Layer[] = []
for (let i = 0, il = scriptLayers.length; i < il; ++i) {
const { script, color, clear } = scriptLayers[i]
layers.push({ loci: Script.toLoci(script, structure), color, clear })
}
return { layers, alpha }
}
export function ofBundle(bundleLayers: { bundle: StructureElement.Bundle, color: Color, clear: boolean }[], alpha: number, structure: Structure): Overpaint {
const layers: Overpaint.Layer[] = []
for (let i = 0, il = bundleLayers.length; i < il; ++i) {
const { bundle, color, clear } = bundleLayers[i]
const loci = StructureElement.Bundle.toLoci(bundle, structure.root)
layers.push({ loci, color, clear })
}
return { layers, alpha }
}
} }
\ No newline at end of file
...@@ -5,6 +5,8 @@ ...@@ -5,6 +5,8 @@
*/ */
import { Loci, EmptyLoci } from '../mol-model/loci'; import { Loci, EmptyLoci } from '../mol-model/loci';
import { StructureElement, Structure } from '../mol-model/structure';
import { Script } from '../mol-script/script';
export { Transparency } export { Transparency }
...@@ -24,4 +26,12 @@ namespace Transparency { ...@@ -24,4 +26,12 @@ namespace Transparency {
if (!Loci.areEqual(tA.loci, tB.loci)) return false if (!Loci.areEqual(tA.loci, tB.loci)) return false
return true return true
} }
export function ofScript(script: Script, value: number, variant: Transparency.Variant, structure: Structure): Transparency {
return { loci: Script.toLoci(script, structure), value, variant }
}
export function ofBundle(bundle: StructureElement.Bundle, value: number, variant: Transparency.Variant, structure: Structure): Transparency {
return { loci: StructureElement.Bundle.toLoci(bundle, structure), value, variant }
}
} }
\ No newline at end of file
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment