/*---------------------------------------------------------------------------------------------
* Copyright (c) Bentley Systems, Incorporated. All rights reserved.
* See LICENSE.md in the project root for license terms and full copyright notice.
*--------------------------------------------------------------------------------------------*/
/** @packageDocumentation
 * @module StatusBar
 */
import "./TileLoadingIndicator.scss";
import classnames from "classnames";
import * as React from "react";
import { Logger } from "@itwin/core-bentley";
import { IModelApp } from "@itwin/core-frontend";
import { ProgressLinear } from "@itwin/itwinui-react";
import { UiFramework } from "../../UiFramework";
/** TileLoadingIndicator React component
 * @public
 */
export class TileLoadingIndicator extends React.PureComponent {
    constructor(props) {
        super(props);
        this._refreshState = (vp) => {
            const requested = vp.numRequestedTiles;
            const ready = vp.numReadyTiles;
            const total = ready + requested;
            const pctComplete = (total > 0) ? (ready / total) * 100 : /* istanbul ignore next */ 100;
            let enabled = this.state.enabled;
            let finished = this.state.finished;
            // istanbul ignore else
            if (!enabled && total !== 0 && pctComplete !== 100)
                enabled = true;
            if (enabled && (total === 0 || pctComplete === 100))
                enabled = false;
            if (pctComplete === 100 && !finished) {
                finished = true;
                Logger.logTrace(UiFramework.loggerCategory(this), `Tiles Finished Loading`);
                Logger.logTrace(UiFramework.loggerCategory(this), `Tiles Load Report (tiles finished / tiles requested):  ${ready} / ${total}`);
            }
            // istanbul ignore else
            if (pctComplete !== 100 && finished)
                finished = false;
            this.setState({ label: `${ready} / ${total}`, progress: pctComplete, enabled, finished });
        };
        this._update = (vp) => {
            // set progress animation before the next repaint.
            setTimeout(() => this._refreshState(vp));
        };
        this._onViewOpen = (vp) => {
            // istanbul ignore next
            this._removeOnRenderListener && this._removeOnRenderListener();
            this._removeOnRenderListener = vp.onRender.addListener(this._update);
        };
        this.state = { label: "", progress: 0, enabled: false, finished: true };
    }
    componentDidMount() {
        // istanbul ignore next
        if (!IModelApp.viewManager)
            return;
        // get selected viewport
        const vp = IModelApp.viewManager.selectedView;
        // if view exists bind update routine to onRender loop, otherwise do so once the onViewOpen event runs
        // istanbul ignore else
        if (vp) {
            this._onViewOpen(vp);
        }
        else {
            this._removeViewOpenListener = IModelApp.viewManager.onViewOpen.addListener(this._onViewOpen);
        }
    }
    componentWillUnmount() {
        // istanbul ignore next
        if (!IModelApp.viewManager)
            return;
        // istanbul ignore next
        if (this._removeViewOpenListener)
            this._removeViewOpenListener();
        // istanbul ignore else
        if (this._removeOnRenderListener)
            this._removeOnRenderListener();
    }
    /** Renders TileLoadingIndicator */
    render() {
        var _a;
        const classes = classnames("uifw-tile-loading-bar", this.state.enabled && "uifw-tile-loading-bar-visible", 
        // eslint-disable-next-line deprecation/deprecation
        ((_a = this.props.isInFooterMode) !== null && _a !== void 0 ? _a : true) && "nz-footer-mode", this.props.className);
        return (React.createElement("div", { className: classes, style: this.props.style },
            React.createElement("span", null, this.state.label),
            React.createElement(ProgressLinear, { value: this.state.progress })));
    }
}
//# sourceMappingURL=TileLoadingIndicator.js.map