@@ -155,6 +155,12 @@ pub const Window = struct {
155155 return 99 ; // not unique, but user cannot make assumptions about it. cancelAnimationFrame will be too late anyway.
156156 }
157157
158+ // Cancels an animation frame request previously scheduled through requestAnimationFrame().
159+ // This is a no-op since _requestAnimationFrame immediately executes the callback.
160+ pub fn _cancelAnimationFrame (_ : * Window , request_id : u32 ) void {
161+ _ = request_id ;
162+ }
163+
158164 // TODO handle callback arguments.
159165 pub fn _setTimeout (self : * Window , cbk : Callback , delay : ? u32 , state : * SessionState ) ! u32 {
160166 return self .createTimeout (cbk , delay , state , false );
@@ -254,3 +260,35 @@ const TimerCallback = struct {
254260 _ = self .window .timers .remove (self .timer_id );
255261 }
256262};
263+
264+ const testing = @import ("../../testing.zig" );
265+ test "Browser.HTML.Window" {
266+ var runner = try testing .jsRunner (testing .tracking_allocator , .{});
267+ defer runner .deinit ();
268+
269+ // requestAnimationFrame should be able to wait by recursively calling itself
270+ // Note however that we in this test do not wait as the request is just send to the browser
271+ try runner .testCases (&.{
272+ .{
273+ \\ let start;
274+ \\ function step(timestamp) {
275+ \\ if (start === undefined) {
276+ \\ start = timestamp;
277+ \\ }
278+ \\ const elapsed = timestamp - start;
279+ \\ if (elapsed < 2000) {
280+ \\ requestAnimationFrame(step);
281+ \\ }
282+ \\ }
283+ ,
284+ "undefined" ,
285+ },
286+ .{ "let id = requestAnimationFrame(step);" , "undefined" },
287+ }, .{});
288+
289+ // cancelAnimationFrame should be able to cancel a request with the given id
290+ try runner .testCases (&.{
291+ .{ "let request_id = requestAnimationFrame(timestamp => {});" , "undefined" },
292+ .{ "cancelAnimationFrame(request_id);" , "undefined" },
293+ }, .{});
294+ }
0 commit comments