var __extends = (this && this.__extends) || (function () {
    var extendStatics = function (d, b) {
        extendStatics = Object.setPrototypeOf ||
            ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
            function (d, b) { for (var p in b) if (Object.prototype.hasOwnProperty.call(b, p)) d[p] = b[p]; };
        return extendStatics(d, b);
    };
    return function (d, b) {
        if (typeof b !== "function" && b !== null)
            throw new TypeError("Class extends value " + String(b) + " is not a constructor or null");
        extendStatics(d, b);
        function __() { this.constructor = d; }
        d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
    };
})();
var __assign = (this && this.__assign) || function () {
    __assign = Object.assign || function(t) {
        for (var s, i = 1, n = arguments.length; i < n; i++) {
            s = arguments[i];
            for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
                t[p] = s[p];
        }
        return t;
    };
    return __assign.apply(this, arguments);
};
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
    var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
    if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
    else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
    return c > 3 && r && Object.defineProperty(target, key, r), r;
};
import React from 'react';
import debounce from 'lodash.debounce';
import { isTestEnv } from '../../lib/currentEnvironment.js';
import { CommonWrapper } from '../../internal/CommonWrapper/index.js';
import { rootNode } from '../../lib/rootNode/index.js';
import { createPropsGetter } from '../../lib/createPropsGetter.js';
import { GlobalLoaderView } from './GlobalLoaderView.js';
export var GlobalLoaderDataTids = {
    root: 'GlobalLoader',
};
var currentGlobalLoader;
/**
 * Универсальный индикатор обмена данными с сервером.
 * Он появляется у верхней границы экрана и выглядит как тоненькая полоска, окрашенная в фирменный цвет продукта.
 *
 * Глобальный лоадер может быть только один в приложении. Поэтому каждый новый экземпляр компонента заменяет предыдущий экземпляр и начинает перехватывать статические методы.
 *
 * Предполагается монтирование компонента в единственном месте. И управление им через статические методы, либо через пропсы.
 *
 */
