首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >等待dispatchEvent:如何在侦听器异步时同步侦听dispatchEvent

等待dispatchEvent:如何在侦听器异步时同步侦听dispatchEvent
EN

Stack Overflow用户
提问于 2022-01-19 08:50:00
回答 1查看 827关注 0票数 1

为了为软件开发插件,我需要听一听dispatchEvent生成的事件,并在接收到此事件时执行一些操作。重要的是,在软件在dispatchEvent之后继续执行代码之前,我的操作应该完成。

因为dispatchEvent是同步的,所以应该是.不幸的是,我的操作是异步的(基本上我需要等待视频被查找),在这种情况下,dispatchEvent会在我自己的代码结束之前继续运行。当被调用的函数是异步的时,是否也可以获得dispatchEvent的同步行为?

示例:

我想要下面的代码来生成输出:

代码语言:javascript
复制
Putting the clothes in the washing machine.
Machine started...
Machine ended...
Picking the washed clothes.

不幸的是,这些衣服是在洗衣机结束前挑选的:

代码语言:javascript
复制
Putting the clothes in the washing machine.
Machine started...
Picking the washed clothes.
Machine ended...

我使用了这个代码:

代码语言:javascript
复制
var button = document.getElementById('button');
button.addEventListener('click', event => {
  console.log("Putting the clothes in the washing machine.");
  const machineResult = button.dispatchEvent(new CustomEvent('startmachine', {
    'detail': {
      timeProgram: 3000
    }
  }));
  if (machineResult.defaultPrevented) {
    console.log("Picking the dirty clothes.");
  } else {
    console.log("Picking the washed clothes.");
  }
});
button.addEventListener('startmachine', async event => {
  console.log("Machine started...");
  await new Promise(r => setTimeout(r, event.detail.timeProgram));
  console.log("Machine ended...");
});
代码语言:javascript
复制
<button id="button">Wash my clothes</button>

编辑:找到一个我不喜欢的肮脏解决方案

显然,这似乎是不可能的,我使用了一种不同的方法,即unfortunately需要在代码dispatchEvent之后进行一些更改(因为我不负责代码的这一部分,所以我更喜欢在dispatchEvent之后不更改代码的方法)。

这样做的目的是在事件中添加一个数组,每个侦听器都可以在其中放置一个异步函数。然后,在dispatchEvent完成后,代码将执行该数组中的所有函数,如果有任何函数返回false,则会认为该事件已被中止。

代码语言:javascript
复制
  var button = document.getElementById('button');
  button.addEventListener('click', async event => {
      console.log("Putting the clothes in the washing machine.");
      var listOfActions = [];
      const machineResult = button.dispatchEvent(new CustomEvent('startmachine', { 'detail': {timeProgram: 3000, listOfActions: listOfActions} }));
      results = await Promise.all(listOfActions.map(x => x()));
      if (machineResult.defaultPrevented || !results.every(x => x != false)) { // Do not use == true or boolean to ensure returning nothing does not abort.
          console.log("Picking the dirty clothes.");
      } else {
          console.log("Picking the washed clothes.");
      }
  });
  
  button.addEventListener('startmachine', event => {
      event.detail.listOfActions.push( async () => {
          console.log(">>> Machine started...");
          await new Promise(r => setTimeout(r, event.detail.timeProgram));
          console.log("<<< Machine ended...");
          // If you want to say that the clothes are dirty:
          // return false
      });
  });
代码语言:javascript
复制
<button id="button">Wash my clothes</button>

编辑2

使用允诺更好地处理错误:

代码语言:javascript
复制
        var button = document.getElementById('button');
  button.addEventListener('click', async event => {
      console.log("Putting the clothes in the washing machine.");
      var listOfActions = [];
      let cancelled = !button.dispatchEvent(new CustomEvent('startmachine', { 'detail': {timeProgram: 3000, listOfActions: listOfActions} }));
      results = await Promise.all(listOfActions);
      // Do not use == true or boolean to ensure returning nothing does not abort.
      cancelled = cancelled || !results.every(x => x != false)
      if (cancelled) {
          console.log("Picking the dirty clothes.");
      } else {
          console.log("Picking the washed clothes.");
      }
  });
  
  button.addEventListener('startmachine', event => {
      event.detail.listOfActions.push((async () => {
          console.log(">>> Machine started...");
          await new Promise(r => setTimeout(r, event.detail.timeProgram));
          console.log("<<< Machine ended...");
          // If you want to say that the clothes are dirty:
          //return false
      })());
      // ^-- The () is useful to push a promise and not an async function.
      // I could also have written let f = async () => { ... };  event....push(f())
  });
代码语言:javascript
复制
<button id="button">Wash my clothes</button>

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2022-01-19 09:54:31

当被调用的函数是异步的时,

是否也可以获得dispatchEvent的同步行为?

不,不是的。

的思想是在每个侦听器可以放置一个async function的事件中添加一个数组。然后,在完成dispatchEvent之后,代码将执行该数组中的所有函数。

是的,这是个好主意。然而,我要使它成为一系列的承诺,而不是一系列的函数。

web平台API在ExtendableEvent中使用相同的模式。不幸的是,该构造函数仅在服务工作人员内部可用:-/

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/70767676

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档