2017-09-26 91 views
2

當用戶單擊鏈接或提交表單時,我希望觸發並忘記請求,且延遲時間很短。這裏有一個簡單的代碼,我使用的是:在Chrome中延遲提交表單

element.addEventListener(eventType, function(event) { 
    if (event.retriggered) { 
    return true; 
    } 

    let target = event.target; 
    let newEvent = new event.constructor(event.type, event); 
    newEvent.retriggered = true; 

    setTimeout(() => { 
    target.dispatchEvent(newEvent); 
    }, 250); 

    // fire and forget the request 
    makeRequest(); 

    event.preventDefault(); 
    return false; 
}); 

這工作正常click事件和它工作得很好submit事件在Firefox,但無法在Chrome。我創建了一個fiddle here。在Firefox中,如果您單擊該按鈕,則可以看到瀏覽器發出GET請求,但在Chrome中不會發生這種情況。根據我的測試,兩個瀏覽器中的原始和新事件看起來都一樣,並且dispatchEvent返回true。儘管如此,實際提交併未在Chrome中觸發,因此我想知道Chrome會停止提交作爲安全措施,還是我錯過了某些內容?

回答

1

您正在調度的事件與您要複製的事件至少有一點不同。您的活動將事件的isTrusted屬性設置爲false。也許這就是Chrome不提交表單的原因。

我所知道的是你如何才能得到你想要的結果,對於表單,稍微不同的代碼。我已經基於你的Fiddle中的代碼,所以它現在只處理表單提交。

let 
 
    form = document.getElementById('form'); 
 

 
form.addEventListener('submit', function(event) { 
 
    setTimeout(() => { 
 
    form.submit(); 
 
    }, 250); 
 

 
    event.preventDefault(); 
 
});
<form id="form" method="get" action="/echo/html/"> 
 
    <button type="submit">Go</button> 
 
</form>

而是派遣自己提交的事件,你可以調用窗體的方法submit()。這將提交表單,但不會導致任何提交處理程序被解僱(根據this MDN文章)。它可以節省您在處理程序中的檢查,以確定提交是否應該延遲。

你可以調整它也與錨工作。

let 
 
    form = document.getElementById('form'), 
 
    anchor = document.getElementById('anchor'); 
 

 
function onDelayNavigationEvent(event) { 
 
    const 
 
    target = event.target; 
 
    
 
    if (target.hasAttribute('is-delayed')) { 
 
    return true; 
 
    } 
 
    
 
    setTimeout(() => { 
 
    if (target.tagName.toLowerCase() === 'form') { 
 
     target.submit(); 
 
    } else { 
 
     target.click(); 
 
    } 
 
    }, 2000); 
 
    
 
    target.setAttribute('is-delayed', true); 
 
    event.preventDefault(); 
 
} 
 

 
function delayNavigation(element, eventName) { 
 
    element.addEventListener(eventName, onDelayNavigationEvent); 
 
} 
 

 
delayNavigation(form, 'submit'); 
 
delayNavigation(anchor, 'click');
<form id="form" method="get" action="/echo/html/"> 
 
    <button type="submit">Go</button> 
 
</form> 
 

 
<a id="anchor" href="//stackoverflow.com">Stack Overflow</a>

+0

這樣的作品,謝謝。我所期待的,不包括特殊情況下的解決方案,但它似乎是Chrome的安全功能防止觸發表單提交程序的事件。 –

+0

你可以嘗試'目標[event.type]();'如果你真的不喜歡的'form'元素的檢查。 – Thijs