/**
 * Cesium - https://github.com/CesiumGS/cesium
 *
 * Copyright 2011-2020 Cesium Contributors
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 *
 * Columbus View (Pat. Pend.)
 *
 * Portions licensed separately.
 * See https://github.com/CesiumGS/cesium/blob/master/LICENSE.md for full licensing details.
 */
define(['./when-8d13db60', './Check-70bec281', './Math-61ede240', './Cartographic-f2a06374', './Cartesian2-16a61632', './BoundingSphere-d018a565', './Cartesian4-5af5bb24', './RuntimeError-ba10bc3e', './WebGLConstants-4c11ee5f', './ComponentDatatype-5862616f', './PrimitiveType-97893bc7', './FeatureDetection-7bd32c34', './IndexDatatype-9435b55f', './createTaskProcessorWorker', './BoundingRectangle-5c75c80b', './Color-69f1845f', './pako_inflate-8ea163f9', './S3MCompressType-8157e6e2'], function (when, Check, _Math, Cartographic, Cartesian2, BoundingSphere, Cartesian4, RuntimeError, WebGLConstants, ComponentDatatype, PrimitiveType, FeatureDetection, IndexDatatype, createTaskProcessorWorker, BoundingRectangle, Color, pako_inflate, S3MCompressType) { 'use strict';

    function Bound3D(left, bottom, right, top, minHeight, maxHeight) {
        this.left = left;
        this.bottom = bottom;
        this.right = right;
        this.top = top;
        this.minHeight = minHeight;
        this.maxHeight = maxHeight;
        this.width = right - left;
        this.length = top - bottom;
        this.height = maxHeight - minHeight;

    }
    function parseGeoPackage(geoPackage, typedArray, view, bytesOffset, transferableObjects) {
        var geoName = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        var byteLength = 0;
        var vertexPackage = {};
        var attributes = vertexPackage.vertexAttributes = [];
        var attrLocation = vertexPackage.attrLocation = {};
        vertexPackage.instanceCount = 0;
        vertexPackage.instanceMode = 0;
        var index = 0;
        var nVertexOptions = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        var vertexDimension = view.getUint16(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        var normalDimension = vertexDimension;
        if (vertexDimension > 4) {
            normalDimension = vertexDimension >> 8;
            vertexDimension = vertexDimension & 0x0f;
        }
        var verticesCount = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        if (verticesCount > 0) {
            var vertexStride = view.getUint16(bytesOffset, true);
            vertexStride = vertexDimension * Float32Array.BYTES_PER_ELEMENT;
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
            byteLength = verticesCount * vertexStride;
            attrLocation['aPosition'] = index;
            attributes.push({
                index: attrLocation['aPosition'],
                typedArray: typedArray.subarray(bytesOffset, bytesOffset + byteLength),
                componentsPerAttribute: vertexDimension,
                componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                offsetInBytes: 0,
                strideInBytes: vertexStride,
                normalize: false
            });
            index++;
            bytesOffset += byteLength;
        }

        var normalCount = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        if (normalCount > 0) {
            var normalStride = view.getUint16(bytesOffset, true);
            normalStride = normalDimension * Float32Array.BYTES_PER_ELEMENT;
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
            byteLength = normalCount * normalStride;
            if(!geoPackage.ignoreNormal){
                attrLocation['aNormal'] = index;
                attributes.push({
                    index: attrLocation['aNormal'],
                    typedArray: typedArray.subarray(bytesOffset, bytesOffset + byteLength),
                    componentsPerAttribute: normalDimension,
                    componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                    offsetInBytes: 0,
                    strideInBytes: normalStride,
                    normalize: false
                });
                index++;
            }
            bytesOffset += byteLength;
        }

        var vertexColorCount = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        if (vertexColorCount > 0) {
            var vertexColor = new Uint8Array(4 * vertexColorCount);
            transferableObjects.push(vertexColor.buffer);
            var vertexColorStride = view.getUint32(bytesOffset, true);
            vertexColorStride = 4 * Float32Array.BYTES_PER_ELEMENT;
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
            byteLength = vertexColorCount * vertexColorStride;
            var oriVertexColor = new Float32Array(typedArray.buffer, bytesOffset, verticesCount * 4);
            for (var m = 0; m < verticesCount; m++) {
                vertexColor[4 * m] = oriVertexColor[4 * m] * 255;
                vertexColor[4 * m + 1] = oriVertexColor[4 * m + 1] * 255;
                vertexColor[4 * m + 2] = oriVertexColor[4 * m + 2] * 255;
                vertexColor[4 * m + 3] = oriVertexColor[4 * m + 3] * 255;
            }
            bytesOffset += byteLength;
            attrLocation['aColor'] = index;
            attributes.push({
                index: attrLocation['aColor'],
                typedArray: vertexColor,
                componentsPerAttribute: 4,
                componentDatatype: ComponentDatatype.ComponentDatatype.UNSIGNED_BYTE,
                offsetInBytes: 0,
                strideInBytes: 4,
                normalize: true
            });
            index++;
        }

        var secondVertexColorCount = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        if (secondVertexColorCount > 0) {
            byteLength = secondVertexColorCount * 16;
            bytesOffset += byteLength;
        }

        var textureCount = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        var instanceIndex = -1;
        var texCoordCount, texCoordStride, texCoordDim;
        for (var j = 0; j < textureCount; j++) {
            texCoordCount = view.getUint32(bytesOffset, true);
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
            texCoordDim = view.getUint16(bytesOffset, true);
            bytesOffset += Uint16Array.BYTES_PER_ELEMENT;
            texCoordStride = view.getUint16(bytesOffset, true);
            bytesOffset += Uint16Array.BYTES_PER_ELEMENT;
            byteLength = texCoordCount * texCoordDim * Float32Array.BYTES_PER_ELEMENT;
            var texBuffer = typedArray.subarray(bytesOffset, bytesOffset + byteLength);
            if (instanceIndex == -1 && (texCoordDim == 20 || texCoordDim == 35)) {
                instanceIndex = j;
                vertexPackage.instanceCount = texCoordCount;
                vertexPackage.instanceMode = texCoordDim;
                vertexPackage.instanceBuffer = texBuffer;
                var byteStride;
                if (texCoordDim === 20) {
                    byteStride = Float32Array.BYTES_PER_ELEMENT * 20;
                    attrLocation['uv2'] = index++;
                    attributes.push({
                        index: attrLocation['uv2'],
                        componentsPerAttribute: 4,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        normalize: false,
                        offsetInBytes: 0,
                        strideInBytes: byteStride,
                        instanceDivisor: 1
                    });

                    attrLocation['uv3'] = index++;
                    attributes.push({
                        index: attrLocation['uv3'],
                        componentsPerAttribute: 4,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        normalize: false,
                        offsetInBytes: 4 * Float32Array.BYTES_PER_ELEMENT,
                        strideInBytes: byteStride,
                        instanceDivisor: 1
                    });

                    attrLocation['uv4'] = index++;
                    attributes.push({
                        index: attrLocation['uv4'],
                        componentsPerAttribute: 4,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        normalize: false,
                        offsetInBytes: 8 * Float32Array.BYTES_PER_ELEMENT,
                        strideInBytes: byteStride,
                        instanceDivisor: 1
                    });

                    attrLocation['secondary_colour'] = index++;
                    attributes.push({
                        index: attrLocation['secondary_colour'],
                        componentsPerAttribute: 4,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        normalize: false,
                        offsetInBytes: 12 * Float32Array.BYTES_PER_ELEMENT,
                        strideInBytes: byteStride,
                        instanceDivisor: 1
                    });

                    attrLocation['uv6'] = index++;
                    attributes.push({
                        index: attrLocation['uv6'],
                        componentsPerAttribute: 4,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        normalize: false,
                        offsetInBytes: 16 * Float32Array.BYTES_PER_ELEMENT,
                        strideInBytes: byteStride,
                        instanceDivisor: 1
                    });
                }
                else if (texCoordDim === 35) {
                    byteStride = Float32Array.BYTES_PER_ELEMENT * 35;
                    attrLocation['uv1'] = index++;
                    attributes.push({
                        index: attrLocation['uv1'],
                        componentsPerAttribute: 4,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        normalize: false,
                        offsetInBytes: 0,
                        strideInBytes: byteStride,
                        instanceDivisor: 1,
                        byteLength: byteLength
                    });
                    attrLocation['uv2'] = index++;
                    attributes.push({
                        index: attrLocation['uv2'],
                        componentsPerAttribute: 4,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        normalize: false,
                        offsetInBytes: 4 * Float32Array.BYTES_PER_ELEMENT,
                        strideInBytes: byteStride,
                        instanceDivisor: 1
                    });
                    attrLocation['uv3'] = index++;
                    attributes.push({
                        index: attrLocation['uv3'],
                        componentsPerAttribute: 4,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        normalize: false,
                        offsetInBytes: 8 * Float32Array.BYTES_PER_ELEMENT,
                        strideInBytes: byteStride,
                        instanceDivisor: 1
                    });
                    attrLocation['uv4'] = index++;
                    attributes.push({
                        index: attrLocation['uv4'],
                        componentsPerAttribute: 4,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        normalize: false,
                        offsetInBytes: 12 * Float32Array.BYTES_PER_ELEMENT,
                        strideInBytes: byteStride,
                        instanceDivisor: 1
                    });
                    attrLocation['uv5'] = index++;
                    attributes.push({
                        index: attrLocation['uv5'],
                        componentsPerAttribute: 4,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        normalize: false,
                        offsetInBytes: 16 * Float32Array.BYTES_PER_ELEMENT,
                        strideInBytes: byteStride,
                        instanceDivisor: 1
                    });
                    attrLocation['uv6'] = index++;
                    attributes.push({
                        index: attrLocation['uv6'],
                        componentsPerAttribute: 4,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        normalize: false,
                        offsetInBytes: 20 * Float32Array.BYTES_PER_ELEMENT,
                        strideInBytes: byteStride,
                        instanceDivisor: 1
                    });
                    attrLocation['uv7'] = index++;
                    attributes.push({
                        index: attrLocation['uv7'],
                        componentsPerAttribute: 3,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        normalize: false,
                        offsetInBytes: 24 * Float32Array.BYTES_PER_ELEMENT,
                        strideInBytes: byteStride,
                        instanceDivisor: 1
                    });
                    attrLocation['secondary_colour'] = index++;
                    attributes.push({
                        index: attrLocation['secondary_colour'],
                        componentsPerAttribute: 4,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        normalize: false,
                        offsetInBytes: 27 * Float32Array.BYTES_PER_ELEMENT,
                        strideInBytes: byteStride,
                        instanceDivisor: 1
                    });
                    attrLocation['uv9'] = index++;
                    attributes.push({
                        index: attrLocation['uv9'],
                        componentsPerAttribute: 4,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        normalize: false,
                        offsetInBytes: 31 * Float32Array.BYTES_PER_ELEMENT,
                        strideInBytes: byteStride,
                        instanceDivisor: 1
                    });
                }
            }
            else {
                if (instanceIndex !== -1) {
                    vertexPackage.instanceBounds = new Float32Array(typedArray.buffer, bytesOffset, texCoordCount * texCoordDim);
                }
                else {
                    var str = 'aTexCoord' + j;
                    attrLocation[str] = index++;
                    attributes.push({
                        index: attrLocation[str],
                        typedArray: texBuffer,
                        componentsPerAttribute: texCoordDim,
                        componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
                        offsetInBytes: 0,
                        strideInBytes: texCoordDim * Float32Array.BYTES_PER_ELEMENT,
                        normalize: false
                    });
                }
            }
            bytesOffset += byteLength;
        }

        vertexPackage.verticesCount = verticesCount;
        vertexPackage.instanceIndex = instanceIndex;
        var indexPackageSize = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        var arrIndexPackage = [];
        for (var j = 0; j < indexPackageSize; j++) {
            var indexPackage = {};
            var indicesCount = view.getUint32(bytesOffset, true);
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
            var indexType = view.getUint8(bytesOffset, true);
            bytesOffset += Uint8Array.BYTES_PER_ELEMENT;
            var useIndex = view.getUint8(bytesOffset, true);
            bytesOffset += Uint8Array.BYTES_PER_ELEMENT;
            var primitiveType = view.getUint8(bytesOffset, true);
            bytesOffset += Uint8Array.BYTES_PER_ELEMENT;
            bytesOffset += 1;
            indexPackage.indicesCount = indicesCount;
            indexPackage.indexType = indexType;
            indexPackage.primitiveType = primitiveType;
            var indexOffset = bytesOffset;
            if (indicesCount > 0) {
                if (indexType == 0) {
                    byteLength = indicesCount * Uint16Array.BYTES_PER_ELEMENT;
                    bytesOffset += byteLength;
                    if (indicesCount % 2 == 1) {
                        bytesOffset += 2;
                    }
                }
                else {
                    byteLength = indicesCount * 4;
                    bytesOffset += byteLength;
                }
            }

            indexPackage.indicesTypedArray = typedArray.subarray(indexOffset, indexOffset + byteLength);
            var passNameCount = view.getUint32(bytesOffset, true);
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
            var materialCode = view.getUint32(bytesOffset, true);
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT * passNameCount;
            indexPackage.materialCode = materialCode;
            arrIndexPackage.push(indexPackage);
        }

        geoPackage[geoName] = {
            vertexPackage: vertexPackage,
            arrIndexPackage: arrIndexPackage
        };

        return bytesOffset;
    }

    function createBatchIdAttribute(vertexPackage, typedArray, instanceDivisor) {
        var vertexAttributes = vertexPackage.vertexAttributes;
        var attrLocation = vertexPackage.attrLocation;
        var len = vertexAttributes.length;
        var attrName = instanceDivisor === 1 ? 'instanceId' : 'batchId';
        attrLocation[attrName] = len;
        vertexAttributes.push({
            index: len,
            typedArray: typedArray,
            componentsPerAttribute: 1,
            componentDatatype: ComponentDatatype.ComponentDatatype.FLOAT,
            offsetInBytes: 0,
            strideInBytes: 0,
            instanceDivisor : instanceDivisor
        });
    }

    function S3MTilesParser(parameters, transferableObjects) {
        var buffer = parameters.buffer;
        //transferableObjects.push(buffer);
        var supportCompressType = parameters.supportCompressType;
        var bVolume = parameters.bVolume;//是否是体渲染数据
        var bound3D = null;
        var volBounds = null;
        var volImageBuffer = null;
        if (bVolume) {
            if (parameters.volbuffer.byteLength < 8) {
                bVolume = false;
            }
        }
        if (bVolume) {

            var volData = parameters.volbuffer;
            var dataZip = new Uint8Array(volData, 8);
            var volumeBuffer = pako_inflate.pako.inflate(dataZip).buffer;
            var volVersion = new Float64Array(volumeBuffer, 0, 1);
            var volFormat = new Uint32Array(volumeBuffer , 48, 1);

            if(volVersion[0] === 0.0 || volFormat[0] === 3200 || volFormat[0] === 3201)
            {
                var nHeaderOffset = 0;
                if(volVersion[0] === 0.0)
                {
                    nHeaderOffset = 8;
                }

                transferableObjects.push(volumeBuffer);
                var boundsArray = new Float64Array(volumeBuffer, nHeaderOffset, 6);
                var left = boundsArray[0];
                var top = boundsArray[1];
                var right = boundsArray[2];
                var bottom = boundsArray[3];
                var minHeight = boundsArray[4] < boundsArray[5] ? boundsArray[4] : boundsArray[5];
                var maxHeight = boundsArray[4] > boundsArray[5] ? boundsArray[4] : boundsArray[5];
                bound3D = new Bound3D(left, bottom, right, top, minHeight, maxHeight);

                volBounds = {
                    left: left,
                    top: top,
                    right: right,
                    bottom: bottom,
                    minHeight: minHeight,
                    maxHeight: maxHeight,
                    width: bound3D.width,
                    length: bound3D.length,
                    height: bound3D.height
                };

                // 中间空出来
                var infoVolume = new Uint32Array(volumeBuffer, 48 + nHeaderOffset, 7);
                var nFormat = infoVolume[0];
                var nSideBlockCount = infoVolume[1];
                var nBlockLength = infoVolume[2];
                var nLength = infoVolume[3];
                var nWidth = infoVolume[4];
                var nHeight = infoVolume[5];
                var nDepth = infoVolume[6];
                var nCount = nLength * nLength * 4;
                var image = new Uint8Array(volumeBuffer, 76 + nHeaderOffset, nCount);
                volImageBuffer = {
                    nFormat: nFormat,
                    nSideBlockCount: nSideBlockCount,
                    nBlockLength: nBlockLength,
                    nLength: nLength,
                    nWidth: nWidth,
                    nHeight: nHeight,
                    nDepth: nDepth,
                    imageArray: image
                };
            }
        }

        var bytesOffset = 0;
        var header = new Uint8Array(buffer, 0, 4);
        if (header[0] !== 115 || header[1] !== 51 || header[2] !== 109) {
            return {
                result: false
            };
        }

        var version = header[3];
        var dataZip = new Uint8Array(buffer, 4);
        var unzipBuffer = pako_inflate.pako.inflate(dataZip).buffer;
        var typedArray = new Uint8Array(unzipBuffer);
        transferableObjects.push(typedArray.buffer);
        var view = new DataView(unzipBuffer);
        var xmlSize = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        var xmlBuffer = new Uint8Array(unzipBuffer, bytesOffset, xmlSize);
        var nAlign = xmlSize % 4;
        if(nAlign){
            nAlign = 4 - nAlign;
        }

        bytesOffset += xmlSize + nAlign;

        var xmlDoc = S3MCompressType.getStringFromTypedArray(xmlBuffer, undefined, undefined, 'gbk');
        xmlDoc = xmlDoc.replace(new RegExp("\r\n",'gm'),'');
        xmlDoc = xmlDoc.replace(new RegExp(":",'gm'),'');

        var packageSize = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        var geoCount = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        var geoPackage = {};
        geoPackage.ignoreNormal = parameters.ignoreNormal;
        for (var i = 0; i < geoCount; i++) {
            bytesOffset = parseGeoPackage(geoPackage, typedArray, view, bytesOffset, transferableObjects);
        }

        var pickInfoPackageCount = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        var pickColorCount = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        for (var i = 0; i < pickColorCount; i++) {
            var geoName = view.getUint32(bytesOffset, true);
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
            var pickIdsCount = view.getUint32(bytesOffset, true);
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
            var pickInfo = {};
            var bInstanced = geoPackage[geoName].vertexPackage.instanceIndex;
            if (bInstanced == -1) {
                var batchIds = new Float32Array(geoPackage[geoName].vertexPackage.verticesCount);
                for (var j = 0; j < pickIdsCount; j++) {
                    var pickId = view.getUint32(bytesOffset, true);
                    bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
                    var size = view.getUint32(bytesOffset, true);
                    bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
                    var vertexCount = 0, vertexColorOffset = 0;
                    pickInfo[pickId] = {
                        batchId : j
                    };
                    for (var k = 0; k < size; k++) {
                        vertexColorOffset = view.getUint32(bytesOffset, true);
                        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
                        vertexCount = view.getUint32(bytesOffset, true);
                        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
                        if (batchIds.fill) {
                            batchIds.fill(j, vertexColorOffset, vertexColorOffset + vertexCount);
                        } else {
                            var total = vertexColorOffset + vertexColorOffset;
                            for(var m = vertexColorOffset; m < total; m++) {
                                batchIds[m] = j;
                            }
                        }
                    }
                    pickInfo[pickId].vertexColorOffset = vertexColorOffset;
                    pickInfo[pickId].vertexColorCount = vertexCount;
                }

                createBatchIdAttribute(geoPackage[geoName].vertexPackage, batchIds, undefined);
            }
            else {
                var instanceCount = geoPackage[geoName].vertexPackage.instanceCount;
                var instanceArray = geoPackage[geoName].vertexPackage.instanceBuffer;
                var instanceMode = geoPackage[geoName].vertexPackage.instanceMode;
                var instanceIds = new Float32Array(instanceCount);
                var instanceIdIndex = 0;
                for (var j = 0; j < pickIdsCount; j++) {
                    var pickId = view.getUint32(bytesOffset, true);
                    bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
                    var size = view.getUint32(bytesOffset, true);
                    bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
                    for (var k = 0; k < size; k++) {
                        var instanceId = view.getUint32(bytesOffset, true);
                        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
                        instanceIds[instanceIdIndex] = instanceIdIndex;
                        if(pickInfo[pickId] === undefined){
                            pickInfo[pickId] = {
                                vertexColorCount : 1,
                                instanceIds : [],
                                vertexColorOffset : instanceIdIndex
                            };
                        }
                        pickInfo[pickId].instanceIds.push(instanceId);
                        instanceIdIndex ++;
                    }

                }

                createBatchIdAttribute(geoPackage[geoName].vertexPackage, instanceIds, 1);
            }

            geoPackage[geoName].pickInfo = pickInfo;
        }

        var texturePackageCount = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        var imageCount = view.getUint32(bytesOffset, true);
        bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
        var texturePackage = {};
        for (var i = 0; i < imageCount; i++) {
            var id = view.getUint32(bytesOffset, true);
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
            var width = view.getUint32(bytesOffset, true);
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
            var height = view.getUint32(bytesOffset, true);
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
            var compressType = view.getUint32(bytesOffset, true);
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
            var size = view.getUint32(bytesOffset, true);
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
            var pixelFormat = view.getUint32(bytesOffset, true);
            bytesOffset += Uint32Array.BYTES_PER_ELEMENT;
            var imageTypedArray = null;
            if (compressType === S3MCompressType.S3MCompressType.enrS3TCDXTN && supportCompressType !== 1) {
                var pEncode = null;
                if (pixelFormat > S3MCompressType.S3MPixelFormat.BGR || pixelFormat === S3MCompressType.S3MPixelFormat.LUMINANCE_ALPHA) {
                    pEncode = new Uint8Array(unzipBuffer, bytesOffset, width * height);
                    imageTypedArray = new Uint8Array(width * height * 4);
                }
                else {
                    pEncode = new Uint16Array(unzipBuffer, bytesOffset, size / 2);
                    imageTypedArray = new Uint16Array(width * height);
                }
                S3MCompressType.DXTTextureDecode.decode(imageTypedArray, width, height, pEncode, pixelFormat);
                transferableObjects.push(imageTypedArray.buffer);
                compressType = 0;
            }
            else {
                imageTypedArray = new Uint8Array(unzipBuffer, bytesOffset, size);
            }

            texturePackage[id] = {
                id: id,
                width: width,
                height: height,
                compressType: compressType,
                nFormat: pixelFormat,
                imageBuffer: imageTypedArray
            };
            bytesOffset += size;
        }

        return {
            result: true,
            version: version,
            xmlDoc: xmlDoc,
            geoPackage: geoPackage,
            texturePackage: texturePackage,
            volImageBuffer: volImageBuffer,
            volBounds: volBounds
        };
    }

    var S3MTilesParser$1 = createTaskProcessorWorker(S3MTilesParser);

    return S3MTilesParser$1;

});
