run pumpmessageloop in its own loop

This commit is contained in:
Pierre Tachoire
2025-07-02 13:16:20 -07:00
parent 1504e36a68
commit 44a76e59f9
2 changed files with 18 additions and 0 deletions

View File

@@ -98,6 +98,10 @@ pub const Browser = struct {
pub fn runMicrotasks(self: *const Browser) void { pub fn runMicrotasks(self: *const Browser) void {
self.env.runMicrotasks(); self.env.runMicrotasks();
}
pub fn runMessageLoop(self: *const Browser) void {
log.debug(.browser, "pumpMessageLoop", .{});
while (self.env.pumpMessageLoop()) { while (self.env.pumpMessageLoop()) {
log.debug(.browser, "pumpMessageLoop", .{}); log.debug(.browser, "pumpMessageLoop", .{});
} }

View File

@@ -78,7 +78,10 @@ pub const Page = struct {
renderer: Renderer, renderer: Renderer,
// run v8 micro tasks
microtask_node: Loop.CallbackNode, microtask_node: Loop.CallbackNode,
// run v8 pump message loop and idle tasks
messageloop_node: Loop.CallbackNode,
keydown_event_node: parser.EventNode, keydown_event_node: parser.EventNode,
window_clicked_event_node: parser.EventNode, window_clicked_event_node: parser.EventNode,
@@ -106,6 +109,7 @@ pub const Page = struct {
.state_pool = &browser.state_pool, .state_pool = &browser.state_pool,
.cookie_jar = &session.cookie_jar, .cookie_jar = &session.cookie_jar,
.microtask_node = .{ .func = microtaskCallback }, .microtask_node = .{ .func = microtaskCallback },
.messageloop_node = .{ .func = messageLoopCallback },
.keydown_event_node = .{ .func = keydownCallback }, .keydown_event_node = .{ .func = keydownCallback },
.window_clicked_event_node = .{ .func = windowClicked }, .window_clicked_event_node = .{ .func = windowClicked },
.request_factory = browser.http_client.requestFactory(.{ .request_factory = browser.http_client.requestFactory(.{
@@ -119,6 +123,10 @@ pub const Page = struct {
try polyfill.load(self.arena, self.main_context); try polyfill.load(self.arena, self.main_context);
_ = try session.browser.app.loop.timeout(1 * std.time.ns_per_ms, &self.microtask_node); _ = try session.browser.app.loop.timeout(1 * std.time.ns_per_ms, &self.microtask_node);
// message loop must run only non-test env
if (comptime !builtin.is_test) {
_ = try session.browser.app.loop.timeout(1 * std.time.ns_per_ms, &self.messageloop_node);
}
} }
fn microtaskCallback(node: *Loop.CallbackNode, repeat_delay: *?u63) void { fn microtaskCallback(node: *Loop.CallbackNode, repeat_delay: *?u63) void {
@@ -127,6 +135,12 @@ pub const Page = struct {
repeat_delay.* = 1 * std.time.ns_per_ms; repeat_delay.* = 1 * std.time.ns_per_ms;
} }
fn messageLoopCallback(node: *Loop.CallbackNode, repeat_delay: *?u63) void {
const self: *Page = @fieldParentPtr("messageloop_node", node);
self.session.browser.runMessageLoop();
repeat_delay.* = 100 * std.time.ns_per_ms;
}
// dump writes the page content into the given file. // dump writes the page content into the given file.
pub fn dump(self: *const Page, out: std.fs.File) !void { pub fn dump(self: *const Page, out: std.fs.File) !void {
if (self.raw_data) |raw_data| { if (self.raw_data) |raw_data| {