Angular:无法向下滚动到元素的底部 [英] Angular: unable to scroll down to bottom in element

查看:105
本文介绍了Angular:无法向下滚动到元素的底部的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我一直在推迟修复这个错误,我现在已经有一段时间了。我有以下聊天窗口:

I've been postponing fixing this error that I have been having for a while now. I have the below chatwindow:

< img src =https://i.stack.imgur.com/ySiDV.pngalt =在此处输入图像说明>

窗口我显示消息的地方是一个单独的组件(chat-window.component.ts)。我想用ngOnChanges滚动到底部。

The window where I display the messages is a separate component (chat-window.component.ts). I want to scroll to the bottom with ngOnChanges.

当我们收到来自父组件的消息的对话时,通过异步请求从服务器接收消息,我们想滚动到窗口元素的底部。我们通过在ngOnChanges生命周期钩子中调用类的 this.scrollToBottom()方法来完成此操作。

When we receive the conversation with the messages from the parent component, where it is received from the server via an asynchronous request, we want to scroll to the bottom of the window element. We do this by calling the this.scrollToBottom() method of the class in the ngOnChanges lifecycle hook.

This.scrollToBottom确实被调用,但它不会滚动到元素的底部。有人能看出原因吗?

chat-window.component.ts:在ngOnchanges中我们在调用this.scrollToBottom()之前会做一些同步的事情。

export class ChatboxWindowComponent implements OnChanges, OnInit, AfterViewChecked {

  @Input('conversation') conversation;
  @ViewChild('window') window;

  constructor() { }

  ngOnChanges() {
    // If the date separators have already been added once, we avoid doing it a second time
    const existingDateObj = this.conversation.messages.findIndex((item, i) => item.dateObj);

    if (existingDateObj === -1) {
      this.conversation.messages.forEach( (item, index, array) => {
        if (index !== 0) {
          const date1 = new Date(array[index - 1].date);
          const date2 = new Date(item.date);

          if (date2.getDate() !== date1.getDate() || date2.getMonth() !== date1.getMonth()) {
            this.conversation.messages.splice(index, 0, {date: date2, dateObj: true});
            console.log(this.conversation.messages.length);
          }
        }
      });
    }

    this.scrollToBottom();
  }

  ngOnInit() {
  }

  ngAfterViewChecked() {
  }

  isItMyMsg(msg) {
    return msg.from._id === this.conversation.otherUser.userId;
  }

  scrollToBottom() {
    try {
      console.log('scrollToBottom called');
      this.window.nativeElement.top = this.window.nativeElement.scrollHeight;
    } catch (err) {}
  }
}

chat-window.component.html

<div #window class="window">
  <ng-container *ngFor="let message of conversation.messages">
    <div class="date-container" *ngIf="!message.msg; else windowMsg">
      <p class="date">{{message.date | amDateFormat:'LL'}}</p>
    </div>
    <ng-template #windowMsg>
      <p
        class="window__message"
        [ngClass]="{
    'window__message--left': isItMyMsg(message),
    'window__message--right': !isItMyMsg(message)
    }"
      >
        {{message.msg}}
      </p>
    </ng-template>
  </ng-container>
</div>


推荐答案

滚动不起作用,因为消息列表当您调用 scrollToBottom 时,尚未呈现。要在显示消息后滚动,请设置模板消息容器上的引用变量(例如 #messageContainer ):

The scroll doesn't work because the list of messages is not rendered yet when you call scrollToBottom. In order to scroll once the messages have been displayed, set a template reference variable (e.g. #messageContainer) on the message containers:

<ng-container #messageContainer *ngFor="let message of conversation.messages">
  ...
</ng-container>

在代码中,您可以使用 ViewChildren 并在触发 QueryList.changes 事件时滚动窗口:

In the code, you can then access these elements with ViewChildren and scroll the window when the QueryList.changes event is triggered:

@ViewChildren("messageContainer") messageContainers: QueryList<ElementRef>;

ngAfterViewInit() {
  this.scrollToBottom(); // For messsages already present
  this.messageContainers.changes.subscribe((list: QueryList<ElementRef>) => {
    this.scrollToBottom(); // For messages added later
  });
}

这篇关于Angular:无法向下滚动到元素的底部的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