mirror of
https://github.com/molstar/molstar.git
synced 2026-06-05 22:31:26 +08:00
Compare commits
17 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
05f1d8085a | ||
|
|
38bbabd742 | ||
|
|
3ab958a93c | ||
|
|
f59d589a30 | ||
|
|
11f7e54704 | ||
|
|
16ebd8266e | ||
|
|
7a796a4d3d | ||
|
|
1cbb915962 | ||
|
|
80486d58c3 | ||
|
|
81bc116c4d | ||
|
|
4249064dd1 | ||
|
|
028c02f50d | ||
|
|
76e97d7b59 | ||
|
|
ad1181a75b | ||
|
|
5d683462fb | ||
|
|
42422bb0ea | ||
|
|
861e5c3e97 |
36
CHANGELOG.md
Normal file
36
CHANGELOG.md
Normal file
@@ -0,0 +1,36 @@
|
||||
# Change Log
|
||||
All notable changes to this project will be documented in this file, following the suggestions of [Keep a CHANGELOG](http://keepachangelog.com/). This project adheres to [Semantic Versioning](http://semver.org/) for its most widely used - and defacto - public interfaces.
|
||||
|
||||
Note that since we don't clearly distinguish between a public and private interfaces there will be changes in non-major versions that are potentially breaking. If we make breaking changes to less used interfaces we will highlight it in here.
|
||||
|
||||
## [Unreleased]
|
||||
|
||||
## [v2.0.3] - 2021-04-09
|
||||
### Added
|
||||
- Support for ``ColorTheme.palette`` designed for providing gradient-like coloring.
|
||||
|
||||
### Changed
|
||||
- [Breaking] The `zip` function is now asynchronous and expects a `RuntimeContext`. Also added `Zip()` returning a `Task`.
|
||||
- [Breaking] Add ``CubeGridFormat`` in ``alpha-orbitals`` extension.
|
||||
|
||||
|
||||
|
||||
## [v2.0.2] - 2021-03-29
|
||||
### Added
|
||||
- `Canvas3D.getRenderObjects`.
|
||||
- [WIP] Animate state interpolating, including model trajectories
|
||||
|
||||
### Changed
|
||||
- Recognise MSE, SEP, TPO, PTR and PCA as non-standard amino-acids.
|
||||
|
||||
### Fixed
|
||||
- VolumeFromDensityServerCif transform label
|
||||
|
||||
|
||||
## [v2.0.1] - 2021-03-23
|
||||
### Fixed
|
||||
- Exclude tsconfig.commonjs.tsbuildinfo from npm bundle
|
||||
|
||||
|
||||
## [v2.0.0] - 2021-03-23
|
||||
Too many changes to list as this is the start of the changelog... Notably, default exports are now forbidden.
|
||||
4
package-lock.json
generated
4
package-lock.json
generated
@@ -1,11 +1,11 @@
|
||||
{
|
||||
"name": "molstar",
|
||||
"version": "2.0.1",
|
||||
"version": "2.0.3",
|
||||
"lockfileVersion": 2,
|
||||
"requires": true,
|
||||
"packages": {
|
||||
"": {
|
||||
"version": "2.0.1",
|
||||
"version": "2.0.3",
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"@types/argparse": "^1.0.38",
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "molstar",
|
||||
"version": "2.0.1",
|
||||
"version": "2.0.3",
|
||||
"description": "A comprehensive macromolecular library.",
|
||||
"homepage": "https://github.com/molstar/molstar#readme",
|
||||
"repository": {
|
||||
@@ -14,6 +14,7 @@
|
||||
"lint": "eslint .",
|
||||
"lint-fix": "eslint . --fix",
|
||||
"test": "npm run lint && jest",
|
||||
"jest": "jest",
|
||||
"build": "npm run build-tsc && npm run build-extra && npm run build-webpack",
|
||||
"build-viewer": "npm run build-tsc && npm run build-extra && npm run build-webpack-viewer",
|
||||
"build-tsc": "concurrently \"tsc --incremental\" \"tsc --build tsconfig.commonjs.json --incremental\"",
|
||||
|
||||
51
src/examples/basic-wrapper/custom-theme.ts
Normal file
51
src/examples/basic-wrapper/custom-theme.ts
Normal file
@@ -0,0 +1,51 @@
|
||||
import { isPositionLocation } from '../../mol-geo/util/location-iterator';
|
||||
import { Vec3 } from '../../mol-math/linear-algebra';
|
||||
import { ColorTheme } from '../../mol-theme/color';
|
||||
import { ThemeDataContext } from '../../mol-theme/theme';
|
||||
import { Color } from '../../mol-util/color';
|
||||
import { ColorNames } from '../../mol-util/color/names';
|
||||
import { ParamDefinition as PD } from '../../mol-util/param-definition';
|
||||
|
||||
export function CustomColorTheme(
|
||||
ctx: ThemeDataContext,
|
||||
props: PD.Values<{}>
|
||||
): ColorTheme<{}> {
|
||||
const { radius, center } = ctx.structure?.boundary.sphere!;
|
||||
const radiusSq = Math.max(radius * radius, 0.001);
|
||||
const scale = ColorTheme.PaletteScale;
|
||||
|
||||
return {
|
||||
factory: CustomColorTheme,
|
||||
granularity: 'vertex',
|
||||
color: location => {
|
||||
if (!isPositionLocation(location)) return ColorNames.black;
|
||||
const dist = Vec3.squaredDistance(location.position, center);
|
||||
const t = Math.min(dist / radiusSq, 1);
|
||||
return ((t * scale) | 0) as Color;
|
||||
},
|
||||
palette: {
|
||||
filter: 'nearest',
|
||||
colors: [
|
||||
ColorNames.red,
|
||||
ColorNames.pink,
|
||||
ColorNames.violet,
|
||||
ColorNames.orange,
|
||||
ColorNames.yellow,
|
||||
ColorNames.green,
|
||||
ColorNames.blue
|
||||
]
|
||||
},
|
||||
props: props,
|
||||
description: '',
|
||||
};
|
||||
}
|
||||
|
||||
export const CustomColorThemeProvider: ColorTheme.Provider<{}, 'basic-wrapper-custom-color-theme'> = {
|
||||
name: 'basic-wrapper-custom-color-theme',
|
||||
label: 'Custom Color Theme',
|
||||
category: ColorTheme.Category.Misc,
|
||||
factory: CustomColorTheme,
|
||||
getParams: () => ({}),
|
||||
defaultValues: { },
|
||||
isApplicable: (ctx: ThemeDataContext) => true,
|
||||
};
|
||||
@@ -97,6 +97,7 @@
|
||||
addHeader('Misc');
|
||||
|
||||
addControl('Apply Stripes', () => BasicMolStarWrapper.coloring.applyStripes());
|
||||
addControl('Apply Custom Theme', () => BasicMolStarWrapper.coloring.applyCustomTheme());
|
||||
addControl('Default Coloring', () => BasicMolStarWrapper.coloring.applyDefault());
|
||||
|
||||
addHeader('Interactivity');
|
||||
|
||||
@@ -18,6 +18,7 @@ import { Asset } from '../../mol-util/assets';
|
||||
import { Color } from '../../mol-util/color';
|
||||
import { StripedResidues } from './coloring';
|
||||
import { CustomToastMessage } from './controls';
|
||||
import { CustomColorThemeProvider } from './custom-theme';
|
||||
import './index.html';
|
||||
import { buildStaticSuperposition, dynamicSuperpositionTest, StaticSuperpositionTestData } from './superposition';
|
||||
require('mol-plugin-ui/skin/light.scss');
|
||||
@@ -42,6 +43,7 @@ class BasicWrapper {
|
||||
});
|
||||
|
||||
this.plugin.representation.structure.themes.colorThemeRegistry.add(StripedResidues.colorThemeProvider!);
|
||||
this.plugin.representation.structure.themes.colorThemeRegistry.add(CustomColorThemeProvider);
|
||||
this.plugin.managers.lociLabels.addProvider(StripedResidues.labelProvider!);
|
||||
this.plugin.customModelProperties.register(StripedResidues.propertyProvider, true);
|
||||
}
|
||||
@@ -103,6 +105,13 @@ class BasicWrapper {
|
||||
}
|
||||
});
|
||||
},
|
||||
applyCustomTheme: async () => {
|
||||
this.plugin.dataTransaction(async () => {
|
||||
for (const s of this.plugin.managers.structure.hierarchy.current.structures) {
|
||||
await this.plugin.managers.structure.component.updateRepresentationsTheme(s.components, { color: CustomColorThemeProvider.name as any });
|
||||
}
|
||||
});
|
||||
},
|
||||
applyDefault: async () => {
|
||||
this.plugin.dataTransaction(async () => {
|
||||
for (const s of this.plugin.managers.structure.hierarchy.current.structures) {
|
||||
|
||||
@@ -9,6 +9,7 @@ import { Grid } from '../../mol-model/volume';
|
||||
import { SphericalBasisOrder } from './spherical-functions';
|
||||
import { Box3D, RegularGrid3d } from '../../mol-math/geometry';
|
||||
import { arrayMin, arrayMax, arrayRms, arrayMean } from '../../mol-util/array';
|
||||
import { ModelFormat } from '../../mol-model-formats/format';
|
||||
|
||||
// Note: generally contracted gaussians are currently not supported.
|
||||
export interface SphericalElectronShell {
|
||||
@@ -59,6 +60,17 @@ export interface CubeGrid {
|
||||
isovalues?: { negative?: number; positive?: number };
|
||||
}
|
||||
|
||||
export type CubeGridFormat = ModelFormat<CubeGrid>;
|
||||
|
||||
// eslint-disable-next-line
|
||||
export function CubeGridFormat(grid: CubeGrid): CubeGridFormat {
|
||||
return { name: 'custom grid', kind: 'cube-grid', data: grid };
|
||||
}
|
||||
|
||||
export function isCubeGridData(f: ModelFormat): f is CubeGridFormat {
|
||||
return f.kind === 'cube-grid';
|
||||
}
|
||||
|
||||
export function initCubeGrid(params: CubeGridComputationParams): CubeGridInfo {
|
||||
const geometry = params.basis.atoms.map(a => a.center);
|
||||
const { gridSpacing: spacing, boxExpand: expand } = params;
|
||||
|
||||
@@ -17,7 +17,7 @@ import { createVolumeRepresentationParams } from '../../mol-plugin-state/helpers
|
||||
import { StateTransformer } from '../../mol-state';
|
||||
import { Theme } from '../../mol-theme/theme';
|
||||
import { VolumeRepresentation3DHelpers } from '../../mol-plugin-state/transforms/representation';
|
||||
import { AlphaOrbital, Basis, CubeGrid } from './data-model';
|
||||
import { AlphaOrbital, Basis, CubeGrid, CubeGridFormat, isCubeGridData } from './data-model';
|
||||
import { createSphericalCollocationDensityGrid } from './density';
|
||||
import { Tensor } from '../../mol-math/linear-algebra';
|
||||
|
||||
@@ -114,7 +114,7 @@ export const CreateOrbitalVolume = PluginStateTransform.BuiltIn({
|
||||
}, a.data.orbitals[params.index], plugin.canvas3d?.webgl).runInContext(ctx);
|
||||
const volume: Volume = {
|
||||
grid: data.grid,
|
||||
sourceData: { name: 'custom grid', kind: 'alpha-orbitals', data },
|
||||
sourceData: CubeGridFormat(data),
|
||||
customProperties: new CustomProperties(),
|
||||
_propertyData: Object.create(null),
|
||||
};
|
||||
@@ -146,7 +146,7 @@ export const CreateOrbitalDensityVolume = PluginStateTransform.BuiltIn({
|
||||
}, a.data.orbitals, plugin.canvas3d?.webgl).runInContext(ctx);
|
||||
const volume: Volume = {
|
||||
grid: data.grid,
|
||||
sourceData: { name: 'custom grid', kind: 'alpha-orbitals', data },
|
||||
sourceData: CubeGridFormat(data),
|
||||
customProperties: new CustomProperties(),
|
||||
_propertyData: Object.create(null),
|
||||
};
|
||||
@@ -210,9 +210,9 @@ export const CreateOrbitalRepresentation3D = PluginStateTransform.BuiltIn({
|
||||
});
|
||||
|
||||
function volumeParams(plugin: PluginContext, volume: PluginStateObject.Volume.Data, params: StateTransformer.Params<typeof CreateOrbitalRepresentation3D>) {
|
||||
if (volume.data.sourceData.kind !== 'alpha-orbitals') throw new Error('Invalid data source kind.');
|
||||
if (!isCubeGridData(volume.data.sourceData)) throw new Error('Invalid data source kind.');
|
||||
|
||||
const { isovalues } = volume.data.sourceData.data as CubeGrid;
|
||||
const { isovalues } = volume.data.sourceData.data;
|
||||
if (!isovalues) throw new Error('Isovalues are not computed.');
|
||||
|
||||
const value = isovalues[params.kind];
|
||||
|
||||
@@ -234,6 +234,7 @@ interface Canvas3D {
|
||||
readonly boundingSphere: Readonly<Sphere3D>
|
||||
setProps(props: PartialCanvas3DProps | ((old: Canvas3DProps) => Partial<Canvas3DProps> | void), doNotRequestDraw?: boolean /* = false */): void
|
||||
getImagePass(props: Partial<ImageProps>): ImagePass
|
||||
getRenderObjects(): GraphicsRenderObject[]
|
||||
|
||||
/** Returns a copy of the current Canvas3D instance props */
|
||||
readonly props: Readonly<Canvas3DProps>
|
||||
@@ -769,6 +770,11 @@ namespace Canvas3D {
|
||||
getImagePass: (props: Partial<ImageProps> = {}) => {
|
||||
return new ImagePass(webgl, renderer, scene, camera, helper, passes.draw.wboitEnabled, props);
|
||||
},
|
||||
getRenderObjects(): GraphicsRenderObject[] {
|
||||
const renderObjects: GraphicsRenderObject[] = [];
|
||||
scene.forEach((_, ro) => renderObjects.push(ro));
|
||||
return renderObjects;
|
||||
},
|
||||
|
||||
get props() {
|
||||
return getProps();
|
||||
|
||||
@@ -18,11 +18,24 @@ export type ColorType = 'uniform' | 'instance' | 'group' | 'groupInstance' | 've
|
||||
export type ColorData = {
|
||||
uColor: ValueCell<Vec3>,
|
||||
tColor: ValueCell<TextureImage<Uint8Array>>,
|
||||
tPalette: ValueCell<TextureImage<Uint8Array>>,
|
||||
uColorTexDim: ValueCell<Vec2>,
|
||||
dColorType: ValueCell<string>,
|
||||
dUsePalette: ValueCell<boolean>,
|
||||
}
|
||||
|
||||
export function createColors(locationIt: LocationIterator, positionIt: LocationIterator, colorTheme: ColorTheme<any>, colorData?: ColorData): ColorData {
|
||||
const data = _createColors(locationIt, positionIt, colorTheme, colorData);
|
||||
if (colorTheme.palette) {
|
||||
ValueCell.updateIfChanged(data.dUsePalette, true);
|
||||
updatePaletteTexture(colorTheme.palette, data.tPalette);
|
||||
} else {
|
||||
ValueCell.updateIfChanged(data.dUsePalette, false);
|
||||
}
|
||||
return data;
|
||||
}
|
||||
|
||||
function _createColors(locationIt: LocationIterator, positionIt: LocationIterator, colorTheme: ColorTheme<any>, colorData?: ColorData): ColorData {
|
||||
switch (Geometry.getGranularity(locationIt, colorTheme.granularity)) {
|
||||
case 'uniform': return createUniformColor(locationIt, colorTheme.color, colorData);
|
||||
case 'instance': return createInstanceColor(locationIt, colorTheme.color, colorData);
|
||||
@@ -42,18 +55,20 @@ export function createValueColor(value: Color, colorData?: ColorData): ColorData
|
||||
return {
|
||||
uColor: ValueCell.create(Color.toVec3Normalized(Vec3(), value)),
|
||||
tColor: ValueCell.create({ array: new Uint8Array(3), width: 1, height: 1 }),
|
||||
tPalette: ValueCell.create({ array: new Uint8Array(3), width: 1, height: 1 }),
|
||||
uColorTexDim: ValueCell.create(Vec2.create(1, 1)),
|
||||
dColorType: ValueCell.create('uniform'),
|
||||
dUsePalette: ValueCell.create(false),
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
/** Creates color uniform */
|
||||
export function createUniformColor(locationIt: LocationIterator, color: LocationColor, colorData?: ColorData): ColorData {
|
||||
function createUniformColor(locationIt: LocationIterator, color: LocationColor, colorData?: ColorData): ColorData {
|
||||
return createValueColor(color(NullLocation, false), colorData);
|
||||
}
|
||||
|
||||
export function createTextureColor(colors: TextureImage<Uint8Array>, type: ColorType, colorData?: ColorData): ColorData {
|
||||
function createTextureColor(colors: TextureImage<Uint8Array>, type: ColorType, colorData?: ColorData): ColorData {
|
||||
if (colorData) {
|
||||
ValueCell.update(colorData.tColor, colors);
|
||||
ValueCell.update(colorData.uColorTexDim, Vec2.create(colors.width, colors.height));
|
||||
@@ -63,14 +78,16 @@ export function createTextureColor(colors: TextureImage<Uint8Array>, type: Color
|
||||
return {
|
||||
uColor: ValueCell.create(Vec3()),
|
||||
tColor: ValueCell.create(colors),
|
||||
tPalette: ValueCell.create({ array: new Uint8Array(3), width: 1, height: 1 }),
|
||||
uColorTexDim: ValueCell.create(Vec2.create(colors.width, colors.height)),
|
||||
dColorType: ValueCell.create(type),
|
||||
dUsePalette: ValueCell.create(false),
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
/** Creates color texture with color for each instance */
|
||||
export function createInstanceColor(locationIt: LocationIterator, color: LocationColor, colorData?: ColorData): ColorData {
|
||||
function createInstanceColor(locationIt: LocationIterator, color: LocationColor, colorData?: ColorData): ColorData {
|
||||
const { instanceCount } = locationIt;
|
||||
const colors = createTextureImage(Math.max(1, instanceCount), 3, Uint8Array, colorData && colorData.tColor.ref.value.array);
|
||||
locationIt.reset();
|
||||
@@ -83,7 +100,7 @@ export function createInstanceColor(locationIt: LocationIterator, color: Locatio
|
||||
}
|
||||
|
||||
/** Creates color texture with color for each group (i.e. shared across instances) */
|
||||
export function createGroupColor(locationIt: LocationIterator, color: LocationColor, colorData?: ColorData): ColorData {
|
||||
function createGroupColor(locationIt: LocationIterator, color: LocationColor, colorData?: ColorData): ColorData {
|
||||
const { groupCount } = locationIt;
|
||||
const colors = createTextureImage(Math.max(1, groupCount), 3, Uint8Array, colorData && colorData.tColor.ref.value.array);
|
||||
locationIt.reset();
|
||||
@@ -95,7 +112,7 @@ export function createGroupColor(locationIt: LocationIterator, color: LocationCo
|
||||
}
|
||||
|
||||
/** Creates color texture with color for each group in each instance */
|
||||
export function createGroupInstanceColor(locationIt: LocationIterator, color: LocationColor, colorData?: ColorData): ColorData {
|
||||
function createGroupInstanceColor(locationIt: LocationIterator, color: LocationColor, colorData?: ColorData): ColorData {
|
||||
const { groupCount, instanceCount } = locationIt;
|
||||
const count = instanceCount * groupCount;
|
||||
const colors = createTextureImage(Math.max(1, count), 3, Uint8Array, colorData && colorData.tColor.ref.value.array);
|
||||
@@ -108,7 +125,7 @@ export function createGroupInstanceColor(locationIt: LocationIterator, color: Lo
|
||||
}
|
||||
|
||||
/** Creates color texture with color for each vertex (i.e. shared across instances) */
|
||||
export function createVertexColor(locationIt: LocationIterator, color: LocationColor, colorData?: ColorData): ColorData {
|
||||
function createVertexColor(locationIt: LocationIterator, color: LocationColor, colorData?: ColorData): ColorData {
|
||||
const { groupCount, stride } = locationIt;
|
||||
const colors = createTextureImage(Math.max(1, groupCount), 3, Uint8Array, colorData && colorData.tColor.ref.value.array);
|
||||
locationIt.reset();
|
||||
@@ -124,7 +141,7 @@ export function createVertexColor(locationIt: LocationIterator, color: LocationC
|
||||
}
|
||||
|
||||
/** Creates color texture with color for each vertex in each instance */
|
||||
export function createVertexInstanceColor(locationIt: LocationIterator, color: LocationColor, colorData?: ColorData): ColorData {
|
||||
function createVertexInstanceColor(locationIt: LocationIterator, color: LocationColor, colorData?: ColorData): ColorData {
|
||||
const { groupCount, instanceCount, stride } = locationIt;
|
||||
const count = instanceCount * groupCount;
|
||||
const colors = createTextureImage(Math.max(1, count), 3, Uint8Array, colorData && colorData.tColor.ref.value.array);
|
||||
@@ -138,3 +155,34 @@ export function createVertexInstanceColor(locationIt: LocationIterator, color: L
|
||||
}
|
||||
return createTextureColor(colors, 'vertexInstance', colorData);
|
||||
}
|
||||
|
||||
function updatePaletteTexture(palette: ColorTheme.Palette, cell: ValueCell<TextureImage<Uint8Array>>) {
|
||||
let isSynced = true;
|
||||
const texture = cell.ref.value;
|
||||
if (palette.colors.length !== texture.width || texture.filter !== palette.filter) {
|
||||
isSynced = false;
|
||||
} else {
|
||||
const data = texture.array;
|
||||
let o = 0;
|
||||
for (const c of palette.colors) {
|
||||
const [r, g, b] = Color.toRgb(c);
|
||||
if (data[o++] !== r || data[o++] !== g || data[o++] !== b) {
|
||||
isSynced = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (isSynced) return;
|
||||
|
||||
const array = new Uint8Array(palette.colors.length * 3);
|
||||
let o = 0;
|
||||
for (const c of palette.colors) {
|
||||
const [r, g, b] = Color.toRgb(c);
|
||||
array[o++] = r;
|
||||
array[o++] = g;
|
||||
array[o++] = b;
|
||||
}
|
||||
|
||||
ValueCell.update(cell, { array, height: 1, width: palette.colors.length, filter: palette.filter });
|
||||
}
|
||||
@@ -133,7 +133,7 @@ describe('renderer', () => {
|
||||
scene.add(points);
|
||||
scene.commit();
|
||||
expect(ctx.stats.resourceCounts.attribute).toBe(ctx.isWebGL2 ? 4 : 5);
|
||||
expect(ctx.stats.resourceCounts.texture).toBe(6);
|
||||
expect(ctx.stats.resourceCounts.texture).toBe(7);
|
||||
expect(ctx.stats.resourceCounts.vertexArray).toBe(6);
|
||||
expect(ctx.stats.resourceCounts.program).toBe(6);
|
||||
expect(ctx.stats.resourceCounts.shader).toBe(12);
|
||||
|
||||
@@ -185,7 +185,9 @@ export const ColorSchema = {
|
||||
uColor: UniformSpec('v3', 'material'),
|
||||
uColorTexDim: UniformSpec('v2'),
|
||||
tColor: TextureSpec('image-uint8', 'rgb', 'ubyte', 'nearest'),
|
||||
tPalette: TextureSpec('image-uint8', 'rgb', 'ubyte', 'nearest'),
|
||||
dColorType: DefineSpec('string', ['uniform', 'attribute', 'instance', 'group', 'groupInstance', 'vertex', 'vertexInstance']),
|
||||
dUsePalette: DefineSpec('boolean'),
|
||||
} as const;
|
||||
export type ColorSchema = typeof ColorSchema
|
||||
export type ColorValues = Values<ColorSchema>
|
||||
|
||||
@@ -7,6 +7,7 @@
|
||||
import { Sphere3D } from '../../mol-math/geometry';
|
||||
import { Vec3, Mat4 } from '../../mol-math/linear-algebra';
|
||||
import { BoundaryHelper } from '../../mol-math/geometry/boundary-helper';
|
||||
import { TextureFilter } from '../webgl/texture';
|
||||
|
||||
export function calculateTextureInfo (n: number, itemSize: number) {
|
||||
n = Math.max(n, 2); // observed issues with 1 pixel textures
|
||||
@@ -22,6 +23,7 @@ export interface TextureImage<T extends Uint8Array | Float32Array | Int32Array>
|
||||
readonly width: number
|
||||
readonly height: number
|
||||
readonly flipY?: boolean
|
||||
readonly filter?: TextureFilter
|
||||
}
|
||||
|
||||
export interface TextureVolume<T extends Uint8Array | Float32Array> {
|
||||
|
||||
@@ -14,6 +14,10 @@ export const assign_color_varying = `
|
||||
vColor.rgb = readFromTexture(tColor, int(aInstance) * uVertexCount + VertexID, uColorTexDim).rgb;
|
||||
#endif
|
||||
|
||||
#ifdef dUsePalette
|
||||
vPaletteV = ((vColor.r * 256.0 * 256.0 * 255.0 + vColor.g * 256.0 * 255.0 + vColor.b * 255.0) - 1.0) / 16777215.0;
|
||||
#endif
|
||||
|
||||
#ifdef dOverpaint
|
||||
vOverpaint = readFromTexture(tOverpaint, aInstance * float(uGroupCount) + group, uOverpaintTexDim);
|
||||
#endif
|
||||
|
||||
@@ -1,6 +1,8 @@
|
||||
export const assign_material_color = `
|
||||
#if defined(dRenderVariant_color)
|
||||
#if defined(dColorType_uniform)
|
||||
#if defined(dUsePalette)
|
||||
vec4 material = vec4(texture2D(tPalette, vec2(vPaletteV, 0.5)).rgb, uAlpha);
|
||||
#elif defined(dColorType_uniform)
|
||||
vec4 material = vec4(uColor, uAlpha);
|
||||
#elif defined(dColorType_varying)
|
||||
vec4 material = vec4(vColor.rgb, uAlpha);
|
||||
|
||||
@@ -21,4 +21,9 @@ export const color_frag_params = `
|
||||
varying float vGroup;
|
||||
varying float vTransparency;
|
||||
#endif
|
||||
|
||||
#ifdef dUsePalette
|
||||
uniform sampler2D tPalette;
|
||||
varying float vPaletteV;
|
||||
#endif
|
||||
`;
|
||||
@@ -30,4 +30,8 @@ export const color_vert_params = `
|
||||
uniform vec2 uTransparencyTexDim;
|
||||
uniform sampler2D tTransparency;
|
||||
#endif
|
||||
|
||||
#ifdef dUsePalette
|
||||
varying float vPaletteV;
|
||||
#endif
|
||||
`;
|
||||
@@ -283,6 +283,9 @@ export function createTexture(gl: GLRenderingContext, extensions: WebGLExtension
|
||||
gl.bindTexture(gl.TEXTURE_2D, texture);
|
||||
gl.texImage2D(gl.TEXTURE_2D, 0, internalFormat, format, type, data);
|
||||
} else if (isTexture2d(data, target, gl)) {
|
||||
const _filter = data.filter ? getFilter(gl, data.filter) : filter;
|
||||
gl.texParameteri(target, gl.TEXTURE_MAG_FILTER, _filter);
|
||||
gl.texParameteri(target, gl.TEXTURE_MIN_FILTER, _filter);
|
||||
gl.pixelStorei(gl.UNPACK_FLIP_Y_WEBGL, !!data.flipY);
|
||||
if (sub) {
|
||||
gl.texSubImage2D(target, 0, 0, 0, data.width, data.height, format, type, data.array);
|
||||
|
||||
@@ -17,7 +17,7 @@ const SdfString = `
|
||||
M CHG 3 1 -1 3 -1 5 -1
|
||||
M END
|
||||
> <DATABASE_ID>
|
||||
DB14523
|
||||
0
|
||||
|
||||
> <DATABASE_NAME>
|
||||
drugbank
|
||||
@@ -127,7 +127,9 @@ Comp 2
|
||||
4 3 1 0 0 0 0
|
||||
4 5 1 0 0 0 0
|
||||
M CHG 3 1 -1 3 -1 5 -1
|
||||
M END`;
|
||||
M END
|
||||
> <DATABASE_ID>
|
||||
1`;
|
||||
|
||||
describe('sdf reader', () => {
|
||||
it('basic', async () => {
|
||||
@@ -159,12 +161,15 @@ describe('sdf reader', () => {
|
||||
expect(bonds.order.value(3)).toBe(1);
|
||||
|
||||
expect(dataItems.dataHeader.value(0)).toBe('DATABASE_ID');
|
||||
expect(dataItems.data.value(0)).toBe('DB14523');
|
||||
expect(dataItems.data.value(0)).toBe('0');
|
||||
|
||||
expect(dataItems.dataHeader.value(1)).toBe('DATABASE_NAME');
|
||||
expect(dataItems.data.value(1)).toBe('drugbank');
|
||||
|
||||
expect(dataItems.dataHeader.value(31)).toBe('SYNONYMS');
|
||||
expect(dataItems.data.value(31)).toBe('Orthophosphate; Phosphate');
|
||||
|
||||
expect(compound1.dataItems.data.value(0)).toBe('0');
|
||||
expect(compound2.dataItems.data.value(0)).toBe('1');
|
||||
});
|
||||
});
|
||||
|
||||
@@ -54,6 +54,12 @@ const StandardComponents = (function() {
|
||||
{ id: 'SEC', name: 'SELENOCYSTEINE', type: 'L-peptide linking' },
|
||||
{ id: 'PYL', name: 'PYRROLYSINE', type: 'L-peptide linking' },
|
||||
|
||||
{ id: 'MSE', name: 'SELENOMETHIONINE', type: 'L-peptide linking' },
|
||||
{ id: 'SEP', name: 'PHOSPHOSERINE', type: 'L-peptide linking' },
|
||||
{ id: 'TPO', name: 'PHOSPHOTHREONINE', type: 'L-peptide linking' },
|
||||
{ id: 'PTR', name: 'O-PHOSPHOTYROSINE', type: 'L-peptide linking' },
|
||||
{ id: 'PCA', name: 'PYROGLUTAMIC ACID', type: 'L-peptide linking' },
|
||||
|
||||
{ id: 'A', name: 'ADENOSINE-5\'-MONOPHOSPHATE', type: 'RNA linking' },
|
||||
{ id: 'C', name: 'CYTIDINE-5\'-MONOPHOSPHATE', type: 'RNA linking' },
|
||||
{ id: 'T', name: 'THYMIDINE-5\'-MONOPHOSPHATE', type: 'RNA linking' },
|
||||
|
||||
@@ -245,7 +245,9 @@ export const WaterNames = new Set([
|
||||
export const AminoAcidNamesL = new Set([
|
||||
'HIS', 'ARG', 'LYS', 'ILE', 'PHE', 'LEU', 'TRP', 'ALA', 'MET', 'PRO', 'CYS',
|
||||
'ASN', 'VAL', 'GLY', 'SER', 'GLN', 'TYR', 'ASP', 'GLU', 'THR', 'SEC', 'PYL',
|
||||
'UNK' // unknown amino acid from CCD
|
||||
'UNK', // unknown amino acid from CCD
|
||||
'MSE', 'SEP', 'TPO', 'PTR', 'PCA' // common
|
||||
|
||||
]);
|
||||
export const AminoAcidNamesD = new Set([
|
||||
'DAL', // D-ALANINE
|
||||
|
||||
@@ -6,12 +6,13 @@
|
||||
|
||||
import { PluginCommands } from '../../../mol-plugin/commands';
|
||||
import { StateTransform } from '../../../mol-state';
|
||||
import { shallowEqual } from '../../../mol-util';
|
||||
import { ParamDefinition as PD } from '../../../mol-util/param-definition';
|
||||
import { PluginStateAnimation } from '../model';
|
||||
|
||||
export const AnimateStateInterpolation = PluginStateAnimation.create({
|
||||
name: 'built-in.animate-state-interpolation',
|
||||
display: { name: 'Animate State Interpolation' },
|
||||
display: { name: 'Animate State (experimental)' },
|
||||
params: () => ({
|
||||
transtionDurationInMs: PD.Numeric(2000, { min: 100, max: 30000, step: 10 })
|
||||
}),
|
||||
@@ -42,15 +43,25 @@ export const AnimateStateInterpolation = PluginStateAnimation.create({
|
||||
|
||||
for (const s of src) {
|
||||
for (const t of tar) {
|
||||
// TODO: better than quadratic alg.
|
||||
// TODO: support for adding/removing nodes
|
||||
if (t.ref !== s.ref) continue;
|
||||
if (t.version === s.version) continue;
|
||||
|
||||
const e = StateTransform.fromJSON(s), f = StateTransform.fromJSON(t);
|
||||
|
||||
const oldState = state.cells.get(s.ref);
|
||||
if (!oldState) continue;
|
||||
|
||||
let newState;
|
||||
if (!e.transformer.definition.interpolate) {
|
||||
update.to(s.ref).update(currentT <= 0.5 ? e.params : f.params);
|
||||
newState = currentT <= 0.5 ? e.params : f.params;
|
||||
} else {
|
||||
update.to(s.ref).update(e.transformer.definition.interpolate(e.params, f.params, currentT, ctx.plugin));
|
||||
newState = e.transformer.definition.interpolate(e.params, f.params, currentT, ctx.plugin);
|
||||
}
|
||||
|
||||
if (!shallowEqual(oldState, newState)) {
|
||||
update.to(s.ref).update(newState);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright (c) 2018-2020 mol* contributors, licensed under MIT, See LICENSE file for more info.
|
||||
* Copyright (c) 2018-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>
|
||||
@@ -12,7 +12,7 @@ import { StatefulPluginComponent } from '../component';
|
||||
import { PluginContext } from '../../mol-plugin/context';
|
||||
import { utf8ByteCount, utf8Write } from '../../mol-io/common/utf8';
|
||||
import { Asset } from '../../mol-util/assets';
|
||||
import { zip } from '../../mol-util/zip/zip';
|
||||
import { Zip } from '../../mol-util/zip/zip';
|
||||
import { readFromFile } from '../../mol-util/data-source';
|
||||
import { objectForEach } from '../../mol-util/object';
|
||||
import { PLUGIN_VERSION } from '../../mol-plugin/version';
|
||||
@@ -217,7 +217,7 @@ class PluginStateSnapshotManager extends StatefulPluginComponent<{
|
||||
zipDataObj['assets.json'] = data;
|
||||
}
|
||||
|
||||
const zipFile = zip(zipDataObj);
|
||||
const zipFile = await this.plugin.runTask(Zip(zipDataObj));
|
||||
return new Blob([zipFile], {type : 'application/zip'});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -414,6 +414,10 @@ const ModelFromTrajectory = PluginStateTransform.BuiltIn({
|
||||
return new SO.Molecule.Model(model, { label, description });
|
||||
});
|
||||
},
|
||||
interpolate(a, b, t) {
|
||||
const modelIndex = t >= 1 ? b.modelIndex : a.modelIndex + Math.floor((b.modelIndex - a.modelIndex + 1) * t);
|
||||
return { modelIndex };
|
||||
},
|
||||
dispose({ b }) {
|
||||
b?.data.customProperties.dispose();
|
||||
}
|
||||
|
||||
@@ -151,7 +151,7 @@ const VolumeFromDensityServerCif = PluginStateTransform.BuiltIn({
|
||||
const densityServerCif = CIF.schema.densityServer(block);
|
||||
const volume = await volumeFromDensityServerData(densityServerCif, { entryId: params.entryId }).runInContext(ctx);
|
||||
const [x, y, z] = volume.grid.cells.space.dimensions;
|
||||
const props = { label: densityServerCif.volume_data_3d_info.name.value(0), description: `Volume ${x}\u00D7${y}\u00D7${z}` };
|
||||
const props = { label: params.entryId ?? densityServerCif.volume_data_3d_info.name.value(0), description: `Volume ${x}\u00D7${y}\u00D7${z}` };
|
||||
return new SO.Volume.Data(volume, props);
|
||||
});
|
||||
},
|
||||
|
||||
@@ -21,6 +21,7 @@ import { StateActions } from '../mol-plugin-state/actions';
|
||||
import { AssignColorVolume } from '../mol-plugin-state/actions/volume';
|
||||
import { StateTransforms } from '../mol-plugin-state/transforms';
|
||||
import { BoxifyVolumeStreaming, CreateVolumeStreamingBehavior, InitVolumeStreaming } from '../mol-plugin/behavior/dynamic/volume-streaming/transformers';
|
||||
import { AnimateStateInterpolation } from '../mol-plugin-state/animation/built-in/state-interpolation';
|
||||
|
||||
export { PluginSpec };
|
||||
|
||||
@@ -126,6 +127,7 @@ export const DefaultPluginSpec = (): PluginSpec => ({
|
||||
AnimateModelIndex,
|
||||
AnimateCameraSpin,
|
||||
AnimateStateSnapshots,
|
||||
AnimateAssemblyUnwind
|
||||
AnimateAssemblyUnwind,
|
||||
AnimateStateInterpolation
|
||||
]
|
||||
});
|
||||
@@ -35,6 +35,7 @@ import { OperatorHklColorThemeProvider } from './color/operator-hkl';
|
||||
import { PartialChargeColorThemeProvider } from './color/partial-charge';
|
||||
import { AtomIdColorThemeProvider } from './color/atom-id';
|
||||
import { EntityIdColorThemeProvider } from './color/entity-id';
|
||||
import { TextureFilter } from '../mol-gl/webgl/texture';
|
||||
|
||||
export type LocationColor = (location: Location, isSecondary: boolean) => Color
|
||||
|
||||
@@ -44,6 +45,9 @@ interface ColorTheme<P extends PD.Params> {
|
||||
readonly granularity: ColorType
|
||||
readonly color: LocationColor
|
||||
readonly props: Readonly<PD.Values<P>>
|
||||
// if palette is defined, 24bit RGB color value normalized to interval [0, 1]
|
||||
// is used as index to the colors
|
||||
readonly palette?: Readonly<ColorTheme.Palette>
|
||||
readonly contextHash?: number
|
||||
readonly description?: string
|
||||
readonly legend?: Readonly<ScaleLegend | TableLegend>
|
||||
@@ -58,6 +62,13 @@ namespace ColorTheme {
|
||||
Misc = 'Miscellaneous',
|
||||
}
|
||||
|
||||
export interface Palette {
|
||||
filter?: TextureFilter,
|
||||
colors: Color[]
|
||||
}
|
||||
|
||||
export const PaletteScale = (1 << 24) - 1;
|
||||
|
||||
export type Props = { [k: string]: any }
|
||||
export type Factory<P extends PD.Params> = (ctx: ThemeDataContext, props: PD.Values<P>) => ColorTheme<P>
|
||||
export const EmptyFactory = () => Empty;
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright (c) 2020 mol* contributors, licensed under MIT, See LICENSE file for more info.
|
||||
* Copyright (c) 2020-2021 mol* contributors, licensed under MIT, See LICENSE file for more info.
|
||||
*
|
||||
* @author Alexander Rose <alexander.rose@weirdbyte.de>
|
||||
*/
|
||||
@@ -10,16 +10,16 @@ import { SyncRuntimeContext } from '../../mol-task/execution/synchronous';
|
||||
describe('zip', () => {
|
||||
it('roundtrip deflate/inflate', async () => {
|
||||
const data = new Uint8Array([1, 2, 3, 4, 5, 6, 7]);
|
||||
const deflated = deflate(data);
|
||||
const deflated = await deflate(SyncRuntimeContext, data);
|
||||
const inflated = await inflate(SyncRuntimeContext, deflated);
|
||||
expect(inflated).toEqual(data);
|
||||
});
|
||||
|
||||
it('roundtrip zip', async () => {
|
||||
it('roundtrip zip/unzip', async () => {
|
||||
const data = {
|
||||
'test.foo': new Uint8Array([1, 2, 3, 4, 5, 6, 7])
|
||||
};
|
||||
const zipped = zip(data);
|
||||
const zipped = await zip(SyncRuntimeContext, data);
|
||||
const unzipped = await unzip(SyncRuntimeContext, zipped);
|
||||
expect(unzipped).toEqual(data);
|
||||
});
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
/**
|
||||
* Copyright (c) 2020 mol* contributors, licensed under MIT, See LICENSE file for more info.
|
||||
* Copyright (c) 2020-2021 mol* contributors, licensed under MIT, See LICENSE file for more info.
|
||||
*
|
||||
* @author Alexander Rose <alexander.rose@weirdbyte.de>
|
||||
*
|
||||
@@ -7,65 +7,54 @@
|
||||
* MIT License, Copyright (c) 2018 Photopea
|
||||
*/
|
||||
|
||||
import { RuntimeContext } from '../../mol-task';
|
||||
import { NumberArray } from '../type-helpers';
|
||||
import { _hufTree } from './huffman';
|
||||
import { U, revCodes, makeCodes } from './util';
|
||||
|
||||
export function _deflateRaw(data: Uint8Array, out: Uint8Array, opos: number, lvl: number) {
|
||||
const opts = [
|
||||
/*
|
||||
ush good_length; /* reduce lazy search above this match length
|
||||
ush max_lazy; /* do not perform lazy search above this match length
|
||||
ush nice_length; /* quit search above this match length
|
||||
*/
|
||||
/* good lazy nice chain */
|
||||
/* 0 */ [ 0, 0, 0, 0, 0], /* store only */
|
||||
/* 1 */ [ 4, 4, 8, 4, 0], /* max speed, no lazy matches */
|
||||
/* 2 */ [ 4, 5, 16, 8, 0],
|
||||
/* 3 */ [ 4, 6, 16, 16, 0],
|
||||
|
||||
/* 4 */ [ 4, 10, 16, 32, 0], /* lazy matches */
|
||||
/* 5 */ [ 8, 16, 32, 32, 0],
|
||||
/* 6 */ [ 8, 16, 128, 128, 0],
|
||||
/* 7 */ [ 8, 32, 128, 256, 0],
|
||||
/* 8 */ [32, 128, 258, 1024, 1],
|
||||
/* 9 */ [32, 258, 258, 4096, 1] /* max compression */
|
||||
];
|
||||
|
||||
const opt = opts[lvl];
|
||||
|
||||
let i = 0, pos = opos << 3, cvrd = 0;
|
||||
const dlen = data.length;
|
||||
|
||||
if(lvl === 0) {
|
||||
while(i < dlen) {
|
||||
const len = Math.min(0xffff, dlen - i);
|
||||
_putsE(out, pos, (i + len === dlen ? 1 : 0));
|
||||
pos = _copyExact(data, i, len, out, pos + 8);
|
||||
i += len;
|
||||
}
|
||||
return pos >>> 3;
|
||||
}
|
||||
|
||||
function DeflateContext(data: Uint8Array, out: Uint8Array, opos: number, lvl: number) {
|
||||
const { lits, strt, prev } = U;
|
||||
let li = 0, lc = 0, bs = 0, ebits = 0, c = 0, nc = 0; // last_item, literal_count, block_start
|
||||
if(dlen > 2) {
|
||||
nc = _hash(data, 0);
|
||||
strt[nc] = 0;
|
||||
}
|
||||
return {
|
||||
data,
|
||||
out,
|
||||
opt: Opts[lvl],
|
||||
i: 0,
|
||||
pos: opos << 3,
|
||||
cvrd: 0,
|
||||
dlen: data.length,
|
||||
|
||||
// let nmch = 0
|
||||
// let nmci = 0
|
||||
li: 0,
|
||||
lc: 0,
|
||||
bs: 0,
|
||||
ebits: 0,
|
||||
c: 0,
|
||||
nc: 0,
|
||||
|
||||
for(i = 0; i < dlen; i++) {
|
||||
lits,
|
||||
strt,
|
||||
prev
|
||||
};
|
||||
}
|
||||
type DeflateContext = ReturnType<typeof DeflateContext>
|
||||
|
||||
|
||||
function deflateChunk(ctx: DeflateContext, count: number) {
|
||||
const { data, dlen, out, opt } = ctx;
|
||||
let { i, pos, cvrd, li, lc, bs, ebits, c, nc } = ctx;
|
||||
const { lits, strt, prev } = U;
|
||||
|
||||
const end = Math.min(i + count, dlen);
|
||||
|
||||
for(; i < end; i++) {
|
||||
c = nc;
|
||||
//*
|
||||
|
||||
if(i + 1 < dlen - 2) {
|
||||
nc = _hash(data, i + 1);
|
||||
const ii = ((i + 1) & 0x7fff);
|
||||
prev[ii] = strt[nc];
|
||||
strt[nc] = ii;
|
||||
} // */
|
||||
}
|
||||
|
||||
if(cvrd <= i) {
|
||||
if((li > 14000 || lc > 26697) && (dlen - i) > 100) {
|
||||
if(cvrd < i) {
|
||||
@@ -79,19 +68,12 @@ export function _deflateRaw(data: Uint8Array, out: Uint8Array, opos: number, lvl
|
||||
}
|
||||
|
||||
let mch = 0;
|
||||
// if(nmci==i) mch= nmch; else
|
||||
if(i < dlen - 2) {
|
||||
mch = _bestMatch(data, i, prev, c, Math.min(opt[2], dlen - i), opt[3]);
|
||||
}
|
||||
/*
|
||||
if(mch!=0 && opt[4]==1 && (mch>>>16)<opt[1] && i+1<dlen-2) {
|
||||
nmch = UZIP.F._bestMatch(data, i+1, prev, nc, opt[2], opt[3]); nmci=i+1;
|
||||
//var mch2 = UZIP.F._bestMatch(data, i+2, prev, nnc); //nmci=i+1;
|
||||
if((nmch>>>16)>(mch>>>16)) mch=0;
|
||||
}//*/
|
||||
// const len = mch>>>16, dst = mch & 0xffff; // if(i-dst<0) throw "e";
|
||||
|
||||
if(mch !== 0) {
|
||||
const len = mch >>> 16, dst = mch & 0xffff; // if(i-dst<0) throw "e";
|
||||
const len = mch >>> 16, dst = mch & 0xffff;
|
||||
const lgi = _goodIndex(len, U.of0); U.lhst[257 + lgi]++;
|
||||
const dgi = _goodIndex(dst, U.df0); U.dhst[ dgi]++; ebits += U.exb[lgi] + U.dxb[dgi];
|
||||
lits[li] = (len << 23) | (i - cvrd); lits[li + 1] = (dst << 16) | (lgi << 8) | dgi; li += 2;
|
||||
@@ -102,6 +84,69 @@ export function _deflateRaw(data: Uint8Array, out: Uint8Array, opos: number, lvl
|
||||
lc++;
|
||||
}
|
||||
}
|
||||
|
||||
ctx.i = i;
|
||||
ctx.pos = pos;
|
||||
ctx.cvrd = cvrd;
|
||||
ctx.li = li;
|
||||
ctx.lc = lc;
|
||||
ctx.bs = bs;
|
||||
ctx.ebits = ebits;
|
||||
ctx.c = c;
|
||||
ctx.nc = nc;
|
||||
}
|
||||
|
||||
/**
|
||||
* - good_length: reduce lazy search above this match length;
|
||||
* - max_lazy: do not perform lazy search above this match length;
|
||||
* - nice_length: quit search above this match length;
|
||||
*/
|
||||
const Opts = [
|
||||
/* good lazy nice chain */
|
||||
/* 0 */ [ 0, 0, 0, 0, 0], /* store only */
|
||||
/* 1 */ [ 4, 4, 8, 4, 0], /* max speed, no lazy matches */
|
||||
/* 2 */ [ 4, 5, 16, 8, 0],
|
||||
/* 3 */ [ 4, 6, 16, 16, 0],
|
||||
|
||||
/* 4 */ [ 4, 10, 16, 32, 0], /* lazy matches */
|
||||
/* 5 */ [ 8, 16, 32, 32, 0],
|
||||
/* 6 */ [ 8, 16, 128, 128, 0],
|
||||
/* 7 */ [ 8, 32, 128, 256, 0],
|
||||
/* 8 */ [32, 128, 258, 1024, 1],
|
||||
/* 9 */ [32, 258, 258, 4096, 1] /* max compression */
|
||||
] as const;
|
||||
|
||||
export async function _deflateRaw(runtime: RuntimeContext, data: Uint8Array, out: Uint8Array, opos: number, lvl: number) {
|
||||
const ctx = DeflateContext(data, out, opos, lvl);
|
||||
const { dlen } = ctx;
|
||||
|
||||
if(lvl === 0) {
|
||||
let { i, pos } = ctx;
|
||||
|
||||
while(i < dlen) {
|
||||
const len = Math.min(0xffff, dlen - i);
|
||||
_putsE(out, pos, (i + len === dlen ? 1 : 0));
|
||||
pos = _copyExact(data, i, len, out, pos + 8);
|
||||
i += len;
|
||||
}
|
||||
return pos >>> 3;
|
||||
}
|
||||
|
||||
if(dlen > 2) {
|
||||
ctx.nc = _hash(data, 0);
|
||||
ctx.strt[ctx.nc] = 0;
|
||||
}
|
||||
|
||||
while (ctx.i < dlen) {
|
||||
if (runtime.shouldUpdate) {
|
||||
await runtime.update({ message: 'Deflating...', current: ctx.pos, max: data.length });
|
||||
}
|
||||
deflateChunk(ctx, 1024 * 1024);
|
||||
}
|
||||
|
||||
let { li, cvrd, pos } = ctx;
|
||||
const { i, lits, bs, ebits } = ctx;
|
||||
|
||||
if(bs !== i || data.length === 0) {
|
||||
if(cvrd < i) {
|
||||
lits[li] = i - cvrd;
|
||||
@@ -109,10 +154,6 @@ export function _deflateRaw(data: Uint8Array, out: Uint8Array, opos: number, lvl
|
||||
cvrd = i;
|
||||
}
|
||||
pos = _writeBlock(1, lits, li, ebits, data, bs, i - bs, out, pos);
|
||||
li = 0;
|
||||
lc = 0;
|
||||
li = lc = ebits = 0;
|
||||
bs = i;
|
||||
}
|
||||
while((pos & 7) !== 0) pos++;
|
||||
return pos >>> 3;
|
||||
|
||||
@@ -13,7 +13,7 @@ import { writeUint, writeUshort, sizeUTF8, writeUTF8, readUshort, readUint, read
|
||||
import { crc, adler } from './checksum';
|
||||
import { _inflate } from './inflate';
|
||||
import { _deflateRaw } from './deflate';
|
||||
import { RuntimeContext } from '../../mol-task';
|
||||
import { RuntimeContext, Task } from '../../mol-task';
|
||||
|
||||
export async function unzip(runtime: RuntimeContext, buf: ArrayBuffer, onlyNames = false) {
|
||||
const out: { [k: string]: Uint8Array | { size: number, csize: number } } = Object.create(null);
|
||||
@@ -174,12 +174,12 @@ export async function ungzip(runtime: RuntimeContext, file: Uint8Array, buf?: Ui
|
||||
return inflated;
|
||||
}
|
||||
|
||||
export function deflate(data: Uint8Array, opts?: { level: number }/* , buf, off*/) {
|
||||
export async function deflate(runtime: RuntimeContext, data: Uint8Array, opts?: { level: number }/* , buf, off*/) {
|
||||
if(opts === undefined) opts = { level: 6 };
|
||||
let off = 0;
|
||||
const buf = new Uint8Array(50 + Math.floor(data.length * 1.1));
|
||||
buf[off] = 120; buf[off + 1] = 156; off += 2;
|
||||
off = _deflateRaw(data, buf, off, opts.level);
|
||||
off = await _deflateRaw(runtime, data, buf, off, opts.level);
|
||||
const crcValue = adler(data, 0, data.length);
|
||||
buf[off + 0] = ((crcValue >>> 24) & 255);
|
||||
buf[off + 1] = ((crcValue >>> 16) & 255);
|
||||
@@ -188,14 +188,18 @@ export function deflate(data: Uint8Array, opts?: { level: number }/* , buf, off*
|
||||
return new Uint8Array(buf.buffer, 0, off + 4);
|
||||
}
|
||||
|
||||
function deflateRaw(data: Uint8Array, opts?: { level: number }) {
|
||||
async function deflateRaw(runtime: RuntimeContext, data: Uint8Array, opts?: { level: number }) {
|
||||
if(opts === undefined) opts = { level: 6 };
|
||||
const buf = new Uint8Array(50 + Math.floor(data.length * 1.1));
|
||||
const off = _deflateRaw(data, buf, 0, opts.level);
|
||||
const off = await _deflateRaw(runtime, data, buf, 0, opts.level);
|
||||
return new Uint8Array(buf.buffer, 0, off);
|
||||
}
|
||||
|
||||
export function zip(obj: { [k: string]: Uint8Array }, noCmpr = false) {
|
||||
export function Zip(obj: { [k: string]: Uint8Array }, noCmpr = false) {
|
||||
return Task.create('Zip', ctx => zip(ctx, obj, noCmpr));
|
||||
}
|
||||
|
||||
export async function zip(runtime: RuntimeContext, obj: { [k: string]: Uint8Array }, noCmpr = false) {
|
||||
let tot = 0;
|
||||
const zpd: { [k: string]: { cpr: boolean, usize: number, crc: number, file: Uint8Array } } = {};
|
||||
for(const p in obj) {
|
||||
@@ -205,7 +209,7 @@ export function zip(obj: { [k: string]: Uint8Array }, noCmpr = false) {
|
||||
cpr,
|
||||
usize: buf.length,
|
||||
crc: crcValue,
|
||||
file: (cpr ? deflateRaw(buf) : buf)
|
||||
file: (cpr ? await deflateRaw(runtime, buf) : buf)
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user