Çözümümü paylaşıyorum, çünkü geri kalanından tamamen memnun değildim. Benim sorunum AfterViewChecked
, bazen yukarı kaydırıyorum ve bazı nedenlerden dolayı, bu yaşam kancası çağrılıyor ve yeni mesaj olmasa bile beni aşağı kaydırıyor. Kullanmayı denedim OnChanges
ama bu beni bu çözüme götüren bir sorundu . Ne yazık ki, yalnızca kullanarak DoCheck
, mesajlar işlenmeden önce aşağı kaydırılıyordu, bu da yararlı değildi, bu yüzden onları birleştirdim, böylece DoCheck temelde AfterViewChecked
çağrı yapıp yapmayacağını belirtiyor scrollToBottom
.
Geri bildirim almaktan mutluluk duyarız.
export class ChatComponent implements DoCheck, AfterViewChecked {
@Input() public messages: Message[] = [];
@ViewChild('scrollable') private scrollable: ElementRef;
private shouldScrollDown: boolean;
private iterableDiffer;
constructor(private iterableDiffers: IterableDiffers) {
this.iterableDiffer = this.iterableDiffers.find([]).create(null);
}
ngDoCheck(): void {
if (this.iterableDiffer.diff(this.messages)) {
this.numberOfMessagesChanged = true;
}
}
ngAfterViewChecked(): void {
const isScrolledDown = Math.abs(this.scrollable.nativeElement.scrollHeight - this.scrollable.nativeElement.scrollTop - this.scrollable.nativeElement.clientHeight) <= 3.0;
if (this.numberOfMessagesChanged && !isScrolledDown) {
this.scrollToBottom();
this.numberOfMessagesChanged = false;
}
}
scrollToBottom() {
try {
this.scrollable.nativeElement.scrollTop = this.scrollable.nativeElement.scrollHeight;
} catch (e) {
console.error(e);
}
}
}
chat.component.html
<div class="chat-wrapper">
<div class="chat-messages-holder" #scrollable>
<app-chat-message *ngFor="let message of messages" [message]="message">
</app-chat-message>
</div>
<div class="chat-input-holder">
<app-chat-input (send)="onSend($event)"></app-chat-input>
</div>
</div>
chat.component.sass
.chat-wrapper
display: flex
justify-content: center
align-items: center
flex-direction: column
height: 100%
.chat-messages-holder
overflow-y: scroll !important
overflow-x: hidden
width: 100%
height: 100%