UNPKG

molstar

Version:

A comprehensive macromolecular library.

421 lines 25 kB
"use strict"; /** * Copyright (c) 2020 mol* contributors, licensed under MIT, See LICENSE file for more info. * * @author Alexander Rose <alexander.rose@weirdbyte.de> */ Object.defineProperty(exports, "__esModule", { value: true }); exports.ValidationReportRandomCoilIndexPreset = exports.ValidationReportDensityFitPreset = exports.ValidationReportGeometryQualityPreset = exports.RCSBValidationReport = void 0; var tslib_1 = require("tslib"); var param_definition_1 = require("../../../mol-util/param-definition"); var behavior_1 = require("../../../mol-plugin/behavior/behavior"); var prop_1 = require("./prop"); var random_coil_index_1 = require("./color/random-coil-index"); var geometry_quality_1 = require("./color/geometry-quality"); var int_1 = require("../../../mol-data/int"); var representation_1 = require("./representation"); var density_fit_1 = require("./color/density-fit"); var util_1 = require("../../../mol-data/util"); var compiler_1 = require("../../../mol-script/runtime/query/compiler"); var structure_selection_query_1 = require("../../../mol-plugin-state/helpers/structure-selection-query"); var builder_1 = require("../../../mol-script/language/builder"); var mol_task_1 = require("../../../mol-task"); var representation_preset_1 = require("../../../mol-plugin-state/builder/structure/representation-preset"); var mol_state_1 = require("../../../mol-state"); var structure_1 = require("../../../mol-model/structure"); exports.RCSBValidationReport = behavior_1.PluginBehavior.create({ name: 'rcsb-validation-report-prop', category: 'custom-props', display: { name: 'Validation Report', description: 'Data from wwPDB Validation Report, obtained via RCSB PDB.' }, ctor: /** @class */ (function (_super) { (0, tslib_1.__extends)(class_1, _super); function class_1() { var _this = _super !== null && _super.apply(this, arguments) || this; _this.provider = prop_1.ValidationReportProvider; _this.labelProvider = { label: function (loci) { if (!_this.params.showTooltip) return; return [ geometryQualityLabel(loci), densityFitLabel(loci), randomCoilIndexLabel(loci) ].filter(function (l) { return !!l; }).join('</br>'); } }; return _this; } class_1.prototype.register = function () { compiler_1.DefaultQueryRuntimeTable.addCustomProp(this.provider.descriptor); this.ctx.customModelProperties.register(this.provider, this.params.autoAttach); this.ctx.managers.lociLabels.addProvider(this.labelProvider); this.ctx.representation.structure.themes.colorThemeRegistry.add(density_fit_1.DensityFitColorThemeProvider); this.ctx.representation.structure.themes.colorThemeRegistry.add(geometry_quality_1.GeometryQualityColorThemeProvider); this.ctx.representation.structure.themes.colorThemeRegistry.add(random_coil_index_1.RandomCoilIndexColorThemeProvider); this.ctx.representation.structure.registry.add(representation_1.ClashesRepresentationProvider); this.ctx.query.structure.registry.add(hasClash); this.ctx.builders.structure.representation.registerPreset(exports.ValidationReportGeometryQualityPreset); this.ctx.builders.structure.representation.registerPreset(exports.ValidationReportDensityFitPreset); this.ctx.builders.structure.representation.registerPreset(exports.ValidationReportRandomCoilIndexPreset); }; class_1.prototype.update = function (p) { var updated = this.params.autoAttach !== p.autoAttach; this.params.autoAttach = p.autoAttach; this.params.showTooltip = p.showTooltip; this.ctx.customStructureProperties.setDefaultAutoAttach(this.provider.descriptor.name, this.params.autoAttach); return updated; }; class_1.prototype.unregister = function () { compiler_1.DefaultQueryRuntimeTable.removeCustomProp(this.provider.descriptor); this.ctx.customStructureProperties.unregister(this.provider.descriptor.name); this.ctx.managers.lociLabels.removeProvider(this.labelProvider); this.ctx.representation.structure.themes.colorThemeRegistry.remove(density_fit_1.DensityFitColorThemeProvider); this.ctx.representation.structure.themes.colorThemeRegistry.remove(geometry_quality_1.GeometryQualityColorThemeProvider); this.ctx.representation.structure.themes.colorThemeRegistry.remove(random_coil_index_1.RandomCoilIndexColorThemeProvider); this.ctx.representation.structure.registry.remove(representation_1.ClashesRepresentationProvider); this.ctx.query.structure.registry.remove(hasClash); this.ctx.builders.structure.representation.unregisterPreset(exports.ValidationReportGeometryQualityPreset); this.ctx.builders.structure.representation.unregisterPreset(exports.ValidationReportDensityFitPreset); this.ctx.builders.structure.representation.unregisterPreset(exports.ValidationReportRandomCoilIndexPreset); }; return class_1; }(behavior_1.PluginBehavior.Handler)), params: function () { return ({ autoAttach: param_definition_1.ParamDefinition.Boolean(false), showTooltip: param_definition_1.ParamDefinition.Boolean(true), baseUrl: param_definition_1.ParamDefinition.Text(prop_1.ValidationReport.DefaultBaseUrl) }); } }); // function geometryQualityLabel(loci) { if (loci.kind === 'element-loci') { if (loci.elements.length === 0) return; if (loci.elements.length === 1 && int_1.OrderedSet.size(loci.elements[0].indices) === 1) { var _a = loci.elements[0], unit = _a.unit, indices = _a.indices; var validationReport = prop_1.ValidationReportProvider.get(unit.model).value; if (!validationReport) return; if (!unit.model.customProperties.hasReference(prop_1.ValidationReportProvider.descriptor)) return; var bondOutliers_1 = validationReport.bondOutliers, angleOutliers_1 = validationReport.angleOutliers; var eI = unit.elements[int_1.OrderedSet.start(indices)]; var issues_1 = new Set(); var bonds = bondOutliers_1.index.get(eI); if (bonds) bonds.forEach(function (b) { return issues_1.add(bondOutliers_1.data[b].tag); }); var angles = angleOutliers_1.index.get(eI); if (angles) angles.forEach(function (a) { return issues_1.add(angleOutliers_1.data[a].tag); }); if (issues_1.size === 0) { return "Geometry Quality <small>(1 Atom)</small>: no issues"; } var summary_1 = []; issues_1.forEach(function (name) { return summary_1.push(name); }); return "Geometry Quality <small>(1 Atom)</small>: " + summary_1.join(', '); } var hasValidationReport = false; var seen_1 = new Set(); var cummulativeIssues_1 = new Map(); var _loop_1 = function (indices, unit) { var validationReport = prop_1.ValidationReportProvider.get(unit.model).value; if (!validationReport) return "continue"; if (!unit.model.customProperties.hasReference(prop_1.ValidationReportProvider.descriptor)) return "continue"; hasValidationReport = true; var geometryIssues = validationReport.geometryIssues; var residueIndex = unit.model.atomicHierarchy.residueAtomSegments.index; var elements = unit.elements; int_1.OrderedSet.forEach(indices, function (idx) { var eI = elements[idx]; var rI = residueIndex[eI]; var residueKey = (0, util_1.cantorPairing)(rI, unit.id); if (!seen_1.has(residueKey)) { var issues = geometryIssues.get(rI); if (issues) { issues.forEach(function (name) { var count = cummulativeIssues_1.get(name) || 0; cummulativeIssues_1.set(name, count + 1); }); } seen_1.add(residueKey); } }); }; for (var _i = 0, _b = loci.elements; _i < _b.length; _i++) { var _c = _b[_i], indices = _c.indices, unit = _c.unit; _loop_1(indices, unit); } if (!hasValidationReport) return; var residueCount = "<small>(" + seen_1.size + " " + (seen_1.size > 1 ? 'Residues' : 'Residue') + ")</small>"; if (cummulativeIssues_1.size === 0) { return "Geometry Quality " + residueCount + ": no issues"; } var summary_2 = []; cummulativeIssues_1.forEach(function (count, name) { summary_2.push("" + name + (count > 1 ? " \u00D7 " + count : '')); }); return "Geometry Quality " + residueCount + ": " + summary_2.join(', '); } } function densityFitLabel(loci) { if (loci.kind === 'element-loci') { if (loci.elements.length === 0) return; var seen_2 = new Set(); var rsrzSeen_1 = new Set(); var rsccSeen_1 = new Set(); var rsrzSum_1 = 0; var rsccSum_1 = 0; var _loop_2 = function (indices, unit) { var validationReport = prop_1.ValidationReportProvider.get(unit.model).value; if (!validationReport) return "continue"; if (!unit.model.customProperties.hasReference(prop_1.ValidationReportProvider.descriptor)) return "continue"; var rsrz = validationReport.rsrz, rscc = validationReport.rscc; var residueIndex = unit.model.atomicHierarchy.residueAtomSegments.index; var elements = unit.elements; int_1.OrderedSet.forEach(indices, function (idx) { var eI = elements[idx]; var rI = residueIndex[eI]; var residueKey = (0, util_1.cantorPairing)(rI, unit.id); if (!seen_2.has(residueKey)) { var rsrzValue = rsrz.get(rI); var rsccValue = rscc.get(rI); if (rsrzValue !== undefined) { rsrzSum_1 += rsrzValue; rsrzSeen_1.add(residueKey); } else if (rsccValue !== undefined) { rsccSum_1 += rsccValue; rsccSeen_1.add(residueKey); } seen_2.add(residueKey); } }); }; for (var _i = 0, _a = loci.elements; _i < _a.length; _i++) { var _b = _a[_i], indices = _b.indices, unit = _b.unit; _loop_2(indices, unit); } if (seen_2.size === 0) return; var summary = []; if (rsrzSeen_1.size) { var rsrzCount = "<small>(" + rsrzSeen_1.size + " " + (rsrzSeen_1.size > 1 ? 'Residues avg.' : 'Residue') + ")</small>"; var rsrzAvg = rsrzSum_1 / rsrzSeen_1.size; summary.push("Real-Space R Z-score " + rsrzCount + ": " + rsrzAvg.toFixed(2)); } if (rsccSeen_1.size) { var rsccCount = "<small>(" + rsccSeen_1.size + " " + (rsccSeen_1.size > 1 ? 'Residues avg.' : 'Residue') + ")</small>"; var rsccAvg = rsccSum_1 / rsccSeen_1.size; summary.push("Real-Space Correlation Coefficient " + rsccCount + ": " + rsccAvg.toFixed(2)); } if (summary.length) { return summary.join('</br>'); } } } function randomCoilIndexLabel(loci) { if (loci.kind === 'element-loci') { if (loci.elements.length === 0) return; var seen_3 = new Set(); var sum_1 = 0; var _loop_3 = function (indices, unit) { var validationReport = prop_1.ValidationReportProvider.get(unit.model).value; if (!validationReport) return "continue"; if (!unit.model.customProperties.hasReference(prop_1.ValidationReportProvider.descriptor)) return "continue"; var rci = validationReport.rci; var residueIndex = unit.model.atomicHierarchy.residueAtomSegments.index; var elements = unit.elements; int_1.OrderedSet.forEach(indices, function (idx) { var eI = elements[idx]; var rI = residueIndex[eI]; var residueKey = (0, util_1.cantorPairing)(rI, unit.id); if (!seen_3.has(residueKey)) { var rciValue = rci.get(rI); if (rciValue !== undefined) { sum_1 += rciValue; seen_3.add(residueKey); } } }); }; for (var _i = 0, _a = loci.elements; _i < _a.length; _i++) { var _b = _a[_i], indices = _b.indices, unit = _b.unit; _loop_3(indices, unit); } if (seen_3.size === 0) return; var residueCount = "<small>(" + seen_3.size + " " + (seen_3.size > 1 ? 'Residues avg.' : 'Residue') + ")</small>"; var rciAvg = sum_1 / seen_3.size; return "Random Coil Index " + residueCount + ": " + rciAvg.toFixed(2); } } // var hasClash = (0, structure_selection_query_1.StructureSelectionQuery)('Residues with Clashes', builder_1.MolScriptBuilder.struct.modifier.union([ builder_1.MolScriptBuilder.struct.modifier.wholeResidues([ builder_1.MolScriptBuilder.struct.modifier.union([ builder_1.MolScriptBuilder.struct.generator.atomGroups({ 'chain-test': builder_1.MolScriptBuilder.core.rel.eq([builder_1.MolScriptBuilder.ammp('objectPrimitive'), 'atomistic']), 'atom-test': prop_1.ValidationReport.symbols.hasClash.symbol(), }) ]) ]) ]), { description: 'Select residues with clashes in the wwPDB validation report.', category: structure_selection_query_1.StructureSelectionCategory.Residue, ensureCustomProperties: function (ctx, structure) { return prop_1.ValidationReportProvider.attach(ctx, structure.models[0]); } }); // exports.ValidationReportGeometryQualityPreset = (0, representation_preset_1.StructureRepresentationPresetProvider)({ id: 'preset-structure-representation-rcsb-validation-report-geometry-uality', display: { name: 'Validation Report (Geometry Quality)', group: 'Annotation', description: 'Color structure based on geometry quality; show geometry clashes. Data from wwPDB Validation Report, obtained via RCSB PDB.' }, isApplicable: function (a) { return a.data.models.length === 1 && prop_1.ValidationReport.isApplicable(a.data.models[0]); }, params: function () { return representation_preset_1.StructureRepresentationPresetProvider.CommonParams; }, apply: function (ref, params, plugin) { var _a; return (0, tslib_1.__awaiter)(this, void 0, void 0, function () { var structureCell, structure, colorTheme, _b, components, representations, clashes, _c, update, builder, typeParams, color, clashesBallAndStick, clashesRepr; var _this = this; return (0, tslib_1.__generator)(this, function (_d) { switch (_d.label) { case 0: structureCell = mol_state_1.StateObjectRef.resolveAndCheck(plugin.state.data, ref); structure = (_a = structureCell === null || structureCell === void 0 ? void 0 : structureCell.obj) === null || _a === void 0 ? void 0 : _a.data; if (!structureCell || !structure) return [2 /*return*/, {}]; return [4 /*yield*/, plugin.runTask(mol_task_1.Task.create('Validation Report', function (runtime) { return (0, tslib_1.__awaiter)(_this, void 0, void 0, function () { return (0, tslib_1.__generator)(this, function (_a) { switch (_a.label) { case 0: return [4 /*yield*/, prop_1.ValidationReportProvider.attach({ runtime: runtime, assetManager: plugin.managers.asset }, structure.models[0])]; case 1: _a.sent(); return [2 /*return*/]; } }); }); }))]; case 1: _d.sent(); colorTheme = geometry_quality_1.GeometryQualityColorThemeProvider.name; return [4 /*yield*/, representation_preset_1.PresetStructureRepresentations.auto.apply(ref, (0, tslib_1.__assign)((0, tslib_1.__assign)({}, params), { theme: { globalName: colorTheme, focus: { name: colorTheme } } }), plugin)]; case 2: _b = _d.sent(), components = _b.components, representations = _b.representations; return [4 /*yield*/, plugin.builders.structure.tryCreateComponentFromExpression(structureCell, hasClash.expression, 'clashes', { label: 'Clashes' })]; case 3: clashes = _d.sent(); _c = representation_preset_1.StructureRepresentationPresetProvider.reprBuilder(plugin, params), update = _c.update, builder = _c.builder, typeParams = _c.typeParams, color = _c.color; if (representations) { clashesBallAndStick = builder.buildRepresentation(update, clashes, { type: 'ball-and-stick', typeParams: typeParams, color: colorTheme }, { tag: 'clashes-ball-and-stick' }); clashesRepr = builder.buildRepresentation(update, clashes, { type: representation_1.ClashesRepresentationProvider.name, typeParams: typeParams, color: color }, { tag: 'clashes-repr' }); } return [4 /*yield*/, update.commit({ revertOnError: true })]; case 4: _d.sent(); return [2 /*return*/, { components: (0, tslib_1.__assign)((0, tslib_1.__assign)({}, components), { clashes: clashes }), representations: (0, tslib_1.__assign)((0, tslib_1.__assign)({}, representations), { clashesBallAndStick: clashesBallAndStick, clashesRepr: clashesRepr }) }]; } }); }); } }); exports.ValidationReportDensityFitPreset = (0, representation_preset_1.StructureRepresentationPresetProvider)({ id: 'preset-structure-representation-rcsb-validation-report-density-fit', display: { name: 'Validation Report (Density Fit)', group: 'Annotation', description: 'Color structure based on density fit. Data from wwPDB Validation Report, obtained via RCSB PDB.' }, isApplicable: function (a) { return a.data.models.length === 1 && prop_1.ValidationReport.isApplicable(a.data.models[0]) && structure_1.Model.isFromXray(a.data.models[0]) && structure_1.Model.probablyHasDensityMap(a.data.models[0]); }, params: function () { return representation_preset_1.StructureRepresentationPresetProvider.CommonParams; }, apply: function (ref, params, plugin) { var _a; return (0, tslib_1.__awaiter)(this, void 0, void 0, function () { var structureCell, structure, colorTheme; var _this = this; return (0, tslib_1.__generator)(this, function (_b) { switch (_b.label) { case 0: structureCell = mol_state_1.StateObjectRef.resolveAndCheck(plugin.state.data, ref); structure = (_a = structureCell === null || structureCell === void 0 ? void 0 : structureCell.obj) === null || _a === void 0 ? void 0 : _a.data; if (!structureCell || !structure) return [2 /*return*/, {}]; return [4 /*yield*/, plugin.runTask(mol_task_1.Task.create('Validation Report', function (runtime) { return (0, tslib_1.__awaiter)(_this, void 0, void 0, function () { return (0, tslib_1.__generator)(this, function (_a) { switch (_a.label) { case 0: return [4 /*yield*/, prop_1.ValidationReportProvider.attach({ runtime: runtime, assetManager: plugin.managers.asset }, structure.models[0])]; case 1: _a.sent(); return [2 /*return*/]; } }); }); }))]; case 1: _b.sent(); colorTheme = density_fit_1.DensityFitColorThemeProvider.name; return [4 /*yield*/, representation_preset_1.PresetStructureRepresentations.auto.apply(ref, (0, tslib_1.__assign)((0, tslib_1.__assign)({}, params), { theme: { globalName: colorTheme, focus: { name: colorTheme } } }), plugin)]; case 2: return [2 /*return*/, _b.sent()]; } }); }); } }); exports.ValidationReportRandomCoilIndexPreset = (0, representation_preset_1.StructureRepresentationPresetProvider)({ id: 'preset-structure-representation-rcsb-validation-report-random-coil-index', display: { name: 'Validation Report (Random Coil Index)', group: 'Annotation', description: 'Color structure based on Random Coil Index. Data from wwPDB Validation Report, obtained via RCSB PDB.' }, isApplicable: function (a) { return a.data.models.length === 1 && prop_1.ValidationReport.isApplicable(a.data.models[0]) && structure_1.Model.isFromNmr(a.data.models[0]); }, params: function () { return representation_preset_1.StructureRepresentationPresetProvider.CommonParams; }, apply: function (ref, params, plugin) { var _a; return (0, tslib_1.__awaiter)(this, void 0, void 0, function () { var structureCell, structure, colorTheme; var _this = this; return (0, tslib_1.__generator)(this, function (_b) { switch (_b.label) { case 0: structureCell = mol_state_1.StateObjectRef.resolveAndCheck(plugin.state.data, ref); structure = (_a = structureCell === null || structureCell === void 0 ? void 0 : structureCell.obj) === null || _a === void 0 ? void 0 : _a.data; if (!structureCell || !structure) return [2 /*return*/, {}]; return [4 /*yield*/, plugin.runTask(mol_task_1.Task.create('Validation Report', function (runtime) { return (0, tslib_1.__awaiter)(_this, void 0, void 0, function () { return (0, tslib_1.__generator)(this, function (_a) { switch (_a.label) { case 0: return [4 /*yield*/, prop_1.ValidationReportProvider.attach({ runtime: runtime, assetManager: plugin.managers.asset }, structure.models[0])]; case 1: _a.sent(); return [2 /*return*/]; } }); }); }))]; case 1: _b.sent(); colorTheme = random_coil_index_1.RandomCoilIndexColorThemeProvider.name; return [4 /*yield*/, representation_preset_1.PresetStructureRepresentations.auto.apply(ref, (0, tslib_1.__assign)((0, tslib_1.__assign)({}, params), { theme: { globalName: colorTheme, focus: { name: colorTheme } } }), plugin)]; case 2: return [2 /*return*/, _b.sent()]; } }); }); } }); //# sourceMappingURL=behavior.js.map