var GlobalLoader = /** @class */ (function (_super) {
    __extends(GlobalLoader, _super);
    function GlobalLoader(props) {
        var _this = _super.call(this, props) || this;
        _this.getProps = createPropsGetter(GlobalLoader_1.defaultProps);
        _this.startTask = debounce(function () {
            var _a, _b;
            _this.setState({ visible: true });
            (_b = (_a = _this.props).onStart) === null || _b === void 0 ? void 0 : _b.call(_a);
        }, _this.getProps().delayBeforeShow);
        _this.stopTask = debounce(function () {
            var _a, _b;
            _this.setState({ visible: false, successAnimationInProgress: false, started: false });
            (_b = (_a = _this.props).onDone) === null || _b === void 0 ? void 0 : _b.call(_a);
        }, _this.getProps().delayBeforeHide);
        _this.resumeTaskAfterSuccessAnimation = debounce(function () {
            _this.setActive();
        }, _this.getProps().delayBeforeHide);
        _this.setActive = function () {
            _this.startTask.cancel();
            if (_this.state.successAnimationInProgress) {
                _this.resumeTaskAfterSuccessAnimation();
            }
            else {
                _this.setState({ visible: false, done: false, rejected: false, accept: false, started: true });
                if (_this.getProps().rejected) {
                    _this.setReject(true);
                }
                else {
                    _this.stopTask.cancel();
                    _this.startTask();
                }
            }
        };
        _this.setDone = function () {
            if (!_this.state.started) {
                return;
            }
            _this.setState({ done: true, successAnimationInProgress: true });
            _this.startTask.cancel();
            _this.resumeTaskAfterSuccessAnimation.cancel();
            _this.stopTask();
        };
        _this.setReject = function (reject) {
            var _a, _b, _c, _d;
            if (!_this.state.visible && (_this.state.started || _this.getProps().active)) {
                _this.setState({ visible: true });
            }
            _this.startTask.cancel();
            _this.stopTask.cancel();
            if (reject) {
                (_b = (_a = _this.props).onReject) === null || _b === void 0 ? void 0 : _b.call(_a);
            }
            else if (_this.state.rejected) {
                _this.setState({ accept: true });
                (_d = (_c = _this.props).onAccept) === null || _d === void 0 ? void 0 : _d.call(_c);
            }
            _this.setState({ rejected: reject });
        };
        _this.kill = function () {
            _this.stopTask.cancel();
            _this.startTask.cancel();
            _this.resumeTaskAfterSuccessAnimation.cancel();
            _this.setState({
                dead: true,
            });
        };
        _this.state = {
            started: false,
            visible: false,
            done: false,
            rejected: false,
            accept: false,
            dead: false,
            successAnimationInProgress: false,
            expectedResponseTime: _this.getProps().expectedResponseTime,
        };
        return _this;
    }
    GlobalLoader_1 = GlobalLoader;
    GlobalLoader.prototype.componentDidMount = function () {
        currentGlobalLoader === null || currentGlobalLoader === void 0 ? void 0 : currentGlobalLoader.kill();
        // eslint-disable-next-line @typescript-eslint/no-this-alias
        currentGlobalLoader = this;
        var _a = this.getProps(), active = _a.active, rejected = _a.rejected;
        if (active) {
            this.setActive();
        }
        if (rejected) {
            this.setReject(true);
        }
    };
    GlobalLoader.prototype.componentWillUnmount = function () {
        currentGlobalLoader = null;
    };
    GlobalLoader.prototype.componentDidUpdate = function (prevProps) {
        var _a = this.getProps(), expectedResponseTime = _a.expectedResponseTime, rejected = _a.rejected, active = _a.active;
        if (expectedResponseTime !== prevProps.expectedResponseTime) {
            this.setState({ expectedResponseTime: expectedResponseTime });
        }
        if (rejected !== prevProps.rejected) {
            this.setReject(rejected);
        }
        if (active !== prevProps.active) {
            if (active) {
                this.setActive();
            }
            else {
                this.setDone();
            }
        }
    };
    GlobalLoader.prototype.render = function () {
        var status = 'standard';
        if (this.state.done) {
            status = 'success';
        }
        else if (this.state.rejected) {
            status = 'error';
        }
        else if (this.state.accept) {
            status = 'accept';
        }
        var _a = this.getProps(), delayBeforeHide = _a.delayBeforeHide, disableAnimations = _a.disableAnimations;
        return (!this.state.dead &&
            this.state.visible && (React.createElement(CommonWrapper, __assign({ rootNodeRef: this.setRootNode }, this.props),
            React.createElement(GlobalLoaderView, { expectedResponseTime: this.state.expectedResponseTime, delayBeforeHide: delayBeforeHide, status: status, "data-tid": GlobalLoaderDataTids.root, disableAnimations: disableAnimations }))));
    };
    GlobalLoader.prototype.updateExpectedResponseTime = function (expectedResponseTime) {
        this.setState({ expectedResponseTime: expectedResponseTime });
    };
    var GlobalLoader_1;
    GlobalLoader.__KONTUR_REACT_UI__ = 'GlobalLoader';
    GlobalLoader.displayName = 'GlobalLoader';
    GlobalLoader.defaultProps = {
        expectedResponseTime: 1000,
        delayBeforeShow: 1000,
        delayBeforeHide: 1000,
        rejected: false,
        active: false,
        disableAnimations: isTestEnv,
    };
    /**
     * Запускает анимацию лоадера. <br />
     * Равносильно установке пропа `active = true`.
     *
     * @public
     */
    GlobalLoader.start = function (expectedResponseTime) {
        currentGlobalLoader === null || currentGlobalLoader === void 0 ? void 0 : currentGlobalLoader.setActive();
        if (typeof expectedResponseTime === 'number') {
            currentGlobalLoader === null || currentGlobalLoader === void 0 ? void 0 : currentGlobalLoader.updateExpectedResponseTime(expectedResponseTime);
        }
    };
    /**
     * Показывает анимацию успешного завершения загрузки. <br />
     * Равносильно установке пропа `active = false`.
     *
     * @public
     */
    GlobalLoader.done = function () {
        currentGlobalLoader === null || currentGlobalLoader === void 0 ? void 0 : currentGlobalLoader.setDone();
    };
    /**
     * Переключает анимацию лоадера в состояние бегающей полоски. <br />
     * Равносильно установке пропа `rejected = true`.
     *
     * @public
     */
    GlobalLoader.reject = function () {
        currentGlobalLoader === null || currentGlobalLoader === void 0 ? void 0 : currentGlobalLoader.setReject(true);
    };
    /**
     * Возвращает лоадер из состояния бегающей полоски в обычное и продолжает анимацию с того места, на котором она была прервана. <br />
     * Равносильно установке пропа `rejected = false`.
     *
     * @public
     */
    GlobalLoader.accept = function () {
        currentGlobalLoader === null || currentGlobalLoader === void 0 ? void 0 : currentGlobalLoader.setReject(false);
    };
    GlobalLoader = GlobalLoader_1 = __decorate([
        rootNode
    ], GlobalLoader);
    return GlobalLoader;
}(React.Component));
export { GlobalLoader };
//# sourceMappingURL=GlobalLoader.js.map