فهرست منبع

LibWeb: Make HTMLImageElement loads delay the document load event

This is something we're supposed to do according to the HTML spec.
Note that image loading is currently completely ad-hoc, and this just
adds a simple DocumentLoadEventDelayer to the existing implementation.

This will allow us to use images in layout tests, which rely on the
document load event firing at a predictable time.
Andreas Kling 2 سال پیش
والد
کامیت
2413de7e10
2فایلهای تغییر یافته به همراه8 افزوده شده و 1 حذف شده
  1. 5 1
      Userland/Libraries/LibWeb/HTML/HTMLImageElement.cpp
  2. 3 0
      Userland/Libraries/LibWeb/HTML/HTMLImageElement.h

+ 5 - 1
Userland/Libraries/LibWeb/HTML/HTMLImageElement.cpp

@@ -28,6 +28,7 @@ HTMLImageElement::HTMLImageElement(DOM::Document& document, DOM::QualifiedName q
         this->document().set_needs_layout();
         this->document().set_needs_layout();
         queue_an_element_task(HTML::Task::Source::DOMManipulation, [this] {
         queue_an_element_task(HTML::Task::Source::DOMManipulation, [this] {
             dispatch_event(DOM::Event::create(this->realm(), EventNames::load).release_value_but_fixme_should_propagate_errors());
             dispatch_event(DOM::Event::create(this->realm(), EventNames::load).release_value_but_fixme_should_propagate_errors());
+            m_load_event_delayer.clear();
         });
         });
     };
     };
 
 
@@ -37,6 +38,7 @@ HTMLImageElement::HTMLImageElement(DOM::Document& document, DOM::QualifiedName q
         this->document().set_needs_layout();
         this->document().set_needs_layout();
         queue_an_element_task(HTML::Task::Source::DOMManipulation, [this] {
         queue_an_element_task(HTML::Task::Source::DOMManipulation, [this] {
             dispatch_event(DOM::Event::create(this->realm(), EventNames::error).release_value_but_fixme_should_propagate_errors());
             dispatch_event(DOM::Event::create(this->realm(), EventNames::error).release_value_but_fixme_should_propagate_errors());
+            m_load_event_delayer.clear();
         });
         });
     };
     };
 
 
@@ -83,8 +85,10 @@ void HTMLImageElement::parse_attribute(DeprecatedFlyString const& name, Deprecat
 {
 {
     HTMLElement::parse_attribute(name, value);
     HTMLElement::parse_attribute(name, value);
 
 
-    if (name == HTML::AttributeNames::src && !value.is_empty())
+    if (name == HTML::AttributeNames::src && !value.is_empty()) {
         m_image_loader.load(document().parse_url(value));
         m_image_loader.load(document().parse_url(value));
+        m_load_event_delayer.emplace(document());
+    }
 
 
     if (name == HTML::AttributeNames::alt) {
     if (name == HTML::AttributeNames::alt) {
         if (layout_node())
         if (layout_node())

+ 3 - 0
Userland/Libraries/LibWeb/HTML/HTMLImageElement.h

@@ -9,6 +9,7 @@
 #include <AK/ByteBuffer.h>
 #include <AK/ByteBuffer.h>
 #include <AK/OwnPtr.h>
 #include <AK/OwnPtr.h>
 #include <LibGfx/Forward.h>
 #include <LibGfx/Forward.h>
+#include <LibWeb/DOM/DocumentLoadEventDelayer.h>
 #include <LibWeb/HTML/FormAssociatedElement.h>
 #include <LibWeb/HTML/FormAssociatedElement.h>
 #include <LibWeb/HTML/HTMLElement.h>
 #include <LibWeb/HTML/HTMLElement.h>
 #include <LibWeb/Loader/ImageLoader.h>
 #include <LibWeb/Loader/ImageLoader.h>
@@ -54,6 +55,8 @@ private:
     virtual JS::GCPtr<Layout::Node> create_layout_node(NonnullRefPtr<CSS::StyleProperties>) override;
     virtual JS::GCPtr<Layout::Node> create_layout_node(NonnullRefPtr<CSS::StyleProperties>) override;
 
 
     ImageLoader m_image_loader;
     ImageLoader m_image_loader;
+
+    Optional<DOM::DocumentLoadEventDelayer> m_load_event_delayer;
 };
 };
 
 
 }
 }