"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
var Wave = (function (_super) {
    __extends(Wave, _super);
    function Wave() {
        var _this = _super !== null && _super.apply(this, arguments) || this;
        _this.duration = 1000;
        _this.waveMethod = 'rotate';
        _this.loop = -1;
        _this.autoPlay = true;
        _this.revert = false;
        _this._oldProps = {};
        return _this;
    }
    Wave.prototype.mounted = function () {
        this._startTime = 0;
        engine.copyProp(this._oldProps, this.host, oldPropFields);
        if (this.autoPlay) {
            this.play();
        }
    };
    Wave.prototype.sleep = function () {
        if (this.revert) {
            this.revertProps();
        }
    };
    Wave.prototype.update = function (t) {
        if (this._playing) {
            if (!this._startTime) {
                this._startTime = t;
            }
            var _a = this, duration_1 = _a.duration, waveParams = _a.waveParams, _waveAlgorithm = _a._waveAlgorithm, host = _a.host, _oldProps = _a._oldProps;
            var pass = (t - this._startTime) % duration_1;
            var r = pass / duration_1 * PI2;
            var loopCounting = Math.floor((t - this._startTime) / duration_1);
            if (loopCounting != this._loopCounting) {
                this._loopCounting = loopCounting;
                if (this.onLoopEnd()) {
                    r = PI2;
                }
            }
            var t2 = void 0;
            if (this.ratio) {
                var ratio = this.ratio.split(',').map(function (item) { return parseFloat(item); });
                if (ratio.length === 2) {
                    var begin = ratio[0], end = ratio[1];
                    if (end >= begin) {
                        var tr = r / PI2;
                        if (tr >= begin && tr < end) {
                            t2 = r / (end - begin);
                        }
                        else {
                            t2 = 0;
                        }
                    }
                    else {
                        t2 = 0;
                    }
                }
                else {
                    t2 = 0;
                }
            }
            else {
                t2 = r;
            }
            var params_1 = waveParams ? (waveParams.split(',').map(function (item) { return parseFloat(item); })) : [];
            var props_1 = _waveAlgorithm.apply(void 0, params_1.concat([t2]));
            if (props_1.hasOwnProperty('x')) {
                host.x = (props_1.x || 0) + _oldProps.x;
            }
            if (props_1.hasOwnProperty('y')) {
                host.y = (props_1.y || 0) + _oldProps.y;
            }
            if (props_1.hasOwnProperty('sx')) {
                host.scaleX = props_1.sx;
            }
            if (props_1.hasOwnProperty('sy')) {
                host.scaleY = props_1.sy;
            }
            if (props_1.hasOwnProperty('r')) {
                host.rotation = props_1.r;
            }
            if (props_1.hasOwnProperty('alpha')) {
                host.alpha = props_1.alpha;
            }
        }
    };
    Wave.prototype.onLoopEnd = function () {
        if (this.loop < 0) {
        }
        else if (this._loopCounting < this.loop) {
        }
        else {
            this._playing = false;
            return true;
        }
    };
    Wave.prototype.play = function () {
        this._loopCounting = 0;
        this._playing = true;
        this._startTime = 0;
    };
    Wave.prototype.stop = function (revert) {
        if (revert === void 0) { revert = false; }
        this._playing = false;
        if (revert) {
            this.revertProps();
        }
    };
    Wave.prototype.revertProps = function () {
        for (var key_1 in this._oldProps) {
            var prop = this._oldProps[key_1];
            if (typeof prop === 'object') {
                engine.injectProp(this.host[key_1], prop);
            }
            else {
                this.host[key_1] = prop;
            }
        }
    };
    Wave.prototype.onModify = function (value, key, oldValue) {
        switch (key) {
            case 'waveMethod':
                this._waveAlgorithm = waveLibs[this.waveMethod];
                break;
        }
    };
    Wave.id = 'wave';
    __decorate([
        engine.dirtyFieldTrigger
    ], Wave.prototype, "waveMethod", void 0);
    return Wave;
}(engine.ScriptBase));
exports.default = Wave;
var PI2 = Math.PI * 2;
var oldPropFields = {
    x: 'x',
    y: 'y',
    scaleX: 'scaleX',
    scaleY: 'scaleY',
    alpha: 'alpha',
    rotation: 'rotation',
};
var cos = Math.cos, sin = Math.sin, PI = Math.PI;
var waveLibs = {
    round: function (radius, t) {
        return { x: cos(t) * radius, y: sin(t) * radius };
    },
    cosWave: function (h, t) {
        return { x: cos(t) * h, y: 0 };
    },
    sinWave: function (h, t) {
        h = h || 1;
        return { x: 0, y: sin(t) * h };
    },
    rotate: function (t) {
        return { r: 360 * t / PI / 2 };
    },
    shake: function (angle, count, t) {
        return { r: sin(t * count) * angle };
    },
    breath: function (scale, t) {
        if (scale === void 0) { scale = 0.1; }
        return { sx: sin(t) * scale + 1, sy: -sin(t + PI / 4) * scale + 1 };
    },
    zoom: function (scale, t) {
        if (scale === void 0) { scale = 0.1; }
        return { sx: sin(t) * scale + 1, sy: sin(t) * scale + 1 };
    },
    fade: function (base, scale, t) {
        if (base === void 0) { base = 0; }
        if (scale === void 0) { scale = 1; }
        return { alpha: (sin(t) + 1) * 0.5 * scale + base };
    },
};
