@@ -6,17 +6,49 @@ import { TraceType, type TraceLog } from '@wdio/devtools-service/types'
66import { Element } from '@core/element'
77import { DataManagerController } from './controller/DataManager.js'
88import { DragController , Direction } from './utils/DragController.js'
9- import { SIDEBAR_MIN_WIDTH } from './controller/constants.js'
9+ import { SIDEBAR_MIN_WIDTH , DARK_MODE_KEY } from './controller/constants.js'
10+ import { POPOUT_QUERY } from './components/workbench/compare/constants.js'
11+
12+ // Bootstrap the dark-mode class on <body> as early as possible so popout
13+ // windows (which don't render the header) still get themed consistently
14+ // with the main dashboard. The header still owns the toggle.
15+ const darkModeInit = localStorage . getItem ( DARK_MODE_KEY )
16+ const isDarkMode =
17+ typeof darkModeInit === 'string'
18+ ? darkModeInit === 'true'
19+ : window . matchMedia ( '(prefers-color-scheme: dark)' ) . matches
20+ if ( isDarkMode ) {
21+ document . body . classList . add ( 'dark' )
22+ }
23+ // Cross-window sync: when the user toggles dark mode in the main dashboard,
24+ // the storage event fires in OTHER windows (popouts) and we mirror the
25+ // theme change there too.
26+ window . addEventListener ( 'storage' , ( e ) => {
27+ if ( e . key === DARK_MODE_KEY ) {
28+ document . body . classList . toggle ( 'dark' , e . newValue === 'true' )
29+ }
30+ } )
1031
1132import './components/header.js'
1233import './components/sidebar.js'
1334import './components/workbench.js'
1435import './components/onboarding/start.js'
36+ import './components/workbench/compare.js'
1537
1638@customElement ( 'wdio-devtools' )
1739export class WebdriverIODevtoolsApplication extends Element {
1840 dataManager = new DataManagerController ( this )
1941
42+ // Popout mode: when opened via the Compare tab's "↗ Pop out" button the
43+ // URL carries ?view=compare&uid=<testUid>. The app then renders only the
44+ // Compare panel full-viewport (no header, no sidebar, no workbench tabs).
45+ #popoutMode =
46+ new URLSearchParams ( window . location . search ) . get ( POPOUT_QUERY . viewKey ) ===
47+ POPOUT_QUERY . viewValue
48+ #popoutUid =
49+ new URLSearchParams ( window . location . search ) . get ( POPOUT_QUERY . uidKey ) ||
50+ undefined
51+
2052 static styles = [
2153 ...Element . styles ,
2254 css `
@@ -56,9 +88,20 @@ export class WebdriverIODevtoolsApplication extends Element {
5688 'clear-execution-data' ,
5789 this . #clearExecutionData. bind ( this )
5890 )
91+ // In popout mode, the URL carries the test uid the parent window was
92+ // viewing. Push it into the context so the Compare component finds the
93+ // matching baseline as soon as the WS reconnects in this new window.
94+ if ( this . #popoutMode && this . #popoutUid) {
95+ this . dataManager . setSelectedTestUid ( this . #popoutUid)
96+ }
5997 }
6098
6199 render ( ) {
100+ if ( this . #popoutMode) {
101+ return html `
102+ < wdio-devtools-compare style ="flex:1 1 auto; "> </ wdio-devtools-compare >
103+ `
104+ }
62105 return html `
63106 < wdio-devtools-header > </ wdio-devtools-header >
64107 ${ this . #mainContent( ) }
0 commit comments