【问题标题】:What is the difference between happening of event on element and emiiting an event from element in dom?在元素上发生事件和从 dom 中的元素发出事件有什么区别?
【发布时间】:2019-04-20 17:57:11
【问题描述】:

我想了解当我单击一个 dom 元素时,该元素上会发生单击事件并调用相关的事件处理函数。这是一个异步函数的基本示例。 我的问题与这背后的实现有关。 当我们单击用户屏幕上的任何 dom 元素时,会发生单击事件。在元素上发生事件与逐个元素发出事件之间有什么区别?发生和发射是一样的吗?如果不是,那有什么区别?

另外当我们注册一个回调函数时,它们在内存中存储在哪里?我不是在这里询问事件循环(主堆栈和回调队列)。

事件对象是如何创建的以及是谁创建的? 事件如何映射到关联的回调函数?

【问题讨论】:

    标签: javascript asynchronous reactive-programming pure-function


    【解决方案1】:

    哇,一下子问了很多问题。呵呵,元帅们不会喜欢吧!但这也需要一个长而详细的答案。

    在元素上发生事件和逐个元素发出事件有什么区别?

    这种差异[还]不是传统的。所以这主要来自我自己的观察,我想很少有人会不同意我的观点。

    发生和发射是一样的吗?

    不,它们是不同的。

    如果不是,那有什么区别?

    发生是用户实际做了一些事情:单击、滚动、拖动开始、拖动结束、悬停、右键单击等...

    发射是与发生相关的逻辑。实际上,您可以在不等待特定事件发生的情况下运行事件发射。

    示例:

    以下代码为点击事件附加了一个监听器。

    const actionable = document.querySelector( 'button[type="button"]' );
    
    actionable.addEventListener( 'click', () =>
    {
        alert( 'Clicked me' );
    });
    <button type="button" class="click-me">
      Click me
    </button>

    只要click 事件发出,就会执行那里的回调。 请注意,我说过,当click 事件将被发出时。 (不是用户点击它的时候。)

    现在,网络浏览器确保当用户点击时,click 事件被触发,并且 DOM API 确保我们的回调被执行。 这是启动它的用户所发生的事情。

    但是,我们仍然可以在没有用户实际点击的情况下模仿这种行为。

    const actionable = document.querySelector( 'button[type="button"]' );
    const actionableState = document.querySelector( 'button[type="button"] > span' );
    
    const hoverable = document.querySelector( 'div.hover-me' );
    const hoverableState = document.querySelector( 'div.hover-me > span' );
    
    let count = 0;
    
    actionable.addEventListener( 'click', () =>
    {
        actionableState.innerText = ++count;
    });
    
    hoverable.addEventListener( 'mouseenter', () =>
    {
        hoverableState.innerText = 'Hovered';
        
        const event = new Event( 'click' );
        
        actionable.dispatchEvent( event );
    });
    
    hoverable.addEventListener( 'mouseout', () =>
    {
        hoverableState.innerText = '-';
    });
    .click-me > span {
        font-style: italic;
    }
    .click-me > span:before { content: '[ '; }
    .click-me > span:after { content: ' time(s) ]'; }
    
    .hover-me {
        padding: 3em;
        margin: 1em 0;
        text-align: center;
        border-radius: 3px;
        background-color: red;
        display: inline-block;
    }
    <button type="button" class="click-me">
        Click me <span>0</span>
    </button>
    
    <div class="hover-me">
        Hover me, please
        <br/>
        <span>-</span>
    </div>

    当用户悬停该框时,我们模拟click 事件。我们创建了一个人工点击事件并发出它 (dispatchEvent())。 这基本上是事件发射。

    它们在内存中的存储位置?

    是的,在内存中。当页面死掉(或关闭)或 JS 运行时崩溃时,它们都会消失。

    事件如何映射到相关的回调函数?

    这个依赖于实现。如果您真的致力于了解它是如何实现的,您可以查看this Event API implementation:它是 TypeScript,但您不会觉得很难。 (我承认代码有一堆 cmets)。但是当我在那里使用 Wea​​kMap 时,其他实现依赖于对象映射 + 数组或事件集。

    如果不是,那有什么区别?

    发生的事件和手工制作的事件之间的内部区别在于isTrusted(布尔)属性,当事件由用户操作/输入触发时为true,否则为false。是documented here

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2023-04-06
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-08-11
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多