"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.bindCallbackInternals = void 0;
const isScheduler_js_1 = require("../util/isScheduler.js");
const Observable_js_1 = require("../Observable.js");
const mapOneOrManyArgs_js_1 = require("../util/mapOneOrManyArgs.js");
const AsyncSubject_js_1 = require("../AsyncSubject.js");
const scheduled_js_1 = require("../scheduled/scheduled.js");
function bindCallbackInternals(isNodeStyle, callbackFunc, resultSelector, scheduler) {
    if (resultSelector) {
        if ((0, isScheduler_js_1.isScheduler)(resultSelector)) {
            scheduler = resultSelector;
        }
        else {
            return function (...args) {
                return (0, mapOneOrManyArgs_js_1.mapOneOrManyArgs)(resultSelector)(bindCallbackInternals(isNodeStyle, callbackFunc, scheduler).apply(this, args));
            };
        }
    }
    if (scheduler) {
        return function (...args) {
            return (0, scheduled_js_1.scheduled)(bindCallbackInternals(isNodeStyle, callbackFunc).apply(this, args), scheduler);
        };
    }
    return function (...args) {
        const subject = new AsyncSubject_js_1.AsyncSubject();
        let uninitialized = true;
        return new Observable_js_1.Observable((subscriber) => {
            const subs = subject.subscribe(subscriber);
            if (uninitialized) {
                uninitialized = false;
                let isAsync = false;
                let isComplete = false;
                callbackFunc.apply(this, [
                    ...args,
                    (...results) => {
                        if (isNodeStyle) {
                            const err = results.shift();
                            if (err != null) {
                                subject.error(err);
                                return;
                            }
                        }
                        subject.next(1 < results.length ? results : results[0]);
                        isComplete = true;
                        if (isAsync) {
                            subject.complete();
                        }
                    },
                ]);
                if (isComplete) {
                    subject.complete();
                }
                isAsync = true;
            }
            return subs;
        });
    };
}
exports.bindCallbackInternals = bindCallbackInternals;