"use strict";
/*---------------------------------------------------------------------------------------------
* Copyright (c) Bentley Systems, Incorporated. All rights reserved.
* See LICENSE.md in the project root for license terms and full copyright notice.
*--------------------------------------------------------------------------------------------*/
/** @packageDocumentation
 * @module WebGL
 */
Object.defineProperty(exports, "__esModule", { value: true });
exports.VisibleTileFeatures = void 0;
const core_bentley_1 = require("@itwin/core-bentley");
const core_common_1 = require("@itwin/core-common");
const ShaderProgram_1 = require("./ShaderProgram");
/** Iterates over features visible in tiles selected for display by a Target by inspecting its RenderCommands.
 * @internal
 */
class VisibleTileFeatures {
    constructor(commands, options, target, iModel) {
        this.includeNonLocatable = true === options.includeNonLocatable;
        this.renderCommands = commands;
        this.target = target;
        this.iModel = iModel;
        target.compositor.preDraw();
    }
    [Symbol.iterator]() {
        return iterator(this);
    }
}
exports.VisibleTileFeatures = VisibleTileFeatures;
const clippedPasses = [
    15 /* RenderPass.BackgroundMap */,
    1 /* RenderPass.OpaqueLayers */,
    2 /* RenderPass.OpaqueLinear */,
    3 /* RenderPass.OpaquePlanar */,
    5 /* RenderPass.OpaqueGeneral */,
    7 /* RenderPass.TranslucentLayers */,
    8 /* RenderPass.Translucent */,
    11 /* RenderPass.OverlayLayers */,
];
function isFeatureVisible(feature, target, includeNonLocatable) {
    const ovrs = target.currentFeatureSymbologyOverrides;
    if (!ovrs)
        return true;
    const app = target.currentBranch.getFeatureAppearance(ovrs, feature.elementId.lower, feature.elementId.upper, feature.subCategoryId.lower, feature.subCategoryId.upper, feature.geometryClass, feature.modelId.lower, feature.modelId.upper, core_common_1.BatchType.Primary, feature.animationNodeId);
    return undefined !== app && (includeNonLocatable || !app.nonLocatable);
}
function* commandIterator(features, pass) {
    const commands = features.renderCommands.getCommands(pass);
    const executor = new ShaderProgram_1.ShaderProgramExecutor(features.target, pass);
    try {
        for (const command of commands) {
            if (command.opcode !== "drawPrimitive")
                command.execute(executor);
            if (command.opcode !== "pushBatch")
                continue;
            const ovrs = command.batch.getOverrides(features.target);
            if (ovrs.allHidden)
                continue;
            const scratchFeature = core_common_1.PackedFeature.createWithIndex();
            const table = command.batch.featureTable;
            for (const feature of table.iterable(scratchFeature)) {
                if (!ovrs.anyOverridden || isFeatureVisible(feature, features.target, features.includeNonLocatable)) {
                    yield {
                        elementId: core_bentley_1.Id64.fromUint32PairObject(feature.elementId),
                        subCategoryId: core_bentley_1.Id64.fromUint32PairObject(feature.subCategoryId),
                        geometryClass: feature.geometryClass,
                        modelId: core_bentley_1.Id64.fromUint32PairObject(feature.modelId),
                        iModel: command.batch.batchIModel ?? features.iModel,
                    };
                }
            }
        }
    }
    finally {
        executor.dispose();
    }
}
function* iterator(features) {
    try {
        features.target.pushViewClip();
        for (const pass of clippedPasses)
            yield* commandIterator(features, pass);
    }
    finally {
        features.target.popViewClip();
    }
}
//# sourceMappingURL=VisibleTileFeatures.js.map