@@ -212,6 +212,16 @@ const SCREENS = [
212212 { name : 'runs-mobile' , path : '/runs' , theme : 'dark' , w : 390 , h : 900 } ,
213213 { name : 'home-collapsed' , path : '/' , theme : 'dark' , w : 1280 , h : 900 , collapsed : true } ,
214214 { name : 'home-collapsed-light' , path : '/' , theme : 'light' , w : 1280 , h : 900 , collapsed : true } ,
215+ // Tall content scrolled to the bottom — the sidebar must stay fixed in place.
216+ {
217+ name : 'runs-scroll' ,
218+ path : '/runs' ,
219+ theme : 'dark' ,
220+ w : 1280 ,
221+ h : 700 ,
222+ manyRuns : true ,
223+ scroll : true ,
224+ } ,
215225] ;
216226
217227await mkdir ( OUT , { recursive : true } ) ;
@@ -269,14 +279,49 @@ try {
269279 }
270280 } ) ;
271281 }
282+ // Seed the theme preference so the footer switcher's active state matches.
283+ await context . addInitScript ( ( theme ) => {
284+ try {
285+ // eslint-disable-next-line no-undef
286+ localStorage . setItem ( 'oc-theme' , theme ) ;
287+ } catch {
288+ /* storage unavailable */
289+ }
290+ } , s . theme ) ;
291+ if ( s . manyRuns ) {
292+ const many = Array . from ( { length : 30 } , ( _ , i ) =>
293+ run ( {
294+ id : `rm${ i } ` ,
295+ status : [ 'running' , 'succeeded' , 'awaiting_human' , 'failed' ] [ i % 4 ] ,
296+ task : `Task ${ i + 1 } — reconcile, validate, and file the result` ,
297+ costCents : ( i * 37 ) % 600 ,
298+ stepsCompleted : ( i % 12 ) + 1 ,
299+ } ) ,
300+ ) ;
301+ // Registered after the general route, so it wins for this exact path.
302+ await context . route ( '**/api/runs' , ( route ) =>
303+ route . fulfill ( {
304+ status : 200 ,
305+ contentType : 'application/json' ,
306+ body : JSON . stringify ( { runs : many } ) ,
307+ } ) ,
308+ ) ;
309+ }
272310 const page = await context . newPage ( ) ;
273311 await page . goto ( `${ BASE_URL } ${ s . path } ` , { waitUntil : 'networkidle' } ) . catch ( ( ) => { } ) ;
274312 await page . evaluate ( ( t ) => {
275313 // eslint-disable-next-line no-undef
276314 document . documentElement . dataset . theme = t ;
277315 } , s . theme ) ;
316+ if ( s . scroll ) {
317+ await page . evaluate ( ( ) => {
318+ // eslint-disable-next-line no-undef
319+ const m = document . querySelector ( '.app-main' ) ;
320+ if ( m ) m . scrollTop = m . scrollHeight ;
321+ } ) ;
322+ }
278323 await page . waitForTimeout ( 350 ) ;
279- await page . screenshot ( { path : path . join ( OUT , `${ s . name } .png` ) , fullPage : true } ) ;
324+ await page . screenshot ( { path : path . join ( OUT , `${ s . name } .png` ) , fullPage : ! s . scroll } ) ;
280325 console . log ( `shot ${ s . name } (${ s . w } ×${ s . h } , ${ s . theme } )` ) ;
281326 await context . close ( ) ;
282327 }
0 commit comments