@@ -20,7 +20,7 @@ function createPropertyRow(label, value) {
20
20
21
21
const labelSpan = document . createElement ( 'span' ) ;
22
22
labelSpan . className = 'property-label' ;
23
- labelSpan . textContent = `${ label } : ` ;
23
+ labelSpan . textContent = `${ label } ` ;
24
24
labelSpan . style . marginRight = '10px' ;
25
25
labelSpan . style . whiteSpace = 'nowrap' ;
26
26
@@ -37,14 +37,34 @@ function createPropertyRow(label, value) {
37
37
return row ;
38
38
}
39
39
40
+ function createVectorRow ( label , vector ) {
41
+ const row = document . createElement ( 'div' ) ;
42
+ row . className = 'property-row' ;
43
+ row . style . marginBottom = '2px' ;
44
+
45
+ // Pad label to ensure consistent alignment
46
+ const paddedLabel = label . padEnd ( 16 , ' ' ) ; // Pad to 16 characters
47
+ const content = `${ paddedLabel } ${ vector . x . toFixed ( 3 ) } \t${ vector . y . toFixed ( 3 ) } \t${ vector . z . toFixed ( 3 ) } ` ;
48
+ row . textContent = content ;
49
+ row . style . fontFamily = 'monospace' ;
50
+ row . style . whiteSpace = 'pre' ;
51
+
52
+ return row ;
53
+ }
54
+
40
55
// --- State ---
41
56
const state = {
42
57
revision : null ,
43
58
scenes : new Map ( ) ,
44
59
renderers : new Map ( ) ,
45
- objects : new Map ( )
60
+ objects : new Map ( ) ,
61
+ selectedObject : null
46
62
} ;
47
63
64
+ // Floating details panel
65
+ let floatingPanel = null ;
66
+ let mousePosition = { x : 0 , y : 0 } ;
67
+
48
68
49
69
// Create a connection to the background page
50
70
const backgroundPageConnection = chrome . runtime . connect ( {
@@ -80,6 +100,15 @@ backgroundPageConnection.onDisconnect.addListener( () => {
80
100
81
101
} ) ;
82
102
103
+ // Function to request object details from the bridge
104
+ function requestObjectDetails ( uuid ) {
105
+ backgroundPageConnection . postMessage ( {
106
+ name : 'request-object-details' ,
107
+ uuid : uuid ,
108
+ tabId : chrome . devtools . inspectedWindow . tabId
109
+ } ) ;
110
+ }
111
+
83
112
84
113
// Store renderer collapse states
85
114
const rendererCollapsedState = new Map ( ) ;
@@ -98,6 +127,13 @@ function clearState() {
98
127
99
128
}
100
129
130
+ // Hide floating panel
131
+ if ( floatingPanel ) {
132
+
133
+ floatingPanel . classList . remove ( 'visible' ) ;
134
+
135
+ }
136
+
101
137
}
102
138
103
139
// Listen for messages from the background page
@@ -139,6 +175,13 @@ function handleThreeEvent( message ) {
139
175
140
176
break ;
141
177
178
+ // Handle object details response
179
+ case 'object-details' :
180
+ state . selectedObject = message . detail ;
181
+ console . log ( 'Panel: Received object details:' , message . detail ) ;
182
+ showFloatingDetails ( message . detail ) ;
183
+ break ;
184
+
142
185
// Handle a batch of objects for a specific scene
143
186
case 'scene' :
144
187
const { sceneUuid, objects : batchObjects } = message . detail ;
@@ -376,6 +419,13 @@ function renderObject( obj, container, level = 0 ) {
376
419
}
377
420
378
421
elem . innerHTML = labelContent ;
422
+
423
+ // Add mouseover handler to request object details
424
+ elem . addEventListener ( 'mouseover' , ( event ) => {
425
+ event . stopPropagation ( ) ; // Prevent bubbling to parent elements
426
+ requestObjectDetails ( obj . uuid ) ;
427
+ } ) ;
428
+
379
429
container . appendChild ( elem ) ;
380
430
381
431
// Handle children (excluding children of renderers, as properties are shown in details)
@@ -477,8 +527,98 @@ function updateUI() {
477
527
478
528
}
479
529
530
+
480
531
}
481
532
533
+ // Create floating details panel
534
+ function createFloatingPanel ( ) {
535
+
536
+ if ( floatingPanel ) return floatingPanel ;
537
+
538
+ floatingPanel = document . createElement ( 'div' ) ;
539
+ floatingPanel . className = 'floating-details' ;
540
+ document . body . appendChild ( floatingPanel ) ;
541
+
542
+ return floatingPanel ;
543
+
544
+ }
545
+
546
+ // Show floating details panel
547
+ function showFloatingDetails ( objectData ) {
548
+
549
+ const panel = createFloatingPanel ( ) ;
550
+
551
+ // Clear previous content
552
+ panel . innerHTML = '' ;
553
+
554
+ if ( objectData . position ) {
555
+
556
+ panel . appendChild ( createVectorRow ( 'Position' , objectData . position ) ) ;
557
+
558
+ }
559
+
560
+ if ( objectData . rotation ) {
561
+
562
+ panel . appendChild ( createVectorRow ( 'Rotation' , objectData . rotation ) ) ;
563
+
564
+ }
565
+
566
+ if ( objectData . scale ) {
567
+
568
+ panel . appendChild ( createVectorRow ( 'Scale' , objectData . scale ) ) ;
569
+
570
+ }
571
+
572
+ // Position panel near mouse
573
+ updateFloatingPanelPosition ( ) ;
574
+
575
+ // Show panel
576
+ panel . classList . add ( 'visible' ) ;
577
+
578
+ }
579
+
580
+ // Update floating panel position
581
+ function updateFloatingPanelPosition ( ) {
582
+
583
+ if ( ! floatingPanel || ! floatingPanel . classList . contains ( 'visible' ) ) return ;
584
+
585
+ const offset = 15 ; // Offset from cursor
586
+ let x = mousePosition . x + offset ;
587
+ let y = mousePosition . y + offset ;
588
+
589
+ // Prevent panel from going off-screen
590
+ const panelRect = floatingPanel . getBoundingClientRect ( ) ;
591
+ const maxX = window . innerWidth - panelRect . width - 10 ;
592
+ const maxY = window . innerHeight - panelRect . height - 10 ;
593
+
594
+ if ( x > maxX ) x = mousePosition . x - panelRect . width - offset ;
595
+ if ( y > maxY ) y = mousePosition . y - panelRect . height - offset ;
596
+
597
+ floatingPanel . style . left = `${ Math . max ( 10 , x ) } px` ;
598
+ floatingPanel . style . top = `${ Math . max ( 10 , y ) } px` ;
599
+
600
+ }
601
+
602
+ // Track mouse position
603
+ document . addEventListener ( 'mousemove' , ( event ) => {
604
+
605
+ mousePosition . x = event . clientX ;
606
+ mousePosition . y = event . clientY ;
607
+ updateFloatingPanelPosition ( ) ;
608
+
609
+ } ) ;
610
+
611
+ // Hide panel when mouse leaves the tree area
612
+ document . addEventListener ( 'mouseover' , ( event ) => {
613
+
614
+ if ( floatingPanel && ! event . target . closest ( '.tree-item' ) ) {
615
+
616
+ floatingPanel . classList . remove ( 'visible' ) ;
617
+
618
+ }
619
+
620
+ } ) ;
621
+
482
622
// Initial UI update
483
623
clearState ( ) ;
484
624
updateUI ( ) ;
0 commit comments