Apakah ada cara untuk menghapus semua waktu tunggu dari jendela tertentu? Saya kira batas waktu disimpan di suatu tempat di window
objek tetapi tidak dapat memastikannya.
Solusi lintas browser apa pun diterima.
Apakah ada cara untuk menghapus semua waktu tunggu dari jendela tertentu? Saya kira batas waktu disimpan di suatu tempat di window
objek tetapi tidak dapat memastikannya.
Solusi lintas browser apa pun diterima.
Jawaban:
Mereka tidak ada di objek jendela, tetapi mereka memiliki id, yang (afaik) adalah bilangan bulat berurutan.
Jadi, Anda dapat menghapus semua waktu tunggu seperti ini:
var id = window.setTimeout(function() {}, 0);
while (id--) {
window.clearTimeout(id); // will do nothing if no timeout with id is present
}
Saya pikir cara termudah untuk mencapai ini adalah dengan menyimpan semua setTimeout
pengenal dalam satu larik, di mana Anda dapat dengan mudah beralih ke clearTimeout()
semuanya.
var timeouts = [];
timeouts.push(setTimeout(function(){alert(1);}, 200));
timeouts.push(setTimeout(function(){alert(2);}, 300));
timeouts.push(setTimeout(function(){alert(3);}, 400));
for (var i=0; i<timeouts.length; i++) {
clearTimeout(timeouts[i]);
}
Saya memiliki tambahan jawaban Pumbaa80 yang mungkin berguna bagi seseorang yang mengembangkan IE lama.
Ya, semua browser utama menerapkan id waktu tunggu sebagai bilangan bulat berurutan (yang tidak diwajibkan oleh spesifikasi ). Melalui nomor awal berbeda dari browser ke browser. Tampaknya Opera, Safari, Chrome dan IE> 8 memulai id batas waktu dari 1, peramban berbasis Gecko dari 2 dan IE <= 8 dari beberapa nomor acak yang secara ajaib disimpan di seluruh penyegaran tab. Anda bisa menemukannya sendiri .
Semua itu berarti bahwa di IE <= 8 while (lastTimeoutId--)
siklus dapat berjalan lebih dari 8 digit kali dan menampilkan pesan " Skrip di halaman ini menyebabkan Internet Explorer berjalan lambat ". Jadi jika Anda tidak dapat menyimpan semua id batas waktu Anda atau tidak ingin menimpa window.setTimeout Anda dapat mempertimbangkan untuk menyimpan id batas waktu pertama pada halaman dan menghapus batas waktu sampai itu.
Jalankan kode pada pemuatan halaman awal:
var clearAllTimeouts = (function () {
var noop = function () {},
firstId = window.setTimeout(noop, 0);
return function () {
var lastId = window.setTimeout(noop, 0);
console.log('Removing', lastId - firstId, 'timeout handlers');
while (firstId != lastId)
window.clearTimeout(++firstId);
};
});
Dan kemudian hapus semua waktu tunggu yang tertunda yang mungkin telah diatur oleh kode asing berkali-kali yang Anda inginkan
Bagaimana dengan menyimpan id batas waktu dalam larik global, dan menentukan metode untuk mendelegasikan panggilan fungsi ke jendela.
GLOBAL={
timeouts : [],//global timeout id arrays
setTimeout : function(code,number){
this.timeouts.push(setTimeout(code,number));
},
clearAllTimeout :function(){
for (var i=0; i<this.timeouts.length; i++) {
window.clearTimeout(this.timeouts[i]); // clear all the timeouts
}
this.timeouts= [];//empty the id array
}
};
Anda harus menulis ulang window.setTimeout
metode dan menyimpan ID batas waktunya.
const timeouts = [];
const originalTimeoutFn = window.setTimeout;
window.setTimeout = function(fun, delay) { //this is over-writing the original method
const t = originalTimeoutFn(fn, delay);
timeouts.push(t);
}
function clearTimeouts(){
while(timeouts.length){
clearTimeout(timeouts.pop();
}
}
Letakkan kode di bawah ini sebelum skrip lain dan itu akan membuat fungsi pembungkus untuk setTimeout
& clearTimeout
.
clearTimeouts
Metode baru akan ditambahkan ke window
Objek, yang memungkinkan penghapusan semua batas waktu (menunggu) ( tautan inti ).
Jawaban lain kekurangan dukungan lengkap untuk kemungkinan argumen yang
setTimeout
mungkin diterima.
// isolated layer wrapper (for the local variables)
(function(_W){
var cache = [], // will store all timeouts IDs
_set = _W.setTimeout, // save original reference
_clear = _W.clearTimeout // save original reference
// Wrap original setTimeout with a function
_W.setTimeout = function( CB, duration, arg ){
// also, wrap the callback, so the cache reference will be removed
// when the timeout has reached (fired the callback)
var id = _set(function(){
CB.apply(null, arguments)
removeCacheItem(id)
}, duration || 0, arg)
cache.push( id ) // store reference in the cache array
// id reference must be returned to be able to clear it
return id
}
// Wrap original clearTimeout with a function
_W.clearTimeout = function( id ){
_clear(id)
removeCacheItem(id)
}
// Add a custom function named "clearTimeouts" to the "window" object
_W.clearTimeouts = function(){
console.log("Clearing " + cache.length + " timeouts")
cache.forEach(n => _clear(n))
cache.length = []
}
// removes a specific id from the cache array
function removeCacheItem( id ){
var idx = cache.indexOf(id)
if( idx > -1 )
cache = cache.filter(n => n != id )
}
})(window);
Untuk kelengkapan, saya ingin memposting solusi umum yang mencakup setTimeout
dan setInterval
.
Tampaknya browser mungkin menggunakan kumpulan ID yang sama untuk keduanya, tetapi dari beberapa jawaban untuk Apakah clearTimeout dan clearInterval sama? , tidak jelas apakah aman mengandalkan clearTimeout
dan clearInterval
menjalankan fungsi yang sama atau hanya bekerja pada jenis pengatur waktu masing-masing.
Oleh karena itu, jika tujuannya adalah untuk menghentikan semua waktu tunggu dan interval, berikut adalah penerapan yang mungkin sedikit lebih defensif di seluruh penerapan saat tidak dapat menguji semuanya:
function clearAll(windowObject) {
var id = Math.max(
windowObject.setInterval(noop, 1000),
windowObject.setTimeout(noop, 1000)
);
while (id--) {
windowObject.clearTimeout(id);
windowObject.clearInterval(id);
}
function noop(){}
}
Anda dapat menggunakannya untuk menghapus semua timer di jendela saat ini:
clearAll(window);
Atau Anda dapat menggunakannya untuk menghapus semua pengatur waktu di iframe
:
clearAll(document.querySelector("iframe").contentWindow);
Saya menggunakan Vue dengan Typecript.
private setTimeoutN;
private setTimeoutS = [];
public myTimeoutStart() {
this.myTimeoutStop();//stop All my timeouts
this.setTimeoutN = window.setTimeout( () => {
console.log('setTimeout');
}, 2000);
this.setTimeoutS.push(this.setTimeoutN)//add THIS timeout ID in array
}
public myTimeoutStop() {
if( this.setTimeoutS.length > 0 ) {
for (let id in this.setTimeoutS) {
console.log(this.setTimeoutS[id]);
clearTimeout(this.setTimeoutS[id]);
}
this.setTimeoutS = [];//clear IDs array
}
}
Gunakan waktu tunggu global tempat semua fungsi Anda lainnya mendapatkan pengaturan waktu. Ini akan membuat semuanya berjalan lebih cepat, dan lebih mudah dikelola, meskipun itu akan menambahkan beberapa abstraksi ke kode Anda.
set_timeout
fungsi global? Bisakah Anda memberikan contoh kode?
Kami baru saja menerbitkan paket yang memecahkan masalah ini.
npm install time-events-manager
Dengan itu, Anda dapat melihat semua waktu tunggu dan interval melalui timeoutCollection
& intervalCollection
objek. Ada juga removeAll
fungsi yang menghapus semua waktu tunggu / interval baik dari koleksi dan browser.
Ini sudah sangat terlambat ... tapi:
Pada dasarnya, setTimeout / setInterval ID berjalan berurutan, jadi buat saja fungsi waktu tunggu dummy untuk mendapatkan ID tertinggi, lalu hapus interval pada semua ID yang lebih rendah dari itu.
const highestId = window.setTimeout(() => {
for (let i = highestId; i >= 0; i--) {
window.clearInterval(i);
}
}, 0);