UNPKG

molstar

Version:

A comprehensive macromolecular library.

238 lines 15.3 kB
/** * Copyright (c) 2019-2021 mol* contributors, licensed under MIT, See LICENSE file for more info. * * @author David Sehnal <david.sehnal@gmail.com> * @author Alexander Rose <alexander.rose@weirdbyte.de> */ import { __assign, __awaiter, __extends, __generator } from "tslib"; import { InteractionsRepresentationProvider } from '../../../../mol-model-props/computed/representations/interactions'; import { InteractionTypeColorThemeProvider } from '../../../../mol-model-props/computed/themes/interaction-type'; import { StructureElement } from '../../../../mol-model/structure'; import { createStructureRepresentationParams } from '../../../../mol-plugin-state/helpers/structure-representation-params'; import { StateTransforms } from '../../../../mol-plugin-state/transforms'; import { PluginBehavior } from '../../../behavior'; import { MolScriptBuilder as MS } from '../../../../mol-script/language/builder'; import { StateSelection, StateTransform } from '../../../../mol-state'; import { SizeTheme } from '../../../../mol-theme/size'; import { ParamDefinition as PD } from '../../../../mol-util/param-definition'; import { PluginCommands } from '../../../commands'; var StructureFocusRepresentationParams = function (plugin) { var reprParams = StateTransforms.Representation.StructureRepresentation3D.definition.params(void 0, plugin); return { expandRadius: PD.Numeric(5, { min: 1, max: 10, step: 1 }), targetParams: PD.Group(reprParams, { label: 'Target', customDefault: createStructureRepresentationParams(plugin, void 0, { type: 'ball-and-stick', size: 'physical', typeParams: { sizeFactor: 0.26, alpha: 0.51 } }) }), surroundingsParams: PD.Group(reprParams, { label: 'Surroundings', customDefault: createStructureRepresentationParams(plugin, void 0, { type: 'ball-and-stick', size: 'physical', typeParams: { sizeFactor: 0.16 } }) }), nciParams: PD.Group(reprParams, { label: 'Non-covalent Int.', customDefault: createStructureRepresentationParams(plugin, void 0, { type: InteractionsRepresentationProvider, color: InteractionTypeColorThemeProvider, size: SizeTheme.BuiltIn.uniform }) }), components: PD.MultiSelect(FocusComponents, PD.arrayToOptions(FocusComponents)), excludeTargetFromSurroundings: PD.Boolean(false, { label: 'Exclude Target', description: 'Exclude the focus "target" from the surroudings component.' }), ignoreHydrogens: PD.Boolean(false) }; }; var FocusComponents = ['target', 'surroundings', 'interactions']; export var StructureFocusRepresentationTags; (function (StructureFocusRepresentationTags) { StructureFocusRepresentationTags["TargetSel"] = "structure-focus-target-sel"; StructureFocusRepresentationTags["TargetRepr"] = "structure-focus-target-repr"; StructureFocusRepresentationTags["SurrSel"] = "structure-focus-surr-sel"; StructureFocusRepresentationTags["SurrRepr"] = "structure-focus-surr-repr"; StructureFocusRepresentationTags["SurrNciRepr"] = "structure-focus-surr-nci-repr"; })(StructureFocusRepresentationTags || (StructureFocusRepresentationTags = {})); var TagSet = new Set([StructureFocusRepresentationTags.TargetSel, StructureFocusRepresentationTags.TargetRepr, StructureFocusRepresentationTags.SurrSel, StructureFocusRepresentationTags.SurrRepr, StructureFocusRepresentationTags.SurrNciRepr]); var StructureFocusRepresentationBehavior = /** @class */ (function (_super) { __extends(StructureFocusRepresentationBehavior, _super); function StructureFocusRepresentationBehavior() { var _this = _super !== null && _super.apply(this, arguments) || this; _this.currentSource = void 0; return _this; } Object.defineProperty(StructureFocusRepresentationBehavior.prototype, "surrLabel", { get: function () { return "[Focus] Surroundings (" + this.params.expandRadius + " \u00C5)"; }, enumerable: false, configurable: true }); StructureFocusRepresentationBehavior.prototype.getReprParams = function (reprParams) { return __assign(__assign({}, this.params.targetParams), { type: { name: reprParams.type.name, params: __assign(__assign({}, reprParams.type.params), { ignoreHydrogens: this.params.ignoreHydrogens }) } }); }; StructureFocusRepresentationBehavior.prototype.ensureShape = function (cell) { var _a; var state = this.plugin.state.data, tree = state.tree; var builder = state.build(); var refs = StateSelection.findUniqueTagsInSubtree(tree, cell.transform.ref, TagSet); // Selections if (!refs[StructureFocusRepresentationTags.TargetSel]) { refs[StructureFocusRepresentationTags.TargetSel] = builder .to(cell) .apply(StateTransforms.Model.StructureSelectionFromBundle, { bundle: StructureElement.Bundle.Empty, label: '[Focus] Target' }, { tags: StructureFocusRepresentationTags.TargetSel }).ref; } if (!refs[StructureFocusRepresentationTags.SurrSel]) { refs[StructureFocusRepresentationTags.SurrSel] = builder .to(cell) .apply(StateTransforms.Model.StructureSelectionFromExpression, { expression: MS.struct.generator.empty(), label: this.surrLabel }, { tags: StructureFocusRepresentationTags.SurrSel }).ref; } var components = this.params.components; // Representations if (components.indexOf('target') >= 0 && !refs[StructureFocusRepresentationTags.TargetRepr]) { refs[StructureFocusRepresentationTags.TargetRepr] = builder .to(refs[StructureFocusRepresentationTags.TargetSel]) .apply(StateTransforms.Representation.StructureRepresentation3D, this.getReprParams(this.params.targetParams), { tags: StructureFocusRepresentationTags.TargetRepr }).ref; } if (components.indexOf('surroundings') >= 0 && !refs[StructureFocusRepresentationTags.SurrRepr]) { refs[StructureFocusRepresentationTags.SurrRepr] = builder .to(refs[StructureFocusRepresentationTags.SurrSel]) .apply(StateTransforms.Representation.StructureRepresentation3D, this.getReprParams(this.params.surroundingsParams), { tags: StructureFocusRepresentationTags.SurrRepr }).ref; } if (components.indexOf('interactions') >= 0 && !refs[StructureFocusRepresentationTags.SurrNciRepr] && cell.obj && InteractionsRepresentationProvider.isApplicable((_a = cell.obj) === null || _a === void 0 ? void 0 : _a.data)) { refs[StructureFocusRepresentationTags.SurrNciRepr] = builder .to(refs[StructureFocusRepresentationTags.SurrSel]) .apply(StateTransforms.Representation.StructureRepresentation3D, this.params.nciParams, { tags: StructureFocusRepresentationTags.SurrNciRepr }).ref; } return { state: state, builder: builder, refs: refs }; }; StructureFocusRepresentationBehavior.prototype.clear = function (root) { var state = this.plugin.state.data; this.currentSource = void 0; var foci = state.select(StateSelection.Generators.byRef(root).subtree().withTag(StructureFocusRepresentationTags.TargetSel)); var surrs = state.select(StateSelection.Generators.byRef(root).subtree().withTag(StructureFocusRepresentationTags.SurrSel)); if (foci.length === 0 && surrs.length === 0) return; var update = state.build(); var bundle = StructureElement.Bundle.Empty; for (var _i = 0, foci_1 = foci; _i < foci_1.length; _i++) { var f = foci_1[_i]; update.to(f).update(StateTransforms.Model.StructureSelectionFromBundle, function (old) { return (__assign(__assign({}, old), { bundle: bundle })); }); } var expression = MS.struct.generator.empty(); for (var _a = 0, surrs_1 = surrs; _a < surrs_1.length; _a++) { var s = surrs_1[_a]; update.to(s).update(StateTransforms.Model.StructureSelectionFromExpression, function (old) { return (__assign(__assign({}, old), { expression: expression })); }); } return PluginCommands.State.Update(this.plugin, { state: state, tree: update, options: { doNotLogTiming: true, doNotUpdateCurrent: true } }); }; StructureFocusRepresentationBehavior.prototype.focus = function (sourceLoci) { return __awaiter(this, void 0, void 0, function () { var parent, loci, residueLoci, residueBundle, target, surroundings, _a, state, builder, refs; var _this = this; return __generator(this, function (_b) { switch (_b.label) { case 0: parent = this.plugin.helpers.substructureParent.get(sourceLoci.structure); if (!parent || !parent.obj) return [2 /*return*/]; this.currentSource = sourceLoci; loci = StructureElement.Loci.remap(sourceLoci, parent.obj.data); residueLoci = StructureElement.Loci.extendToWholeResidues(loci); residueBundle = StructureElement.Bundle.fromLoci(residueLoci); target = StructureElement.Bundle.toExpression(residueBundle); surroundings = MS.struct.modifier.includeSurroundings({ 0: target, radius: this.params.expandRadius, 'as-whole-residues': true }); if (this.params.excludeTargetFromSurroundings) { surroundings = MS.struct.modifier.exceptBy({ 0: surroundings, by: target }); } _a = this.ensureShape(parent), state = _a.state, builder = _a.builder, refs = _a.refs; builder.to(refs[StructureFocusRepresentationTags.TargetSel]).update(StateTransforms.Model.StructureSelectionFromBundle, function (old) { return (__assign(__assign({}, old), { bundle: residueBundle })); }); builder.to(refs[StructureFocusRepresentationTags.SurrSel]).update(StateTransforms.Model.StructureSelectionFromExpression, function (old) { return (__assign(__assign({}, old), { expression: surroundings, label: _this.surrLabel })); }); return [4 /*yield*/, PluginCommands.State.Update(this.plugin, { state: state, tree: builder, options: { doNotLogTiming: true, doNotUpdateCurrent: true } })]; case 1: _b.sent(); return [2 /*return*/]; } }); }); }; StructureFocusRepresentationBehavior.prototype.register = function (ref) { var _this = this; this.subscribeObservable(this.plugin.managers.structure.focus.behaviors.current, function (entry) { if (entry) _this.focus(entry.loci); else _this.clear(StateTransform.RootRef); }); }; StructureFocusRepresentationBehavior.prototype.update = function (params) { return __awaiter(this, void 0, void 0, function () { var old, state, builder, all, components, hasComponent, _i, _a, repr, _b, _c, repr, _d, _e, repr; return __generator(this, function (_f) { switch (_f.label) { case 0: old = this.params; this.params = params; if (old.excludeTargetFromSurroundings !== params.excludeTargetFromSurroundings) { if (this.currentSource) { this.focus(this.currentSource); } return [2 /*return*/, true]; } state = this.plugin.state.data; builder = state.build(); all = StateSelection.Generators.root.subtree(); components = this.params.components; hasComponent = components.indexOf('target') >= 0; for (_i = 0, _a = state.select(all.withTag(StructureFocusRepresentationTags.TargetRepr)); _i < _a.length; _i++) { repr = _a[_i]; if (!hasComponent) builder.delete(repr.transform.ref); else builder.to(repr).update(this.getReprParams(this.params.targetParams)); } hasComponent = components.indexOf('surroundings') >= 0; for (_b = 0, _c = state.select(all.withTag(StructureFocusRepresentationTags.SurrRepr)); _b < _c.length; _b++) { repr = _c[_b]; if (!hasComponent) builder.delete(repr.transform.ref); else builder.to(repr).update(this.getReprParams(this.params.surroundingsParams)); } hasComponent = components.indexOf('interactions') >= 0; for (_d = 0, _e = state.select(all.withTag(StructureFocusRepresentationTags.SurrNciRepr)); _d < _e.length; _d++) { repr = _e[_d]; if (!hasComponent) builder.delete(repr.transform.ref); else builder.to(repr).update(this.params.nciParams); } return [4 /*yield*/, PluginCommands.State.Update(this.plugin, { state: state, tree: builder, options: { doNotLogTiming: true, doNotUpdateCurrent: true } })]; case 1: _f.sent(); if (params.expandRadius !== old.expandRadius) { if (this.currentSource) { this.focus(this.currentSource); } return [2 /*return*/, true]; } return [2 /*return*/, true]; } }); }); }; return StructureFocusRepresentationBehavior; }(PluginBehavior.WithSubscribers)); export var StructureFocusRepresentation = PluginBehavior.create({ name: 'create-structure-focus-representation', display: { name: 'Structure Focus Representation' }, category: 'interaction', ctor: StructureFocusRepresentationBehavior, params: function (_, plugin) { return StructureFocusRepresentationParams(plugin); } }); //# sourceMappingURL=structure-focus-representation.js.map