Pracuję nad rozszerzeniem w Chrome i zastanawiam się: jaki jest najlepszy sposób, aby dowiedzieć się, kiedy powstaje element? Używając zwykłego javascript, z interwałem sprawdzającym, aż element będzie istniał, czy też jQuery ma jakiś łatwy sposób to zrobić?
236
MutationObserver
>DOM Mutation Events
>setTimeout
.setTimeout
jest kompatybilny, prosty w implementacji, prosty w utrzymaniu i ma znikomy narzut.setTimeout
+jQuery
jest moim zdaniem mniej niż idealny z dwóch powodów: 1.) wzdęcia jQuery 2.) niepotrzebnie ręcznie sprawdzasz DOM w poszukiwaniu elementów, zdarzenia szybko biją tak szybko, 3.) zawsze będzie wolniejszy niż jakikolwiek natywny realizacja. Jeśli musisz zrobić coś w oparciu o obecność elementu dość szybko, zwłaszcza jeśli Twoim celem jest bezproblemowa obsługa, jest gorszy.Odpowiedzi:
DOMNodeInserted
jest przestarzałe, podobnie jak inne zdarzenia mutacji DOM, z powodu problemów z wydajnością - zalecanym podejściem jest użycie MutationObserver do oglądania DOM. Jest obsługiwany tylko w nowszych przeglądarkach, więc powinieneś wrócić do niego,DOMNodeInserted
gdyMutationObserver
nie jest dostępny.źródło
if (mutation.addedNodes.length)
ponieważif (mutation.addedNodes)
nadal zwróciłoby wartość true, nawet jeśli jest to pusta tablica. (2) Nie możesz tego zrobić,mutation.addedNodes.forEach()
ponieważ addedNodes to nodeList i nie możesz iterować przez nodeList za pomocą forEach. Aby znaleźć rozwiązanie tego problemu, zobacz toddmotto.com/ditch-the-array-foreach-call-nodelist-hackMiałem ten sam problem, więc napisałem wtyczkę .
$(selector).waitUntilExists(function);
Kod:
źródło
window.setInterval
). Nie wiem, czyMutationObserver
odpowiedź zadziała również przez ankietę ...;
na początku funkcji (;(function ($, window) {
)?Oto podstawowa funkcja JavaScript, która czeka na wyświetlenie elementu.
Parametry:
selector
: Ta funkcja szuka elementu $ {selector}time
: Ta funkcja sprawdza, czy ten element istnieje co milisekundy $ {time}.Na przykład ustawiam
selector="#div1"
itime=5000
będzie szukał znacznika HTML, któregoid="div1"
każde 5000 milisekund.źródło
querySelector
? developer.mozilla.org/en-US/docs/Web/API/Document/querySelectorMożesz słuchać
DOMNodeInserted
lubDOMSubtreeModified
zdarzeń, które są uruchamiane, gdy nowy element jest dodawany do DOM.Istnieje również wtyczka jQuery LiveQuery, która wykrywa, kiedy tworzony jest nowy element:
źródło
Użyłem tego podejścia, aby poczekać na pojawienie się elementu, aby potem móc wykonać inne funkcje.
Powiedzmy, że
doTheRestOfTheStuff(parameters)
funkcję należy wywołać dopiero pothe_Element_ID
pojawieniu się elementu o identyfikatorze lub zakończeniu ładowania, możemy użyć,źródło
Możesz to zrobić
Należy pamiętać, że zadziała to tylko wtedy, gdy element będzie obecny w DOM, gdy zostanie o to poproszony z serwera. Jeśli element jest dynamicznie dodawany przez JavaScript, nie będzie działać i być może będziesz musiał spojrzeć na inne odpowiedzi.
źródło
.ready()
funkcja działa na prawie wszystko (jeśli nie na nic), nie tylkodocument
. Po prostu nie będzie działać z dynamicznie tworzonymi elementami, nawet na.live()
.$(document).ready()
, a nie element, który Twoim zdaniem będzie miał zastosowanie. Właśnie tak działa ten specjalny słuchacz. PrzykładMyślę, że wciąż nie ma tu odpowiedzi na łatwy i czytelny przykład działania. Użyj MutationObserver,
interface
aby wykryć zmiany DOM, takie jak to:źródło
Po prostu dodaj żądany selektor. Po znalezieniu elementu możesz uzyskać dostęp do funkcji wywołania zwrotnego.
źródło
Dla prostego podejścia przy użyciu jQuery okazało się, że działa dobrze:
Tutaj po prostu sprawdzamy co 500 ms, aby zobaczyć, czy element jest załadowany, a kiedy jest, możemy go użyć.
Jest to szczególnie przydatne do dodawania procedur obsługi kliknięć do elementów, które zostały dynamicznie dodane do dokumentu.
źródło
Co powiesz na bibliotekę insertionQuery ?
insertionQuery używa wywołań zwrotnych Animacji CSS dołączonych do określonych selektorów, aby uruchomić wywołanie zwrotne podczas tworzenia elementu. Ta metoda umożliwia uruchamianie wywołań zwrotnych za każdym razem, gdy tworzony jest element, a nie tylko za pierwszym razem.
Z github:
źródło
Oto funkcja, która działa jak cienkie opakowanie wokół MutationObserver. Jedynym wymaganiem jest to, że przeglądarka obsługuje MutationObserver; nie ma zależności od JQuery. Uruchom poniższy fragment kodu, aby zobaczyć działający przykład.
źródło
Oto obiecujące rozwiązanie w waniliowym JavaScript (bez niechlujnych wywołań zwrotnych). Domyślnie sprawdza co 200 ms.
źródło
Oto czysta funkcja Javascript, która pozwala na cokolwiek czekać. Ustaw interwał dłużej, aby zajął mniej zasobów procesora.
Aby to nazwać, na przykład w jQuery, użyj czegoś takiego:
źródło
Rozwiązanie zwracające
Promise
i pozwalające na użycie limitu czasu (zgodny IE 11+).W przypadku pojedynczego elementu (typ Element):
W przypadku wielu elementów (wpisz NodeList):
Przykłady:
Działa zarówno z listą elementów, jak i pojedynczym elementem.
źródło
element instanceof HTMLElement
? Czy może to być coś innego niżnull
lubHTMLElement
?Element
zamiast tego (naprawiony). Po prostu sprawdzam, ponieważ chcę mieć pewność, że zmiennaelement
ma właściwość,innerHTML
jak stwierdza dokumentacja Element MDN . Możesz go usunąć, jeśli Cię to nie obchodzi!Czystszy przykład przy użyciu MutationObserver:
źródło
Jest to proste rozwiązanie dla tych, którzy są przyzwyczajeni do obietnic i nie chcą używać żadnych bibliotek ani timerów stron trzecich.
Od jakiegoś czasu używam go w swoich projektach
Aby go użyć:
lub za pomocą async / czekaj
źródło
async
/await
też. Być może będziesz w stanie wycisnąć z niego większą wydajność, robiącmutations.addedNodes.find(node => node.matchesSelector("..."))
Jeśli chcesz, aby przestał się troszczyć po pewnym czasie (limit czasu), będzie działać następujący jQuery. Upłynie limit czasu po 10 sekundach. Musiałem użyć tego kodu zamiast czystego JS, ponieważ musiałem wybrać dane wejściowe według nazwy i miałem problem z implementacją niektórych innych rozwiązań.
źródło
Zwykle używam tego fragmentu dla Menedżera tagów:
źródło
jeśli masz asynchroniczne zmiany w domach, ta funkcja sprawdza (z limitem czasu w sekundach) elementy DOM, nie będzie to trudne dla DOM i opartej na nim obietnicy :)
źródło