File size: 3,471 Bytes
4d70170 |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 |
import type { BackendContext } from '@vue-devtools/app-backend-api'
import type { ID, ScreenshotOverlayRenderContext } from '@vue/devtools-api'
import { SharedData } from '@vue-devtools/shared-utils'
import { JobQueue } from './util/queue'
import { builtinLayers } from './timeline-builtins'
let overlay: HTMLDivElement
let image: HTMLImageElement
let container: HTMLDivElement
const jobQueue = new JobQueue()
interface Screenshot {
id: ID
time: number
image: string
events: ID[]
}
export async function showScreenshot(screenshot: Screenshot, ctx: BackendContext) {
await jobQueue.queue('showScreenshot', async () => {
if (screenshot) {
if (!container) {
createElements()
}
image.src = screenshot.image
image.style.visibility = screenshot.image ? 'visible' : 'hidden'
clearContent()
const events = screenshot.events.map(id => ctx.timelineEventMap.get(id)).filter(Boolean).map(eventData => ({
layer: builtinLayers.concat(ctx.timelineLayers).find(layer => layer.id === eventData.layerId),
event: {
...eventData.event,
layerId: eventData.layerId,
renderMeta: {},
},
}))
const renderContext: ScreenshotOverlayRenderContext = {
screenshot,
events: events.map(({ event }) => event),
index: 0,
}
for (let i = 0; i < events.length; i++) {
const { layer, event } = events[i]
if (layer.screenshotOverlayRender) {
renderContext.index = i
try {
const result = await layer.screenshotOverlayRender(event, renderContext)
if (result !== false) {
if (typeof result === 'string') {
container.innerHTML += result
}
else {
container.appendChild(result)
}
}
}
catch (e) {
if (SharedData.debugInfo) {
console.error(e)
}
}
}
}
showElement()
}
else {
hideElement()
}
})
}
function createElements() {
overlay = document.createElement('div')
overlay.style.position = 'fixed'
overlay.style.zIndex = '9999999999999'
overlay.style.pointerEvents = 'none'
overlay.style.left = '0'
overlay.style.top = '0'
overlay.style.width = '100vw'
overlay.style.height = '100vh'
overlay.style.backgroundColor = 'rgba(0,0,0,0.5)'
overlay.style.overflow = 'hidden'
const imageBox = document.createElement('div')
imageBox.style.position = 'relative'
overlay.appendChild(imageBox)
image = document.createElement('img')
imageBox.appendChild(image)
container = document.createElement('div')
container.style.position = 'absolute'
container.style.left = '0'
container.style.top = '0'
imageBox.appendChild(container)
const style = document.createElement('style')
style.innerHTML = '.__vuedevtools_no-scroll { overflow: hidden; }'
document.head.appendChild(style)
}
function showElement() {
if (!overlay.parentNode) {
document.body.appendChild(overlay)
document.body.classList.add('__vuedevtools_no-scroll')
}
}
function hideElement() {
if (overlay && overlay.parentNode) {
overlay.parentNode.removeChild(overlay)
document.body.classList.remove('__vuedevtools_no-scroll')
clearContent()
}
}
function clearContent() {
while (container.firstChild) {
container.removeChild(container.lastChild)
}
}
|