@@ -18,32 +18,27 @@ function keyEvent(key: number, mods = 0): ZrevEvent {
1818 return { kind : "key" , timeMs : 0 , key, mods, action : "down" } ;
1919}
2020
21- function mouseDownEvent ( x : number , y : number ) : ZrevEvent {
21+ function mouseEvent (
22+ x : number ,
23+ y : number ,
24+ mouseKind : 1 | 2 | 3 | 4 | 5 ,
25+ opts : Readonly < { wheelX ?: number ; wheelY ?: number } > = { } ,
26+ ) : ZrevEvent {
2227 return {
2328 kind : "mouse" ,
2429 timeMs : 0 ,
2530 x,
2631 y,
27- mouseKind : 3 ,
32+ mouseKind,
2833 mods : 0 ,
2934 buttons : 0 ,
30- wheelX : 0 ,
31- wheelY : 0 ,
35+ wheelX : opts . wheelX ?? 0 ,
36+ wheelY : opts . wheelY ?? 0 ,
3237 } ;
3338}
3439
35- function mouseEvent ( x : number , y : number , mouseKind : 1 | 2 | 3 | 4 | 5 ) : ZrevEvent {
36- return {
37- kind : "mouse" ,
38- timeMs : 0 ,
39- x,
40- y,
41- mouseKind,
42- mods : 0 ,
43- buttons : 0 ,
44- wheelX : 0 ,
45- wheelY : 0 ,
46- } ;
40+ function mouseDownEvent ( x : number , y : number ) : ZrevEvent {
41+ return mouseEvent ( x , y , 3 ) ;
4742}
4843
4944function createNoopBackend ( ) : RuntimeBackend {
@@ -560,6 +555,42 @@ describe("WidgetRenderer integration battery", () => {
560555 assert . deepEqual ( selected , [ "b:1" ] ) ;
561556 } ) ;
562557
558+ test ( "virtualList onScroll fires for wheel and key-driven scroll" , ( ) => {
559+ const backend = createNoopBackend ( ) ;
560+ const renderer = new WidgetRenderer < void > ( {
561+ backend,
562+ requestRender : ( ) => { } ,
563+ } ) ;
564+
565+ const scrolled : Array < Readonly < { scrollTop : number ; range : [ number , number ] } > > = [ ] ;
566+
567+ const vnode = ui . virtualList ( {
568+ id : "v" ,
569+ items : new Array < number > ( 100 ) . fill ( 0 ) . map ( ( _ , i ) => i ) ,
570+ itemHeight : 1 ,
571+ renderItem : ( item ) => ui . text ( String ( item ) ) ,
572+ onScroll : ( scrollTop , range ) => scrolled . push ( Object . freeze ( { scrollTop, range } ) ) ,
573+ } ) ;
574+
575+ const res = renderer . submitFrame (
576+ ( ) => vnode ,
577+ undefined ,
578+ { cols : 20 , rows : 10 } ,
579+ defaultTheme ,
580+ noRenderHooks ( ) ,
581+ ) ;
582+ assert . ok ( res . ok ) ;
583+
584+ renderer . routeEngineEvent ( mouseEvent ( 1 , 1 , 5 , { wheelY : 1 } ) ) ;
585+ renderer . routeEngineEvent ( keyEvent ( 3 /* TAB */ ) ) ;
586+ renderer . routeEngineEvent ( keyEvent ( 13 /* END */ ) ) ;
587+
588+ assert . deepEqual ( scrolled , [
589+ { scrollTop : 3 , range : [ 0 , 16 ] } ,
590+ { scrollTop : 90 , range : [ 87 , 100 ] } ,
591+ ] ) ;
592+ } ) ;
593+
563594 test ( "table routing moves focused row and activates on Enter" , ( ) => {
564595 const backend = createNoopBackend ( ) ;
565596 const renderer = new WidgetRenderer < void > ( {
0 commit comments