UNPKG

openlime

Version:
1,729 lines 331 kB
/** * #Type * Supported image layout types including both single-resolution and multi-resolution formats. * - image: Standard web image formats (jpg, png, gif, etc.) * - deepzoom: Microsoft Deep Zoom format with root tile > 1px * - deepzoom1px: Microsoft Deep Zoom format with 1px root tile * - google: Google Maps tiling scheme * - zoomify: Zoomify tiling format * - iiif: International Image Interoperability Framework * - iip: Internet Imaging Protocol * - tarzoom: OpenLIME custom format (single TAR of DeepZoom pyramid) * - itarzoom: OpenLIME custom interleaved TAR format */ export type Layout = 'image' | 'deepzoom' | 'deepzoom1px' | 'google' | 'zoomify' | 'iiif' | 'iip' | 'tarzoom' | 'itarzoom'; /** * #Format * Defines the color format for image data storage in textures and renderbuffers. */ export type Raster = ('vec3' | 'vec4' | 'float'); /** * #Format * Defines the 16-bit format for image data storage in textures. */ export type Raster16Bit = ('r16f' | 'rg16f' | 'rgb16f' | 'rgba16f' | 'r16ui' | 'rg16ui' | 'rgb16ui' | 'rgba16ui' | 'r16i' | 'rg16i' | 'rgb16i' | 'rgba16i' | 'depth16'); /** * ~Sampler * A reference to a 2D texture used in the shader. */ export type Shader = { /** * - Unique identifier for the sampler */ id: number; /** * - Sampler variable name in shader program (e.g., "kd" for diffuse texture) */ name: string; /** * - Display label for UI/menus */ label: string; /** * - Array of raster definitions */ samplers: Array<any>; /** * - Raster type (e.g., 'color', 'normal') */ type: string; /** * - Whether sampler should be bound in prepareGL */ bind?: boolean; /** * - Whether sampler should load from raster */ load?: boolean; /** * - Shader uniform variables */ uniforms: Array<any>; /** * - Whether uniform needs GPU update */ needsUpdate: boolean; /** * - Uniform value or array of values */ value: number; }; /** * ~Operation * A shader operation that combines two textures. */ export type ShaderCombiner = { /** * - Assigns first texture as output (cout = c1) */ first: string; /** * - Assigns second texture as output (cout = c2) */ second: string; /** * - Calculates average of textures (cout = (c1 + c2)/2.0) */ mean: string; /** * - Calculates difference between textures (cout = c2.rgb - c1.rgb) */ diff: string; }; /** * ~Mode * A shader filter mode configuration */ export type ShaderFilter = { /** * - Unique identifier for the mode */ id: string; /** * - Whether the mode is active */ enable: boolean; /** * - GLSL source code for the mode */ src: string; }; /** * ~Options * Configuration options for colormap filter */ export type ShaderFilterColormap = { /** * - Input value range [min, max] for mapping */ inDomain?: number[]; /** * - RGB channel weights for grayscale conversion */ channelWeights?: number[]; /** * - Number of discrete steps in the colormap texture */ maxSteps?: number; }; /** * ~Options * Configuration options for vector field visualization */ export type ShaderFilterVector = { /** * - Input value range [min, max] for magnitude mapping */ inDomain?: number[]; /** * - Number of discrete steps in the colormap texture */ maxSteps?: number; /** * - RGBA color for arrows when using 'col' mode */ arrowColor?: number[]; }; /** * ~Options * Configuration options for glyph-based vector field visualization */ export type ShaderFilterVectorGlyph = { /** * - Input value range [min, max] for magnitude mapping */ inDomain?: number[]; /** * - Number of discrete steps in the colormap texture */ maxSteps?: number; /** * - RGBA color for glyphs when using 'col' mode */ glyphColor?: number[]; /** * - Horizontal spacing between glyphs in the sprite sheet */ glyphsStride?: number; /** * - Dimensions of the glyph sprite sheet [width, height] */ glyphsSize?: number[]; }; /** * ~NetworkConfig * Configuration for neural network weights and parameters */ export type ShaderNeural = { /** * - Number of neurons per layer (padded to multiple of 4) */ n: number; /** * - Number of input channels (padded to multiple of 4) */ c: number; /** * - Color space for processing ('rgb'|'xyz'|etc) */ colorspace: string; /** * - Number of coefficient planes */ nplanes: number; /** * - Dequantization scale factor */ scale: number; /** * - Dequantization bias */ bias: number; }; /** * ~Basis * Configuration data for basis functions */ export type ShaderRTI = { /** * - PCA basis for rbf and bln modes */ basis?: Float32Array; /** * - Light directions for rbf interpolation */ lights?: number[][]; /** * - RBF interpolation parameter */ sigma?: number; /** * - PCA dimension space */ ndimensions?: number; }; export type SignalHandler = { /** * - Map of event names to arrays of callback functions */ signals: { [x: string]: Function[]; }; /** * - List of all registered signal names */ allSignals: string[]; }; /** * Callback for position updates. */ export type updatePosition = (x: number, y: number) => any; /** * A [x, y, xc, yc] point. */ export type BezierPoint = { /** * 0 The x-coordinate. */ "": number; }; /** * A tuple of [x, y] representing a 2D point. */ export type APoint = Array<number>; /** * Object representation of a 2D point */ export type Point = { /** * - X coordinate */ x: number; /** * - Y coordinate */ y: number; }; export type TransformParameters = { /** * - X translation component */ x?: number; /** * - Y translation component */ y?: number; /** * - Rotation angle in degrees */ a?: number; /** * - Scale factor */ z?: number; /** * - Timestamp for animations */ t?: number; }; /** * Animation easing function type */ export type EasingFunction = 'linear' | 'ease-out' | 'ease-in-out'; export type TileProperties = { /** * - Unique identifier for the tile */ index: number; /** * - Bounding box coordinates [minX, minY, maxX, maxY] */ bbox: number[]; /** * - Zoom level in the pyramid (for tiled layouts) */ level: number; /** * - Horizontal grid position */ x: number; /** * - Vertical grid position */ y: number; /** * - Tile width (for image layouts) */ w: number; /** * - Tile height (for image layouts) */ h: number; /** * - Starting byte position in dataset (for tar-based formats) */ start: number; /** * - Ending byte position in dataset (for tar-based formats) */ end: number; /** * - Array of WebGL textures (one per channel) */ tex: WebGLTexture[]; /** * - Count of pending channel data requests */ missing: number; /** * - Creation timestamp for cache management */ time: number; /** * - Loading priority for cache management */ priority: number; /** * - Total size in bytes for cache management */ size: number; }; export type TileObj = { /** * - Zoom level in the image pyramid */ level: number; /** * - Horizontal position in tile grid */ x: number; /** * - Vertical position in tile grid */ y: number; /** * - Unique tile identifier */ index: number; /** * - Starting byte position in dataset (for tar formats) */ start?: number; /** * - Ending byte position in dataset (for tar formats) */ end?: number; /** * - Number of pending channel data requests */ missing: number; /** * - Array of textures (one per channel) */ tex: WebGLTexture[]; /** * - Tile creation timestamp for cache management */ time: number; /** * - Loading priority for cache management */ priority: number; /** * - Total tile size in bytes */ size: number; }; export type LayoutType = 'image' | 'deepzoom' | 'deepzoom1px' | 'google' | 'zoomify' | 'iiif' | 'tarzoom' | 'itarzoom'; export type LayoutOptions = { /** * - Image width (required for google layout) */ width?: number; /** * - Image height (required for google layout) */ height?: number; /** * - Tile file extension */ suffix?: string; /** * - Available subdomains for URL templates */ subdomains?: string; }; export type LayerOptions = { /** * - Layout/format of input raster images */ layout?: string | Layout; /** * - Identifier for specific derived layer class */ type?: string; /** * - Unique layer identifier */ id?: string; /** * - Display label for UI (defaults to id) */ label?: string; /** * - Transform from layer to canvas coordinates */ transform?: Transform; /** * - Whether layer should be rendered */ visible?: boolean; /** * - Stack order for rendering (higher = on top) */ zindex?: number; /** * - Whether layer renders in overlay mode */ overlay?: boolean; /** * - Tile prefetch threshold in tile units */ prefetchBorder?: number; /** * - Texture resolution selection bias (0=highest, 1=lowest) */ mipmapBias?: number; /** * - Map of available shaders */ shaders?: { [x: string]: Shader; }; /** * - Array of active UI controllers */ controllers?: Controller[]; /** * - Layer to share tiles with */ sourceLayer?: Layer; /** * - Physical size of a pixel in mm */ pixelSize?: number; }; /** * Defines a rectangular viewing region inside a canvas area. */ export type Viewport = { /** * - X-coordinate of the lower-left corner */ x: number; /** * - Y-coordinate of the lower-left corner */ y: number; /** * - Width of the viewport */ dx: number; /** * - Height of the viewport */ dy: number; /** * - Total canvas width */ w: number; /** * - Total canvas height */ h: number; }; export type LayerImageOptions = { /** * - URL of the image to display (required) */ url: string; /** * - Layout format for image display */ layout?: string | Layout; /** * - Image data format for WebGL processing */ format?: string; /** * - Must be 'image' when using Layer factory */ type?: string; }; export type LayerCombinerOptions = { /** * - Array of layers to be combined (required) */ layers: Layer[]; /** * - Map of available shaders */ shaders?: { [x: string]: Shader; }; /** * - Must be 'combiner' when using Layer factory */ type?: string; /** * - Whether the combined output is visible */ visible?: boolean; }; export type LayerAnnotationOptions = { /** * - CSS styles for annotation rendering */ style?: string; /** * - URL of JSON annotation data or array of annotations */ annotations?: string | Annotation[]; /** * - Whether annotations render as overlay */ overlay?: boolean; /** * - Set of selected annotation IDs */ selected?: Set<string>; /** * - UI entry for annotations list */ annotationsListEntry?: any; }; export type LayerAnnotationImageOptions = { /** * - URL to the annotations JSON file */ url?: string; /** * - Base path for annotation image files */ path?: string; /** * - Raster format for image data */ format?: string; }; export type LayerMaskedImageOptions = { /** * - URL of the masked image to display (required) */ url: string; /** * - Image data format */ format?: string; /** * - Must be 'maskedimage' when using Layer factory */ type?: string; }; /** * Configuration options for Viewer initialization */ export type ViewerOptions = { /** * - CSS background style */ background?: string; /** * - Auto-fit camera to scene */ autofit?: boolean; /** * - Canvas configuration options */ canvas?: any; /** * - Custom camera instance */ camera?: Camera; }; export type ShaderMultispectralOptions = { /** * - Initial rendering mode ('rgb' or 'single_band') */ mode?: string; /** * - Enable debug output in console */ debug?: boolean; /** * - Array of wavelengths in nanometers */ wavelength?: number[]; }; export type LayerMultispectralOptions = { /** * - URL to multispectral info.json file (required) */ url: string; /** * - Layout type: 'image', 'deepzoom', 'google', 'iiif', 'zoomify', 'tarzoom', 'itarzoom' */ layout: string; /** * - Initial visualization mode ('rgb' or 'single_band') */ defaultMode?: string; /** * - IIP server URL (for IIP layout) */ server?: string; /** * - Whether to use linear color space for rasters (recommended for scientific accuracy) */ linearRaster?: boolean; /** * - Path to presets JSON file or presets object containing CTW configurations */ presets: string | any; }; export type DataLoaderCallback = Function; export type LayerHDROptions = { /** * - URL of the image to display (required) */ url: string; /** * - Layout format for image display */ layout?: string | Layout; /** * - Image data format for WebGL processing */ format?: string; /** * - Enable debug output */ debug?: boolean; }; /** * A UI icon element from the skin file */ export type SkinIcon = { /** * - CSS class name (must start with 'openlime-') */ class: string; /** * - SVG DOM element */ element: SVGElement; }; /** * Action configuration for toolbar buttons */ export type UIAction = { /** * - Display title for the action */ title: string; /** * - Whether to show in toolbar */ display: boolean; /** * - Keyboard shortcut key */ key?: string; /** * - Callback function for action */ task: Function; /** * - Custom SVG icon path or content */ icon?: string; /** * - HTML content for help dialog */ html?: string; }; /** * Menu configuration item */ export type MenuEntry = { /** * - Large title text */ title?: string; /** * - Section header text */ section?: string; /** * - Raw HTML content */ html?: string; /** * - Button text */ button?: string; /** * - Button group identifier */ group?: string; /** * - Associated layer ID */ layer?: string; /** * - Layer visualization mode */ mode?: string; /** * - Click handler */ onclick?: Function; /** * - Input handler for sliders */ oninput?: Function; /** * - Nested menu entries */ list?: MenuEntry[]; }; export type LayerRTIOptions = { /** * - URL to RTI info.json file (required) */ url: string; /** * - Layout type: 'image', 'deepzoom', 'google', 'iiif', 'zoomify', 'tarzoom', 'itarzoom' */ layout: string; /** * - Whether to load normal maps */ normals?: boolean; /** * - IIP server URL (for IIP layout) */ server?: string; /** * - Global rotation offset */ worldRotation?: number; }; export type LayerNeuralRTIOptions = { /** * - URL to the Neural RTI configuration JSON */ url: string; /** * - Layout system for image loading */ layout: Layout; /** * - Speed of quality convergence */ convergenceSpeed?: number; /** * - Maximum number of tiles to process */ maxTiles?: number; /** * - Color space for processing */ colorspace?: string; }; export type LayerBRDFOptions = { /** * - Required channels for BRDF rendering */ channels: { kd: string; ks: string; normals: string; gloss: string; }; /** * - Color space definitions for material properties */ colorspaces?: { kd?: ('linear' | 'srgb'); ks?: ('linear' | 'srgb'); }; /** * - Overall brightness adjustment */ brightness?: number; /** * - Gamma correction value */ gamma?: number; /** * - Range for glossiness/roughness */ alphaLimits?: number[]; /** * - RGB color for monochrome rendering */ monochromeMaterial?: number[]; /** * - Ambient light coefficient */ kAmbient?: number; }; /** * ~Uniforms * Uniform definitions for lens shader */ export type ShaderLens = { /** * - Lens parameters [centerX, centerY, radius, borderWidth] */ u_lens: number[]; /** * - Viewport dimensions [width, height] */ u_width_height: number[]; /** * - RGBA border color [r, g, b, a] */ u_border_color: number[]; /** * - Whether to show lens border */ u_border_enable: boolean; }; export type LayerLensOptions = { /** * - Whether the lens renders as an overlay */ overlay?: boolean; /** * - Initial lens radius in pixels */ radius?: number; /** * - RGBA border color */ borderColor?: number[]; /** * - Border width in pixels */ borderWidth?: number; /** * - Whether to show lens border */ borderEnable?: boolean; /** * - Dashboard UI component for lens control */ dashboard?: any; /** * - Camera instance (required) */ camera: Camera; }; export type Focus = { /** * - Lens center position in dataset coordinates */ position: { x: number; y: number; }; /** * - Lens radius in dataset units */ radius: number; }; export type TextToSpeechOptions = { /** * - Language code for speech synthesis (e.g., 'en-US', 'it-IT') */ language?: string; /** * - Speech rate (0.1 to 10) */ rate?: number; /** * - Speech volume (0 to 1) */ volume?: number; /** * - Whether to remove HTML tags and format text */ cleanText?: boolean; /** * - Index of preferred voice (-1 for auto-selection) */ voiceSelected?: number; }; export type AnnoClass = { /** * - CSS color for SVG elements (lines, text, outlines) */ stroke: string; /** * - Display name for the class */ label: string; }; export type AnnoClasses = { [x: string]: AnnoClass; }; export type LayerSvgAnnotationOptions = { /** * - Annotation class definitions with styles */ classes: AnnoClasses; /** * - Callback for annotation click events (param: selected annotation) */ onClick?: Function; /** * - Whether to use Shadow DOM for SVG elements */ shadow?: boolean; /** * - Container for SVG overlay */ overlayElement?: HTMLElement; /** * - Additional CSS styles for annotations */ style?: string; /** * - Custom update function for annotations */ annotationUpdate?: Function; }; /** * Class representing an audio player with playback control capabilities. * Supports playing, pausing, resuming, and stopping audio files with volume control * and playback speed adjustment. */ export class AudioPlayer { audio: HTMLAudioElement; isPlaying: boolean; isPaused: boolean; isMuted: boolean; previousVolume: number; playStartTime: number; playDuration: number; /** * Plays an audio file with optional playback speed adjustment. * If audio is paused, it will resume playback instead of starting a new file. * * @param {string} audioFile - The path or URL to the audio file. * @param {number} [speed=1.0] - Playback speed multiplier (1.0 is normal speed). * @returns {Promise<void>} Resolves when the audio playback completes. */ play(audioFile: string, speed?: number): Promise<void>; /** * Pauses the currently playing audio. * Updates play duration when pausing. */ pause(): void; /** * Resumes playback of a paused audio file. * * @returns {Promise<void>} Resolves when the resumed audio playback completes. */ continue(): Promise<void>; /** * Stops the current audio playback and resets all player states. * Removes event listeners and updates final play duration. */ stop(): void; /** * Updates the total play duration based on the current session. * Called internally when playback is paused, stopped, or ends. * @private */ private updatePlayDuration; /** * Returns the total play duration in milliseconds. * * @returns {number} Total play duration in milliseconds. */ getPlayDuration(): number; /** * Sets the audio volume level. * * @param {number} volume - Volume level between 0.0 and 1.0. */ setVolume(volume: number): void; /** * Creates a delay in the execution flow. * * @param {number} ms - Number of milliseconds to wait. * @returns {Promise<void>} Resolves after the specified delay. */ silence(ms: number): Promise<void>; /** * Set the mute state of the audio player. * Stores the previous volume level when muting and restores it when unmuting. * @param {boolean} b Whether to mute the audio playback */ setMute(b: boolean): void; /** * Emits an event of the specified type * @param {string} type - The event type to emit */ emit(type: string): void; } /** * Represents an axis-aligned rectangular bounding box that can be wrapped tightly around geometric elements. * The box is defined by two opposite vertices (low and high corners) and provides a comprehensive set of * utility methods for manipulating and analyzing bounding boxes. */ export class BoundingBox { /** * Creates a new BoundingBox instance. * @param {Object} [options] - Configuration options for the bounding box * @param {number} [options.xLow=1e20] - X coordinate of the lower corner * @param {number} [options.yLow=1e20] - Y coordinate of the lower corner * @param {number} [options.xHigh=-1e20] - X coordinate of the upper corner * @param {number} [options.yHigh=-1e20] - Y coordinate of the upper corner */ constructor(options?: { xLow?: number; yLow?: number; xHigh?: number; yHigh?: number; }); /** * Initializes the bounding box from an array of coordinates. * @param {number[]} x - Array containing coordinates in order [xLow, yLow, xHigh, yHigh] */ fromArray(x: number[]): void; xLow: any; yLow: any; xHigh: any; yHigh: any; /** * Resets the bounding box to an empty state by setting coordinates to extreme values. */ toEmpty(): void; /** * Checks if the bounding box is empty (has no valid area). * A box is considered empty if its low corner coordinates are greater than its high corner coordinates. * @returns {boolean} True if the box is empty, false otherwise */ isEmpty(): boolean; /** * Converts the bounding box coordinates to an array. * @returns {number[]} Array of coordinates in order [xLow, yLow, xHigh, yHigh] */ toArray(): number[]; /** * Creates a space-separated string representation of the bounding box coordinates. * @returns {string} String in format "xLow yLow xHigh yHigh" */ toString(): string; /** * Enlarges this bounding box to include another bounding box. * If this box is empty, it will adopt the dimensions of the input box. * If the input box is null, no changes are made. * @param {BoundingBox|null} box - The bounding box to merge with this one */ mergeBox(box: BoundingBox | null): void; /** * Enlarges this bounding box to include a point. * @param {{x: number, y: number}} p - The point to include in the bounding box */ mergePoint(p: { x: number; y: number; }): void; /** * Moves the bounding box by the specified displacement. * @param {number} dx - Displacement along the x-axis * @param {number} dy - Displacement along the y-axis */ shift(dx: number, dy: number): void; /** * Quantizes the bounding box coordinates by dividing by a specified value and rounding down. * This creates a grid-aligned bounding box. * @param {number} side - The value to divide coordinates by */ quantize(side: number): void; /** * Calculates the width of the bounding box. * @returns {number} The difference between xHigh and xLow */ width(): number; /** * Calculates the height of the bounding box. * @returns {number} The difference between yHigh and yLow */ height(): number; /** * Calculates the area of the bounding box. * @returns {number} The area (width × height) */ area(): number; /** * Calculates the center point of the bounding box. * @returns {{x: number, y: number}} The coordinates of the center point */ center(): { x: number; y: number; }; /** * Gets the coordinates of a specific corner of the bounding box. * @param {number} i - Corner index (0: bottom-left, 1: bottom-right, 2: top-left, 3: top-right) * @returns {{x: number, y: number}} The coordinates of the specified corner */ corner(i: number): { x: number; y: number; }; /** * Checks if this bounding box intersects with another bounding box. * @param {BoundingBox} box - The other bounding box to check intersection with * @returns {boolean} True if the boxes intersect, false otherwise */ intersects(box: BoundingBox): boolean; /** * Calculates the intersection of this bounding box with another box. * @param {BoundingBox} box - The other bounding box * @returns {BoundingBox|null} A new bounding box representing the intersection, or null if there is no intersection */ intersection(box: BoundingBox): BoundingBox | null; /** * Creates a clone of this bounding box. * @returns {BoundingBox} A new BoundingBox instance with the same coordinates */ clone(): BoundingBox; /** * Checks if a point is contained within this bounding box. * A point is considered inside if its coordinates are greater than or equal to * the low corner and less than or equal to the high corner. * * @param {{x: number, y: number}} p - The point to check * @param {number} [epsilon=0] - Optional tolerance value for boundary checks * @returns {boolean} True if the point is inside the box, false otherwise * * @example * // Check if a point is inside a box * const box = new BoundingBox({xLow: 0, yLow: 0, xHigh: 10, yHigh: 10}); * const point = {x: 5, y: 5}; * const isInside = box.containsPoint(point); // true * * // Using epsilon tolerance for boundary cases * const boundaryPoint = {x: 10.001, y: 10}; * const isInsideWithTolerance = box.containsPoint(boundaryPoint, 0.01); // true */ containsPoint(p: { x: number; y: number; }, epsilon?: number): boolean; /** * Prints the bounding box coordinates to the console in a formatted string. * Output format: "BOX=xLow, yLow, xHigh, yHigh" with values rounded to 2 decimal places */ print(): void; } /** * Defines a rectangular viewing region inside a canvas area. * @typedef {Object} Viewport * @property {number} x - X-coordinate of the lower-left corner * @property {number} y - Y-coordinate of the lower-left corner * @property {number} dx - Width of the viewport * @property {number} dy - Height of the viewport * @property {number} w - Total canvas width * @property {number} h - Total canvas height */ /** * Camera class that manages viewport parameters and camera transformations. * Acts as a container for parameters needed to define the viewport and camera position, * supporting smooth animations between positions using source and target transforms. * * The camera maintains two Transform objects: * - source: represents current position * - target: represents destination position * * Animation between positions is handled automatically by the OpenLIME system * unless manually interrupted by user input. */ export class Camera { /** * Creates a new Camera instance. * @param {Object} [options] - Configuration options * @param {boolean} [options.bounded=true] - Whether to limit camera translation to scene boundaries * @param {number} [options.maxFixedZoom=2] - Maximum allowed pixel size * @param {number} [options.minScreenFraction=1] - Minimum portion of screen to show when zoomed in * @param {Transform} [options.target] - Initial target transform * @fires Camera#update */ constructor(options?: { bounded?: boolean; maxFixedZoom?: number; minScreenFraction?: number; target?: Transform; }); target: Transform; source: Transform; easing: string; /** * Creates a deep copy of the camera instance. * @returns {Camera} A new Camera instance with copied properties */ copy(): Camera; /** * Updates the viewport while maintaining the camera position as close as possible to the previous one. * @param {Viewport} view - The new viewport in CSS coordinates */ setViewport(view: Viewport): void; viewport: Viewport; /** * Returns the current viewport in device coordinates (accounting for device pixel ratio). * @returns {Viewport} The current viewport scaled for device pixels */ glViewport(): Viewport; /** * Sets the camera target parameters for a new position. * @param {number} dt - Animation duration in milliseconds * @param {number} x - X component of translation * @param {number} y - Y component of translation * @param {number} z - Zoom factor * @param {number} a - Rotation angle in degrees * @param {string} [easing] - Easing function name for animation * @fires Camera#update */ setPosition(dt: number, x: number, y: number, z: number, a: number, easing?: string): void; /** * Pans the camera by a specified amount in canvas coordinates. * @param {number} dt - Animation duration in milliseconds * @param {number} dx - Horizontal displacement * @param {number} dy - Vertical displacement */ pan(dt: number, dx: number, dy: number): void; /** * Zooms the camera to a specific point in canvas coordinates. * @param {number} dt - Animation duration in milliseconds * @param {number} z - Target zoom level * @param {number} [x=0] - X coordinate to zoom towards * @param {number} [y=0] - Y coordinate to zoom towards */ zoom(dt: number, z: number, x?: number, y?: number): void; /** * Rotates the camera around its z-axis. * @param {number} dt - Animation duration in milliseconds * @param {number} a - Rotation angle in degrees */ rotate(dt: number, a: number): void; /** * Applies a relative zoom change at a specific point. * @param {number} dt - Animation duration in milliseconds * @param {number} dz - Relative zoom change factor * @param {number} [x=0] - X coordinate to zoom around * @param {number} [y=0] - Y coordinate to zoom around */ deltaZoom(dt: number, dz: number, x?: number, y?: number): void; /** * Gets the camera transform at a specific time. * @param {number} time - Current time in milliseconds (from performance.now()) * @returns {Transform} The interpolated transform at the specified time with isComplete flag */ getCurrentTransform(time: number): Transform; /** * Checks if the camera animation has completed. * @param {Transform} currentTransform - The current transform (optional, will be calculated if not provided) * @returns {boolean} True if the camera has reached its target position */ hasReachedTarget(currentTransform: Transform): boolean; /** * Gets the camera transform at a specific time in device coordinates. * @param {number} time - Current time in milliseconds (from performance.now()) * @returns {Transform} The interpolated transform scaled for device pixels */ getGlCurrentTransform(time: number): Transform; /** * Adjusts the camera to frame a specified bounding box. * @param {BoundingBox} box - The box to frame in canvas coordinates * @param {number} [dt=0] - Animation duration in milliseconds */ fit(box: BoundingBox, dt?: number): void; /** * Resets the camera to show the entire scene. * @param {number} dt - Animation duration in milliseconds */ fitCameraBox(dt: number): void; /** * Updates the camera's boundary constraints and zoom limits. * @private * @param {BoundingBox} box - New bounding box for constraints * @param {number} minScale - Minimum scale factor */ private updateBounds; boundingBox: BoundingBox; minZoom: number; maxZoom: any; } /** * Canvas class that manages WebGL context, layers, and scene rendering. * Handles layer management, WebGL context creation/restoration, and render timing. */ export class Canvas { /** * Creates a new Canvas instance with WebGL context and overlay support. * @param {HTMLCanvasElement|string} canvas - Canvas DOM element or selector * @param {HTMLElement|string} overlay - Overlay DOM element or selector for decorations (annotations, glyphs) * @param {Camera} camera - Scene camera instance * @param {Object} [options] - Configuration options * @param {Object} [options.layers] - Layer configurations mapping layer IDs to Layer instances * @param {boolean} [options.preserveDrawingBuffer=false] - Whether to preserve WebGL buffers until manually cleared * @param {number} [options.targetfps=30] - Target frames per second for rendering * @param {boolean} [options.srgb=true] - Whether to enable sRGB color space or display-P3 for the output framebuffer * @param {boolean} [options.stencil=false] - Whether to enable stencil buffer support * @param {boolean} [options.useOffscreenFramebuffer=true] - Whether to use offscreen framebuffer for rendering * @fires Canvas#update * @fires Canvas#updateSize * @fires Canvas#ready */ constructor(canvas: HTMLCanvasElement | string, overlay: HTMLElement | string, camera: Camera, options?: { layers?: any; preserveDrawingBuffer?: boolean; targetfps?: number; srgb?: boolean; stencil?: boolean; useOffscreenFramebuffer?: boolean; }); /** * Records render timing information and updates FPS statistics. * @param {number} elapsed - Time elapsed since last frame in milliseconds * @private */ private addRenderTiming; overBudget: number; fps: number; /** * Initializes WebGL context and sets up event listeners. * @param {HTMLCanvasElement|string} canvas - Canvas element or selector * @param {HTMLElement|string} overlay - Overlay element or selector * @throws {Error} If canvas or overlay elements cannot be found or initialized * @private */ private init; canvasElement: string | HTMLCanvasElement; overlayElement: string | HTMLElement; gl: any; hasFloatRender: boolean; hasLinearFloat: boolean; /** * Sets up the offscreen framebuffer for rendering * @private */ private setupOffscreenFramebuffer; offscreenFramebuffer: any; offscreenTexture: any; offscreenRenderbuffer: any; useOffscreenFramebuffer: boolean; /** * Resizes the offscreen framebuffer when canvas size changes * @private */ private resizeOffscreenFramebuffer; /** * Gets the currently active framebuffer. * Use this when you need to save the state before changing framebuffers. * @returns {WebGLFramebuffer} The currently active framebuffer */ getActiveFramebuffer(): WebGLFramebuffer; /** * Sets the active framebuffer. * Use this to restore a previously saved state. * @param {WebGLFramebuffer} framebuffer - The framebuffer to activate */ setActiveFramebuffer(framebuffer: WebGLFramebuffer): void; _renderingToOffscreen: boolean; /** * Updates the state of the canvas and its components. * @param {Object} state - State object containing updates * @param {Object} [state.camera] - Camera state updates * @param {Object} [state.layers] - Layer state updates * @param {number} dt - Animation duration in milliseconds * @param {string} [easing='linear'] - Easing function for animations */ setState(state: { camera?: any; layers?: any; }, dt: number, easing?: string): void; /** * Retrieves current state of the canvas and its components. * @param {Object} [stateMask=null] - Optional mask to filter returned state properties * @returns {Object} Current state object */ getState(stateMask?: any): any; /** * Restores WebGL context after loss. * Reinitializes shaders and textures for all layers. * @private */ private restoreWebGL; /** * Adds a layer to the canvas. * @param {string} id - Unique identifier for the layer * @param {Layer} layer - Layer instance to add * @fires Canvas#update * @fires Canvas#ready * @throws {Error} If layer ID already exists */ addLayer(id: string, layer: Layer): void; ready: boolean; /** * Removes a layer from the canvas. * @param {Layer} layer - Layer instance to remove * @example * const layer = new Layer(options); * canvas.addLayer('map', layer); * // ... later ... * canvas.removeLayer(layer); */ removeLayer(layer: Layer): void; updateSize(): void; /** * Enables or disables split viewport mode and sets which layers appear on each side * @param {boolean} enabled - Whether split viewport mode is enabled * @param {string[]} leftLayerIds - Array of layer IDs to show on left side * @param {string[]} rightLayerIds - Array of layer IDs to show on right side * @fires Canvas#update */ setSplitViewport(enabled: boolean, leftLayerIds?: string[], rightLayerIds?: string[]): void; splitViewport: boolean; leftLayers: string[]; rightLayers: string[]; /** * Renders a frame at the specified time. * @param {number} time - Current time in milliseconds * @returns {boolean} True if all animations are complete * @private */ private draw; /** * Draws the offscreen framebuffer texture to the canvas * @private */ private drawOffscreenToCanvas; _fullscreenQuadProgram: WebGLProgram; _positionLocation: any; _texCoordLocation: any; _textureLocation: any; _quadPositionBuffer: any; _quadTexCoordBuffer: any; _quadVAO: any; /** * Helper method to create a shader * @param {WebGL2RenderingContext} gl - WebGL context * @param {number} type - Shader type (gl.VERTEX_SHADER or gl.FRAGMENT_SHADER) * @param {string} source - Shader source code * @returns {WebGLShader} Compiled shader * @private */ private _createShader; /** * Helper method to create a shader program * @param {WebGL2RenderingContext} gl - WebGL context * @param {WebGLShader} vertexShader - Vertex shader * @param {WebGLShader} fragmentShader - Fragment shader * @returns {WebGLProgram} Linked shader program * @private */ private _createProgram; /** * Schedules tile downloads based on current view. * @param {Object} [transform] - Optional transform override, defaults to current camera transform * @private */ private prefetch; /** * Cleanup resources when canvas is no longer needed */ dispose(): void; } /** * Represents a color in RGBA format with values normalized between 0 and 1. */ export class Color { static clamp: (num: any, min?: number, max?: number) => number; static hex(c: any): any; static normalizedRGBA(c: any): number; static rgbToHex(r: any, g: any, b: any): string; static rgbToHexa(r: any, g: any, b: any, a: any): string; /** * Creates a new Color instance. * @param {number|string} r - Red component [0.0, 1.0] or color string ('#RGB', '#RGBA', '#RRGGBB', '#RRGGBBAA', 'rgb()', 'rgba()') * @param {number} [g] - Green component [0.0, 1.0] * @param {number} [b] - Blue component [0.0, 1.0] * @param {number} [a] - Alpha component [0.0, 1.0] * @throws {Error} If string value is not a valid color format */ constructor(r: number | string, g?: number, b?: number, a?: number); r: number; g: number; b: number; a: number; /** * Gets color components as an array. * @returns {number[]} Array of [r, g, b, a] values */ value(): number[]; /** * Converts color to RGB values [0, 255]. * @returns {number[]} Array of [r, g, b] values */ toRGB(): number[]; /** * Converts color to hexadecimal string. * @returns {string} Color in '#RRGGBB' format */ toHex(): string; /** * Converts color to hexadecimal string with alpha. * @returns {string} Color in '#RRGGBBAA' format */ toHexa(): string; /** * Converts color to RGBA values [0-255]. * @returns {number[]} Array of [r, g, b, a] values */ toRGBA(): number[]; } /** * Creates a colormap for mapping numerical values to colors. * Supports linear, spline, and bar interpolation between colors. */ export class Colormap { static clamp: (num: any, min: any, max: any) => number; /** * Creates a new Colormap instance. * @param {Color[]} [colors=[black, white]] - Array of colors to interpolate between * @param {Object} [options] - Configuration options * @param {number[]} [options.domain=[0,1]] - Domain range for mapping * @param {Color} [options.lowColor] - Color for values below domain (defaults to first color) * @param {Color} [options.highColor] - Color for values above domain (defaults to last color) * @param {string} [options.description=''] - Description of the colormap * @param {('linear'|'spline'|'bar')} [options.type='linear'] - Interpolation type * @throws {Error} If colors/domain format is invalid */ constructor(colors?: Color[], options?: { domain?: number[]; lowColor?: Color; highColor?: Color; description?: string; type?: ('linear' | 'spline' | 'bar'); }); lowColor: Color; highColor: Color; xarr: any[]; rarr: number[]; garr: number[]; barr: number[]; aarr: number[]; rspline: Spline; gspline: Spline; bspline: Spline; aspline: Spline; /** * Gets the domain range of the colormap. * @returns {number[]} Array containing [min, max] of domain */ rangeDomain(): number[]; /** * Gets color for a value using bar interpolation. * @param {number} x - Value to get color for * @returns {Color} Corresponding color * @private */ private bar; /** * Gets color for a value using linear interpolation. * @param {number} x - Value to get color for * @returns {Color} Corresponding color * @private */ private linear; /** * Gets color for a value using spline interpolation. * @param {number} x - Value to get color for * @returns {Color} Corresponding color * @private */ private spline; /** * Gets color for a value using configured interpolation type. * @param {number} x - Value to get color for * @returns {Color} Corresponding color * @throws {Error} If interpolation type is invalid */ at(x: number): Color; /** * Samples the colormap into a buffer. * @param {number} maxSteps - Number of samples to generate * @returns {{min: number, max: number, buffer: Uint8Array}} Sample data and buffer */ sample(maxSteps: number): { min: number; max: number; buffer: Uint8Array; }; } /** * Creates a visual legend for a colormap. */ export class ColormapLegend { /** * Creates a new ColormapLegend instance. * @param {Object} viewer - Viewer instance to attach legend to * @param {Colormap} colorscale - Colormap to create legend for * @param {Object} [options] - Configuration options * @param {number} [options.nticks=6] - Number of ticks/divisions in legend * @param {number} [options.legendWidth=25] - Width of legend as percentage * @param {string} [options.textColor='#fff'] - Color of text labels * @param {string} [options.class='openlime-legend'] - CSS class for legend container */ constructor(viewer: any, colorscale: Colormap, options?: { nticks?: number; legendWidth?: number; textColor?: string; class?: string; }); viewer: any; colorscale: Colormap; container: Element; scale: HTMLDivElement; /** * Creates legend for linear interpolation. * @private */ private legendLinear; /** * Creates legend for bar interpolation. * @private */ private legendBar; } /** * Base class that handles user interaction via device events (mouse/touch events). * Provides an abstract user interface to define interaction actions such as panning, pinching, tapping, etc... * The actions are implemented by pre-defined callback functions: * * `panStart(e)` intercepts the initial pan event (movement of the mouse after pressing a mouse button or moving a finger). * The event is captured calling `e.preventDefault()`. * * `panMove(e)` receives and handles the pan event. * * `panEnd(e)` intercepts the final pan event (the user releases the left mouse button or removes his finger from the screen). * * `pinchStart(e1, e2)` intercepts the initial pinch event (a continuous gesture that tracks the positions between the first two fingers that touch the screen). * The event is captured calling `e1.preventDefault()`. * * `pinchMove(e1,e2)` receives and handles the pinch event. * * `pinchEnd(e1,e2)` intercepts the final pinch event (the user removes one of their two fingers from the screen). * * `mouseWheel(e)` receives and handles the mouse wheel event (the user rotates the mouse wheel button). * * `fingerSingleTap(e)` receives and handles the single-tap event (the user presses a mouse button quickly or touches the screen shortly with a finger). * * `fingerDoubleTap(e)` receives and handles the double-tap event (the user quickly presses a mouse button twice or shortly touches the screen with a finger twice). * * `e.preventDefault()` will capture the event and wont be propagated to other controllers. * * This class only describes user interactions by implementing actions or callbacks. A **Controller** works in concert with a **PointerManager** object * that emits events and links them to actions. * * @abstract * @example * // Create a pan-zoom controller and associate it with the viewer's pointer manager * const panzoom = new OpenLIME.ControllerPanZoom(viewer.camera, { * priority: -1000, * activeModifiers: [0, 1] * }); * viewer.pointerManager.onEvent(panzoom); */ export class Controller { /** * Creates a new Controller instance. * @param {Object} [options] - Configuration options * @param {boolean} [options.active=true] - Whether the controller is initially active * @param {boolean} [options.debug=false] - Enable debug logging * @param {number} [options.panDelay=50] - Inertial value for panning movements in milliseconds * @param {number} [options.zoomDelay=200] - Delay for smoothing zoom events in milliseconds * @param {number} [options.priority=0] - Controllers with higher priority are invoked first * @param {number[]} [options.activeModifiers=[0]] - Array of modifier states that activate this controller */ constructor(options?: { active?: boolean; debug?: boolean; panDelay?: number; zoomDelay?: number; priority?: number; activeModifiers?: number[]; }); /** * Gets the modifier state from an event. * @param {Event} e - The event to check * @returns {number} Modifier st