组合observable有一点(或很大)的问题。我正在实现某种标签输入。
this._allTags
都是可用的标签。
我有4个流:
this._suggestions = new this.rx.Subject;
this._searchText = new this.rx.Subject;
this._selectedIndex = new this.rx.Subject;
this._eventsStream = new this.rx.Subject;
搜索方法:
search(searchText) {
this._searchText.onNext(searchText);
this._selectedIndex.onNext(-1);
}
KeyDown方法:
keyDown(event) {
this._eventsStream.onNext(event);
}
搜索逻辑:
const partitionSearchText = this._searchText
.partition((searchText) => !!searchText); //check if searchText is not empty
//put filtered array to this._suggestions stream
partitionSearchText[0]
.subscribe((searchText) => this._suggestions.onNext(
this._allTags.filter((item) => ~item.name.toLowerCase().indexOf(searchText.toLowerCase()))
));
//put empty array to this._suggestions stream if there is no searchText
partitionSearchText[1]
.subscribe((searchText) => this._suggestions.onNext([]));
我想实施活动。如果有searchText和keyDown
事件,那么我想增加this._selectedIndex
,但如果this._selectedIndex
与this._suggestions
长度相同,则不要增加它。
这是我实施的目标:
const eventsWithSearchText = this._searchText
.map((searchText) => !!searchText ? this._eventsStream : this.rx.Observable.empty())
.switch()
const keyDownEvents = eventsWithSearchText
.filter((event) => event.keyCode === DOWN_KEY)
keyDownEvents
.subscribe((event) => event.preventDefault())
const isNotLast = this._selectedIndex
.combineLatest(this._suggestions, (index, sugg) => index !== sugg.length - 1);
keyDownEvents
.subscribe((item) => {
this._selectedIndexValue++
this._selectedIndex.onNext(this._selectedIndexValue);
});
所以,它正在递增this._selectedIndex
但不会在与this._suggestions
长度相同时停止。
你能帮忙吗?
答案 0 :(得分:3)
我做到了!这是代码:
const eventsWithSearchText = this._searchText
.map((searchText) => !!searchText ? this._eventsStream : this.rx.Observable.empty())
.switch()
const keyDownEvents = eventsWithSearchText
.filter((event) => event.keyCode === DOWN_KEY)
keyDownEvents
.subscribe((event) => event.preventDefault())
const keyUpEvents = eventsWithSearchText
.filter((event) => event.keyCode === UP_KEY)
keyUpEvents
.subscribe((event) => event.preventDefault())
const enterEvents = eventsWithSearchText
.filter((event) => event.keyCode === ENTER_KEY)
enterEvents
.subscribe((event) => event.preventDefault())
const isNotLast = this._selectedIndex
.combineLatest(this._suggestions, (index, sugg) => index !== sugg.length - 1);
const keyDownAndNotLast = keyDownEvents
.map(() => +1)
.withLatestFrom(isNotLast, (value, notLast) => notLast ? value : false)
.filter((item) => item)
const keyUpEventsAndNotFirst = keyUpEvents
.map(() => -1)
.withLatestFrom(this._selectedIndex, (value, index) => !!index ? value : false)
.filter((item) => item)
this.rx.Observable.merge(
keyDownAndNotLast,
keyUpEventsAndNotFirst,
enterEvents
.map(() => ({reset: true}))
)
.scan((acc, value) => value.reset ? -1 : acc + value, -1)
.subscribe((item) => {
this._selectedIndex.onNext(item);
});
https://plnkr.co/edit/soaChC?p=preview
希望它会对某人有所帮助。