“use strict”; module.exports = function(Promise, PromiseArray) { var util = require(“./util.js”); var async = require(“./async.js”); var tryCatch = util.tryCatch; var errorObj = util.errorObj;

Promise.prototype.progressed = function (handler) {

return this._then(undefined, undefined, handler, undefined, undefined);

};

Promise.prototype._progress = function (progressValue) {

if (this._isFollowingOrFulfilledOrRejected()) return;
this._target()._progressUnchecked(progressValue);

};

Promise.prototype._progressHandlerAt = function (index) {

return index === 0
    ? this._progressHandler0
    : this[(index << 2) + index - 5 + 2];

};

Promise.prototype._doProgressWith = function (progression) {

var progressValue = progression.value;
var handler = progression.handler;
var promise = progression.promise;
var receiver = progression.receiver;

var ret = tryCatch(handler).call(receiver, progressValue);
if (ret === errorObj) {
    if (ret.e != null &&
        ret.e.name !== "StopProgressPropagation") {
        var trace = util.canAttachTrace(ret.e)
            ? ret.e : new Error(util.toString(ret.e));
        promise._attachExtraTrace(trace);
        promise._progress(ret.e);
    }
} else if (ret instanceof Promise) {
    ret._then(promise._progress, null, null, promise, undefined);
} else {
    promise._progress(ret);
}

};

Promise.prototype._progressUnchecked = function (progressValue) {

var len = this._length();
var progress = this._progress;
for (var i = 0; i < len; i++) {
    var handler = this._progressHandlerAt(i);
    var promise = this._promiseAt(i);
    if (!(promise instanceof Promise)) {
        var receiver = this._receiverAt(i);
        if (typeof handler === "function") {
            handler.call(receiver, progressValue, promise);
        } else if (receiver instanceof PromiseArray &&
                   !receiver._isResolved()) {
            receiver._promiseProgressed(progressValue, promise);
        }
        continue;
    }

    if (typeof handler === "function") {
        async.invoke(this._doProgressWith, this, {
            handler: handler,
            promise: promise,
            receiver: this._receiverAt(i),
            value: progressValue
        });
    } else {
        async.invoke(progress, promise, progressValue);
    }
}

}; };