{"version":3,"file":"webgl-Cdyc36Za.cjs","names":["RenderCache","VideoEntity","isOffscreenCanvasSupported"],"sources":["../src/player/render/webgl/index.ts"],"sourcesContent":["import {logger} from 'src/helper/logger'\nimport {isOffscreenCanvasSupported} from 'src/helper/utils'\nimport RenderCache from 'src/player/render/common/renderCache'\nimport VideoEntity from 'src/player/render/common/videoEntity'\nimport type {MixEvideoOptions, ResizeCanvasType, VideoAnimateDataItemType, WebglVersion} from 'src/type/mix'\nexport default class WglRender {\n  public isPlay = false\n  public videoEntity: VideoEntity\n  public renderType = 'webgl'\n  public renderCache: RenderCache\n  public PER_SIZE = 9\n  public canvas?: HTMLCanvasElement //显示画布\n  public ctx?: CanvasRenderingContext2D\n  public ofs: HTMLCanvasElement | OffscreenCanvas\n  public version: WebglVersion\n  public gl!: WebGLRenderingContext | WebGL2RenderingContext | null\n  //\n  // private dpr = 1\n  private op: MixEvideoOptions\n  private textureMap: any = {}\n  private imagePos: any\n  private currentFrame = -1 //过滤重复帧\n  private video: HTMLVideoElement | undefined\n  private program: WebGLProgram | undefined\n  private VERTEX_SHADER: string\n  private FRAGMENT_SHADER: string\n  constructor(op: MixEvideoOptions) {\n    logger.debug('[Render In Webgl]')\n    this.op = op\n    // this.dpr = self.devicePixelRatio\n    this.createCanvas(op)\n\n    //TODO 观察是否需要添加\n    this.ofs.addEventListener('webglcontextlost', e => {\n      logger.debug('[webglcontextlost]', e)\n      // 阻止浏览器的默认处理行为。（浏览器对上下文丢失事件的默认行为是，不再触发上下文恢复事件，所以我们要阻止浏览器的默认行为）\n      e.preventDefault()\n      // 重置program， 等恢复上下文后再重新初始化\n      this.program = undefined\n    })\n    this.ofs.addEventListener('webglcontextrestored', async () => {\n      logger.debug('[webglcontextrestored]')\n      this.initGlContext()\n      await this.prepareShader()\n      this.initWebgl()\n    })\n\n    this.renderCache = new RenderCache(this.ofs, this.op)\n    this.videoEntity = new VideoEntity(op)\n  }\n  public videoSeekedEvent() {\n    return this.renderCache.mCache.videoSeekedEvent()\n  }\n  public async setup(video?: HTMLVideoElement) {\n    if (!video) throw new Error('video must support!')\n    // 先加载 video 实体和缓存，拿到 effect 数量后再生成 shader\n    await this.renderCache.setup()\n    await this.videoEntity.setup()\n    await this.prepareShader()\n    this.video = video\n    //\n    this.resizeCanvasToDisplaySize()\n    this.initWebgl()\n    // this.video.currentTime 当前播放位置\n    // this.video.duration 媒体的持续时间(总长度)，以秒为单位\n  }\n  private async prepareShader() {\n    const effect = this.videoEntity.config?.effect\n    const effectCount = effect ? Object.keys(effect).length : 0\n    if (this.version === 2) {\n      const {VERTEX_SHADER, FRAGMENT_SHADER} = await import('./webgl-2')\n      this.VERTEX_SHADER = VERTEX_SHADER()\n      this.FRAGMENT_SHADER = FRAGMENT_SHADER(this.gl, this.PER_SIZE, effectCount)\n    } else if (this.version === 1) {\n      const {VERTEX_SHADER, FRAGMENT_SHADER} = await import('./webgl-1')\n      this.VERTEX_SHADER = VERTEX_SHADER()\n      this.FRAGMENT_SHADER = FRAGMENT_SHADER(this.gl, this.PER_SIZE, effectCount)\n    }\n  }\n  private resizeCanvasToDisplaySize() {\n    const descript = this.videoEntity.config?.descript\n    const ofs = this.ofs\n    if (!descript) {\n      if (!this.video) return\n      const vw = this.video.videoWidth ? this.video.videoWidth / 2 : 900\n      const vh = this.video.videoHeight ? this.video.videoHeight : 1000\n      logger.debug('[resizeCanvasToDisplaySize]', vw, vh)\n      // 默认左右结构\n      ofs.width = vw\n      ofs.height = vh\n    } else {\n      // 实际渲染大小\n      const [x, y, w, h] = descript.rgbFrame\n      ofs.width = w\n      ofs.height = h\n    }\n    if (this.op.useOfsRender) {\n      this.canvas.width = ofs.width\n      this.canvas.height = ofs.height\n    }\n  }\n  public destroy() {\n    this.webglDestroy()\n    this.videoEntity.destroy()\n    this.renderCache.destroy()\n  }\n\n  // public render(nextFPS: number) {\n  public render(frame = 0) {\n    // console.log('[render]', frame, this.op.useFrameCache)\n    if (!this.isPlay || !this.gl || !this.video || !this.program || this.currentFrame === frame) return\n\n    this.currentFrame = frame\n    const gl = this.gl\n    //\n    if (this.op.useFrameCache) {\n      const {width, height} = this.canvas\n      const frameItem = this.renderCache.getCache(frame)\n      // console.log('[frameItem]', frameItem)\n      if (frameItem === 'skip') return\n      if (frameItem) {\n        // console.log('[in frame cache]', frame, frameItem)\n        this.ctx.clearRect(0, 0, width, height)\n        this.ctx.drawImage(frameItem, 0, 0, width, height, 0, 0, width, height)\n        return\n      }\n\n      // if (frame > 0) {\n      //   //对上一帧，即是渲染已经生效的帧缓存，\n      //   //因为对webgl的调用是post类型的操作，即调用不一定马上生效，渲染结果不一定马上呈现，在渲染代码后面缓存有可能是上一帧的结果，导致缓存帧跳动\n      //   this.renderCache.setCache(frame - 1)\n      // }\n    }\n\n    const descript = this.videoEntity.config?.descript\n    if (descript) {\n      /* const timePoint = info && info.mediaTime && info.mediaTime >= 0 ? info.mediaTime : this.video.currentTime\n      const fps = info.fps || this.op.fps || 20\n      const frame = Math.round(timePoint * fps) + (this.op.offset || 0) */\n      //\n      const frameData = this.videoEntity.getFrame(frame)\n      const frameItem = frameData ? frameData[this.videoEntity.data] : undefined\n      let posArr: any = []\n      const {width: vW, height: vH} = descript\n      if (frameItem) {\n        frameItem.forEach((o: VideoAnimateDataItemType) => {\n          posArr[posArr.length] = +this.textureMap[o[this.videoEntity.effectId]]\n          // frame坐标是最终展示坐标，这里glsl中计算使用视频坐标\n          const [rgbX, rgbY] = descript.rgbFrame\n          const [x, y, w, h] = o[this.videoEntity.renderFrame]\n          const [mX, mY, mW, mH] = o[this.videoEntity.outputFrame]\n          const coord = this.computeCoord(x + rgbX, y + rgbY, w, h, vW, vH)\n          const mCoord = this.computeCoord(mX, mY, mW, mH, vW, vH)\n\n          posArr = posArr.concat(coord).concat(mCoord)\n        })\n      }\n      //\n      const size = (gl.getParameter(gl.MAX_TEXTURE_IMAGE_UNITS) - 1) * this.PER_SIZE\n      posArr = posArr.concat(new Array(size - posArr.length).fill(0))\n      this.imagePos = this.imagePos || gl.getUniformLocation(this.program, 'image_pos')\n      gl.uniform1fv(this.imagePos, new Float32Array(posArr))\n    }\n    // 如果意外暂停播放，尝试再次播放。\n    // if (this.video.paused) {\n    //   this.video.play()\n    // }\n    gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGB, gl.RGB, gl.UNSIGNED_BYTE, this.video) // 指定二维纹理方式\n    /**\n     * 评估是否需要加入\n     */\n    // gl.clear(gl.COLOR_BUFFER_BIT)\n    //\n    gl.drawArrays(gl.TRIANGLE_STRIP, 0, 4)\n    //\n    if (this.op.useOfsRender) {\n      const {width, height} = this.canvas\n      this.ctx.clearRect(0, 0, width, height)\n      this.ctx.drawImage(gl.canvas, 0, 0, width, height, 0, 0, width, height)\n    }\n    if (this.op.useFrameCache) {\n      this.renderCache.setCache(frame)\n    }\n  }\n  private getScale() {\n    let scaleX = 1\n    let scaleY = 1\n    if (this.video && this.op.mode) {\n      const ofs = this.canvas ? this.canvas : (this.ofs as HTMLCanvasElement)\n      const canvasAspect = ofs.clientWidth / ofs.clientHeight\n      const videoAspect = ofs.width / ofs.height\n\n      ofs.setAttribute('class', `e-video-${this.op.mode.toLocaleLowerCase()}`)\n      switch (this.op.mode) {\n        case 'AspectFill':\n        case 'vertical': //fit vertical | AspectFill 竖屏\n          scaleY = 1\n          scaleX = videoAspect / canvasAspect\n          break\n        case 'AspectFit':\n        case 'horizontal': //fit horizontal | AspectFit 横屏\n          scaleX = 1\n          scaleY = canvasAspect / videoAspect\n          break\n        case 'contain':\n          scaleY = 1\n          scaleX = videoAspect / canvasAspect\n          if (scaleX > 1) {\n            scaleY = 1 / scaleX\n            scaleX = 1\n          }\n          break\n        case 'Fill':\n        case 'cover':\n          scaleY = 1\n          scaleX = videoAspect / canvasAspect\n          if (scaleX < 1) {\n            scaleY = 1 / scaleX\n            scaleX = 1\n          }\n          break\n      }\n      // console.log('canvasAspect', canvasAspect)\n      // console.log('videoAspect', videoAspect)\n      // console.log('scaleX', scaleX, scaleY)\n    }\n    return [scaleX, scaleY]\n  }\n  private initWebgl() {\n    if (!this.gl) return\n    const gl = this.gl\n    // 设置canvas宽高\n    gl.viewport(0, 0, gl.drawingBufferWidth, gl.drawingBufferHeight)\n    //=================== 混合功能，将片元颜色和颜色缓冲区的颜色进行混合\n    gl.disable(gl.BLEND)\n    //=================== 分别设置应用在 RGB 和 Alpha 上的 factor。比如我们不想修改混合颜色之后的 Alpha 值，可以这样做\n    gl.blendFuncSeparate(gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA, gl.SRC_ALPHA, gl.ONE_MINUS_SRC_ALPHA)\n    //=================== 对纹理图像进行y轴反转，\n    // 因为WebGL纹理坐标系统的t轴（分为t轴和s轴）的方向和图片的坐标系统Y轴方向相反。因此将Y轴进行反转。\n    gl.pixelStorei(gl.UNPACK_FLIP_Y_WEBGL, true)\n    gl.pixelStorei(gl.UNPACK_PREMULTIPLY_ALPHA_WEBGL, true) // 预乘alpha通道\n    //=================== 创建着色器程序\n    const program = this.createProgram(gl)\n    if (!program) return\n    this.program = program\n    this.initTexture(gl, program)\n    this.initVideoTexture(gl, program)\n    //\n    const scaleLocation = gl.getUniformLocation(program, 'u_scale')\n    //\n    const scale = this.getScale()\n    gl.uniform2fv(scaleLocation, new Float32Array(scale))\n    // gl.uniform2fv(scaleLocation, [this.dpr, this.dpr])\n    // console.log('this.webgl.gl', this.webgl.gl)\n  }\n  private initTexture(gl: WebGLRenderingContext, program: WebGLProgram) {\n    let i = 1\n    const effect = this.videoEntity.config?.effect\n    if (effect) {\n      for (const k in effect) {\n        const r = effect[k]\n        // console.log('### effect videoEntity', r)\n        r.img && this.createTexture(gl, i, r.img)\n        const sampler = gl.getUniformLocation(program, `u_image${i}`)\n        gl.uniform1i(sampler, i)\n        this.textureMap[r[this.videoEntity.effectId]] = i++\n      }\n      // dump?\n      const dumpTexture = gl.createTexture()\n      gl.activeTexture(gl.TEXTURE0)\n      gl.bindTexture(gl.TEXTURE_2D, dumpTexture)\n      gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGBA, 1, 1, 0, gl.RGBA, gl.UNSIGNED_BYTE, null)\n    }\n    // video\n    this.createTexture(gl, i)\n    const sampler = gl.getUniformLocation(program, `u_image_video`)\n    gl.uniform1i(sampler, i)\n  }\n  private getRgbaPos() {\n    const descript = this.videoEntity.config?.descript\n    if (descript) {\n      //=================== 创建缓冲区\n      const {width: vW, height: vH} = descript\n      const [rgbX, rgbY, rgbW, rgbH] = descript.rgbFrame\n      const [aX, aY, aW, aH] = descript.alphaFrame\n      return {rgbX, rgbY, rgbW, rgbH, vW, vH, aX, aY, aW, aH}\n    } else if (this.video) {\n      //默认为左右均分\n      const vW = this.video.videoWidth ? this.video.videoWidth : 1800\n      const vH = this.video.videoHeight ? this.video.videoHeight : 1000\n      const stageW = vW / 2\n      const [rgbX, rgbY, rgbW, rgbH] = this.op.alphaDirection === 'right' ? [0, 0, stageW, vH] : [stageW, 0, stageW, vH]\n      const [aX, aY, aW, aH] = this.op.alphaDirection === 'right' ? [stageW, 0, stageW, vH] : [0, 0, stageW, vH]\n      return {rgbX, rgbY, rgbW, rgbH, vW, vH, aX, aY, aW, aH}\n    }\n  }\n  private initVideoTexture(gl: WebGLRenderingContext, program: WebGLProgram) {\n    const ver = []\n    const pos = this.getRgbaPos()\n    if (!pos) return\n    const {rgbX, rgbY, rgbW, rgbH, vW, vH, aX, aY, aW, aH} = pos\n    const rgbCoord = this.computeCoord(rgbX, rgbY, rgbW, rgbH, vW, vH)\n    const aCoord = this.computeCoord(aX, aY, aW, aH, vW, vH)\n    ver.push(...[-1, 1, rgbCoord[0], rgbCoord[3], aCoord[0], aCoord[3]])\n    ver.push(...[1, 1, rgbCoord[1], rgbCoord[3], aCoord[1], aCoord[3]])\n    ver.push(...[-1, -1, rgbCoord[0], rgbCoord[2], aCoord[0], aCoord[2]])\n    ver.push(...[1, -1, rgbCoord[1], rgbCoord[2], aCoord[1], aCoord[2]])\n    const view = new Float32Array(ver)\n    gl.bindBuffer(gl.ARRAY_BUFFER, gl.createBuffer()) // 创建buffer 把缓冲区对象绑定到目标\n    gl.bufferData(gl.ARRAY_BUFFER, view, gl.STATIC_DRAW) // 向缓冲区对象写入刚定义的顶点数据\n    //关联 program变量\n    const aPosition = gl.getAttribLocation(program, 'a_position')\n    gl.enableVertexAttribArray(aPosition)\n    const aTexCoord = gl.getAttribLocation(program, 'a_texCoord')\n    gl.enableVertexAttribArray(aTexCoord)\n    const aAlphaTexCoord = gl.getAttribLocation(program, 'a_alpha_texCoord')\n    gl.enableVertexAttribArray(aAlphaTexCoord)\n    // 将缓冲区对象分配给a_position变量、a_texCoord变量\n    const size = view.BYTES_PER_ELEMENT\n\n    gl.vertexAttribPointer(aPosition, 2, gl.FLOAT, false, size * 6, 0) // 顶点着色器位置\n    gl.vertexAttribPointer(aTexCoord, 2, gl.FLOAT, false, size * 6, size * 2) // rgb像素位置\n    gl.vertexAttribPointer(aAlphaTexCoord, 2, gl.FLOAT, false, size * 6, size * 4) // rgb像素位置\n  }\n  private createProgram(gl: WebGLRenderingContext) {\n    // vec4代表4维变量，因为rgba是4个值\n    // -0.5代表画布左侧，取值是rgb中的r值\n    // const vsSource = this.getVsSource() // 顶点着色器glsl代码\n    // const fsSource = this.getFsSource() // 片元着色器 glsl 代码\n    const vsShader = this.createShader(gl, gl.VERTEX_SHADER, this.VERTEX_SHADER)\n    const fsShader = this.createShader(gl, gl.FRAGMENT_SHADER, this.FRAGMENT_SHADER)\n    const program = gl.createProgram()\n    if (!program || !vsShader || !fsShader) return\n    gl.attachShader(program, vsShader)\n    gl.attachShader(program, fsShader)\n    gl.linkProgram(program)\n    if (!gl.getProgramParameter(program, gl.LINK_STATUS)) {\n      const info = gl.getProgramInfoLog(program)\n      logger.error(info)\n      gl.deleteProgram(program)\n      return null\n    }\n    gl.useProgram(program)\n    return program\n  }\n  private createShader(gl: WebGLRenderingContext, type: number, source: string) {\n    const shader = gl.createShader(type)\n    if (!shader) return\n    gl.shaderSource(shader, source)\n    gl.compileShader(shader)\n    if (!gl.getShaderParameter(shader, gl.COMPILE_STATUS)) {\n      logger.error(gl.getShaderInfoLog(shader))\n      gl.deleteShader(shader)\n      return null\n    }\n    return shader\n  }\n  /**\n   *\n   * @param x 位移转矩阵坐标\n   * @param y\n   * @param w\n   * @param h\n   * @param vw\n   * @param vh\n   * @returns\n   */\n  private computeCoord(x: number, y: number, w: number, h: number, vw: number, vh: number) {\n    // leftX rightX bottomY topY\n    return [x / vw, (x + w) / vw, (vh - y - h) / vh, (vh - y) / vh]\n  }\n  /**\n   *\n   * @param gl 创建纹理\n   * @param index\n   * @param imgData\n   * @returns\n   */\n  private createTexture(gl: WebGLRenderingContext, index: number, imgData?: TexImageSource) {\n    const texture = gl.createTexture()\n    const textrueIndex = gl.TEXTURE0 + index\n    logger.debug('[createTexture]', textrueIndex, index, `[ImageBitmap]Object`)\n    gl.activeTexture(textrueIndex)\n    gl.bindTexture(gl.TEXTURE_2D, texture)\n    // gl.pixelStorei(gl.UNPACK_FLIP_Y_WEBGL, true);\n    gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MIN_FILTER, gl.NEAREST)\n    gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_MAG_FILTER, gl.NEAREST)\n    gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_S, gl.CLAMP_TO_EDGE)\n    gl.texParameteri(gl.TEXTURE_2D, gl.TEXTURE_WRAP_T, gl.CLAMP_TO_EDGE)\n    if (imgData) {\n      gl.texImage2D(gl.TEXTURE_2D, 0, gl.RGBA, gl.RGBA, gl.UNSIGNED_BYTE, imgData)\n    }\n    return texture\n  }\n  private createCanvas(op: MixEvideoOptions) {\n    if (op.useOfsRender) {\n      this.canvas = document.createElement('canvas')\n      this.ctx = this.canvas.getContext('2d')\n      op.container.appendChild(this.canvas)\n      if (op.resizeCanvas) {\n        // this.canvas.style.width = '100%'\n        // this.canvas.style.height = '100%'\n        this.setSizeCanvas(this.canvas, op.resizeCanvas)\n      }\n      // this.ofs = MCache.getOfs(op)\n      this.ofs =\n        isOffscreenCanvasSupported() && !!self.createImageBitmap && op.useBitmap\n          ? new OffscreenCanvas(300, 300)\n          : document.createElement('canvas')\n    } else {\n      this.ofs = document.createElement('canvas')\n      if (op.resizeCanvas) {\n        // this.ofs.style.width = '100%'\n        // this.ofs.style.height = '100%'\n        this.setSizeCanvas(this.ofs, op.resizeCanvas)\n      }\n      op.container.appendChild(this.ofs)\n    }\n    this.initGlContext()\n    this.op = op\n  }\n  private setSizeCanvas(canvas: HTMLCanvasElement, resizeCanvas: ResizeCanvasType) {\n    switch (resizeCanvas) {\n      case 'percent':\n        canvas.style.width = '100%'\n        canvas.style.height = '100%'\n        break\n      case 'percentH':\n        canvas.style.height = '100%'\n        break\n      case 'percentW':\n        canvas.style.width = '100%'\n        break\n      default:\n        break\n    }\n  }\n  private initGlContext() {\n    const canvas = this.ofs\n    const op: WebGLContextAttributes = {\n      alpha: true, //指示Canvas是否含有透明通道，若设置为false不透明，如果Canvas下叠加了其他元素时，可以在绘制时提升一些性能\n      antialias: false, //绘制时是否开启抗锯齿功能\n      depth: true, //是否开启深度缓冲功能\n      failIfMajorPerformanceCaveat: false, //性能较低时，将不允许创建context。也就是是getContext()返回null [ios 会因此产生问题]\n      premultipliedAlpha: true, //将alpha通道预先乘入rgb通道内，以提高合成性能\n      stencil: false, //是否开启模板缓冲功能\n      preserveDrawingBuffer: false, //是否保留缓冲区数据，如果你需要读取像素，或者复用绘制到主屏幕上的图像\n    }\n    this.gl = canvas.getContext('webgl2', op) as WebGL2RenderingContext\n    this.version = 2\n    if (!this.gl) {\n      this.gl = canvas.getContext('webgl', op) as WebGLRenderingContext\n      this.version = 1\n      if (!this.gl) {\n        this.version = null\n      }\n    }\n    logger.debug('[Webgl]initGlContext, version=', this.version)\n    // gl.enable(this.gl.STENCIL_TEST)\n  }\n  private webglDestroy() {\n    if (this.gl) {\n      this.gl.clear(this.gl.COLOR_BUFFER_BIT)\n      const lose_context = this.gl.getExtension('WEBGL_lose_context')\n      if (lose_context) {\n        lose_context.loseContext()\n        logger.debug('lose_context')\n      }\n\n      this.gl = null\n    }\n    if (this.canvas) this.canvas.remove()\n    if (this.ofs instanceof HTMLCanvasElement) {\n      this.ofs.remove()\n      this.gl = null\n      logger.debug('[destroy remove canvas]')\n    } else this.ofs = undefined\n  }\n}\n"],"mappings":"gFAKA,IAAqB,EAArB,KAA+B,CAC7B,OAAgB,GAChB,YACA,WAAoB,QACpB,YACA,SAAkB,EAClB,OACA,IACA,IACA,QACA,GAGA,GACA,WAA0B,EAAE,CAC5B,SACA,aAAuB,GACvB,MACA,QACA,cACA,gBACA,YAAY,EAAsB,CAChC,EAAA,EAAO,MAAM,oBAAoB,CACjC,KAAK,GAAK,EAEV,KAAK,aAAa,EAAG,CAGrB,KAAK,IAAI,iBAAiB,mBAAoB,GAAK,CACjD,EAAA,EAAO,MAAM,qBAAsB,EAAE,CAErC,EAAE,gBAAgB,CAElB,KAAK,QAAU,IAAA,IACf,CACF,KAAK,IAAI,iBAAiB,uBAAwB,SAAY,CAC5D,EAAA,EAAO,MAAM,yBAAyB,CACtC,KAAK,eAAe,CACpB,MAAM,KAAK,eAAe,CAC1B,KAAK,WAAW,EAChB,CAEF,KAAK,YAAc,IAAIA,EAAAA,EAAY,KAAK,IAAK,KAAK,GAAG,CACrD,KAAK,YAAc,IAAIC,EAAAA,EAAY,EAAG,CAExC,kBAA0B,CACxB,OAAO,KAAK,YAAY,OAAO,kBAAkB,CAEnD,MAAa,MAAM,EAA0B,CAC3C,GAAI,CAAC,EAAO,MAAU,MAAM,sBAAsB,CAElD,MAAM,KAAK,YAAY,OAAO,CAC9B,MAAM,KAAK,YAAY,OAAO,CAC9B,MAAM,KAAK,eAAe,CAC1B,KAAK,MAAQ,EAEb,KAAK,2BAA2B,CAChC,KAAK,WAAW,CAIlB,MAAc,eAAgB,CAC5B,IAAM,EAAS,KAAK,YAAY,QAAQ,OAClC,EAAc,EAAS,OAAO,KAAK,EAAO,CAAC,OAAS,EAC1D,GAAI,KAAK,UAAY,EAAG,CACtB,GAAM,CAAC,gBAAe,mBAAmB,MAAA,QAAA,SAAA,CAAA,SAAA,QAAM,yBAAA,CAAA,CAC/C,KAAK,cAAgB,GAAe,CACpC,KAAK,gBAAkB,EAAgB,KAAK,GAAI,KAAK,SAAU,EAAY,SAClE,KAAK,UAAY,EAAG,CAC7B,GAAM,CAAC,gBAAe,mBAAmB,MAAA,QAAA,SAAA,CAAA,SAAA,QAAM,yBAAA,CAAA,CAC/C,KAAK,cAAgB,GAAe,CACpC,KAAK,gBAAkB,EAAgB,KAAK,GAAI,KAAK,SAAU,EAAY,EAG/E,2BAAoC,CAClC,IAAM,EAAW,KAAK,YAAY,QAAQ,SACpC,EAAM,KAAK,IACjB,GAAK,EAQE,CAEL,GAAM,CAAC,EAAG,EAAG,EAAG,GAAK,EAAS,SAC9B,EAAI,MAAQ,EACZ,EAAI,OAAS,MAZA,CACb,GAAI,CAAC,KAAK,MAAO,OACjB,IAAM,EAAK,KAAK,MAAM,WAAa,KAAK,MAAM,WAAa,EAAI,IACzD,EAAK,KAAK,MAAM,YAAc,KAAK,MAAM,YAAc,IAC7D,EAAA,EAAO,MAAM,8BAA+B,EAAI,EAAG,CAEnD,EAAI,MAAQ,EACZ,EAAI,OAAS,EAOX,KAAK,GAAG,eACV,KAAK,OAAO,MAAQ,EAAI,MACxB,KAAK,OAAO,OAAS,EAAI,QAG7B,SAAiB,CACf,KAAK,cAAc,CACnB,KAAK,YAAY,SAAS,CAC1B,KAAK,YAAY,SAAS,CAI5B,OAAc,EAAQ,EAAG,CAEvB,GAAI,CAAC,KAAK,QAAU,CAAC,KAAK,IAAM,CAAC,KAAK,OAAS,CAAC,KAAK,SAAW,KAAK,eAAiB,EAAO,OAE7F,KAAK,aAAe,EACpB,IAAM,EAAK,KAAK,GAEhB,GAAI,KAAK,GAAG,cAAe,CACzB,GAAM,CAAC,QAAO,UAAU,KAAK,OACvB,EAAY,KAAK,YAAY,SAAS,EAAM,CAElD,GAAI,IAAc,OAAQ,OAC1B,GAAI,EAAW,CAEb,KAAK,IAAI,UAAU,EAAG,EAAG,EAAO,EAAO,CACvC,KAAK,IAAI,UAAU,EAAW,EAAG,EAAG,EAAO,EAAQ,EAAG,EAAG,EAAO,EAAO,CACvE,QAUJ,IAAM,EAAW,KAAK,YAAY,QAAQ,SAC1C,GAAI,EAAU,CAKZ,IAAM,EAAY,KAAK,YAAY,SAAS,EAAM,CAC5C,EAAY,EAAY,EAAU,KAAK,YAAY,MAAQ,IAAA,GAC7D,EAAc,EAAE,CACd,CAAC,MAAO,EAAI,OAAQ,GAAM,EAC5B,GACF,EAAU,QAAS,GAAgC,CACjD,EAAO,EAAO,QAAU,CAAC,KAAK,WAAW,EAAE,KAAK,YAAY,WAE5D,GAAM,CAAC,EAAM,GAAQ,EAAS,SACxB,CAAC,EAAG,EAAG,EAAG,GAAK,EAAE,KAAK,YAAY,aAClC,CAAC,EAAI,EAAI,EAAI,GAAM,EAAE,KAAK,YAAY,aACtC,EAAQ,KAAK,aAAa,EAAI,EAAM,EAAI,EAAM,EAAG,EAAG,EAAI,EAAG,CAC3D,EAAS,KAAK,aAAa,EAAI,EAAI,EAAI,EAAI,EAAI,EAAG,CAExD,EAAS,EAAO,OAAO,EAAM,CAAC,OAAO,EAAO,EAC5C,CAGJ,IAAM,GAAQ,EAAG,aAAa,EAAG,wBAAwB,CAAG,GAAK,KAAK,SACtE,EAAS,EAAO,OAAW,MAAM,EAAO,EAAO,OAAO,CAAC,KAAK,EAAE,CAAC,CAC/D,KAAK,SAAW,KAAK,UAAY,EAAG,mBAAmB,KAAK,QAAS,YAAY,CACjF,EAAG,WAAW,KAAK,SAAU,IAAI,aAAa,EAAO,CAAC,CAcxD,GARA,EAAG,WAAW,EAAG,WAAY,EAAG,EAAG,IAAK,EAAG,IAAK,EAAG,cAAe,KAAK,MAAM,CAM7E,EAAG,WAAW,EAAG,eAAgB,EAAG,EAAE,CAElC,KAAK,GAAG,aAAc,CACxB,GAAM,CAAC,QAAO,UAAU,KAAK,OAC7B,KAAK,IAAI,UAAU,EAAG,EAAG,EAAO,EAAO,CACvC,KAAK,IAAI,UAAU,EAAG,OAAQ,EAAG,EAAG,EAAO,EAAQ,EAAG,EAAG,EAAO,EAAO,CAErE,KAAK,GAAG,eACV,KAAK,YAAY,SAAS,EAAM,CAGpC,UAAmB,CACjB,IAAI,EAAS,EACT,EAAS,EACb,GAAI,KAAK,OAAS,KAAK,GAAG,KAAM,CAC9B,IAAM,EAAM,KAAK,OAAS,KAAK,OAAU,KAAK,IACxC,EAAe,EAAI,YAAc,EAAI,aACrC,EAAc,EAAI,MAAQ,EAAI,OAGpC,OADA,EAAI,aAAa,QAAS,WAAW,KAAK,GAAG,KAAK,mBAAmB,GAAG,CAChE,KAAK,GAAG,KAAhB,CACE,IAAK,aACL,IAAK,WACH,EAAS,EACT,EAAS,EAAc,EACvB,MACF,IAAK,YACL,IAAK,aACH,EAAS,EACT,EAAS,EAAe,EACxB,MACF,IAAK,UACH,EAAS,EACT,EAAS,EAAc,EACnB,EAAS,IACX,EAAS,EAAI,EACb,EAAS,GAEX,MACF,IAAK,OACL,IAAK,QACH,EAAS,EACT,EAAS,EAAc,EACnB,EAAS,IACX,EAAS,EAAI,EACb,EAAS,GAEX,OAMN,MAAO,CAAC,EAAQ,EAAO,CAEzB,WAAoB,CAClB,GAAI,CAAC,KAAK,GAAI,OACd,IAAM,EAAK,KAAK,GAEhB,EAAG,SAAS,EAAG,EAAG,EAAG,mBAAoB,EAAG,oBAAoB,CAEhE,EAAG,QAAQ,EAAG,MAAM,CAEpB,EAAG,kBAAkB,EAAG,UAAW,EAAG,oBAAqB,EAAG,UAAW,EAAG,oBAAoB,CAGhG,EAAG,YAAY,EAAG,oBAAqB,GAAK,CAC5C,EAAG,YAAY,EAAG,+BAAgC,GAAK,CAEvD,IAAM,EAAU,KAAK,cAAc,EAAG,CACtC,GAAI,CAAC,EAAS,OACd,KAAK,QAAU,EACf,KAAK,YAAY,EAAI,EAAQ,CAC7B,KAAK,iBAAiB,EAAI,EAAQ,CAElC,IAAM,EAAgB,EAAG,mBAAmB,EAAS,UAAU,CAEzD,EAAQ,KAAK,UAAU,CAC7B,EAAG,WAAW,EAAe,IAAI,aAAa,EAAM,CAAC,CAIvD,YAAoB,EAA2B,EAAuB,CACpE,IAAI,EAAI,EACF,EAAS,KAAK,YAAY,QAAQ,OACxC,GAAI,EAAQ,CACV,IAAK,IAAM,KAAK,EAAQ,CACtB,IAAM,EAAI,EAAO,GAEjB,EAAE,KAAO,KAAK,cAAc,EAAI,EAAG,EAAE,IAAI,CACzC,IAAM,EAAU,EAAG,mBAAmB,EAAS,UAAU,IAAI,CAC7D,EAAG,UAAU,EAAS,EAAE,CACxB,KAAK,WAAW,EAAE,KAAK,YAAY,WAAa,IAGlD,IAAM,EAAc,EAAG,eAAe,CACtC,EAAG,cAAc,EAAG,SAAS,CAC7B,EAAG,YAAY,EAAG,WAAY,EAAY,CAC1C,EAAG,WAAW,EAAG,WAAY,EAAG,EAAG,KAAM,EAAG,EAAG,EAAG,EAAG,KAAM,EAAG,cAAe,KAAK,CAGpF,KAAK,cAAc,EAAI,EAAE,CACzB,IAAM,EAAU,EAAG,mBAAmB,EAAS,gBAAgB,CAC/D,EAAG,UAAU,EAAS,EAAE,CAE1B,YAAqB,CACnB,IAAM,EAAW,KAAK,YAAY,QAAQ,SAC1C,GAAI,EAAU,CAEZ,GAAM,CAAC,MAAO,EAAI,OAAQ,GAAM,EAC1B,CAAC,EAAM,EAAM,EAAM,GAAQ,EAAS,SACpC,CAAC,EAAI,EAAI,EAAI,GAAM,EAAS,WAClC,MAAO,CAAC,OAAM,OAAM,OAAM,OAAM,KAAI,KAAI,KAAI,KAAI,KAAI,KAAG,SAC9C,KAAK,MAAO,CAErB,IAAM,EAAK,KAAK,MAAM,WAAa,KAAK,MAAM,WAAa,KACrD,EAAK,KAAK,MAAM,YAAc,KAAK,MAAM,YAAc,IACvD,EAAS,EAAK,EACd,CAAC,EAAM,EAAM,EAAM,GAAQ,KAAK,GAAG,iBAAmB,QAAU,CAAC,EAAG,EAAG,EAAQ,EAAG,CAAG,CAAC,EAAQ,EAAG,EAAQ,EAAG,CAC5G,CAAC,EAAI,EAAI,EAAI,GAAM,KAAK,GAAG,iBAAmB,QAAU,CAAC,EAAQ,EAAG,EAAQ,EAAG,CAAG,CAAC,EAAG,EAAG,EAAQ,EAAG,CAC1G,MAAO,CAAC,OAAM,OAAM,OAAM,OAAM,KAAI,KAAI,KAAI,KAAI,KAAI,KAAG,EAG3D,iBAAyB,EAA2B,EAAuB,CACzE,IAAM,EAAM,EAAE,CACR,EAAM,KAAK,YAAY,CAC7B,GAAI,CAAC,EAAK,OACV,GAAM,CAAC,OAAM,OAAM,OAAM,OAAM,KAAI,KAAI,KAAI,KAAI,KAAI,MAAM,EACnD,EAAW,KAAK,aAAa,EAAM,EAAM,EAAM,EAAM,EAAI,EAAG,CAC5D,EAAS,KAAK,aAAa,EAAI,EAAI,EAAI,EAAI,EAAI,EAAG,CACxD,EAAI,KAAS,GAAI,EAAG,EAAS,GAAI,EAAS,GAAI,EAAO,GAAI,EAAO,GAAI,CACpE,EAAI,KAAS,EAAG,EAAG,EAAS,GAAI,EAAS,GAAI,EAAO,GAAI,EAAO,GAAI,CACnE,EAAI,KAAS,GAAI,GAAI,EAAS,GAAI,EAAS,GAAI,EAAO,GAAI,EAAO,GAAI,CACrE,EAAI,KAAS,EAAG,GAAI,EAAS,GAAI,EAAS,GAAI,EAAO,GAAI,EAAO,GAAI,CACpE,IAAM,EAAO,IAAI,aAAa,EAAI,CAClC,EAAG,WAAW,EAAG,aAAc,EAAG,cAAc,CAAC,CACjD,EAAG,WAAW,EAAG,aAAc,EAAM,EAAG,YAAY,CAEpD,IAAM,EAAY,EAAG,kBAAkB,EAAS,aAAa,CAC7D,EAAG,wBAAwB,EAAU,CACrC,IAAM,EAAY,EAAG,kBAAkB,EAAS,aAAa,CAC7D,EAAG,wBAAwB,EAAU,CACrC,IAAM,EAAiB,EAAG,kBAAkB,EAAS,mBAAmB,CACxE,EAAG,wBAAwB,EAAe,CAE1C,IAAM,EAAO,EAAK,kBAElB,EAAG,oBAAoB,EAAW,EAAG,EAAG,MAAO,GAAO,EAAO,EAAG,EAAE,CAClE,EAAG,oBAAoB,EAAW,EAAG,EAAG,MAAO,GAAO,EAAO,EAAG,EAAO,EAAE,CACzE,EAAG,oBAAoB,EAAgB,EAAG,EAAG,MAAO,GAAO,EAAO,EAAG,EAAO,EAAE,CAEhF,cAAsB,EAA2B,CAK/C,IAAM,EAAW,KAAK,aAAa,EAAI,EAAG,cAAe,KAAK,cAAc,CACtE,EAAW,KAAK,aAAa,EAAI,EAAG,gBAAiB,KAAK,gBAAgB,CAC1E,EAAU,EAAG,eAAe,CAC9B,MAAC,GAAW,CAAC,GAAY,CAAC,GAI9B,IAHA,EAAG,aAAa,EAAS,EAAS,CAClC,EAAG,aAAa,EAAS,EAAS,CAClC,EAAG,YAAY,EAAQ,CACnB,CAAC,EAAG,oBAAoB,EAAS,EAAG,YAAY,CAAE,CACpD,IAAM,EAAO,EAAG,kBAAkB,EAAQ,CAG1C,OAFA,EAAA,EAAO,MAAM,EAAK,CAClB,EAAG,cAAc,EAAQ,CAClB,KAGT,OADA,EAAG,WAAW,EAAQ,CACf,GAET,aAAqB,EAA2B,EAAc,EAAgB,CAC5E,IAAM,EAAS,EAAG,aAAa,EAAK,CAC/B,KAQL,OAPA,EAAG,aAAa,EAAQ,EAAO,CAC/B,EAAG,cAAc,EAAO,CACnB,EAAG,mBAAmB,EAAQ,EAAG,eAAe,CAK9C,GAJL,EAAA,EAAO,MAAM,EAAG,iBAAiB,EAAO,CAAC,CACzC,EAAG,aAAa,EAAO,CAChB,MAcX,aAAqB,EAAW,EAAW,EAAW,EAAW,EAAY,EAAY,CAEvF,MAAO,CAAC,EAAI,GAAK,EAAI,GAAK,GAAK,EAAK,EAAI,GAAK,GAAK,EAAK,GAAK,EAAG,CASjE,cAAsB,EAA2B,EAAe,EAA0B,CACxF,IAAM,EAAU,EAAG,eAAe,CAC5B,EAAe,EAAG,SAAW,EAYnC,OAXA,EAAA,EAAO,MAAM,kBAAmB,EAAc,EAAO,sBAAsB,CAC3E,EAAG,cAAc,EAAa,CAC9B,EAAG,YAAY,EAAG,WAAY,EAAQ,CAEtC,EAAG,cAAc,EAAG,WAAY,EAAG,mBAAoB,EAAG,QAAQ,CAClE,EAAG,cAAc,EAAG,WAAY,EAAG,mBAAoB,EAAG,QAAQ,CAClE,EAAG,cAAc,EAAG,WAAY,EAAG,eAAgB,EAAG,cAAc,CACpE,EAAG,cAAc,EAAG,WAAY,EAAG,eAAgB,EAAG,cAAc,CAChE,GACF,EAAG,WAAW,EAAG,WAAY,EAAG,EAAG,KAAM,EAAG,KAAM,EAAG,cAAe,EAAQ,CAEvE,EAET,aAAqB,EAAsB,CACrC,EAAG,cACL,KAAK,OAAS,SAAS,cAAc,SAAS,CAC9C,KAAK,IAAM,KAAK,OAAO,WAAW,KAAK,CACvC,EAAG,UAAU,YAAY,KAAK,OAAO,CACjC,EAAG,cAGL,KAAK,cAAc,KAAK,OAAQ,EAAG,aAAa,CAGlD,KAAK,IACHC,EAAAA,GAA4B,EAAM,KAAK,mBAAqB,EAAG,UAC3D,IAAI,gBAAgB,IAAK,IAAI,CAC7B,SAAS,cAAc,SAAS,GAEtC,KAAK,IAAM,SAAS,cAAc,SAAS,CACvC,EAAG,cAGL,KAAK,cAAc,KAAK,IAAK,EAAG,aAAa,CAE/C,EAAG,UAAU,YAAY,KAAK,IAAI,EAEpC,KAAK,eAAe,CACpB,KAAK,GAAK,EAEZ,cAAsB,EAA2B,EAAgC,CAC/E,OAAQ,EAAR,CACE,IAAK,UACH,EAAO,MAAM,MAAQ,OACrB,EAAO,MAAM,OAAS,OACtB,MACF,IAAK,WACH,EAAO,MAAM,OAAS,OACtB,MACF,IAAK,WACH,EAAO,MAAM,MAAQ,OACrB,MACF,QACE,OAGN,eAAwB,CACtB,IAAM,EAAS,KAAK,IACd,EAA6B,CACjC,MAAO,GACP,UAAW,GACX,MAAO,GACP,6BAA8B,GAC9B,mBAAoB,GACpB,QAAS,GACT,sBAAuB,GACxB,CACD,KAAK,GAAK,EAAO,WAAW,SAAU,EAAG,CACzC,KAAK,QAAU,EACV,KAAK,KACR,KAAK,GAAK,EAAO,WAAW,QAAS,EAAG,CACxC,KAAK,QAAU,EACV,KAAK,KACR,KAAK,QAAU,OAGnB,EAAA,EAAO,MAAM,iCAAkC,KAAK,QAAQ,CAG9D,cAAuB,CACrB,GAAI,KAAK,GAAI,CACX,KAAK,GAAG,MAAM,KAAK,GAAG,iBAAiB,CACvC,IAAM,EAAe,KAAK,GAAG,aAAa,qBAAqB,CAC3D,IACF,EAAa,aAAa,CAC1B,EAAA,EAAO,MAAM,eAAe,EAG9B,KAAK,GAAK,KAER,KAAK,QAAQ,KAAK,OAAO,QAAQ,CACjC,KAAK,eAAe,mBACtB,KAAK,IAAI,QAAQ,CACjB,KAAK,GAAK,KACV,EAAA,EAAO,MAAM,0BAA0B,EAClC,KAAK,IAAM,IAAA"}