From 1ea3672c5f98772f47861501bdc83ef3f98d7866 Mon Sep 17 00:00:00 2001 From: Alexander Rose <alex.rose@rcsb.org> Date: Wed, 14 Nov 2018 17:09:52 -0800 Subject: [PATCH] wip, refactored param definitions --- src/apps/canvas/component/viewport.tsx | 2 +- src/apps/schema-generator/util/generate.ts | 2 +- src/mol-app/component/parameter/number.tsx | 2 +- src/mol-app/component/parameter/range.tsx | 44 -------- src/mol-app/component/parameters.tsx | 3 - .../geometry/direct-volume/direct-volume.ts | 6 +- src/mol-geo/geometry/geometry.ts | 16 +-- src/mol-geo/geometry/lines/lines.ts | 2 +- src/mol-geo/geometry/mesh/mesh.ts | 6 +- src/mol-geo/geometry/points/points.ts | 6 +- .../structure/unit/gaussian-density.ts | 10 +- src/mol-plugin/state/actions/basic.ts | 2 +- src/mol-plugin/state/transforms/data.ts | 6 +- src/mol-plugin/state/transforms/model.ts | 6 +- src/mol-plugin/state/transforms/visuals.ts | 8 +- src/mol-plugin/ui/controls/parameters.tsx | 1 - src/mol-repr/structure/complex-visual.ts | 4 +- .../representation/ball-and-stick.ts | 10 +- .../structure/representation/cartoon.ts | 8 +- .../structure/units-representation.ts | 2 +- .../visual/carbohydrate-link-cylinder.ts | 2 +- .../visual/carbohydrate-symbol-mesh.ts | 2 +- .../structure/visual/element-point.ts | 2 +- .../structure/visual/element-sphere.ts | 6 +- .../visual/gaussian-density-point.ts | 2 +- .../visual/gaussian-surface-wireframe.ts | 2 +- .../visual/intra-unit-link-cylinder.ts | 2 +- .../structure/visual/nucleotide-block-mesh.ts | 2 +- .../visual/polymer-backbone-cylinder.ts | 2 +- .../visual/polymer-direction-wedge.ts | 2 +- .../structure/visual/polymer-gap-cylinder.ts | 4 +- .../structure/visual/polymer-trace-mesh.ts | 10 +- src/mol-repr/structure/visual/util/link.ts | 6 +- src/mol-repr/volume/isosurface-mesh.ts | 2 +- src/mol-repr/volume/representation.ts | 2 +- src/mol-theme/color/chain-id.ts | 2 +- src/mol-theme/color/cross-link.ts | 4 +- src/mol-theme/color/element-index.ts | 2 +- src/mol-theme/color/polymer-index.ts | 2 +- src/mol-theme/color/sequence-id.ts | 2 +- src/mol-theme/color/uniform.ts | 2 +- src/mol-theme/color/unit-index.ts | 2 +- src/mol-theme/size/uniform.ts | 2 +- src/mol-util/index.ts | 5 - src/mol-util/param-definition.ts | 102 +++++++++++------- src/mol-util/string.ts | 28 +++++ 46 files changed, 173 insertions(+), 174 deletions(-) delete mode 100644 src/mol-app/component/parameter/range.tsx create mode 100644 src/mol-util/string.ts diff --git a/src/apps/canvas/component/viewport.tsx b/src/apps/canvas/component/viewport.tsx index c6c6f547b..35c108815 100644 --- a/src/apps/canvas/component/viewport.tsx +++ b/src/apps/canvas/component/viewport.tsx @@ -28,7 +28,7 @@ interface ViewportState { backgroundColor: Color } -const BackgroundColorParam = PD.Color('Background Color', '', Color(0x000000)) +const BackgroundColorParam = PD.Color(Color(0x000000), { label: 'Background Color' }) export class Viewport extends React.Component<ViewportProps, ViewportState> { private container: HTMLDivElement | null = null; diff --git a/src/apps/schema-generator/util/generate.ts b/src/apps/schema-generator/util/generate.ts index ecf33b495..439867d65 100644 --- a/src/apps/schema-generator/util/generate.ts +++ b/src/apps/schema-generator/util/generate.ts @@ -5,7 +5,7 @@ */ import { Database, Filter, Column } from './schema' -import { indentString } from 'mol-util'; +import { indentString } from 'mol-util/string'; function header (name: string, info: string, importDatabasePath = 'mol-data/db') { return `/** diff --git a/src/mol-app/component/parameter/number.tsx b/src/mol-app/component/parameter/number.tsx index fee73d651..3ee613df7 100644 --- a/src/mol-app/component/parameter/number.tsx +++ b/src/mol-app/component/parameter/number.tsx @@ -23,7 +23,7 @@ export class NumberParamComponent extends React.Component<NumberParamComponentPr } onChange(valueStr: string) { - const value = Number.isInteger(this.props.param.step) ? parseInt(valueStr) : parseFloat(valueStr) + const value = this.props.param.step && Number.isInteger(this.props.param.step) ? parseInt(valueStr) : parseFloat(valueStr) this.setState({ value }) this.props.onChange(value) } diff --git a/src/mol-app/component/parameter/range.tsx b/src/mol-app/component/parameter/range.tsx deleted file mode 100644 index 45b9cf639..000000000 --- a/src/mol-app/component/parameter/range.tsx +++ /dev/null @@ -1,44 +0,0 @@ -/** - * Copyright (c) 2018 mol* contributors, licensed under MIT, See LICENSE file for more info. - * - * @author Alexander Rose <alexander.rose@weirdbyte.de> - */ - -import * as React from 'react' -import { ParamDefinition as PD } from 'mol-util/param-definition'; - -export interface RangeParamComponentProps { - param: PD.Range - value: number - onChange(v: number): void -} - -export interface RangeParamComponentState { - value: number -} - -export class RangeParamComponent extends React.Component<RangeParamComponentProps, RangeParamComponentState> { - state = { - value: this.props.value - } - - onChange(valueStr: string) { - const value = Number.isInteger(this.props.param.step) ? parseInt(valueStr) : parseFloat(valueStr) - this.setState({ value }) - this.props.onChange(value) - } - - render() { - return <div> - <span>{this.props.param.label} </span> - <input type='range' - value={this.state.value} - min={this.props.param.min} - max={this.props.param.max} - step={this.props.param.step} - onChange={e => this.onChange(e.currentTarget.value)} - > - </input> - </div>; - } -} \ No newline at end of file diff --git a/src/mol-app/component/parameters.tsx b/src/mol-app/component/parameters.tsx index c5c0c673c..e493dd358 100644 --- a/src/mol-app/component/parameters.tsx +++ b/src/mol-app/component/parameters.tsx @@ -8,7 +8,6 @@ import * as React from 'react' import { ParamDefinition as PD } from 'mol-util/param-definition'; import { BooleanParamComponent } from './parameter/boolean'; import { NumberParamComponent } from './parameter/number'; -import { RangeParamComponent } from './parameter/range'; import { SelectParamComponent } from './parameter/select'; import { MultiSelectParamComponent } from './parameter/multi-select'; import { TextParamComponent } from './parameter/text'; @@ -28,8 +27,6 @@ function getParamComponent<P extends PD.Any>(p: PD.Any, value: P['defaultValue'] return <BooleanParamComponent param={p} value={value} onChange={onChange} /> case 'number': return <NumberParamComponent param={p} value={value} onChange={onChange} /> - case 'range': - return <RangeParamComponent param={p} value={value} onChange={onChange} /> case 'select': return <SelectParamComponent param={p} value={value} onChange={onChange} /> case 'multi-select': diff --git a/src/mol-geo/geometry/direct-volume/direct-volume.ts b/src/mol-geo/geometry/direct-volume/direct-volume.ts index 47527c3d2..af49e2124 100644 --- a/src/mol-geo/geometry/direct-volume/direct-volume.ts +++ b/src/mol-geo/geometry/direct-volume/direct-volume.ts @@ -70,9 +70,9 @@ export namespace DirectVolume { export const Params = { ...Geometry.Params, - isoValue: PD.Range('Iso Value', '', 0.22, -1, 1, 0.01), - renderMode: PD.Select('Render Mode', '', 'isosurface', RenderModeOptions), - controlPoints: PD.Text('Control Points', '', '0.19:0.1, 0.2:0.5, 0.21:0.1, 0.4:0.3'), + isoValue: PD.Numeric(0.22, { min: -1, max: 1, step: 0.01 }), + renderMode: PD.Select('isosurface', RenderModeOptions), + controlPoints: PD.Text('0.19:0.1, 0.2:0.5, 0.21:0.1, 0.4:0.3'), } export type Params = typeof Params diff --git a/src/mol-geo/geometry/geometry.ts b/src/mol-geo/geometry/geometry.ts index 79d665d11..598e50977 100644 --- a/src/mol-geo/geometry/geometry.ts +++ b/src/mol-geo/geometry/geometry.ts @@ -61,16 +61,16 @@ export namespace Geometry { // export const Params = { - alpha: PD.Range('Opacity', '', 1, 0, 1, 0.01), - depthMask: PD.Boolean('Depth Mask', '', true), - useFog: PD.Boolean('Use Fog', '', false), - highlightColor: PD.Color('Highlight Color', '', Color.fromNormalizedRgb(1.0, 0.4, 0.6)), - selectColor: PD.Color('Select Color', '', Color.fromNormalizedRgb(0.2, 1.0, 0.1)), + alpha: PD.Numeric(1, { min: 0, max: 1, step: 0.01 }, { label: 'Opacity' }), + depthMask: PD.Boolean(true), + useFog: PD.Boolean(false), + highlightColor: PD.Color(Color.fromNormalizedRgb(1.0, 0.4, 0.6)), + selectColor: PD.Color(Color.fromNormalizedRgb(0.2, 1.0, 0.1)), - quality: PD.Select<VisualQuality>('Quality', '', 'auto', VisualQualityOptions), + quality: PD.Select<VisualQuality>('auto', VisualQualityOptions), - colorTheme: PD.Select<BuiltInColorThemeName>('Color Name', '', 'uniform', BuiltInColorThemeOptions), - sizeTheme: PD.Select<BuiltInSizeThemeName>('Size Name', '', 'uniform', BuiltInSizeThemeOptions), + colorTheme: PD.Select<BuiltInColorThemeName>('uniform', BuiltInColorThemeOptions), + sizeTheme: PD.Select<BuiltInSizeThemeName>('uniform', BuiltInSizeThemeOptions), } export type Params = typeof Params diff --git a/src/mol-geo/geometry/lines/lines.ts b/src/mol-geo/geometry/lines/lines.ts index 0cf5bfef2..5e2764ce4 100644 --- a/src/mol-geo/geometry/lines/lines.ts +++ b/src/mol-geo/geometry/lines/lines.ts @@ -95,7 +95,7 @@ export namespace Lines { export const Params = { ...Geometry.Params, - lineSizeAttenuation: PD.Boolean('Line Size Attenuation', '', false), + lineSizeAttenuation: PD.Boolean(false), } export type Params = typeof Params diff --git a/src/mol-geo/geometry/mesh/mesh.ts b/src/mol-geo/geometry/mesh/mesh.ts index 0f7910745..02349efae 100644 --- a/src/mol-geo/geometry/mesh/mesh.ts +++ b/src/mol-geo/geometry/mesh/mesh.ts @@ -341,9 +341,9 @@ export namespace Mesh { export const Params = { ...Geometry.Params, - doubleSided: PD.Boolean('Double Sided', '', false), - flipSided: PD.Boolean('Flip Sided', '', false), - flatShaded: PD.Boolean('Flat Shaded', '', false), + doubleSided: PD.Boolean(false), + flipSided: PD.Boolean(false), + flatShaded: PD.Boolean(false), } export type Params = typeof Params diff --git a/src/mol-geo/geometry/points/points.ts b/src/mol-geo/geometry/points/points.ts index 2b245338d..4d443427c 100644 --- a/src/mol-geo/geometry/points/points.ts +++ b/src/mol-geo/geometry/points/points.ts @@ -57,9 +57,9 @@ export namespace Points { export const Params = { ...Geometry.Params, - pointSizeAttenuation: PD.Boolean('Point Size Attenuation', '', false), - pointFilledCircle: PD.Boolean('Point Filled Circle', '', false), - pointEdgeBleach: PD.Numeric('Point Edge Bleach', '', 0.2, 0, 1, 0.05), + pointSizeAttenuation: PD.Boolean(false), + pointFilledCircle: PD.Boolean(false), + pointEdgeBleach: PD.Numeric(0.2, { min: 0, max: 1, step: 0.05 }), } export type Params = typeof Params diff --git a/src/mol-model/structure/structure/unit/gaussian-density.ts b/src/mol-model/structure/structure/unit/gaussian-density.ts index 0acfa52fd..328bf2c12 100644 --- a/src/mol-model/structure/structure/unit/gaussian-density.ts +++ b/src/mol-model/structure/structure/unit/gaussian-density.ts @@ -15,11 +15,11 @@ import { WebGLContext } from 'mol-gl/webgl/context'; import { PhysicalSizeTheme } from 'mol-theme/size/physical'; export const GaussianDensityParams = { - resolution: PD.Numeric('Resolution', '', 1, 0.1, 10, 0.1), - radiusOffset: PD.Numeric('Radius Offset', '', 0, 0, 10, 0.1), - smoothness: PD.Numeric('Smoothness', '', 1.5, 0.5, 2.5, 0.1), - useGpu: PD.Boolean('Use GPU', '', true), - ignoreCache: PD.Boolean('Ignore Cache', '', false), + 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(true), + ignoreCache: PD.Boolean(false), } export const DefaultGaussianDensityProps = PD.getDefaultValues(GaussianDensityParams) export type GaussianDensityProps = typeof DefaultGaussianDensityProps diff --git a/src/mol-plugin/state/actions/basic.ts b/src/mol-plugin/state/actions/basic.ts index 85c3814a8..7ccbf3c40 100644 --- a/src/mol-plugin/state/actions/basic.ts +++ b/src/mol-plugin/state/actions/basic.ts @@ -20,7 +20,7 @@ export const CreateStructureFromPDBe = StateAction.create<PluginStateObject.Root params: { default: () => ({ id: '1grm' }), definition: () => ({ - id: PD.Text('PDB id', '', '1grm'), + id: PD.Text('1grm', { label: 'PDB id' }), }), // validate: p => !p.id || !p.id.trim() ? [['Enter id.', 'id']] : void 0 }, diff --git a/src/mol-plugin/state/transforms/data.ts b/src/mol-plugin/state/transforms/data.ts index 3c7c043fd..78499dcd9 100644 --- a/src/mol-plugin/state/transforms/data.ts +++ b/src/mol-plugin/state/transforms/data.ts @@ -27,9 +27,9 @@ const Download = PluginStateTransform.Create<SO.Root, SO.Data.String | SO.Data.B url: 'https://www.ebi.ac.uk/pdbe/static/entry/1cbs_updated.cif' }), definition: () => ({ - url: PD.Text('URL', 'Resource URL. Must be the same domain or support CORS.', ''), - label: PD.Text('Label', '', ''), - isBinary: PD.Boolean('Binary', 'If true, download data as binary (string otherwise)', false) + url: PD.Text('', { description: 'Resource URL. Must be the same domain or support CORS.' }), + label: PD.Text(''), + isBinary: PD.Boolean(false, { description: 'If true, download data as binary (string otherwise)' }) }), // validate: p => !p.url || !p.url.trim() ? [['Enter url.', 'url']] : void 0 }, diff --git a/src/mol-plugin/state/transforms/model.ts b/src/mol-plugin/state/transforms/model.ts index 2ad0eed9f..220220e34 100644 --- a/src/mol-plugin/state/transforms/model.ts +++ b/src/mol-plugin/state/transforms/model.ts @@ -29,7 +29,7 @@ const ParseTrajectoryFromMmCif = PluginStateTransform.Create<SO.Data.Cif, SO.Mol const { blocks } = a.data; if (blocks.length === 0) return {}; return { - blockHeader: PD.Select('Header', 'Header of the block to parse', blocks[0].header, blocks.map(b => [b.header, b.header] as [string, string])) + blockHeader: PD.Select(blocks[0].header, blocks.map(b => [b.header, b.header] as [string, string]), { description: 'Header of the block to parse' }) }; } }, @@ -58,7 +58,7 @@ const CreateModelFromTrajectory = PluginStateTransform.Create<SO.Molecule.Trajec to: [SO.Molecule.Model], params: { default: () => ({ modelIndex: 0 }), - definition: a => ({ modelIndex: PD.Range('Model Index', 'Model Index', 0, 0, Math.max(0, a.data.length - 1), 1) }) + definition: a => ({ modelIndex: PD.Numeric(0, { min: 0, max: Math.max(0, a.data.length - 1), step: 1 }, { description: 'Model Index' }) }) }, isApplicable: a => a.data.length > 0, apply({ a, params }) { @@ -106,7 +106,7 @@ const CreateStructureAssembly = PluginStateTransform.Create<SO.Molecule.Model, S definition(a) { const model = a.data; const ids = model.symmetry.assemblies.map(a => [a.id, a.id] as [string, string]); - return { id: PD.Select('Asm Id', 'Assembly Id', ids.length ? ids[0][0] : '', ids) }; + return { id: PD.Select(ids.length ? ids[0][0] : '', ids, { label: 'Asm Id', description: 'Assembly Id' }) }; } }, apply({ a, params }) { diff --git a/src/mol-plugin/state/transforms/visuals.ts b/src/mol-plugin/state/transforms/visuals.ts index fb24bc2bc..81760fc7e 100644 --- a/src/mol-plugin/state/transforms/visuals.ts +++ b/src/mol-plugin/state/transforms/visuals.ts @@ -33,10 +33,14 @@ const CreateStructureRepresentation = PluginStateTransform.Create<SO.Molecule.St } }), definition: (a, ctx: PluginContext) => ({ - type: PD.Mapped('Type', '', + type: PD.Mapped( ctx.structureReprensentation.registry.default.name, ctx.structureReprensentation.registry.types, - name => PD.Group('Params', '', ctx.structureReprensentation.registry.get(name).getParams(ctx.structureReprensentation.themeCtx, a.data))) + name => PD.Group( + ctx.structureReprensentation.registry.get(name).getParams(ctx.structureReprensentation.themeCtx, a.data), + { label: 'Params' } + ) + ) }) }, apply({ a, params }, plugin: PluginContext) { diff --git a/src/mol-plugin/ui/controls/parameters.tsx b/src/mol-plugin/ui/controls/parameters.tsx index 28807f96b..2ac820fcc 100644 --- a/src/mol-plugin/ui/controls/parameters.tsx +++ b/src/mol-plugin/ui/controls/parameters.tsx @@ -41,7 +41,6 @@ function controlFor(param: PD.Any): ValueControl { switch (param.type) { case 'boolean': return BoolControl; case 'number': return NumberControl; - case 'range': return NumberControl; case 'multi-select': return MultiSelectControl; case 'color': return ColorControl; case 'select': return SelectControl; diff --git a/src/mol-repr/structure/complex-visual.ts b/src/mol-repr/structure/complex-visual.ts index b24737ef3..25823c82f 100644 --- a/src/mol-repr/structure/complex-visual.ts +++ b/src/mol-repr/structure/complex-visual.ts @@ -30,7 +30,7 @@ export interface ComplexVisual<P extends StructureParams> extends Visual<Struct const ComplexParams = { ...StructureParams, - unitKinds: PD.MultiSelect<UnitKind>('Unit Kind', '', ['atomic', 'spheres'], UnitKindOptions), + unitKinds: PD.MultiSelect<UnitKind>(['atomic', 'spheres'], UnitKindOptions), } type ComplexParams = typeof ComplexParams @@ -176,7 +176,7 @@ export function ComplexVisual<P extends ComplexParams>(builder: ComplexVisualGeo export const ComplexMeshParams = { ...StructureMeshParams, - unitKinds: PD.MultiSelect<UnitKind>('Unit Kind', '', [ 'atomic', 'spheres' ], UnitKindOptions), + unitKinds: PD.MultiSelect<UnitKind>([ 'atomic', 'spheres' ], UnitKindOptions), } export type ComplexMeshParams = typeof ComplexMeshParams diff --git a/src/mol-repr/structure/representation/ball-and-stick.ts b/src/mol-repr/structure/representation/ball-and-stick.ts index d411043d0..a5fe7d277 100644 --- a/src/mol-repr/structure/representation/ball-and-stick.ts +++ b/src/mol-repr/structure/representation/ball-and-stick.ts @@ -30,11 +30,11 @@ export const BallAndStickParams = { ...ElementSphereParams, ...IntraUnitLinkParams, ...InterUnitLinkParams, - unitKinds: PD.MultiSelect<UnitKind>('Unit Kind', '', ['atomic'], UnitKindOptions), - sizeFactor: PD.Numeric('Size Factor', '', 0.2, 0.01, 10, 0.01), - sizeTheme: PD.Select<BuiltInSizeThemeName>('Size Theme', '', 'uniform', BuiltInSizeThemeOptions), - colorTheme: PD.Select<BuiltInColorThemeName>('Color Theme', '', 'polymer-index', BuiltInColorThemeOptions), - visuals: PD.MultiSelect<BallAndStickVisualName>('Visuals', '', ['element-sphere', 'intra-link', 'inter-link'], BallAndStickVisualOptions), + unitKinds: PD.MultiSelect<UnitKind>(['atomic'], UnitKindOptions), + sizeFactor: PD.Numeric(0.2, { min: 0.01, max: 10, step: 0.01 }), + sizeTheme: PD.Select<BuiltInSizeThemeName>('uniform', BuiltInSizeThemeOptions), + colorTheme: PD.Select<BuiltInColorThemeName>('polymer-index', BuiltInColorThemeOptions), + visuals: PD.MultiSelect<BallAndStickVisualName>(['element-sphere', 'intra-link', 'inter-link'], BallAndStickVisualOptions), } export type BallAndStickParams = typeof BallAndStickParams export function getBallAndStickParams(ctx: ThemeRegistryContext, structure: Structure) { diff --git a/src/mol-repr/structure/representation/cartoon.ts b/src/mol-repr/structure/representation/cartoon.ts index 8e5430564..1bdd3534b 100644 --- a/src/mol-repr/structure/representation/cartoon.ts +++ b/src/mol-repr/structure/representation/cartoon.ts @@ -31,10 +31,10 @@ export const CartoonParams = { ...PolymerGapParams, ...NucleotideBlockParams, ...PolymerDirectionParams, - sizeFactor: PD.Numeric('Size Factor', '', 0.2, 0, 10, 0.01), - sizeTheme: PD.Select<BuiltInSizeThemeName>('Size Theme', '', 'uniform', BuiltInSizeThemeOptions), - colorTheme: PD.Select<BuiltInColorThemeName>('Color Theme', '', 'polymer-index', BuiltInColorThemeOptions), - visuals: PD.MultiSelect<CartoonVisualName>('Visuals', '', ['polymer-trace', 'polymer-gap', 'nucleotide-block'], CartoonVisualOptions), + sizeFactor: PD.Numeric(0.2, { min: 0, max: 10, step: 0.01 }), + sizeTheme: PD.Select<BuiltInSizeThemeName>('uniform', BuiltInSizeThemeOptions), + colorTheme: PD.Select<BuiltInColorThemeName>('polymer-index', BuiltInColorThemeOptions), + visuals: PD.MultiSelect<CartoonVisualName>(['polymer-trace', 'polymer-gap', 'nucleotide-block'], CartoonVisualOptions), } export type CartoonParams = typeof CartoonParams export function getCartoonParams(ctx: ThemeRegistryContext, structure: Structure) { diff --git a/src/mol-repr/structure/units-representation.ts b/src/mol-repr/structure/units-representation.ts index f0d38b669..b836cc849 100644 --- a/src/mol-repr/structure/units-representation.ts +++ b/src/mol-repr/structure/units-representation.ts @@ -21,7 +21,7 @@ import { BehaviorSubject } from 'rxjs'; export const UnitsParams = { ...StructureParams, - unitKinds: PD.MultiSelect<UnitKind>('Unit Kind', '', ['atomic', 'spheres'], UnitKindOptions), + unitKinds: PD.MultiSelect<UnitKind>(['atomic', 'spheres'], UnitKindOptions), } export type UnitsParams = typeof UnitsParams diff --git a/src/mol-repr/structure/visual/carbohydrate-link-cylinder.ts b/src/mol-repr/structure/visual/carbohydrate-link-cylinder.ts index bc2b296c4..e58322f57 100644 --- a/src/mol-repr/structure/visual/carbohydrate-link-cylinder.ts +++ b/src/mol-repr/structure/visual/carbohydrate-link-cylinder.ts @@ -63,7 +63,7 @@ async function createCarbohydrateLinkCylinderMesh(ctx: VisualContext, structure: export const CarbohydrateLinkParams = { ...UnitsMeshParams, ...LinkCylinderParams, - detail: PD.Numeric('Sphere Detail', '', 0, 0, 3, 1), + detail: PD.Numeric(0, { min: 0, max: 3, step: 1 }), } export type CarbohydrateLinkParams = typeof CarbohydrateLinkParams diff --git a/src/mol-repr/structure/visual/carbohydrate-symbol-mesh.ts b/src/mol-repr/structure/visual/carbohydrate-symbol-mesh.ts index ab85e6f2a..440d6e834 100644 --- a/src/mol-repr/structure/visual/carbohydrate-symbol-mesh.ts +++ b/src/mol-repr/structure/visual/carbohydrate-symbol-mesh.ts @@ -147,7 +147,7 @@ async function createCarbohydrateSymbolMesh(ctx: VisualContext, structure: Struc export const CarbohydrateSymbolParams = { ...ComplexMeshParams, - detail: PD.Numeric('Sphere Detail', '', 0, 0, 3, 1), + detail: PD.Numeric(0, { min: 0, max: 3, step: 1 }), } export type CarbohydrateSymbolParams = typeof CarbohydrateSymbolParams diff --git a/src/mol-repr/structure/visual/element-point.ts b/src/mol-repr/structure/visual/element-point.ts index 174080b4e..2b146bde3 100644 --- a/src/mol-repr/structure/visual/element-point.ts +++ b/src/mol-repr/structure/visual/element-point.ts @@ -18,7 +18,7 @@ import { Theme } from 'mol-theme/theme'; export const ElementPointParams = { ...UnitsPointsParams, - pointSizeAttenuation: PD.Boolean('Point Size Attenuation', '', false), + pointSizeAttenuation: PD.Boolean(false), } export type ElementPointParams = typeof ElementPointParams diff --git a/src/mol-repr/structure/visual/element-sphere.ts b/src/mol-repr/structure/visual/element-sphere.ts index 90a871221..4c1832195 100644 --- a/src/mol-repr/structure/visual/element-sphere.ts +++ b/src/mol-repr/structure/visual/element-sphere.ts @@ -14,9 +14,9 @@ import { BuiltInSizeThemeName, BuiltInSizeThemeOptions } from 'mol-theme/size'; export const ElementSphereParams = { ...UnitsMeshParams, - sizeTheme: PD.Select<BuiltInSizeThemeName>('Size Theme', '', 'physical', BuiltInSizeThemeOptions), - sizeFactor: PD.Numeric('Size Factor', '', 1, 0, 10, 0.1), - detail: PD.Numeric('Sphere Detail', '', 0, 0, 3, 1), + sizeTheme: PD.Select<BuiltInSizeThemeName>('physical', BuiltInSizeThemeOptions), + sizeFactor: PD.Numeric(1, { min: 0, max: 10, step: 0.1 }), + detail: PD.Numeric(0, { min: 0, max: 3, step: 1 }), } export type ElementSphereParams = typeof ElementSphereParams diff --git a/src/mol-repr/structure/visual/gaussian-density-point.ts b/src/mol-repr/structure/visual/gaussian-density-point.ts index 875705c3c..6a7e20353 100644 --- a/src/mol-repr/structure/visual/gaussian-density-point.ts +++ b/src/mol-repr/structure/visual/gaussian-density-point.ts @@ -21,7 +21,7 @@ import { Theme } from 'mol-theme/theme'; export const GaussianDensityPointParams = { ...UnitsPointsParams, ...GaussianDensityParams, - pointSizeAttenuation: PD.Boolean('Point Size Attenuation', '', false), + pointSizeAttenuation: PD.Boolean(false), } export type GaussianDensityPointParams = typeof GaussianDensityPointParams diff --git a/src/mol-repr/structure/visual/gaussian-surface-wireframe.ts b/src/mol-repr/structure/visual/gaussian-surface-wireframe.ts index eec416e57..dea76bc8d 100644 --- a/src/mol-repr/structure/visual/gaussian-surface-wireframe.ts +++ b/src/mol-repr/structure/visual/gaussian-surface-wireframe.ts @@ -35,7 +35,7 @@ async function createGaussianWireframe(ctx: VisualContext, unit: Unit, structure export const GaussianWireframeParams = { ...UnitsLinesParams, ...GaussianDensityParams, - lineSizeAttenuation: PD.Boolean('Line Size Attenuation', '', false), + lineSizeAttenuation: PD.Boolean(false), } export type GaussianWireframeParams = typeof GaussianWireframeParams diff --git a/src/mol-repr/structure/visual/intra-unit-link-cylinder.ts b/src/mol-repr/structure/visual/intra-unit-link-cylinder.ts index 0355d66ba..5efdb9cbd 100644 --- a/src/mol-repr/structure/visual/intra-unit-link-cylinder.ts +++ b/src/mol-repr/structure/visual/intra-unit-link-cylinder.ts @@ -67,7 +67,7 @@ async function createIntraUnitLinkCylinderMesh(ctx: VisualContext, unit: Unit, s export const IntraUnitLinkParams = { ...UnitsMeshParams, ...LinkCylinderParams, - sizeFactor: PD.Numeric('Size Factor', '', 0.2, 0, 10, 0.01), + sizeFactor: PD.Numeric(0.2, { min: 0, max: 10, step: 0.01 }), } export type IntraUnitLinkParams = typeof IntraUnitLinkParams diff --git a/src/mol-repr/structure/visual/nucleotide-block-mesh.ts b/src/mol-repr/structure/visual/nucleotide-block-mesh.ts index 2d9d82716..e208a134b 100644 --- a/src/mol-repr/structure/visual/nucleotide-block-mesh.ts +++ b/src/mol-repr/structure/visual/nucleotide-block-mesh.ts @@ -35,7 +35,7 @@ const sVec = Vec3.zero() const box = Box() export const NucleotideBlockMeshParams = { - sizeFactor: PD.Numeric('Size Factor', '', 0.2, 0, 10, 0.01), + sizeFactor: PD.Numeric(0.2, { min: 0, max: 10, step: 0.01 }), } export const DefaultNucleotideBlockMeshProps = PD.getDefaultValues(NucleotideBlockMeshParams) export type NucleotideBlockMeshProps = typeof DefaultNucleotideBlockMeshProps diff --git a/src/mol-repr/structure/visual/polymer-backbone-cylinder.ts b/src/mol-repr/structure/visual/polymer-backbone-cylinder.ts index b10d5cee0..62777f8bc 100644 --- a/src/mol-repr/structure/visual/polymer-backbone-cylinder.ts +++ b/src/mol-repr/structure/visual/polymer-backbone-cylinder.ts @@ -21,7 +21,7 @@ import { VisualContext } from 'mol-repr/representation'; import { Theme } from 'mol-theme/theme'; export const PolymerBackboneCylinderParams = { - radialSegments: PD.Numeric('Radial Segments', '', 16, 3, 56, 1), + radialSegments: PD.Numeric(16, { min: 3, max: 56, step: 1 }), } export const DefaultPolymerBackboneCylinderProps = PD.getDefaultValues(PolymerBackboneCylinderParams) export type PolymerBackboneCylinderProps = typeof DefaultPolymerBackboneCylinderProps diff --git a/src/mol-repr/structure/visual/polymer-direction-wedge.ts b/src/mol-repr/structure/visual/polymer-direction-wedge.ts index 1bca05adc..852fdbda7 100644 --- a/src/mol-repr/structure/visual/polymer-direction-wedge.ts +++ b/src/mol-repr/structure/visual/polymer-direction-wedge.ts @@ -30,7 +30,7 @@ const heightFactor = 6 const wedge = Wedge() export const PolymerDirectionWedgeParams = { - sizeFactor: PD.Numeric('Size Factor', '', 0.2, 0, 10, 0.01), + sizeFactor: PD.Numeric(0.2, { min: 0, max: 10, step: 0.01 }), } export const DefaultPolymerDirectionWedgeProps = PD.getDefaultValues(PolymerDirectionWedgeParams) export type PolymerDirectionWedgeProps = typeof DefaultPolymerDirectionWedgeProps diff --git a/src/mol-repr/structure/visual/polymer-gap-cylinder.ts b/src/mol-repr/structure/visual/polymer-gap-cylinder.ts index 0d60c1660..7b74e19ec 100644 --- a/src/mol-repr/structure/visual/polymer-gap-cylinder.ts +++ b/src/mol-repr/structure/visual/polymer-gap-cylinder.ts @@ -23,8 +23,8 @@ import { Theme } from 'mol-theme/theme'; const segmentCount = 10 export const PolymerGapCylinderParams = { - sizeFactor: PD.Numeric('Size Factor', '', 0.2, 0, 10, 0.01), - radialSegments: PD.Numeric('Radial Segments', '', 16, 3, 56, 1), + sizeFactor: PD.Numeric(0.2, { min: 0, max: 10, step: 0.01 }), + radialSegments: PD.Numeric(16, { min: 3, max: 56, step: 1 }), } export const DefaultPolymerGapCylinderProps = PD.getDefaultValues(PolymerGapCylinderParams) export type PolymerGapCylinderProps = typeof DefaultPolymerGapCylinderProps diff --git a/src/mol-repr/structure/visual/polymer-trace-mesh.ts b/src/mol-repr/structure/visual/polymer-trace-mesh.ts index 698f1f10e..e4eaad776 100644 --- a/src/mol-repr/structure/visual/polymer-trace-mesh.ts +++ b/src/mol-repr/structure/visual/polymer-trace-mesh.ts @@ -19,11 +19,11 @@ import { VisualContext } from 'mol-repr/representation'; import { Theme } from 'mol-theme/theme'; export const PolymerTraceMeshParams = { - sizeFactor: PD.Numeric('Size Factor', '', 0.2, 0, 10, 0.01), - linearSegments: PD.Numeric('Linear Segments', '', 8, 1, 48, 1), - radialSegments: PD.Numeric('Radial Segments', '', 16, 3, 56, 1), - aspectRatio: PD.Numeric('Aspect Ratio', '', 5, 0.1, 5, 0.1), - arrowFactor: PD.Numeric('Arrow Factor', '', 1.5, 0.1, 5, 0.1), + sizeFactor: PD.Numeric(0.2, { min: 0, max: 10, step: 0.01 }), + linearSegments: PD.Numeric(8, { min: 1, max: 48, step: 1 }), + radialSegments: PD.Numeric(16, { min: 3, max: 56, step: 1 }), + aspectRatio: PD.Numeric(5, { min: 0.1, max: 5, step: 0.1 }), + arrowFactor: PD.Numeric(1.5, { min: 0.1, max: 5, step: 0.1 }), } export const DefaultPolymerTraceMeshProps = PD.getDefaultValues(PolymerTraceMeshParams) export type PolymerTraceMeshProps = typeof DefaultPolymerTraceMeshProps diff --git a/src/mol-repr/structure/visual/util/link.ts b/src/mol-repr/structure/visual/util/link.ts index 179464f52..a080395f4 100644 --- a/src/mol-repr/structure/visual/util/link.ts +++ b/src/mol-repr/structure/visual/util/link.ts @@ -16,9 +16,9 @@ import { LocationIterator } from 'mol-geo/util/location-iterator'; import { VisualContext } from 'mol-repr/representation'; export const LinkCylinderParams = { - linkScale: PD.Range('Link Scale', '', 0.4, 0, 1, 0.1), - linkSpacing: PD.Range('Link Spacing', '', 1, 0, 2, 0.01), - radialSegments: PD.Numeric('Radial Segments', '', 16, 3, 56, 1), + linkScale: PD.Numeric(0.4, { min: 0, max: 1, step: 0.1 }), + linkSpacing: PD.Numeric(1, { min: 0, max: 2, step: 0.01 }), + radialSegments: PD.Numeric(16, { min: 3, max: 56, step: 1 }), } export const DefaultLinkCylinderProps = PD.getDefaultValues(LinkCylinderParams) export type LinkCylinderProps = typeof DefaultLinkCylinderProps diff --git a/src/mol-repr/volume/isosurface-mesh.ts b/src/mol-repr/volume/isosurface-mesh.ts index c7d6e015f..a0387ec44 100644 --- a/src/mol-repr/volume/isosurface-mesh.ts +++ b/src/mol-repr/volume/isosurface-mesh.ts @@ -41,7 +41,7 @@ export async function createVolumeIsosurface(ctx: VisualContext, volume: VolumeD export const IsosurfaceParams = { ...Mesh.Params, - isoValue: PD.Range('Iso Value', '', 0.22, -1, 1, 0.01), + isoValue: PD.Numeric(0.22, { min: -1, max: 1, step: 0.01 }), } export type IsosurfaceParams = typeof IsosurfaceParams export function getIsosurfaceParams(ctx: ThemeRegistryContext, volume: VolumeData) { diff --git a/src/mol-repr/volume/representation.ts b/src/mol-repr/volume/representation.ts index 907d7cfbd..c252534c8 100644 --- a/src/mol-repr/volume/representation.ts +++ b/src/mol-repr/volume/representation.ts @@ -135,7 +135,7 @@ export type VolumeRepresentationProvider<P extends VolumeParams> = Representatio export const VolumeParams = { ...Geometry.Params, - isoValue: PD.Range('Iso Value', '', 0.22, -1, 1, 0.01), + isoValue: PD.Numeric(0.22, { min: -1, max: 1, step: 0.01 }), } export type VolumeParams = typeof VolumeParams diff --git a/src/mol-theme/color/chain-id.ts b/src/mol-theme/color/chain-id.ts index 50018cacd..139da7c8a 100644 --- a/src/mol-theme/color/chain-id.ts +++ b/src/mol-theme/color/chain-id.ts @@ -17,7 +17,7 @@ const DefaultColor = Color(0xCCCCCC) const Description = 'Gives every chain a color based on its `asym_id` value.' export const ChainIdColorThemeParams = { - list: PD.Select<ColorListName>('Color Scale', '', 'RdYlBu', ColorListOptions), + list: PD.Select<ColorListName>('RdYlBu', ColorListOptions), } export function getChainIdColorThemeParams(ctx: ThemeDataContext) { return ChainIdColorThemeParams // TODO return copy diff --git a/src/mol-theme/color/cross-link.ts b/src/mol-theme/color/cross-link.ts index 220455d57..1f6ff23b4 100644 --- a/src/mol-theme/color/cross-link.ts +++ b/src/mol-theme/color/cross-link.ts @@ -18,8 +18,8 @@ const DefaultColor = Color(0xCCCCCC) const Description = 'Colors cross-links by the deviation of the observed distance versus the modeled distance (e.g. `ihm_cross_link_restraint.distance_threshold`).' export const CrossLinkColorThemeParams = { - domain: PD.Interval('Color Domain', '', [-10, 10]), - list: PD.Select<ColorListName>('Color Scale', '', 'RdYlBu', ColorListOptions), + domain: PD.Interval([-10, 10]), + list: PD.Select<ColorListName>('RdYlBu', ColorListOptions), } export function getCrossLinkColorThemeParams(ctx: ThemeDataContext) { return CrossLinkColorThemeParams // TODO return copy diff --git a/src/mol-theme/color/element-index.ts b/src/mol-theme/color/element-index.ts index c21938103..d0eb06e61 100644 --- a/src/mol-theme/color/element-index.ts +++ b/src/mol-theme/color/element-index.ts @@ -17,7 +17,7 @@ const DefaultColor = Color(0xCCCCCC) const Description = 'Gives every element (atom or coarse sphere/gaussian) a unique color based on the position (index) of the element in the list of elements in the structure.' export const ElementIndexColorThemeParams = { - list: PD.Select<ColorListName>('Color Scale', '', 'RdYlBu', ColorListOptions), + list: PD.Select<ColorListName>('RdYlBu', ColorListOptions), } export function getElementIndexColorThemeParams(ctx: ThemeDataContext) { return ElementIndexColorThemeParams // TODO return copy diff --git a/src/mol-theme/color/polymer-index.ts b/src/mol-theme/color/polymer-index.ts index de03c8700..f34dc35a7 100644 --- a/src/mol-theme/color/polymer-index.ts +++ b/src/mol-theme/color/polymer-index.ts @@ -16,7 +16,7 @@ const DefaultColor = Color(0xCCCCCC) const Description = 'Gives every polymer a unique color based on the position (index) of the polymer in the list of polymers in the structure.' export const PolymerIndexColorThemeParams = { - list: PD.Select<ColorListName>('Color Scale', '', 'RdYlBu', ColorListOptions), + list: PD.Select<ColorListName>('RdYlBu', ColorListOptions), } export function getPolymerIndexColorThemeParams(ctx: ThemeDataContext) { return PolymerIndexColorThemeParams // TODO return copy diff --git a/src/mol-theme/color/sequence-id.ts b/src/mol-theme/color/sequence-id.ts index 881c2057d..43023587e 100644 --- a/src/mol-theme/color/sequence-id.ts +++ b/src/mol-theme/color/sequence-id.ts @@ -17,7 +17,7 @@ const DefaultColor = Color(0xCCCCCC) const Description = 'Gives every polymer residue a color based on its `seq_id` value.' export const SequenceIdColorThemeParams = { - list: PD.Select<ColorListName>('Color Scale', '', 'rainbow', ColorListOptions), + list: PD.Select<ColorListName>('rainbow', ColorListOptions), } export function getSequenceIdColorThemeParams(ctx: ThemeDataContext) { return SequenceIdColorThemeParams // TODO return copy diff --git a/src/mol-theme/color/uniform.ts b/src/mol-theme/color/uniform.ts index 6f445450b..905deb9b3 100644 --- a/src/mol-theme/color/uniform.ts +++ b/src/mol-theme/color/uniform.ts @@ -13,7 +13,7 @@ const DefaultColor = Color(0xCCCCCC) const Description = 'Gives everything the same, uniform color.' export const UniformColorThemeParams = { - value: PD.Color('Color Value', '', DefaultColor), + value: PD.Color(DefaultColor), } export function getUniformColorThemeParams(ctx: ThemeDataContext) { return UniformColorThemeParams // TODO return copy diff --git a/src/mol-theme/color/unit-index.ts b/src/mol-theme/color/unit-index.ts index d821a61d6..0a5079615 100644 --- a/src/mol-theme/color/unit-index.ts +++ b/src/mol-theme/color/unit-index.ts @@ -16,7 +16,7 @@ const DefaultColor = Color(0xCCCCCC) const Description = 'Gives every unit (single chain or collection of single elements) a unique color based on the position (index) of the unit in the list of units in the structure.' export const UnitIndexColorThemeParams = { - list: PD.Select<ColorListName>('Color Scale', '', 'RdYlBu', ColorListOptions), + list: PD.Select<ColorListName>('RdYlBu', ColorListOptions), } export function getUnitIndexColorThemeParams(ctx: ThemeDataContext) { return UnitIndexColorThemeParams // TODO return copy diff --git a/src/mol-theme/size/uniform.ts b/src/mol-theme/size/uniform.ts index dee1b97bf..8d12a1600 100644 --- a/src/mol-theme/size/uniform.ts +++ b/src/mol-theme/size/uniform.ts @@ -11,7 +11,7 @@ import { ThemeDataContext } from 'mol-theme/theme'; const Description = 'Gives everything the same, uniform size.' export const UniformSizeThemeParams = { - value: PD.Numeric('Size Value', '', 1, 0, 20, 0.1), + value: PD.Numeric(1, { min: 0, max: 20, step: 0.1 }), } export function getUniformSizeThemeParams(ctx: ThemeDataContext) { return UniformSizeThemeParams // TODO return copy diff --git a/src/mol-util/index.ts b/src/mol-util/index.ts index b7c5b083f..9c1aa24bf 100644 --- a/src/mol-util/index.ts +++ b/src/mol-util/index.ts @@ -183,9 +183,4 @@ export function formatProgress(p: Progress) { if (tp.isIndeterminate) return tp.message; const x = (100 * tp.current / tp.max).toFixed(2); return `${tp.message} ${x}%`; -} - -const reLine = /^/mg -export function indentString(str: string, count: number, indent: string) { - return count === 0 ? str : str.replace(reLine, indent.repeat(count)) } \ No newline at end of file diff --git a/src/mol-util/param-definition.ts b/src/mol-util/param-definition.ts index 6e9e58ece..3b36bbd2a 100644 --- a/src/mol-util/param-definition.ts +++ b/src/mol-util/param-definition.ts @@ -7,19 +7,24 @@ import { Color as ColorData } from './color'; import { shallowClone } from 'mol-util'; +import { Vec2 } from 'mol-math/linear-algebra'; +import { camelCaseToWords } from './string'; export namespace ParamDefinition { - export interface Base<T> { - label: string - description: string + export interface Info { + label?: string + description?: string + } + + export interface Base<T> extends Info { defaultValue: T } export interface Value<T> extends Base<T> { type: 'value' } - export function Value<T>(label: string, description: string, defaultValue: T): Value<T> { - return { type: 'value', label, description, defaultValue } + export function Value<T>(defaultValue: T, info: Info = {}): Value<T> { + return { type: 'value', defaultValue, ...info } } export interface Select<T extends string> extends Base<T> { @@ -27,8 +32,8 @@ export namespace ParamDefinition { /** array of (value, label) tuples */ options: [T, string][] } - export function Select<T extends string>(label: string, description: string, defaultValue: T, options: [T, string][]): Select<T> { - return { type: 'select', label, description, defaultValue, options } + export function Select<T extends string>(defaultValue: T, options: [T, string][], info: Info = {}): Select<T> { + return { type: 'select', defaultValue, options, ...info } } export interface MultiSelect<E extends string, T = E[]> extends Base<T> { @@ -36,66 +41,67 @@ export namespace ParamDefinition { /** array of (value, label) tuples */ options: [E, string][] } - export function MultiSelect<E extends string, T = E[]>(label: string, description: string, defaultValue: T, options: [E, string][]): MultiSelect<E, T> { - return { type: 'multi-select', label, description, defaultValue, options } + export function MultiSelect<E extends string, T = E[]>(defaultValue: T, options: [E, string][], info: Info = {}): MultiSelect<E, T> { + return { type: 'multi-select', defaultValue, options, ...info } } export interface Boolean extends Base<boolean> { type: 'boolean' } - export function Boolean(label: string, description: string, defaultValue: boolean): Boolean { - return { type: 'boolean', label, description, defaultValue } - } - - export interface Range extends Base<number> { - type: 'range' - min: number - max: number - /** if an `integer` parse value with parseInt, otherwise use parseFloat */ - step: number - } - export function Range(label: string, description: string, defaultValue: number, min: number, max: number, step: number): Range { - return { type: 'range', label, description, defaultValue, min, max, step } + export function Boolean(defaultValue: boolean, info: Info = {}): Boolean { + return { type: 'boolean', defaultValue, ...info } } export interface Text extends Base<string> { type: 'text' } - export function Text(label: string, description: string, defaultValue: string = ''): Text { - return { type: 'text', label, description, defaultValue } + export function Text(defaultValue: string = '', info: Info = {}): Text { + return { type: 'text', defaultValue, ...info } } export interface Color extends Base<ColorData> { type: 'color' } - export function Color(label: string, description: string, defaultValue: ColorData): Color { - return { type: 'color', label, description, defaultValue } + export function Color(defaultValue: ColorData, info: Info = {}): Color { + return { type: 'color', defaultValue, ...info } } export interface Numeric extends Base<number> { type: 'number' - min: number - max: number - /** if an `integer` parse value with parseInt, otherwise use parseFloat */ - step: number + /** If given treat as a range. */ + min?: number + /** If given treat as a range. */ + max?: number + /** + * If given treat as a range. + * If an `integer` parse value with parseInt, otherwise use parseFloat. + */ + step?: number } - export function Numeric(label: string, description: string, defaultValue: number, min: number, max: number, step: number): Numeric { - return { type: 'number', label, description, defaultValue, min, max, step } + export function Numeric(defaultValue: number, range: { min?: number, max?: number, step?: number } = {}, info: Info = {}): Numeric { + return { type: 'number', defaultValue, ...range, ...info } } export interface Interval extends Base<[number, number]> { type: 'interval' } - export function Interval(label: string, description: string, defaultValue: [number, number]): Interval { - return { type: 'interval', label, description, defaultValue } + export function Interval(defaultValue: [number, number], info: Info = {}): Interval { + return { type: 'interval', defaultValue, ...info } + } + + export interface LineGraph extends Base<Vec2[]> { + type: 'line-graph' + } + export function LineGraph(defaultValue: Vec2[], info: Info = {}): LineGraph { + return { type: 'line-graph', defaultValue, ...info } } export interface Group<T> extends Base<T> { type: 'group', params: Params } - export function Group<P extends Params>(label: string, description: string, params: P): Group<Values<P>> { - return { type: 'group', label, description, defaultValue: getDefaultValues(params) as any, params }; + export function Group<P extends Params>(params: P, info: Info = {}): Group<Values<P>> { + return { type: 'group', defaultValue: getDefaultValues(params) as any, params }; } export interface Mapped<T> extends Base<{ name: string, params: T }> { @@ -103,18 +109,23 @@ export namespace ParamDefinition { select: Select<string>, map(name: string): Any } - export function Mapped<T>(label: string, description: string, defaultKey: string, names: [string, string][], map: Mapped<T>['map']): Mapped<T> { + export function Mapped<T>(defaultKey: string, names: [string, string][], map: Mapped<T>['map'], info: Info = {}): Mapped<T> { return { type: 'mapped', - label, - description, defaultValue: { name: defaultKey, params: map(defaultKey).defaultValue as any }, - select: Select<string>(label, description, defaultKey, names), + select: Select<string>(defaultKey, names, info), map }; } - export type Any = Value<any> | Select<any> | MultiSelect<any> | Boolean | Range | Text | Color | Numeric | Interval | Group<any> | Mapped<any> + export interface Converted<T, C> extends Base<T> { + type: 'converted', + convertedControl: Base<C>, + fromValue(v: T): C, + toValue(v: C): T + } + + export type Any = Value<any> | Select<any> | MultiSelect<any> | Boolean | Text | Color | Numeric | Interval | LineGraph | Group<any> | Mapped<any> | Converted<any, any> export type Params = { [k: string]: Any } export type Values<T extends Params> = { [k in keyof T]: T[k]['defaultValue'] } @@ -125,6 +136,15 @@ export namespace ParamDefinition { return d as Values<T> } + export function getLabels<T extends Params>(params: T) { + const d: { [k: string]: string } = {} + Object.keys(params).forEach(k => { + const label = params[k].label + d[k] = label === undefined ? camelCaseToWords(k) : label + }) + return d as { [k in keyof T]: string } + } + export function clone<P extends Params>(params: P): P { return shallowClone(params) } diff --git a/src/mol-util/string.ts b/src/mol-util/string.ts new file mode 100644 index 000000000..a40026c5d --- /dev/null +++ b/src/mol-util/string.ts @@ -0,0 +1,28 @@ +/** + * Copyright (c) 2018 mol* contributors, licensed under MIT, See LICENSE file for more info. + * + * @author Alexander Rose <alexander.rose@weirdbyte.de> + */ + +const reLine = /^/mg +export function indentString(str: string, count: number, indent: string) { + return count === 0 ? str : str.replace(reLine, indent.repeat(count)) +} + +/** Add space between camelCase text. */ +export function splitCamelCase(str: string) { + return str.replace(/([a-z\xE0-\xFF])([A-Z\xC0\xDF])/g, '$1 $2') +} + +/** Split camelCase text and capitalize. */ +export function camelCaseToWords(str: string) { + return capitalize(splitCamelCase(str)) +} + +export const lowerCase = (str: string) => str.toLowerCase() +export const upperCase = (str: string) => str.toUpperCase() + +/** Uppercase the first character of each word. */ +export function capitalize(str: string) { + return str.toLowerCase().replace(/^\w|\s\w/g, upperCase); +} \ No newline at end of file -- GitLab