Skip to content

Commit ad8f305

Browse files
authored
feat: use webcomponents for embedded views (#864)
1 parent 44a3947 commit ad8f305

28 files changed

Lines changed: 1455 additions & 971 deletions

‎eslint.config.mjs‎

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,9 @@ export default antfu(
66
formatters: true,
77
unocss: true,
88
pnpm: true,
9+
ignore: [
10+
'**/.generated/**',
11+
],
912
},
1013
{
1114
rules: {

‎package.json‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
"type": "module",
44
"version": "2.4.1",
55
"private": true,
6-
"packageManager": "pnpm@10.11.0",
6+
"packageManager": "pnpm@10.11.1",
77
"repository": {
88
"type": "git",
99
"url": "git+https://github.com/nuxt/devtools.git"

‎packages/devtools-kit/types.d.ts‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
export*from'./dist/types'
1+
exporttype*from'./dist/types.d.mts'
Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
importtype{NuxtDevtoolsIframeClient}from'@nuxt/devtools-kit/types'
2+
importtype{Ref}from'vue'
13
import{useDevtoolsClient}from'@nuxt/devtools-kit/iframe-client'
24

3-
exportconstdevToolsClient=useDevtoolsClient()
5+
exportconstdevToolsClient: Ref<NuxtDevtoolsIframeClient|undefined>=useDevtoolsClient()

‎packages/devtools/build.config.ts‎

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,25 +1,43 @@
11
import{defineBuildConfig}from'unbuild'
2+
importVuefrom'unplugin-vue/rollup'
3+
import{buildCSS}from'./src/webcomponents/scripts/build-css'
24

35
exportdefaultdefineBuildConfig({
46
entries: [
57
'src/module',
68
// Chunking
79
'src/types',
810
'src/dirs',
11+
'src/webcomponents/index',
912
],
1013
externals: [
1114
'nuxt',
1215
'nuxt/schema',
1316
'vite',
1417
'@nuxt/kit',
1518
'@nuxt/schema',
19+
'@nuxt/devtools',
20+
'@nuxt/devtools/webcomponents',
1621
// Type only
1722
'vue',
1823
'vue-router',
1924
'unstorage',
2025
'nitropack',
26+
'vite-plugin-vue-tracer',
2127
],
2228
rollup: {
2329
inlineDependencies: true,
2430
},
31+
hooks: {
32+
'build:before': async(ctx)=>{
33+
if(ctx.options.stub)
34+
return
35+
awaitbuildCSS()
36+
},
37+
'rollup:options': function(ctx,options){
38+
if(ctx.options.stub)
39+
return
40+
options.plugins.push(Vue())
41+
},
42+
},
2543
})

‎packages/devtools/client/composables/editor.ts‎

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,10 @@ export function useOpenInEditor() {
1212
constrouter=useRouter()
1313
constvirtualFileId=useCurrentVirtualFile()
1414

15-
returnasync(filepath: string)=>{
15+
returnasync(filepath?: string)=>{
16+
if(!filepath)
17+
return
18+
1619
constbuildDir=config.value?.buildDir
1720
constpath=(buildDir&&filepath.startsWith(buildDir))
1821
? `#build${filepath.slice(buildDir.length)}`

‎packages/devtools/package.json‎

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,10 @@
1515
"types": "./dist/module.d.mts",
1616
"import": "./dist/module.mjs"
1717
},
18+
"./webcomponents": {
19+
"types": "./dist/webcomponents/index.d.mts",
20+
"import": "./dist/webcomponents/index.mjs"
21+
},
1822
"./types": {
1923
"types": "./dist/types.d.mts"
2024
},
@@ -85,6 +89,7 @@
8589
"@iconify-json/bxl": "catalog:icons",
8690
"@iconify-json/carbon": "catalog:icons",
8791
"@iconify-json/logos": "catalog:icons",
92+
"@iconify-json/ph": "catalog:icons",
8893
"@iconify-json/ri": "catalog:icons",
8994
"@iconify-json/simple-icons": "catalog:icons",
9095
"@iconify-json/tabler": "catalog:icons",
@@ -103,9 +108,11 @@
103108
"@xterm/addon-fit": "catalog:frontend",
104109
"@xterm/xterm": "catalog:frontend",
105110
"cronstrue": "catalog:frontend",
111+
"exsolve": "catalog:buildtools",
106112
"floating-vue": "catalog:frontend",
107113
"fuse.js": "catalog:frontend",
108114
"json-editor-vue": "catalog:frontend",
115+
"lightningcss": "catalog:buildtools",
109116
"markdown-it": "catalog:frontend",
110117
"markdown-it-link-attributes": "catalog:frontend",
111118
"my-ua-parser": "catalog:frontend",
@@ -120,6 +127,7 @@
120127
"tsx": "catalog:cli",
121128
"unimport": "catalog:types",
122129
"unocss": "catalog:buildtools",
130+
"unplugin-vue": "catalog:buildtools",
123131
"unplugin-vue-markdown": "catalog:buildtools",
124132
"vanilla-jsoneditor": "catalog:frontend",
125133
"vis-data": "catalog:frontend",

‎packages/devtools/src/runtime/plugins/view/client.ts‎

Lines changed: 68 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,22 @@
11
importtype{NuxtDevtoolsHostClient,TimelineEventRoute,TimelineMetrics}from'@nuxt/devtools/types'
2+
importtype{NuxtDevToolsInspectorProps}from'@nuxt/devtools/webcomponents'
23
importtype{$Fetch}from'ofetch'
34
importtype{Ref}from'vue'
4-
importtype{Router}from'vue-router'
55

6+
importtype{Router}from'vue-router'
67
// eslint-disable-next-line ts/ban-ts-comment
78
// @ts-ignore tsconfig
89
import{useAppConfig,useRuntimeConfig}from'#imports'
10+
import{NuxtDevtoolsFrame,NuxtDevtoolsInspectPanel}from'@nuxt/devtools/webcomponents'
911
import{setIframeServerContext}from'@vue/devtools-kit'
12+
1013
import{createHooks}from'hookable'
1114
import{debounce}from'perfect-debounce'
12-
1315
import{eventsasinspectorEvents,hasDataasinspectorHasData,stateasinspectorState}from'vite-plugin-vue-tracer/client/overlay'
14-
import{computed,createApp,h,markRaw,ref,shallowReactive,shallowRef,toRef,watch}from'vue'
15-
import{initTimelineMetrics}from'../../function-metrics-helpers'
16-
importMainfrom'./Main.vue'
16+
import{computed,markRaw,reactive,ref,shallowReactive,shallowRef,toRef,watch}from'vue'
1717

18+
import{initTimelineMetrics}from'../../function-metrics-helpers'
19+
import{settings}from'../../settings'
1820
import{popupWindow,state}from'./state'
1921

2022
constclientRef=shallowRef<NuxtDevtoolsHostClient>()
@@ -34,6 +36,9 @@ export async function setupDevToolsClient({
3436
timeMetric: any
3537
router: Router
3638
}){
39+
letiframe: HTMLIFrameElement|undefined
40+
letinspector: NuxtDevtoolsHostClient['inspector']|undefined
41+
3742
constcolorMode=useClientColorMode()
3843
consttimeline=initTimelineMetrics()
3944

@@ -108,8 +113,6 @@ export async function setupDevToolsClient({
108113

109114
window.__NUXT_DEVTOOLS_HOST__=client
110115

111-
letiframe: HTMLIFrameElement|undefined
112-
113116
functionsyncClient(){
114117
if(!client.inspector)
115118
client.inspector=getInspectorInstance()
@@ -183,33 +186,65 @@ export async function setupDevToolsClient({
183186
}
184187

185188
functiongetInspectorInstance(): NuxtDevtoolsHostClient['inspector']{
186-
constisAvailable=ref(inspectorHasData())
189+
if(inspector)
190+
returninspector
187191

188-
if(!inspectorEvents.events.disabled?.length){
189-
inspectorEvents.on('disabled',()=>{
190-
inspectorState.isVisible=false
191-
client?.hooks.callHook('host:inspector:close')
192-
})
193-
}
194-
if(!inspectorEvents.events.enabled?.length){
195-
inspectorEvents.on('enabled',()=>{
196-
inspectorState.isVisible=true
197-
})
198-
}
199-
if(!inspectorEvents.events.click?.length){
200-
inspectorEvents.on('click',async(info)=>{
201-
inspectorState.isEnabled=false
202-
awaitclient.hooks.callHook('host:inspector:click',info.fullpath)
203-
})
204-
}
192+
constprops=reactive<NuxtDevToolsInspectorProps>({
193+
mouse: {x: 0,y: 0},
194+
matched: undefined,
195+
})
205196

197+
constcomponent=newNuxtDevtoolsInspectPanel(reactive({ props }))
198+
document.body.appendChild(component)
199+
Object.assign(component.style,{
200+
zIndex: 999999,
201+
position: 'fixed',
202+
})
203+
component.addEventListener('close',()=>{
204+
props.matched=undefined
205+
inspectorState.isEnabled=false
206+
})
207+
component.addEventListener('selectParent',()=>{
208+
constparent=inspectorState.main?.getParent()
209+
if(parent){
210+
inspectorState.main=parent
211+
props.matched=parent
212+
}
213+
})
214+
// eslint-disable-next-line ts/ban-ts-comment
215+
// @ts-ignore WebComponent types
216+
component.addEventListener('openInEditor',(e)=>{
217+
consturl=(easany)?.detail?.[0]
218+
if(url)
219+
client.hooks.callHook('host:inspector:click',url)
220+
})
221+
222+
inspectorEvents.on('hover',()=>{
223+
inspectorState.isFocused=false
224+
})
225+
inspectorEvents.on('disabled',()=>{
226+
inspectorState.isVisible=false
227+
client?.hooks.callHook('host:inspector:close')
228+
})
229+
inspectorEvents.on('enabled',()=>{
230+
inspectorState.isVisible=true
231+
})
232+
inspectorEvents.on('click',async(info,e)=>{
233+
inspectorState.isFocused=true
234+
inspectorState.isVisible=true
235+
236+
props.matched=info
237+
props.mouse={x: e.clientX,y: e.clientY}
238+
})
239+
240+
constisAvailable=ref(inspectorHasData())
206241
if(!isAvailable.value){
207242
inspectorEvents.on('hover',async()=>{
208243
isAvailable.value=inspectorHasData()
209244
})
210245
}
211246

212-
returnmarkRaw({
247+
returninspector=markRaw({
213248
isAvailable,
214249
isEnabled: toRef(inspectorState,'isEnabled'),
215250
enable: ()=>{
@@ -284,13 +319,13 @@ export async function setupDevToolsClient({
284319
client.devtools.toggle()
285320
})
286321

287-
constapp=createApp({
288-
render: ()=>h(Main,{client}),
289-
devtools: {
290-
hide: true,
291-
},
292-
})
293-
app.mount(holder)
322+
constframe=newNuxtDevtoolsFrame(reactive({
323+
client,
324+
settings,
325+
state,
326+
popupWindow,
327+
}))
328+
holder.appendChild(frame)
294329
}
295330

296331
exportfunctionuseClientColorMode(): Ref<ColorScheme>{

‎packages/devtools/src/runtime/plugins/view/state.ts‎

Lines changed: 0 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2,10 +2,6 @@ import type { DevToolsFrameState } from '@nuxt/devtools/types'
22
import{shallowRef}from'vue'
33
import{useObjectStorage}from'./utils'
44

5-
exportconstPANEL_PADDING=10
6-
exportconstPANEL_MIN=20
7-
exportconstPANEL_MAX=100
8-
95
exportconstpopupWindow=shallowRef<Window|null>(null)
106

117
exportconststate=useObjectStorage<DevToolsFrameState>('nuxt-devtools-frame-state',{

0 commit comments

Comments
 (0)