UNPKG

molstar

Version:

A comprehensive macromolecular library.

85 lines (84 loc) 3.61 kB
/** * Copyright (c) 2019-2022 mol* contributors, licensed under MIT, See LICENSE file for more info. * * @author Alexander Rose <alexander.rose@weirdbyte.de> */ import { createComputeRenderable } from '../../renderable'; import { createComputeRenderItem } from '../../webgl/render-item'; import { TextureSpec } from '../../renderable/schema'; import { ShaderCode } from '../../../mol-gl/shader-code'; import { ValueCell } from '../../../mol-util'; import { unpackRGBToInt } from '../../../mol-util/number-packing'; import { QuadSchema, QuadValues } from '../util'; import { quad_vert } from '../../../mol-gl/shader/quad.vert'; import { sum_frag } from '../../../mol-gl/shader/histogram-pyramid/sum.frag'; import { isWebGL2 } from '../../webgl/compat'; import { isTimingMode } from '../../../mol-util/debug'; const HistopyramidSumSchema = { ...QuadSchema, tTexture: TextureSpec('texture', 'rgba', 'float', 'nearest'), }; const HistopyramidSumName = 'histopyramid-sum'; function getHistopyramidSumRenderable(ctx, texture) { if (ctx.namedComputeRenderables[HistopyramidSumName]) { const v = ctx.namedComputeRenderables[HistopyramidSumName].values; ValueCell.update(v.tTexture, texture); ctx.namedComputeRenderables[HistopyramidSumName].update(); } else { ctx.namedComputeRenderables[HistopyramidSumName] = createHistopyramidSumRenderable(ctx, texture); } return ctx.namedComputeRenderables[HistopyramidSumName]; } function createHistopyramidSumRenderable(ctx, texture) { const values = { ...QuadValues, tTexture: ValueCell.create(texture), }; const schema = { ...HistopyramidSumSchema }; const shaderCode = ShaderCode('sum', quad_vert, sum_frag, {}, { 0: 'ivec4' }); const renderItem = createComputeRenderItem(ctx, 'triangles', shaderCode, schema, values); return createComputeRenderable(renderItem, values); } function setRenderingDefaults(ctx) { const { gl, state } = ctx; state.disable(gl.CULL_FACE); state.disable(gl.BLEND); state.disable(gl.DEPTH_TEST); state.disable(gl.SCISSOR_TEST); state.depthMask(false); state.colorMask(true, true, true, true); state.clearColor(0, 0, 0, 0); } const sumBytes = new Uint8Array(4); const sumInts = new Int32Array(4); export function getHistopyramidSum(ctx, pyramidTopTexture) { if (isTimingMode) ctx.timer.mark('getHistopyramidSum'); const { gl, state, resources } = ctx; const renderable = getHistopyramidSumRenderable(ctx, pyramidTopTexture); ctx.state.currentRenderItemId = -1; if (!ctx.namedFramebuffers[HistopyramidSumName]) { ctx.namedFramebuffers[HistopyramidSumName] = resources.framebuffer(); } const framebuffer = ctx.namedFramebuffers[HistopyramidSumName]; if (!ctx.namedTextures[HistopyramidSumName]) { ctx.namedTextures[HistopyramidSumName] = isWebGL2(gl) ? resources.texture('image-int32', 'rgba', 'int', 'nearest') : resources.texture('image-uint8', 'rgba', 'ubyte', 'nearest'); ctx.namedTextures[HistopyramidSumName].define(1, 1); } const sumTexture = ctx.namedTextures[HistopyramidSumName]; sumTexture.attachFramebuffer(framebuffer, 0); setRenderingDefaults(ctx); state.viewport(0, 0, 1, 1); renderable.render(); gl.finish(); ctx.readPixels(0, 0, 1, 1, isWebGL2(gl) ? sumInts : sumBytes); ctx.unbindFramebuffer(); if (isTimingMode) ctx.timer.markEnd('getHistopyramidSum'); return isWebGL2(gl) ? sumInts[0] : unpackRGBToInt(sumBytes[0], sumBytes[1], sumBytes[2]); }