javascript - 设计程序以便 Angular 不会在每次更新推送到商店时重新渲染 MediaStream 组件?

标签 javascript angular rxjs angular-akita akita

我创建的示例 Angular 应用程序演示了我遇到的问题,可以找到此应用程序 here

基本上我有两个商店,我正在使用状态管理库Akita对于这些商店。两者都是 Entity Stores ,第一个存储用于所有消息,它的签名如下:

interface MessageInterface {
 // Unique identifier
 id: ID;
 // The time is was created
 time: number;
 // The actual string message
 value: string;
} 

第二个商店适用于我的所有连接,连接具有如下签名:

interface ConnectionInterface {
  // Unique identifier
  id: ID;
  // The MediaStream (webcam stream object)
  stream: MediaStream;
  // An array of unique ids where each id relates to an id in the MessageStore
  messages: ID[] | MessageInterface[]
}

以下是应用程序启动时执行的步骤:

  1. 使用 getUserMedia 启动网络摄像头流。
  2. 然后将生成的流保存到 ConnectionStore 中。
  3. 然后开始每秒创建 1 条消息,创建每条消息后,将消息保存到 MessageStore 中,然后通过将创建的消息的索引添加到消息数组的开头来将该消息与 ConnectionStore 关联起来。 ConnectionStore 实体。

以下是两家商店最终的样子:

消息存储:

entities: {
  3ea9454682: {id: "3ea9454682", time: 1548117443764, value: "CIAO"}
  4a66b34aad: {id: "4a66b34aad", time: 1548117444765, value: "SALAAM"}
  4e165d4887: {id: "4e165d4887", time: 1548117445767, value: "SALAAM"}
  4eb22b42a6: {id: "4eb22b42a6", time: 1548117441763, value: "BONJOUR"}
  5cbc594983: {id: "5cbc594983", time: 1548117447771, value: "HELLO"}
  6c574e44a8: {id: "6c574e44a8", time: 1548117446770, value: "NAMASTE"}
  bfdcc344aa: {id: "bfdcc344aa", time: 1548117448771, value: "NAMASTE"}
  c7c55d45a7: {id: "c7c55d45a7", time: 1548117440762, value: "NAMASTE"}
  cc86a045af: {id: "cc86a045af", time: 1548117442764, value: "HOLA"}
  fd2cf744ab: {id: "fd2cf744ab", time: 1548117439760, value: "CIAO"}
}

连接存储:

entities: {
  fda7464bbe: {
     id: "fda7464bbe",
     mediaStream: {
       active: true
       id: "bQO4NI86L7pEHNzEwEK9dVht5wtHf5s81TfV"
       onactive: null
       onaddtrack: null
       oninactive: null
       onremovetrack: null
     },
     messages: [
       "bfdcc344aa"
       "5cbc594983"
       "6c574e44a8"
       "4e165d4887"
       "4a66b34aad"
       "3ea9454682"
       "cc86a045af"
       "4eb22b42a6"
       "c7c55d45a7"
       "fd2cf744ab"
     ]
  }
}

我遇到的问题是每次我生成消息并将其保存到存储中时,您都会看到网络摄像头视频闪烁。也许我构建的结构是错误的?也许有一种方法可以只重新渲染消息而不让它影响流?任何建议都会有很大的帮助,感谢任何尝试解决这个问题的人!

最佳答案

您可以通过在 ngFor 中使用 trackBy 来解决问题:

<li *ngFor="let connection of connections | async; trackBy: trackByFunction">

在 typescript 中像这样声明 trackByFunction:

trackByFunction(index, item) {
  return index;
}

这有助于 Angular 跟踪列表中添加或删除的项目,并仅重新渲染已更改的项目。

我必须将以下内容添加到您的 polyfills.ts 文件中才能使其编译:

import 'core-js/es7/reflect';

希望有帮助。

关于javascript - 设计程序以便 Angular 不会在每次更新推送到商店时重新渲染 MediaStream 组件?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54315072/

相关文章:

javascript - HTML, javascript 启用禁用按钮

javascript - 使用 reactjs 进行电子邮件 otp 验证

javascript - 修复按钮保持禁用状态,直到用户也选中复选框

javascript - 如何使用 tensorflow.js 以 Angular 正确上传预训练模型?

javascript - 在重新执行之前从 Observable 获取值

javascript - 从一个未柯里化(Currying)的函数组成一个函数

javascript - 错误 TypeError : array. map 不是 Angular 管道中的函数

javascript - 如何从 rxjs from(array) 获取数组

angular - Observable.next() 不是函数

javascript - 查询参数对 Angular2+ 没有影响