withLatestFrom.js
5.07 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
"use strict";
var __extends = (this && this.__extends) || function (d, b) {
for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p];
function __() { this.constructor = d; }
d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
};
var OuterSubscriber_1 = require('../OuterSubscriber');
var subscribeToResult_1 = require('../util/subscribeToResult');
/* tslint:disable:max-line-length */
/**
* Combines the source Observable with other Observables to create an Observable
* whose values are calculated from the latest values of each, only when the
* source emits.
*
* <span class="informal">Whenever the source Observable emits a value, it
* computes a formula using that value plus the latest values from other input
* Observables, then emits the output of that formula.</span>
*
* <img src="./img/withLatestFrom.png" width="100%">
*
* `withLatestFrom` combines each value from the source Observable (the
* instance) with the latest values from the other input Observables only when
* the source emits a value, optionally using a `project` function to determine
* the value to be emitted on the output Observable. All input Observables must
* emit at least one value before the output Observable will emit a value.
*
* @example <caption>On every click event, emit an array with the latest timer event plus the click event</caption>
* var clicks = Rx.Observable.fromEvent(document, 'click');
* var timer = Rx.Observable.interval(1000);
* var result = clicks.withLatestFrom(timer);
* result.subscribe(x => console.log(x));
*
* @see {@link combineLatest}
*
* @param {Observable} other An input Observable to combine with the source
* Observable. More than one input Observables may be given as argument.
* @param {Function} [project] Projection function for combining values
* together. Receives all values in order of the Observables passed, where the
* first parameter is a value from the source Observable. (e.g.
* `a.withLatestFrom(b, c, (a1, b1, c1) => a1 + b1 + c1)`). If this is not
* passed, arrays will be emitted on the output Observable.
* @return {Observable} An Observable of projected values from the most recent
* values from each input Observable, or an array of the most recent values from
* each input Observable.
* @method withLatestFrom
* @owner Observable
*/
function withLatestFrom() {
var args = [];
for (var _i = 0; _i < arguments.length; _i++) {
args[_i - 0] = arguments[_i];
}
var project;
if (typeof args[args.length - 1] === 'function') {
project = args.pop();
}
var observables = args;
return this.lift(new WithLatestFromOperator(observables, project));
}
exports.withLatestFrom = withLatestFrom;
var WithLatestFromOperator = (function () {
function WithLatestFromOperator(observables, project) {
this.observables = observables;
this.project = project;
}
WithLatestFromOperator.prototype.call = function (subscriber, source) {
return source.subscribe(new WithLatestFromSubscriber(subscriber, this.observables, this.project));
};
return WithLatestFromOperator;
}());
/**
* We need this JSDoc comment for affecting ESDoc.
* @ignore
* @extends {Ignored}
*/
var WithLatestFromSubscriber = (function (_super) {
__extends(WithLatestFromSubscriber, _super);
function WithLatestFromSubscriber(destination, observables, project) {
_super.call(this, destination);
this.observables = observables;
this.project = project;
this.toRespond = [];
var len = observables.length;
this.values = new Array(len);
for (var i = 0; i < len; i++) {
this.toRespond.push(i);
}
for (var i = 0; i < len; i++) {
var observable = observables[i];
this.add(subscribeToResult_1.subscribeToResult(this, observable, observable, i));
}
}
WithLatestFromSubscriber.prototype.notifyNext = function (outerValue, innerValue, outerIndex, innerIndex, innerSub) {
this.values[outerIndex] = innerValue;
var toRespond = this.toRespond;
if (toRespond.length > 0) {
var found = toRespond.indexOf(outerIndex);
if (found !== -1) {
toRespond.splice(found, 1);
}
}
};
WithLatestFromSubscriber.prototype.notifyComplete = function () {
// noop
};
WithLatestFromSubscriber.prototype._next = function (value) {
if (this.toRespond.length === 0) {
var args = [value].concat(this.values);
if (this.project) {
this._tryProject(args);
}
else {
this.destination.next(args);
}
}
};
WithLatestFromSubscriber.prototype._tryProject = function (args) {
var result;
try {
result = this.project.apply(this, args);
}
catch (err) {
this.destination.error(err);
return;
}
this.destination.next(result);
};
return WithLatestFromSubscriber;
}(OuterSubscriber_1.OuterSubscriber));
//# sourceMappingURL=withLatestFrom.js.map