var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
    return new (P || (P = Promise))(function (resolve, reject) {
        function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
        function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
        function step(result) { result.done ? resolve(result.value) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
var __generator = (this && this.__generator) || function (thisArg, body) {
    var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g;
    return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() { return this; }), g;
    function verb(n) { return function (v) { return step([n, v]); }; }
    function step(op) {
        if (f) throw new TypeError("Generator is already executing.");
        while (_) try {
            if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;
            if (y = 0, t) op = [op[0] & 2, t.value];
            switch (op[0]) {
                case 0: case 1: t = op; break;
                case 4: _.label++; return { value: op[1], done: false };
                case 5: _.label++; y = op[1]; op = [0]; continue;
                case 7: op = _.ops.pop(); _.trys.pop(); continue;
                default:
                    if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }
                    if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }
                    if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }
                    if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }
                    if (t[2]) _.ops.pop();
                    _.trys.pop(); continue;
            }
            op = body.call(thisArg, _);
        } catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }
        if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };
    }
};
import { _ContentParser, _PdfContentStream, _PdfReference, PdfBitmap, PdfPath, PdfRotationAngle } from '@syncfusion/ej2-pdf';
import { TextGlyph, TextLine, TextWord } from './text-structure';
import { _TextProcessingMode } from './enum';
import { _decodeEncodedText, _getXObject, _isArrayEqual } from './utils';
import { _PdfTextParser } from './pdf-text-parser';
import { _PdfShapeParser } from './redaction/shape-parser-helper';
import { _ImageStructure } from './image-extraction/image-structure';
import { PdfEmbeddedImage } from './image-extraction/pdf-embedded-image';
import { _PdfImage } from './image-extraction/image';
var _PdfContentParserHelper = /** @class */ (function () {
    function _PdfContentParserHelper(mode, redaction) {
        this._identityMatrix = [1, 0, 0, 1, 0, 0];
        this._width = 0;
        this._imageInfo = [];
        this._pt = 1.3333;
        this._height = 0;
        this._resultantText = '';
        this._textGlyph = [];
        this._textWord = [];
        this._textLine = [];
        this._isContainsRedactionText = false;
        this._yPosition = 0;
        this._xPosition = 0;
        this._parser = new _PdfTextParser();
        if (typeof (mode) !== 'undefined') {
            this._mode = mode;
        }
        if (this._mode === _TextProcessingMode.redaction) {
            this._redaction = redaction;
            this._document = redaction._document;
        }
    }
    _PdfContentParserHelper.prototype._getPageRecordCollection = function (page) {
        var combinedContent = page._combineContent();
        var parser = new _ContentParser(combinedContent);
        var recordCollection = parser._readContent();
        return recordCollection;
    };
    _PdfContentParserHelper.prototype._processTjOperator = function (record, textState, currentFont, page, fontCollection) {
        currentFont = this._parser._getTextFont(fontCollection, textState, this._crossReference);
        var element = '';
        if (record._operator === '"') {
            element = record._operands[2];
        }
        else {
            element = record._operands[0];
        }
        var result; // eslint-disable-line
        var elements; // eslint-disable-line
        var textGlyphs = [];
        var encodedText = [];
        var decodedText = [];
        var updatedText = '';
        var isChangeOperator = false;
        var object; // eslint-disable-line
        var extractedText;
        var text;
        if (this._mode === _TextProcessingMode.textLineExtraction) {
            result = this._parser._getSplitText(element, currentFont, record._splitText);
            object = this._getTextElementsFromTjOperator(result.decodedList, currentFont, textState, page);
            extractedText = object.extractedText;
            text = object.tempString;
            this._setTextLineCollection(text, currentFont, textState, page, extractedText);
        }
        else if (this._mode === _TextProcessingMode.textExtraction) {
            currentFont = this._parser._getTextFont(fontCollection, textState, this._crossReference);
            this._extractTextElement(element, currentFont, record._splitText);
            if (record._operator === "'" || record._operator === '"') { //eslint-disable-line
                this._resultantText += '\r\n';
            }
        }
        else if (this._mode === _TextProcessingMode.redaction) {
            if (this._isContainsRedactionText) {
                var glyphs = [];
                result = this._parser._getSplitText(element, currentFont, record._splitText, true);
                elements = this._getTextElementsFromTjOperator(result.decodedList, currentFont, textState, page, glyphs, result.inputType);
                textGlyphs = elements.textGlyphs;
                decodedText = elements.decodedText;
                encodedText = elements.encodedText;
                updatedText = this._redaction._replacedText(textGlyphs, encodedText, element, decodedText);
                if (updatedText === record._operands[0]) {
                    this._isNotUpdated = true;
                }
                else {
                    isChangeOperator = true;
                }
                return { updatedText: updatedText, isChangeOperator: isChangeOperator };
            }
        }
    };
    _PdfContentParserHelper.prototype._setTextLineCollection = function (text, currentFont, textState, page, extractedText) {
        if (text !== '') {
            var textWord = new TextWord();
            textWord._text = text;
            textWord._glyphs = this._textGlyph;
            var pdfPath_1 = new PdfPath();
            for (var i = 0; i < this._textGlyph.length; i++) {
                pdfPath_1.addRectangle(this._textGlyph[Number.parseInt(i.toString(), 10)]._bounds);
            }
            var pathBounds_1 = pdfPath_1._getBounds();
            textWord._bounds = { x: pathBounds_1[0], y: pathBounds_1[1], width: pathBounds_1[2], height: pathBounds_1[3] };
            textWord._fontName = currentFont._name;
            textWord._fontStyle = currentFont._fontStyle;
            textWord._fontSize = this._fontSize;
            this._textWord.push(textWord);
            this._height = 0;
        }
        this._width = 0;
        this._textGlyph = [];
        var textLine1 = new TextLine();
        textLine1._text = extractedText;
        textLine1._wordCollection = this._textWord;
        textLine1._fontName = currentFont._name;
        textLine1._fontStyle = currentFont._fontStyle;
        textLine1._fontSize = textState._fontSize;
        textLine1._pageIndex = page._pageIndex;
        var pdfPath = new PdfPath();
        for (var i = 0; i < this._textWord.length; i++) {
            pdfPath.addRectangle(this._textWord[Number.parseInt(i.toString(), 10)]._bounds);
        }
        var pathBounds = pdfPath._getBounds();
        textLine1._bounds = { x: pathBounds[0], y: pathBounds[1], width: pathBounds[2], height: pathBounds[3] };
        this._textLine.push(textLine1);
    };
    _PdfContentParserHelper.prototype._processTJOperator = function (record, textState, currentFont, page, fontCollection) {
        currentFont = this._parser._getTextFont(fontCollection, textState, this._crossReference);
        var element = record._operands[0];
        var result; // eslint-disable-line
        var elements; // eslint-disable-line
        var textGlyphs = [];
        var encodedText = [];
        var updatedText = '';
        var decodedText = [];
        var isChangeOperator = false;
        currentFont = this._parser._getTextFont(fontCollection, textState, this._crossReference);
        if (this._mode === _TextProcessingMode.textLineExtraction) {
            result = this._parser._getSplitText(element[0], currentFont, record._splitText);
            var object = this._getTextElementsFromTJOperator(result.decodedList, currentFont, textState, page); // eslint-disable-line
            this._setTextLineCollection(object.tempString, currentFont, textState, page, object.extractedText);
        }
        else if (this._mode === _TextProcessingMode.textExtraction) {
            currentFont = this._parser._getTextFont(fontCollection, textState, this._crossReference);
            this._extractTextElement(element, currentFont, record._splitText);
            if (record._operator === "'") { //eslint-disable-line
                this._resultantText += '\r\n';
            }
        }
        else if (this._mode === _TextProcessingMode.redaction) {
            if (this._isContainsRedactionText) {
                var glyphs = [];
                result = this._parser._getSplitText(element[0], currentFont, record._splitText, true);
                elements = this._getTextElementsFromTJOperator(result.decodedList, currentFont, textState, page, glyphs, result.inputType);
                textGlyphs = elements.textGlyphs;
                decodedText = elements.decodedText;
                encodedText = elements.encodeText;
                updatedText = this._redaction._replacedText(textGlyphs, encodedText, element, decodedText);
                if (updatedText === element) {
                    this._isNotUpdated = true;
                }
                else {
                    isChangeOperator = true;
                }
            }
        }
        return { updatedText: updatedText, isChangeOperator: isChangeOperator };
    };
    _PdfContentParserHelper.prototype._processSingleQuoteOperator = function (record, textState, currentFont, page, fontCollection) {
        textState._carriageReturn();
        var result = this._processTjOperator(record, textState, currentFont, page, fontCollection); // eslint-disable-line
        if (typeof result === 'object' && result !== null) {
            var updatedText = result.updatedText, isChangeOperator = result.isChangeOperator;
            return { updatedText: updatedText, isChangeOperator: isChangeOperator };
        }
    };
    _PdfContentParserHelper.prototype._intersect = function (redaction, imageBounds) {
        var x1 = Math.max(redaction.x, imageBounds.x);
        var x2 = Math.min(redaction.x + redaction.width, imageBounds.x + imageBounds.width);
        var y1 = Math.max(redaction.y, imageBounds.y);
        var y2 = Math.min(redaction.y + redaction.height, imageBounds.y + imageBounds.height);
        if (x2 >= x1 && y2 >= y1) {
            return true;
        }
        return false;
    };
    _PdfContentParserHelper.prototype._multiply = function (matrix1, matrix2) {
        var matrix = [];
        matrix[0] = matrix1[0] * matrix2[0] + matrix1[1] * matrix2[2];
        matrix[1] = matrix1[0] * matrix2[1] + matrix1[1] * matrix2[3];
        matrix[2] = matrix1[2] * matrix2[0] + matrix1[3] * matrix2[2];
        matrix[3] = matrix1[2] * matrix2[1] + matrix1[3] * matrix2[3];
        matrix[4] = matrix1[4] * matrix2[0] + matrix1[5] * matrix2[2] + matrix2[4];
        matrix[5] = matrix1[4] * matrix2[1] + (matrix1[5] * matrix2[3]) + matrix2[5];
        return matrix;
    };
    _PdfContentParserHelper.prototype._processDoubleQuoteOperator = function (record, textState, currentFont, page, fontCollection) {
        textState._wordSpacing = Number(record._operands[0]);
        textState._charSpacing = Number(record._operands[1]);
        textState._carriageReturn();
        var result = this._processTjOperator(record, textState, currentFont, page, fontCollection); // eslint-disable-line
        if (typeof result === 'object' && result !== null) {
            var updatedText = result.updatedText, isChangeOperator = result.isChangeOperator;
            return { updatedText: updatedText, isChangeOperator: isChangeOperator };
        }
    };
    _PdfContentParserHelper.prototype._processRecordCollection = function (recordCollection, page, fontCollection, xObjectCollection, graphicState, imageCollection) {
        var textState;
        var red = 0;
        var green = 0;
        var blue = 0;
        var updatedText = '';
        var parser;
        var skipUntil = -1;
        var stream = new _PdfContentStream([]);
        for (var i = 0; i < recordCollection.length; i++) {
            var record = recordCollection[Number.parseInt(i.toString(), 10)];
            var token = record._operator;
            var element = record._operands;
            this._parser._processCommand(token, element, graphicState);
            textState = graphicState._state;
            i = this._processPdfRecordCollection(textState, i, updatedText, page, recordCollection, fontCollection, xObjectCollection, graphicState, parser, red, green, blue, skipUntil, stream);
        }
        if (this._mode === _TextProcessingMode.redaction) {
            stream.write('\r\n');
            return stream;
        }
        else if (this._mode === _TextProcessingMode.textExtraction) {
            return this._resultantText;
        }
        else if (this._mode === _TextProcessingMode.textLineExtraction) {
            return this._textLine;
        }
        return;
    };
    _PdfContentParserHelper.prototype._processImageRecordCollection = function (recordCollection, page, fontCollection, xObjectCollection, graphicState, callBack, mode, options, isValidCanvas) {
        return __awaiter(this, void 0, void 0, function () {
            var textState, red, green, blue, updatedText, parser, skipUntil, bounds, stream, _loop_1, this_1, i;
            var _this = this;
            return __generator(this, function (_a) {
                switch (_a.label) {
                    case 0:
                        red = 0;
                        green = 0;
                        blue = 0;
                        updatedText = '';
                        skipUntil = -1;
                        bounds = [];
                        stream = new _PdfContentStream([]);
                        _loop_1 = function (i) {
                            var record, token, element, xobject, base, pdfStream, objectId, strParts, reference, imageInfo, value, ctm, scaleMatrix, scale, transformMatrix, documentMatrix, isTextOnly, pt_1, imgRect_1, matchingRegions, _i, matchingRegions_1, region, bytes, isIntersect, pdfImage, image, image, pdfImage, image;
                            return __generator(this, function (_a) {
                                switch (_a.label) {
                                    case 0:
                                        record = recordCollection[Number.parseInt(i.toString(), 10)];
                                        token = record._operator;
                                        element = record._operands;
                                        this_1._parser._processCommand(token, element, graphicState);
                                        textState = graphicState._state;
                                        if (!(token !== 'Do')) return [3 /*break*/, 1];
                                        this_1._processPdfRecordCollection(textState, i, updatedText, page, recordCollection, fontCollection, xObjectCollection, graphicState, parser, red, green, blue, skipUntil, stream);
                                        return [3 /*break*/, 10];
                                    case 1:
                                        xobject = element[0].replace('/', '');
                                        if (!xObjectCollection.has(xobject)) return [3 /*break*/, 10];
                                        base = xObjectCollection.get(xobject);
                                        if (!base) return [3 /*break*/, 9];
                                        pdfStream = void 0;
                                        if (!!(base instanceof _ImageStructure)) return [3 /*break*/, 2];
                                        pdfStream = _getXObject(element, page, xObjectCollection, this_1, this_1._mode, graphicState);
                                        if (typeof (pdfStream) !== 'undefined') {
                                            delete base.dictionary._map.Length;
                                            delete base.dictionary._map.Filter;
                                            base.dictionary.update('Length', pdfStream.length);
                                            pdfStream.dictionary = base.dictionary;
                                            pdfStream.dictionary._updated = true;
                                            objectId = base.dictionary.objId;
                                            strParts = objectId.split(' ');
                                            reference = _PdfReference.get(Number(strParts[0]), Number(strParts[1]));
                                            this_1._document._crossReference._cacheMap.set(reference, pdfStream);
                                        }
                                        return [3 /*break*/, 9];
                                    case 2:
                                        if (!(this_1._mode === _TextProcessingMode.imageExtraction || isValidCanvas)) return [3 /*break*/, 9];
                                        imageInfo = new PdfEmbeddedImage();
                                        value = function (n) { return Number(Math.fround(n).toFixed(8)); };
                                        ctm = graphicState._state._ctm;
                                        scaleMatrix = [1, 0, 0, -1.01, 0, 1];
                                        scale = value(1.33333333333333);
                                        transformMatrix = this_1._multiply(scaleMatrix, graphicState._state._ctm);
                                        documentMatrix = [scale, 0, 0, -scale, 0,
                                            Number(value(page.size.height * scale).toFixed(4))];
                                        transformMatrix = this_1._multiply(transformMatrix, documentMatrix);
                                        if (page.rotation === PdfRotationAngle.angle90) {
                                            if (transformMatrix[0] !== 0 && transformMatrix[3] !== 0) {
                                                bounds = [Math.floor(transformMatrix[5] / 1.33333333333333), (page.size.width) - (Math.round((transformMatrix[4] / 1.33333333333333)) + transformMatrix[0] / 1.33333333333333), ctm[3],
                                                    ctm[0]];
                                            }
                                            else {
                                                bounds = [Math.floor(transformMatrix[5] / 1.33333333333333), (Math.floor(page.size.width)) -
                                                        (Math.round((transformMatrix[4] / 1.33333333333333)) +
                                                            Math.floor(transformMatrix[0] / 1.3333333333333333)),
                                                    Math.abs(ctm[1]), Math.abs(ctm[2])];
                                            }
                                        }
                                        else if (page.rotation === PdfRotationAngle.angle180) {
                                            if (transformMatrix[0] === 0 && transformMatrix[3] === 0) {
                                                bounds = [page.size.height - transformMatrix[5] / 1.33333333333333,
                                                    transformMatrix[4] / 1.33333333333333, ctm[1], ctm[2]];
                                            }
                                            else {
                                                bounds = [page.size.height - (transformMatrix[5] / 1.3333333333333333) - ctm[3],
                                                    transformMatrix[4] / 1.3333333333333333, ctm[3], ctm[0]];
                                            }
                                        }
                                        else if (page.rotation === PdfRotationAngle.angle270) {
                                            bounds = [page.size.width - (transformMatrix[4] / 1.33333333333333) - ctm[0], page.size.height - ctm[3] -
                                                    Math.round((transformMatrix[5] / 1.3333333333333333)), ctm[0], ctm[3]];
                                        }
                                        else {
                                            if (transformMatrix[0] === 0 && transformMatrix[3] === 0) {
                                                if (transformMatrix[1] < 0 && transformMatrix[2] > 0) {
                                                    bounds = [(page.size.height - (transformMatrix[5] / 1.33333333333333)), Math.round((transformMatrix[4] / 1.3333333333333333)), -(ctm[2]), (ctm[1])];
                                                }
                                                else if (transformMatrix[1] > 0 && transformMatrix[2] < 0) {
                                                    bounds = [(transformMatrix[5] / 1.33333333333333), Math.round((page.size.width -
                                                            transformMatrix[4] / 1.3333333333333333)), -(ctm[2]), -(ctm[1])];
                                                }
                                                else if (transformMatrix[1] < 0 && transformMatrix[2] < 0) {
                                                    bounds = [page.size.width - (transformMatrix[4] / 1.33333333333333) - ctm[0], page.size.height -
                                                            ctm[3] - Math.round((transformMatrix[5] / 1.3333333333333333)), ctm[0],
                                                        ctm[3]];
                                                }
                                                else {
                                                    bounds = [page.size.width - (transformMatrix[4] / 1.33333333333333) - ctm[0], page.size.height -
                                                            ctm[3] - Math.round((transformMatrix[5] / 1.3333333333333333)), ctm[0],
                                                        ctm[3]];
                                                }
                                            }
                                            else {
                                                bounds = [(transformMatrix[4] / 1.33333333333333), Math.round((transformMatrix[5] /
                                                        1.3333333333333333)), ctm[0], ctm[3]];
                                            }
                                        }
                                        isTextOnly = false;
                                        if (options && options.length > 0) {
                                            pt_1 = 1.3333;
                                            imgRect_1 = { x: bounds[0] * pt_1, y: bounds[1] * pt_1, width: bounds[2] * pt_1,
                                                height: bounds[3] * pt_1 };
                                            matchingRegions = options.filter(function (opt) {
                                                return _this._intersect({ x: opt.bounds.x * pt_1, y: opt.bounds.y * pt_1, width: opt.bounds.width * pt_1,
                                                    height: opt.bounds.height * pt_1 }, imgRect_1);
                                            });
                                            for (_i = 0, matchingRegions_1 = matchingRegions; _i < matchingRegions_1.length; _i++) {
                                                region = matchingRegions_1[_i];
                                                if (region.isTextOnly) {
                                                    isTextOnly = true;
                                                    continue;
                                                }
                                            }
                                        }
                                        if (!(this_1._mode === _TextProcessingMode.imageExtraction || !isTextOnly)) return [3 /*break*/, 9];
                                        bytes = void 0;
                                        isIntersect = void 0;
                                        if (!base._isImageMask) return [3 /*break*/, 5];
                                        pdfImage = new _PdfImage();
                                        return [4 /*yield*/, pdfImage._initializeFromImage(base._crossReference, base._stream, false, base._smask, base._mask, false)];
                                    case 3:
                                        image = _a.sent();
                                        image._imageFormat = base._imageFormat;
                                        image._canvasRenderCallback = callBack;
                                        if (mode === _TextProcessingMode.imageRedaction) {
                                            image._bounds = bounds;
                                            image._options = options;
                                            image._page = page;
                                        }
                                        return [4 /*yield*/, image._createMask(base._stream, true)];
                                    case 4:
                                        bytes = _a.sent();
                                        isIntersect = image._isIntersect;
                                        imageInfo._data = bytes;
                                        return [3 /*break*/, 8];
                                    case 5:
                                        image = new _PdfImage();
                                        return [4 /*yield*/, image._buildImage(base._crossReference, base._stream, false, callBack)];
                                    case 6:
                                        pdfImage = _a.sent();
                                        pdfImage._imageFormat = base._imageFormat;
                                        pdfImage._canvasRenderCallback = callBack;
                                        if (mode === _TextProcessingMode.imageRedaction) {
                                            pdfImage._bounds = bounds;
                                            pdfImage._options = options;
                                            pdfImage._page = page;
                                        }
                                        return [4 /*yield*/, pdfImage._createImageData(false, true)];
                                    case 7:
                                        bytes = _a.sent();
                                        isIntersect = pdfImage._isIntersect;
                                        imageInfo._data = bytes;
                                        _a.label = 8;
                                    case 8:
                                        if (isIntersect) {
                                            image = new PdfBitmap(bytes);
                                            image._key = xobject;
                                            image._reference = base._imageReference;
                                            if (base._isImageMasked) {
                                                image._maskReference = base._maskReference;
                                            }
                                            if (base._smaskReference) {
                                                image._maskReference = base._smaskReference;
                                            }
                                            image._save();
                                            if (image && image._imageStream && image._imageStream.dictionary) {
                                                this_1._document._crossReference._cacheMap.delete(image._reference);
                                                this_1._document._crossReference._cacheMap.set(image._reference, image._imageStream);
                                                image._imageStream.dictionary._updated = true;
                                                if (image._maskStream && image._maskStream.dictionary) {
                                                    this_1._document._crossReference._cacheMap.delete(image._maskReference);
                                                    this_1._document._crossReference._cacheMap.set(image._maskReference, image._maskStream);
                                                    image._maskStream.dictionary._updated = true;
                                                    image._imageStream.dictionary.set('SMask', image._maskReference);
                                                }
                                            }
                                        }
                                        else {
                                            imageInfo._resourceName = xobject;
                                            imageInfo._physicalDimension = { width: base._width, height: base._height };
                                            imageInfo._type = base._imageFormat;
                                            imageInfo._isImageInterpolated = base._isImageInterpolated;
                                            imageInfo._isSoftMasked = base._isSoftMasked;
                                            imageInfo._isImageInterpolated = base._isImageInterpolated;
                                            imageInfo._pageIndex = base._pageIndex;
                                            imageInfo._bounds = { x: bounds[0], y: bounds[1], width: bounds[2], height: bounds[3] };
                                            this_1._imageInfo.push(imageInfo);
                                        }
                                        _a.label = 9;
                                    case 9:
                                        if (this_1._mode === _TextProcessingMode.redaction) {
                                            this_1._redaction._optimizeContent(recordCollection, i, updatedText, stream);
                                        }
                                        _a.label = 10;
                                    case 10: return [2 /*return*/];
                                }
                            });
                        };
                        this_1 = this;
                        i = 0;
                        _a.label = 1;
                    case 1:
                        if (!(i < recordCollection.length)) return [3 /*break*/, 4];
                        return [5 /*yield**/, _loop_1(i)];
                    case 2:
                        _a.sent();
                        _a.label = 3;
                    case 3:
                        i++;
                        return [3 /*break*/, 1];
                    case 4:
                        if (stream._bytes.length > 0 && this._mode === _TextProcessingMode.redaction) {
                            stream.write('\r\n');
                            return [2 /*return*/, stream];
                        }
                        if (this._mode === _TextProcessingMode.imageExtraction) {
                            return [2 /*return*/, this._imageInfo];
                        }
                        return [2 /*return*/];
                }
            });
        });
    };
    _PdfContentParserHelper.prototype._processPdfRecordCollection = function (textState, index, updatedText, page, recordCollection, fontCollection, xObjectCollection, // eslint-disable-line
    graphicState, parser, red, green, blue, skipUntil, stream) {
        var isChangeOperator = false;
        var currentFont;
        var currentIndex = index;
        var record = recordCollection[Number.parseInt(index.toString(), 10)];
        var token = record._operator;
        var element = record._operands;
        switch (token) {
            case 'Tm':
                if (this._mode !== _TextProcessingMode.textExtraction) {
                    this._parser._setTextMatrix(element, textState);
                }
                if (this._mode === _TextProcessingMode.redaction) {
                    var x = textState._textMatrix[4];
                    var y = textState._textMatrix[5];
                    if (this._parser._isFoundText(x, y, page, this._redaction._redactionRegion)) {
                        this._isContainsRedactionText = true;
                    }
                    if (recordCollection.length !== index + 1 && !this._isContainsRedactionText) {
                        this._isContainsRedactionText = true;
                    }
                    if (!this._isContainsRedactionText && page.size.height === y) {
                        this._isContainsRedactionText = true;
                    }
                }
                break;
            case 'cm':
                {
                    if (this._mode === _TextProcessingMode.redaction) {
                        var x = parseFloat(element[4]);
                        var y = parseFloat(element[5]);
                        if (this._parser._isFoundText(x, y, page, this._redaction._redactionRegion)) {
                            this._isContainsRedactionText = true;
                        }
                    }
                }
                break;
            case 'BT':
                if (this._mode !== _TextProcessingMode.textExtraction) {
                    this._parser._beginText(textState, this._identityMatrix);
                }
                break;
            case 'ET':
                if (this._mode === _TextProcessingMode.textExtraction) {
                    this._resultantText += '\r\n';
                }
                else if (this._mode === _TextProcessingMode.redaction) {
                    this._isContainsRedactionText = false;
                    this._xPosition = 0;
                    this._yPosition = 0;
                }
                break;
            case 'Tf':
                this._parser._setFont(element, textState);
                break;
            case 'Tc':
                if (this._mode !== _TextProcessingMode.textExtraction) {
                    this._parser._setCharSpacing(element, textState);
                }
                break;
            case 'Tw':
                if (this._mode !== _TextProcessingMode.textExtraction) {
                    this._parser._setWordSpacing(element, textState);
                }
                break;
            case 'Tz':
                if (this._mode !== _TextProcessingMode.textExtraction) {
                    this._parser._setTextHorizontalScale(element, textState);
                }
                break;
            case 'TL':
                if (this._mode !== _TextProcessingMode.textExtraction) {
                    this._parser._updateTextLeading(element, textState);
                }
                break;
            case 'Td':
                if (this._mode !== _TextProcessingMode.textExtraction) {
                    this._parser._moveTextPlacement(element, textState);
                }
                if (this._mode === _TextProcessingMode.redaction) {
                    this._xPosition = this._xPosition + parseFloat(element[0]);
                    this._yPosition = this._yPosition - parseFloat(element[1]);
                    if (this._parser._isFoundText(this._xPosition, this._yPosition, page, this._redaction._redactionRegion)) {
                        this._isContainsRedactionText = true;
                    }
                    if (recordCollection.length !== index + 1 && !this._isContainsRedactionText) {
                        var temp = recordCollection[index + 1]._operator;
                        if (temp === 'Tj' || temp === 'TJ' || temp === '"' || temp === "'") { // eslint-disable-line
                            this._isContainsRedactionText = true;
                        }
                    }
                }
                break;
            case 'TD':
                if (this._mode !== _TextProcessingMode.textExtraction) {
                    this._parser._moveTextPlacementAndSetLeading(element, textState);
                }
                if (this._mode === _TextProcessingMode.redaction) {
                    this._xPosition = this._xPosition + parseFloat(element[0]);
                    this._yPosition = this._yPosition - parseFloat(element[1]);
                    if (this._parser._isFoundText(this._xPosition, this._yPosition, page, this._redaction._redactionRegion)) {
                        this._isContainsRedactionText = true;
                    }
                    if (recordCollection.length !== index + 1 && !this._isContainsRedactionText) {
                        var temp = recordCollection[index + 1]._operator;
                        if (temp === 'Tj' || temp === 'TJ' || temp === '"' || temp === "'") { // eslint-disable-line
                            this._isContainsRedactionText = true;
                        }
                    }
                }
                break;
            case 'Ts':
                if (this._mode !== _TextProcessingMode.textExtraction) {
                    this._parser._setTextRise(element, textState);
                }
                break;
            case 'Tj':
                {
                    if (this._mode !== _TextProcessingMode.imageExtraction) {
                        var result = this._processTjOperator(record, textState, currentFont, page, fontCollection); // eslint-disable-line
                        if (record._operands) {
                            if (typeof result === 'object' && result !== null) {
                                updatedText = result.updatedText;
                                isChangeOperator = result.isChangeOperator;
                            }
                        }
                    }
                    break;
                }
            case 'TJ':
                {
                    if (this._mode !== _TextProcessingMode.imageExtraction) {
                        var result = this._processTJOperator(record, textState, currentFont, page, fontCollection); // eslint-disable-line
                        if (typeof result === 'object' && result !== null) {
                            updatedText = result.updatedText;
                            isChangeOperator = result.isChangeOperator;
                        }
                    }
                    break;
                }
            case "'": // eslint-disable-line
                {
                    if (this._mode !== _TextProcessingMode.imageExtraction) {
                        var result = this._processSingleQuoteOperator(record, textState, currentFont, page, // eslint-disable-line 
                        fontCollection);
                        if (typeof result === 'object' && result !== null) {
                            updatedText = result.updatedText;
                            isChangeOperator = result.isChangeOperator;
                        }
                    }
                    break;
                }
            case '"':
                {
                    if (this._mode !== _TextProcessingMode.imageExtraction) {
                        var result = this._processDoubleQuoteOperator(record, textState, currentFont, page, // eslint-disable-line
                        fontCollection);
                        if (typeof result === 'object' && result !== null) {
                            updatedText = result.updatedText;
                            isChangeOperator = result.isChangeOperator;
                        }
                    }
                    break;
                }
            case 'T*':
                if (this._mode === _TextProcessingMode.textExtraction) {
                    this._resultantText += '\r\n';
                }
                else {
                    this._parser._setNewLineWithLeading(textState);
                }
                break;
            case 'RG':
            case 'k':
            case 'g':
            case 'rg':
                red = Number(element[0]);
                green = Number(element[1]);
                blue = Number(element[2]);
                textState._textColor = { r: red, g: green, b: blue };
                break;
            case 'Do':
                {
                    var xobject = element[0].replace('/', '');
                    if (xObjectCollection.has(xobject)) {
                        var base = xObjectCollection.get(xobject); //eslint-disable-line
                        if (base) {
                            if (this._mode === _TextProcessingMode.textExtraction || this._mode === _TextProcessingMode.textLineExtraction) {
                                _getXObject(element, page, xObjectCollection, this, this._mode, graphicState);
                            }
                            else if (this._mode === _TextProcessingMode.redaction) {
                                var pdfStream = _getXObject(element, page, xObjectCollection, this, this._mode, graphicState); // eslint-disable-line
                                delete base.dictionary._map.Length;
                                delete base.dictionary._map.Filter;
                                base.dictionary.update('Length', pdfStream.length);
                                pdfStream.dictionary = base.dictionary;
                                pdfStream.dictionary._updated = true;
                                var objectId = base.dictionary.objId; // eslint-disable-line
                                var strParts = objectId.split(' ');
                                var reference = _PdfReference.get(Number(strParts[0]), Number(strParts[1]));
                                this._document._crossReference._cacheMap.set(reference, pdfStream);
                            }
                        }
                    }
                    break;
                }
            case 're':
                {
                    parser = new _PdfShapeParser();
                    var numberArray = element.map(function (value) {
                        return Number(value);
                    });
                    if (_isArrayEqual(page.mediaBox, numberArray)) {
                        break;
                    }
                    var records = parser._processRectangle(recordCollection, index, element);
                    if (record && records.length > 0) {
                        recordCollection.splice.apply(recordCollection, [index--, 1].concat(records));
                    }
                    break;
                }
            case 'm':
                parser = new _PdfShapeParser();
                skipUntil = parser._findRedactPath(recordCollection, index, page, this._redaction, this._mode, stream);
                if (skipUntil !== -1) {
                    index = skipUntil;
                }
                break;
        }
        if (this._mode === _TextProcessingMode.redaction && currentIndex === index) {
            if (!isChangeOperator) {
                updatedText = '';
            }
            this._redaction._optimizeContent(recordCollection, index, updatedText, stream);
            isChangeOperator = false;
        }
        if (this._mode !== _TextProcessingMode.imageExtraction) {
            return index;
        }
    };
    _PdfContentParserHelper.prototype._extractTextElement = function (elements, currentFont, inputText) {
        var decodedText = _decodeEncodedText(elements, currentFont, inputText);
        this._resultantText += decodedText;
    };
    _PdfContentParserHelper.prototype._getTextElementsFromTjOperator = function (decodedList, currentFont, textState, page, textGlyphs, inputType) {
        this._textWord = [];
        var tempString = '';
        var text = decodedList;
        var previousRect = { x: 0, y: 0, width: 0, height: 0 };
        var decodedText = [];
        var encodedText = [];
        var extractedText = '';
        var index = 0;
        var hex = [];
        if (text.length > 0) {
            if (typeof (textGlyphs) !== 'undefined') {
                if (inputType[0] !== ' ') {
                    hex = this._parser._splitHexString(inputType[0]);
                }
                var result = this._parser._getTextContentItem(currentFont, text[0], 0, textState, page, tempString, previousRect, extractedText, this, textGlyphs, hex, index, encodedText); // eslint-disable-line
                decodedText[0] = '(' + result.extractedText + ')';
                encodedText = result.encodedText;
                extractedText = result.extractedText;
                return { textGlyphs: textGlyphs, decodedText: decodedText, encodedText: encodedText };
            }
            else {
                var result = this._parser._getTextContentItem(currentFont, text[0], 0, textState, page, tempString, previousRect, extractedText, this); //eslint-disable-line
                tempString = result.tempString;
                extractedText = result.extractedText;
                this._fontSize = result.fontSize;
                return { tempString: tempString, extractedText: extractedText };
            }
        }
    };
    _PdfContentParserHelper.prototype._getTextElementsFromTJOperator = function (decodedList, currentFont, textState, page, textGlyphs, inputType) {
        var textValues = [];
        this._textWord = [];
        var tempString = '';
        textValues = decodedList;
        var iszerspace = false;
        var text = '';
        var str = '';
        var previousRect = { x: 0, y: 0, width: 0, height: 0 };
        var decodedText = [];
        var encodedText = [];
        var index = 0;
        var i = 0;
        var hex = [];
        var extractedText = '';
        var spaceFactor = ((currentFont._vertical ? 1 : -1) * textState._fontSize) / 1000;
        for (var j = 0; j < textValues.length; j++) {
            var word = textValues[Number.parseInt(j.toString(), 10)];
            var digit = Number(word); // eslint-disable-line
            if (digit || digit === 0) {
                if (typeof (textGlyphs) !== 'undefined') {
                    if (j > 0 && inputType[j - 1] !== ' ') {
                        hex = this._parser._splitHexString(inputType[j - 1]);
                    }
                    var result = this._parser._getTextContentItem(currentFont, text, digit * spaceFactor, textState, page, tempString, previousRect, extractedText, this, textGlyphs, hex, index, encodedText); // eslint-disable-line
                    textGlyphs = result.textGlyphs;
                    extractedText = result.extractedText;
                    encodedText = result.encodedText;
                    index = result.index;
                    extractedText = '';
                    decodedText[i++] = '(' + result.extractedText + ')';
                    decodedText[i++] = word;
                }
                else {
                    var result = this._parser._getTextContentItem(currentFont, text, digit * spaceFactor, textState, page, tempString, previousRect, extractedText, this); // eslint-disable-line
                    tempString = result.tempString;
                    extractedText = result.extractedText;
                    this._fontSize = result.fontSize;
                    previousRect = result.previousRect;
                }
            }
            else if (digit !== 0) {
                text = word;
                if (iszerspace) {
                    text = str + text;
                    iszerspace = false;
                }
            }
            else {
                iszerspace = true;
                str = text;
            }
        }
        if (typeof (textGlyphs) !== 'undefined') {
            if (inputType[textValues.length - 1] !== ' ') {
                hex = this._parser._splitHexString(inputType[textValues.length - 1]);
            }
            var result = this._parser._getTextContentItem(currentFont, text, 0, textState, page, // eslint-disable-line
            tempString, previousRect, extractedText, this, textGlyphs, hex, index, encodedText);
            decodedText[Number.parseInt(i.toString(), 10)] = '(' + result.extractedText + ')';
            var encodeText = result.encodedText;
            return { textGlyphs: textGlyphs, decodedText: decodedText, encodeText: encodeText };
        }
        else {
            var result = this._parser._getTextContentItem(currentFont, text, 0, textState, page, // eslint-disable-line
            tempString, previousRect, extractedText, this);
            tempString = result.tempString;
            extractedText = result.extractedText;
            this._fontSize = result.fontSize;
            return { tempString: tempString, extractedText: extractedText };
        }
    };
    _PdfContentParserHelper.prototype._splitWords = function (glyph, tempString, fontName, fontStyle, page, rotation, textColor, fontSize, textBounds, previousRect) {
        var _this = this;
        var isSpace = false;
        if (/\s/.test(glyph)) {
            isSpace = true;
        }
        var currentRect = textBounds;
        var addTextWord = function (text, glyphs, width) {
            var textWord = new TextWord();
            textWord._text = text;
            textWord._glyphs = glyphs;
            var pdfPath = new PdfPath();
            for (var i = 0; i < glyphs.length; i++) {
                pdfPath.addRectangle(glyphs[Number.parseInt(i.toString(), 10)]._bounds);
            }
            var pathBounds = pdfPath._getBounds();
            textWord._bounds = { x: pathBounds[0], y: pathBounds[1], width: pathBounds[2], height: pathBounds[3] };
            textWord._fontName = fontName;
            textWord._fontStyle = fontStyle;
            textWord._fontSize = fontSize;
            _this._textWord.push(textWord);
        };
        if (isSpace) {
            if (tempString) {
                if (page.rotation === PdfRotationAngle.angle90 || page.rotation === PdfRotationAngle.angle270 || rotation === 90) {
                    addTextWord(tempString, this._textGlyph, this._height);
                }
                else {
                    addTextWord(tempString, this._textGlyph, this._width);
                }
                this._textGlyph = [];
                tempString = '';
            }
            var textGlyph = new TextGlyph();
            textGlyph._text = glyph;
            textGlyph._bounds = currentRect;
            textGlyph._fontName = fontName;
            textGlyph._fontStyle = fontStyle;
            textGlyph._fontSize = fontSize;
            textGlyph._color = textColor;
            if (page.rotation !== PdfRotationAngle.angle0) {
                textGlyph._isRotated = true;
            }
            else {
                textGlyph._isRotated = false;
            }
            this._textGlyph.push(textGlyph);
            if (page.rotation === PdfRotationAngle.angle90 || page.rotation === PdfRotationAngle.angle270 || rotation === 90) {
                addTextWord(glyph, this._textGlyph, currentRect.height);
            }
            else {
                addTextWord(glyph, this._textGlyph, currentRect.width);
            }
            this._width = 0;
            this._height = 0;
            this._textGlyph = [];
            previousRect = null;
        }
        else if (previousRect !== null && previousRect.width > 0) {
            var spacingFactor = currentRect.height * 0.07;
            if (spacingFactor < 2) {
                spacingFactor = 2;
            }
            var difference = void 0;
            if (page.rotation === PdfRotationAngle.angle90) {
                difference = previousRect.y + previousRect.height - currentRect.y;
            }
            else if (page.rotation === PdfRotationAngle.angle270 || rotation === 90) {
                difference = currentRect.y + currentRect.height - previousRect.y;
            }
            else if (page.rotation === PdfRotationAngle.angle180) {
                difference = currentRect.x + currentRect.width - previousRect.x;
            }
            else {
                difference = previousRect.x + previousRect.width - currentRect.x;
            }
            if (difference > 0) {
                if (spacingFactor === 2) {
                    spacingFactor = 2.5;
                }
            }
            if (Math.abs(difference) > spacingFactor) {
                if (page.rotation === PdfRotationAngle.angle90 || page.rotation === PdfRotationAngle.angle270) {
                    addTextWord(tempString, this._textGlyph, this._height);
                }
                else {
                    addTextWord(tempString, this._textGlyph, this._width);
                }
                this._width = 0;
                this._height = 0;
                this._textGlyph = [];
                tempString = '';
                previousRect = { x: 0, y: 0, width: 0, height: 0 };
            }
        }
        if (!isSpace) {
            var textGlyph = new TextGlyph();
            textGlyph._text = glyph;
            textGlyph._bounds = currentRect;
            textGlyph._fontName = fontName;
            textGlyph._fontStyle = fontStyle;
            textGlyph._fontSize = fontSize;
            textGlyph._color = textColor;
            if (page.rotation !== PdfRotationAngle.angle0) {
                textGlyph._isRotated = true;
            }
            else {
                textGlyph._isRotated = false;
            }
            textGlyph._isRotated = false;
            this._textGlyph.push(textGlyph);
            if (page.rotation === PdfRotationAngle.angle90 || page.rotation === PdfRotationAngle.angle270 || rotation === 90) {
                this._height += currentRect.height;
            }
            else {
                this._width += currentRect.width;
            }
            tempString += glyph;
        }
        return { tempString: tempString, previousRect: previousRect };
    };
    return _PdfContentParserHelper;
}());
export { _PdfContentParserHelper };
