creation of a dedicated controller for loading the statuses
This commit is contained in:
parent
f33f2e37bb
commit
27d3507922
|
@ -41,6 +41,7 @@ import { HashtagComponent } from './components/stream/hashtag/hashtag.component'
|
||||||
import { StreamOverlayComponent } from './components/stream/stream-overlay/stream-overlay.component';
|
import { StreamOverlayComponent } from './components/stream/stream-overlay/stream-overlay.component';
|
||||||
import { DatabindedTextComponent } from './components/stream/status/databinded-text/databinded-text.component';
|
import { DatabindedTextComponent } from './components/stream/status/databinded-text/databinded-text.component';
|
||||||
import { TimeAgoPipe } from './pipes/time-ago.pipe';
|
import { TimeAgoPipe } from './pipes/time-ago.pipe';
|
||||||
|
import { StreamStatusesComponent } from './components/stream/stream-statuses/stream-statuses.component';
|
||||||
|
|
||||||
const routes: Routes = [
|
const routes: Routes = [
|
||||||
{ path: "", redirectTo: "home", pathMatch: "full" },
|
{ path: "", redirectTo: "home", pathMatch: "full" },
|
||||||
|
@ -74,7 +75,8 @@ const routes: Routes = [
|
||||||
HashtagComponent,
|
HashtagComponent,
|
||||||
StreamOverlayComponent,
|
StreamOverlayComponent,
|
||||||
DatabindedTextComponent,
|
DatabindedTextComponent,
|
||||||
TimeAgoPipe
|
TimeAgoPipe,
|
||||||
|
StreamStatusesComponent
|
||||||
],
|
],
|
||||||
imports: [
|
imports: [
|
||||||
BrowserModule,
|
BrowserModule,
|
||||||
|
|
|
@ -16,7 +16,6 @@ export class FloatingColumnComponent implements OnInit {
|
||||||
|
|
||||||
openPanel: string;
|
openPanel: string;
|
||||||
|
|
||||||
|
|
||||||
constructor(private readonly navigationService: NavigationService) { }
|
constructor(private readonly navigationService: NavigationService) { }
|
||||||
|
|
||||||
ngOnInit() {
|
ngOnInit() {
|
||||||
|
|
|
@ -0,0 +1,6 @@
|
||||||
|
<div class="stream-toots flexcroll" #statusstream (scroll)="onScroll()">
|
||||||
|
<!-- data-simplebar -->
|
||||||
|
<div class="stream-toots__status" *ngFor="let statusWrapper of statuses">
|
||||||
|
<app-status [statusWrapper]="statusWrapper" (browseAccount)="accountSelected($event)" (browseHashtag)="hashtagSelected($event)"></app-status>
|
||||||
|
</div>
|
||||||
|
</div>
|
|
@ -0,0 +1,13 @@
|
||||||
|
@import "variables";
|
||||||
|
@import "commons";
|
||||||
|
|
||||||
|
.stream-toots {
|
||||||
|
height: calc(100%);
|
||||||
|
width: calc(100%);
|
||||||
|
|
||||||
|
overflow: auto;
|
||||||
|
&__status:not(:last-child) {
|
||||||
|
border: solid #06070b;
|
||||||
|
border-width: 0 0 1px 0;
|
||||||
|
}
|
||||||
|
}
|
|
@ -0,0 +1,25 @@
|
||||||
|
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
||||||
|
|
||||||
|
import { StreamStatusesComponent } from './stream-statuses.component';
|
||||||
|
|
||||||
|
describe('StreamStatusesComponent', () => {
|
||||||
|
let component: StreamStatusesComponent;
|
||||||
|
let fixture: ComponentFixture<StreamStatusesComponent>;
|
||||||
|
|
||||||
|
beforeEach(async(() => {
|
||||||
|
TestBed.configureTestingModule({
|
||||||
|
declarations: [ StreamStatusesComponent ]
|
||||||
|
})
|
||||||
|
.compileComponents();
|
||||||
|
}));
|
||||||
|
|
||||||
|
beforeEach(() => {
|
||||||
|
fixture = TestBed.createComponent(StreamStatusesComponent);
|
||||||
|
component = fixture.componentInstance;
|
||||||
|
fixture.detectChanges();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should create', () => {
|
||||||
|
expect(component).toBeTruthy();
|
||||||
|
});
|
||||||
|
});
|
|
@ -0,0 +1,198 @@
|
||||||
|
import { Component, OnInit, Input, ViewChild, ElementRef, OnDestroy, EventEmitter, Output } from '@angular/core';
|
||||||
|
import { Store } from '@ngxs/store';
|
||||||
|
|
||||||
|
import { StreamElement } from '../../../states/streams.state';
|
||||||
|
import { AccountInfo } from '../../../states/accounts.state';
|
||||||
|
import { StreamingService, EventEnum, StreamingWrapper, StatusUpdate } from '../../../services/streaming.service';
|
||||||
|
import { Status } from '../../../services/models/mastodon.interfaces';
|
||||||
|
import { MastodonService } from '../../../services/mastodon.service';
|
||||||
|
import { Observable, Subscription } from 'rxjs';
|
||||||
|
import { StatusWrapper } from '../stream.component';
|
||||||
|
|
||||||
|
|
||||||
|
@Component({
|
||||||
|
selector: 'app-stream-statuses',
|
||||||
|
templateUrl: './stream-statuses.component.html',
|
||||||
|
styleUrls: ['./stream-statuses.component.scss']
|
||||||
|
})
|
||||||
|
export class StreamStatusesComponent implements OnInit, OnDestroy {
|
||||||
|
private _streamElement: StreamElement;
|
||||||
|
private account: AccountInfo;
|
||||||
|
private websocketStreaming: StreamingWrapper;
|
||||||
|
|
||||||
|
statuses: StatusWrapper[] = [];
|
||||||
|
private bufferStream: Status[] = [];
|
||||||
|
private bufferWasCleared: boolean;
|
||||||
|
|
||||||
|
@Output() browseAccount = new EventEmitter<string>();
|
||||||
|
@Output() browseHashtag = new EventEmitter<string>();
|
||||||
|
@Output() browseThread = new EventEmitter<string>();
|
||||||
|
|
||||||
|
@Input()
|
||||||
|
set streamElement(streamElement: StreamElement) {
|
||||||
|
this._streamElement = streamElement;
|
||||||
|
|
||||||
|
const splitedUserName = streamElement.accountId.split('@');
|
||||||
|
const user = splitedUserName[0];
|
||||||
|
const instance = splitedUserName[1];
|
||||||
|
this.account = this.getRegisteredAccounts().find(x => x.username == user && x.instance == instance);
|
||||||
|
|
||||||
|
this.retrieveToots();
|
||||||
|
this.launchWebsocket();
|
||||||
|
}
|
||||||
|
get streamElement(): StreamElement {
|
||||||
|
return this._streamElement;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Input() goToTop: Observable<void>;
|
||||||
|
|
||||||
|
private goToTopSubscription: Subscription;
|
||||||
|
|
||||||
|
constructor(
|
||||||
|
private readonly store: Store,
|
||||||
|
private readonly streamingService: StreamingService,
|
||||||
|
private readonly mastodonService: MastodonService) {
|
||||||
|
}
|
||||||
|
|
||||||
|
ngOnInit() {
|
||||||
|
this.goToTopSubscription = this.goToTop.subscribe(() => {
|
||||||
|
this.applyGoToTop();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
ngOnDestroy(){
|
||||||
|
if( this.goToTopSubscription) this.goToTopSubscription.unsubscribe();
|
||||||
|
}
|
||||||
|
|
||||||
|
private launchWebsocket(): void {
|
||||||
|
this.websocketStreaming = this.streamingService.getStreaming(this.account, this._streamElement);
|
||||||
|
this.websocketStreaming.statusUpdateSubjet.subscribe((update: StatusUpdate) => {
|
||||||
|
if (update) {
|
||||||
|
if (update.type === EventEnum.update) {
|
||||||
|
if (!this.statuses.find(x => x.status.id == update.status.id)) {
|
||||||
|
if (this.streamPositionnedAtTop) {
|
||||||
|
const wrapper = new StatusWrapper(update.status, this.account);
|
||||||
|
this.statuses.unshift(wrapper);
|
||||||
|
} else {
|
||||||
|
this.bufferStream.push(update.status);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
this.checkAndCleanUpStream();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ViewChild('statusstream') public statustream: ElementRef;
|
||||||
|
private applyGoToTop(): boolean {
|
||||||
|
this.loadBuffer();
|
||||||
|
if (this.statuses.length > 2 * this.streamingService.nbStatusPerIteration) {
|
||||||
|
this.statuses.length = 2 * this.streamingService.nbStatusPerIteration;
|
||||||
|
}
|
||||||
|
const stream = this.statustream.nativeElement as HTMLElement;
|
||||||
|
stream.scrollTo({
|
||||||
|
top: 0,
|
||||||
|
behavior: 'smooth'
|
||||||
|
});
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
private streamPositionnedAtTop: boolean = true;
|
||||||
|
private isProcessingInfiniteScroll: boolean;
|
||||||
|
|
||||||
|
onScroll() {
|
||||||
|
var element = this.statustream.nativeElement as HTMLElement;
|
||||||
|
const atBottom = element.scrollHeight <= element.clientHeight + element.scrollTop + 1000;
|
||||||
|
const atTop = element.scrollTop === 0;
|
||||||
|
|
||||||
|
this.streamPositionnedAtTop = false;
|
||||||
|
if (atBottom && !this.isProcessingInfiniteScroll) {
|
||||||
|
this.scrolledToBottom();
|
||||||
|
} else if (atTop) {
|
||||||
|
this.scrolledToTop();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
accountSelected(accountName: string): void {
|
||||||
|
console.warn(`status comp: accountSelected ${accountName}`);
|
||||||
|
this.browseAccount.next(accountName);
|
||||||
|
}
|
||||||
|
|
||||||
|
hashtagSelected(hashtag: string): void {
|
||||||
|
console.warn(`status comp: hashtagSelected ${hashtag}`);
|
||||||
|
this.browseHashtag.next(hashtag);
|
||||||
|
}
|
||||||
|
|
||||||
|
textSelected(): void {
|
||||||
|
console.warn(`status comp: textSelected`);
|
||||||
|
}
|
||||||
|
|
||||||
|
private scrolledToTop() {
|
||||||
|
this.streamPositionnedAtTop = true;
|
||||||
|
|
||||||
|
this.loadBuffer();
|
||||||
|
}
|
||||||
|
|
||||||
|
private loadBuffer(){
|
||||||
|
if(this.bufferWasCleared) {
|
||||||
|
this.statuses.length = 0;
|
||||||
|
this.bufferWasCleared = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (const status of this.bufferStream) {
|
||||||
|
const wrapper = new StatusWrapper(status, this.account);
|
||||||
|
this.statuses.unshift(wrapper);
|
||||||
|
}
|
||||||
|
|
||||||
|
this.bufferStream.length = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
private scrolledToBottom() {
|
||||||
|
this.isProcessingInfiniteScroll = true;
|
||||||
|
|
||||||
|
const lastStatus = this.statuses[this.statuses.length - 1];
|
||||||
|
this.mastodonService.getTimeline(this.account, this._streamElement.type, lastStatus.status.id, null, this.streamingService.nbStatusPerIteration, this._streamElement.tag, this._streamElement.list)
|
||||||
|
.then((status: Status[]) => {
|
||||||
|
for (const s of status) {
|
||||||
|
const wrapper = new StatusWrapper(s, this.account);
|
||||||
|
this.statuses.push(wrapper);
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.catch(err => {
|
||||||
|
console.error(err);
|
||||||
|
})
|
||||||
|
.then(() => {
|
||||||
|
this.isProcessingInfiniteScroll = false;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
private getRegisteredAccounts(): AccountInfo[] {
|
||||||
|
var regAccounts = <AccountInfo[]>this.store.snapshot().registeredaccounts.accounts;
|
||||||
|
return regAccounts;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
private retrieveToots(): void {
|
||||||
|
this.mastodonService.getTimeline(this.account, this._streamElement.type, null, null, this.streamingService.nbStatusPerIteration, this._streamElement.tag, this._streamElement.list)
|
||||||
|
.then((results: Status[]) => {
|
||||||
|
for (const s of results) {
|
||||||
|
const wrapper = new StatusWrapper(s, this.account);
|
||||||
|
this.statuses.push(wrapper);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
private checkAndCleanUpStream(): void {
|
||||||
|
if (this.streamPositionnedAtTop && this.statuses.length > 3 * this.streamingService.nbStatusPerIteration) {
|
||||||
|
this.statuses.length = 2 * this.streamingService.nbStatusPerIteration;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.bufferStream.length > 3 * this.streamingService.nbStatusPerIteration) {
|
||||||
|
this.bufferWasCleared = true;
|
||||||
|
this.bufferStream.length = 2 * this.streamingService.nbStatusPerIteration;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -10,10 +10,10 @@
|
||||||
<h1>{{ streamElement.name.toUpperCase() }}</h1>
|
<h1>{{ streamElement.name.toUpperCase() }}</h1>
|
||||||
</a>
|
</a>
|
||||||
</div>
|
</div>
|
||||||
<div class="stream-toots flexcroll" #statusstream (scroll)="onScroll()">
|
<app-stream-statuses class="stream-statuses" [streamElement]="streamElement" [goToTop]="goToTopSubject.asObservable()" (browseAccount)="browseAccount($event)" (browseHashtag)="browseHashtag($event)"></app-stream-statuses>
|
||||||
<!-- data-simplebar -->
|
<!-- <div class="stream-toots flexcroll" #statusstream (scroll)="onScroll()">
|
||||||
<div class="stream-toots__status" *ngFor="let statusWrapper of statuses">
|
<div class="stream-toots__status" *ngFor="let statusWrapper of statuses">
|
||||||
<app-status [statusWrapper]="statusWrapper" (browseAccount)="browseAccount($event)" (browseHashtag)="browseHashtag($event)"></app-status>
|
<app-status [statusWrapper]="statusWrapper" (browseAccount)="browseAccount($event)" (browseHashtag)="browseHashtag($event)"></app-status>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div> -->
|
||||||
</div>
|
</div>
|
|
@ -22,16 +22,22 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.stream-toots {
|
.stream-statuses {
|
||||||
|
display: block;
|
||||||
height: calc(100% - 30px);
|
height: calc(100% - 30px);
|
||||||
width: 320px;
|
width: 320px;
|
||||||
overflow: auto;
|
|
||||||
&__status:not(:last-child) {
|
|
||||||
border: solid #06070b;
|
|
||||||
border-width: 0 0 1px 0;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// .stream-toots {
|
||||||
|
// height: calc(100% - 30px);
|
||||||
|
// width: 320px;
|
||||||
|
// overflow: auto;
|
||||||
|
// &__status:not(:last-child) {
|
||||||
|
// border: solid #06070b;
|
||||||
|
// border-width: 0 0 1px 0;
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
.stream-overlay {
|
.stream-overlay {
|
||||||
position: absolute;
|
position: absolute;
|
||||||
|
|
||||||
|
|
|
@ -1,11 +1,9 @@
|
||||||
import { Component, OnInit, Input, ElementRef, ViewChild, HostListener } from "@angular/core";
|
import { Component, OnInit, Input, ElementRef, ViewChild, HostListener } from "@angular/core";
|
||||||
import { AccountWrapper } from "../../models/account.models";
|
import { Subject } from "rxjs";
|
||||||
import { StreamElement, StreamTypeEnum } from "../../states/streams.state";
|
|
||||||
import { StreamingService, StreamingWrapper, EventEnum, StatusUpdate } from "../../services/streaming.service";
|
import { StreamElement } from "../../states/streams.state";
|
||||||
import { Store } from "@ngxs/store";
|
|
||||||
import { AccountInfo } from "../../states/accounts.state";
|
|
||||||
import { Status } from "../../services/models/mastodon.interfaces";
|
import { Status } from "../../services/models/mastodon.interfaces";
|
||||||
import { MastodonService } from "../../services/mastodon.service";
|
import { AccountInfo } from "../../states/accounts.state";
|
||||||
|
|
||||||
@Component({
|
@Component({
|
||||||
selector: "app-stream",
|
selector: "app-stream",
|
||||||
|
@ -13,54 +11,34 @@ import { MastodonService } from "../../services/mastodon.service";
|
||||||
styleUrls: ["./stream.component.scss"]
|
styleUrls: ["./stream.component.scss"]
|
||||||
})
|
})
|
||||||
export class StreamComponent implements OnInit {
|
export class StreamComponent implements OnInit {
|
||||||
private _streamElement: StreamElement;
|
|
||||||
private account: AccountInfo;
|
|
||||||
private websocketStreaming: StreamingWrapper;
|
|
||||||
|
|
||||||
statuses: StatusWrapper[] = [];
|
|
||||||
private bufferStream: Status[] = [];
|
|
||||||
private bufferWasCleared: boolean;
|
|
||||||
|
|
||||||
overlayActive: boolean;
|
overlayActive: boolean;
|
||||||
overlayAccountToBrowse: string;
|
overlayAccountToBrowse: string;
|
||||||
overlayHashtagToBrowse: string;
|
overlayHashtagToBrowse: string;
|
||||||
|
|
||||||
@Input()
|
private goToTopSubject: Subject<void> = new Subject<void>();
|
||||||
set streamElement(streamElement: StreamElement) {
|
|
||||||
this._streamElement = streamElement;
|
|
||||||
|
|
||||||
const splitedUserName = streamElement.accountId.split('@');
|
@Input() streamElement: StreamElement;
|
||||||
const user = splitedUserName[0];
|
|
||||||
const instance = splitedUserName[1];
|
|
||||||
this.account = this.getRegisteredAccounts().find(x => x.username == user && x.instance == instance);
|
|
||||||
|
|
||||||
this.retrieveToots();
|
constructor() { }
|
||||||
this.launchWebsocket();
|
|
||||||
}
|
|
||||||
|
|
||||||
get streamElement(): StreamElement {
|
|
||||||
return this._streamElement;
|
|
||||||
}
|
|
||||||
|
|
||||||
constructor(
|
|
||||||
private readonly store: Store,
|
|
||||||
private readonly streamingService: StreamingService,
|
|
||||||
private readonly mastodonService: MastodonService) {
|
|
||||||
}
|
|
||||||
|
|
||||||
ngOnInit() {
|
ngOnInit() {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
goToTop(): boolean {
|
||||||
|
this.goToTopSubject.next();
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
browseAccount(account: string): void {
|
browseAccount(account: string): void {
|
||||||
this.overlayAccountToBrowse = account;
|
this.overlayAccountToBrowse = account;
|
||||||
this.overlayHashtagToBrowse = null;
|
this.overlayHashtagToBrowse = null;
|
||||||
this.overlayActive = true;
|
this.overlayActive = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
browseHashtag(hashtag: string): void {
|
browseHashtag(hashtag: string): void {
|
||||||
this.overlayAccountToBrowse = null;
|
this.overlayAccountToBrowse = null;
|
||||||
this.overlayHashtagToBrowse = hashtag;
|
this.overlayHashtagToBrowse = hashtag;
|
||||||
this.overlayActive = true;
|
this.overlayActive = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
browseThread(thread: string): void {
|
browseThread(thread: string): void {
|
||||||
|
@ -72,126 +50,11 @@ export class StreamComponent implements OnInit {
|
||||||
this.overlayAccountToBrowse = null;
|
this.overlayAccountToBrowse = null;
|
||||||
this.overlayActive = false;
|
this.overlayActive = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ViewChild('statusstream') public statustream: ElementRef;
|
|
||||||
goToTop(): boolean {
|
|
||||||
this.loadBuffer();
|
|
||||||
if (this.statuses.length > 2 * this.streamingService.nbStatusPerIteration) {
|
|
||||||
this.statuses.length = 2 * this.streamingService.nbStatusPerIteration;
|
|
||||||
}
|
|
||||||
const stream = this.statustream.nativeElement as HTMLElement;
|
|
||||||
stream.scrollTo({
|
|
||||||
top: 0,
|
|
||||||
behavior: 'smooth'
|
|
||||||
});
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
private streamPositionnedAtTop: boolean = true;
|
|
||||||
private isProcessingInfiniteScroll: boolean;
|
|
||||||
|
|
||||||
onScroll() {
|
|
||||||
var element = this.statustream.nativeElement as HTMLElement;
|
|
||||||
const atBottom = element.scrollHeight <= element.clientHeight + element.scrollTop + 1000;
|
|
||||||
const atTop = element.scrollTop === 0;
|
|
||||||
|
|
||||||
this.streamPositionnedAtTop = false;
|
|
||||||
if (atBottom && !this.isProcessingInfiniteScroll) {
|
|
||||||
this.scrolledToBottom();
|
|
||||||
} else if (atTop) {
|
|
||||||
this.scrolledToTop();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
private scrolledToTop() {
|
|
||||||
this.streamPositionnedAtTop = true;
|
|
||||||
|
|
||||||
this.loadBuffer();
|
|
||||||
}
|
|
||||||
|
|
||||||
private loadBuffer(){
|
|
||||||
if(this.bufferWasCleared) {
|
|
||||||
this.statuses.length = 0;
|
|
||||||
this.bufferWasCleared = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
for (const status of this.bufferStream) {
|
|
||||||
const wrapper = new StatusWrapper(status, this.account);
|
|
||||||
this.statuses.unshift(wrapper);
|
|
||||||
}
|
|
||||||
|
|
||||||
this.bufferStream.length = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
private scrolledToBottom() {
|
|
||||||
this.isProcessingInfiniteScroll = true;
|
|
||||||
|
|
||||||
const lastStatus = this.statuses[this.statuses.length - 1];
|
|
||||||
this.mastodonService.getTimeline(this.account, this._streamElement.type, lastStatus.status.id, null, this.streamingService.nbStatusPerIteration, this._streamElement.tag, this._streamElement.list)
|
|
||||||
.then((status: Status[]) => {
|
|
||||||
for (const s of status) {
|
|
||||||
const wrapper = new StatusWrapper(s, this.account);
|
|
||||||
this.statuses.push(wrapper);
|
|
||||||
}
|
|
||||||
})
|
|
||||||
.catch(err => {
|
|
||||||
console.error(err);
|
|
||||||
})
|
|
||||||
.then(() => {
|
|
||||||
this.isProcessingInfiniteScroll = false;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
private getRegisteredAccounts(): AccountInfo[] {
|
|
||||||
var regAccounts = <AccountInfo[]>this.store.snapshot().registeredaccounts.accounts;
|
|
||||||
return regAccounts;
|
|
||||||
}
|
|
||||||
|
|
||||||
private retrieveToots(): void {
|
|
||||||
this.mastodonService.getTimeline(this.account, this._streamElement.type, null, null, this.streamingService.nbStatusPerIteration, this._streamElement.tag, this._streamElement.list)
|
|
||||||
.then((results: Status[]) => {
|
|
||||||
for (const s of results) {
|
|
||||||
const wrapper = new StatusWrapper(s, this.account);
|
|
||||||
this.statuses.push(wrapper);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
private launchWebsocket(): void {
|
|
||||||
this.websocketStreaming = this.streamingService.getStreaming(this.account, this._streamElement);
|
|
||||||
this.websocketStreaming.statusUpdateSubjet.subscribe((update: StatusUpdate) => {
|
|
||||||
if (update) {
|
|
||||||
if (update.type === EventEnum.update) {
|
|
||||||
if (!this.statuses.find(x => x.status.id == update.status.id)) {
|
|
||||||
if (this.streamPositionnedAtTop) {
|
|
||||||
const wrapper = new StatusWrapper(update.status, this.account);
|
|
||||||
this.statuses.unshift(wrapper);
|
|
||||||
} else {
|
|
||||||
this.bufferStream.push(update.status);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
this.checkAndCleanUpStream();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
private checkAndCleanUpStream(): void {
|
|
||||||
if (this.streamPositionnedAtTop && this.statuses.length > 3 * this.streamingService.nbStatusPerIteration) {
|
|
||||||
this.statuses.length = 2 * this.streamingService.nbStatusPerIteration;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (this.bufferStream.length > 3 * this.streamingService.nbStatusPerIteration) {
|
|
||||||
this.bufferWasCleared = true;
|
|
||||||
this.bufferStream.length = 2 * this.streamingService.nbStatusPerIteration;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export class StatusWrapper {
|
export class StatusWrapper {
|
||||||
constructor(
|
constructor(
|
||||||
public status: Status,
|
public status: Status,
|
||||||
public provider: AccountInfo
|
public provider: AccountInfo
|
||||||
) {}
|
) { }
|
||||||
}
|
}
|
Loading…
Reference in New Issue