@@ -1331,6 +1331,7 @@ export default {
|
|||||||
series.SliceIndex = 0
|
series.SliceIndex = 0
|
||||||
series.LoadedImageCount = 0
|
series.LoadedImageCount = 0
|
||||||
series.LoadedImageProgress = 0
|
series.LoadedImageProgress = 0
|
||||||
|
series.ImageLoadState = {}
|
||||||
series.TaskInfo = Object.assign({}, taskInfo)
|
series.TaskInfo = Object.assign({}, taskInfo)
|
||||||
series.StudyIndex = studyIndex
|
series.StudyIndex = studyIndex
|
||||||
series.SeriesIndex = seriesIndex
|
series.SeriesIndex = seriesIndex
|
||||||
@@ -1951,15 +1952,38 @@ export default {
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
// 设置图像下载进度信息
|
// 设置图像下载进度信息
|
||||||
|
// setImageLoadedProgress(series, percentComplete, instanceId) {
|
||||||
|
// let loadedImageCount = series.LoadedImageCount
|
||||||
|
// if (percentComplete === 100) {
|
||||||
|
// ++loadedImageCount
|
||||||
|
// this.$set(series, 'LoadedImageCount', loadedImageCount)
|
||||||
|
// }
|
||||||
|
// const newLoadedImageProgress = series.LoadedImageProgress - this.instanceInfo[instanceId].percentComplete + percentComplete
|
||||||
|
// this.instanceInfo[instanceId].percentComplete = percentComplete
|
||||||
|
// this.$set(series, 'LoadedImageProgress', newLoadedImageProgress)
|
||||||
|
// },
|
||||||
|
// 设置图像下载进度信息
|
||||||
setImageLoadedProgress(series, percentComplete, instanceId) {
|
setImageLoadedProgress(series, percentComplete, instanceId) {
|
||||||
let loadedImageCount = series.LoadedImageCount
|
if (!series || !instanceId) return
|
||||||
if (percentComplete === 100) {
|
if (!series.ImageLoadState || typeof series.ImageLoadState !== 'object') {
|
||||||
++loadedImageCount
|
this.$set(series, 'ImageLoadState', {})
|
||||||
this.$set(series, 'LoadedImageCount', loadedImageCount)
|
|
||||||
}
|
}
|
||||||
const newLoadedImageProgress = series.LoadedImageProgress - this.instanceInfo[instanceId].percentComplete + percentComplete
|
const imageLoadState = series.ImageLoadState
|
||||||
this.instanceInfo[instanceId].percentComplete = percentComplete
|
const prevPercentComplete = Number(imageLoadState[instanceId]?.percentComplete || 0)
|
||||||
|
const normalizedPercentComplete = Math.max(prevPercentComplete, Number(percentComplete || 0))
|
||||||
|
const wasLoaded = Boolean(imageLoadState[instanceId]?.loaded)
|
||||||
|
const isLoaded = wasLoaded || normalizedPercentComplete === 100
|
||||||
|
|
||||||
|
this.$set(imageLoadState, instanceId, {
|
||||||
|
percentComplete: normalizedPercentComplete,
|
||||||
|
loaded: isLoaded
|
||||||
|
})
|
||||||
|
|
||||||
|
const newLoadedImageProgress = series.LoadedImageProgress - prevPercentComplete + normalizedPercentComplete
|
||||||
this.$set(series, 'LoadedImageProgress', newLoadedImageProgress)
|
this.$set(series, 'LoadedImageProgress', newLoadedImageProgress)
|
||||||
|
if (!wasLoaded && isLoaded) {
|
||||||
|
this.$set(series, 'LoadedImageCount', series.LoadedImageCount + 1)
|
||||||
|
}
|
||||||
},
|
},
|
||||||
addHistoryAnnotations(taskId) {
|
addHistoryAnnotations(taskId) {
|
||||||
// if (this.renderedTaskIds.includes(taskId)) return
|
// if (this.renderedTaskIds.includes(taskId)) return
|
||||||
|
|||||||
@@ -515,30 +515,65 @@ export default {
|
|||||||
getImageFileSizeByImageId(imageId) {
|
getImageFileSizeByImageId(imageId) {
|
||||||
const instanceId = this.getImageInstanceId(imageId)
|
const instanceId = this.getImageInstanceId(imageId)
|
||||||
if (!instanceId) return 0
|
if (!instanceId) return 0
|
||||||
const fileSize = Number(this.instanceFileSizeMap[String(instanceId)] || 0)
|
return Number(this.instanceFileSizeMap[instanceId] || 0)
|
||||||
return Number.isFinite(fileSize) && fileSize > 0 ? fileSize : 0
|
|
||||||
},
|
},
|
||||||
|
// async prefetchMetadataInformation(imageIdsToPrefetch, modality, initialLoadedBytes = 0, enableInitPrefetchLimit = false) {
|
||||||
|
// let totalLoadedBytes = initialLoadedBytes
|
||||||
|
// let taskPromises = []
|
||||||
|
// for (let i = 0; i < imageIdsToPrefetch.length; i++) {
|
||||||
|
// const imageId = imageIdsToPrefetch[i]
|
||||||
|
// const nextImageBytes = this.getImageFileSizeByImageId(imageId)
|
||||||
|
// // 初始化预取累计超过 2G 后停止,剩余切片在用户滚动时按需加载
|
||||||
|
// if (enableInitPrefetchLimit && (totalLoadedBytes >= InitPrefetchMaxBytes || (nextImageBytes > 0 && totalLoadedBytes + nextImageBytes > InitPrefetchMaxBytes))) {
|
||||||
|
// console.info(`[Viewport] 初始化预取累计下载达到 ${this.formatBytes(totalLoadedBytes)},停止继续预取。`)
|
||||||
|
// break
|
||||||
|
// }
|
||||||
|
// taskPromises.push(cornerstoneDICOMImageLoader.wadouri.loadImage(imageIdsToPrefetch[i]).promise)
|
||||||
|
// totalLoadedBytes += nextImageBytes
|
||||||
|
// if (taskPromises.length >= 6 || i === imageIdsToPrefetch.length - 1) {
|
||||||
|
// let res = await Promise.all(taskPromises)
|
||||||
|
// if (modality === 'PT') {
|
||||||
|
// this.cachePTMetadata(res)
|
||||||
|
// }
|
||||||
|
// taskPromises = []
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
// },
|
||||||
async prefetchMetadataInformation(imageIdsToPrefetch, modality, initialLoadedBytes = 0, enableInitPrefetchLimit = false) {
|
async prefetchMetadataInformation(imageIdsToPrefetch, modality, initialLoadedBytes = 0, enableInitPrefetchLimit = false) {
|
||||||
let totalLoadedBytes = Number.isFinite(initialLoadedBytes) && initialLoadedBytes > 0 ? initialLoadedBytes : 0
|
if (!imageIdsToPrefetch?.length) return
|
||||||
let taskPromises = []
|
|
||||||
for (let i = 0; i < imageIdsToPrefetch.length; i++) {
|
const CONCURRENT_LIMIT = 6 // 最大并发数
|
||||||
const imageId = imageIdsToPrefetch[i]
|
let totalLoadedBytes = initialLoadedBytes
|
||||||
const nextImageBytes = this.getImageFileSizeByImageId(imageId)
|
let currentIndex = 0
|
||||||
// 初始化预取累计超过 2G 后停止,剩余切片在用户滚动时按需加载
|
// 单个任务:不断取下一个切片加载,直到全部完成或中止
|
||||||
if (enableInitPrefetchLimit && (totalLoadedBytes >= InitPrefetchMaxBytes || (nextImageBytes > 0 && totalLoadedBytes + nextImageBytes > InitPrefetchMaxBytes))) {
|
const runWorker = async () => {
|
||||||
console.info(`[Viewport] 初始化预取累计下载达到 ${this.formatBytes(totalLoadedBytes)},停止继续预取。`)
|
while (currentIndex < imageIdsToPrefetch.length) {
|
||||||
break
|
const index = currentIndex++
|
||||||
}
|
const imageId = imageIdsToPrefetch[index]
|
||||||
taskPromises.push(cornerstoneDICOMImageLoader.wadouri.loadImage(imageIdsToPrefetch[i]).promise)
|
const nextImageBytes = this.getImageFileSizeByImageId(imageId)
|
||||||
totalLoadedBytes += nextImageBytes
|
|
||||||
if (taskPromises.length >= 6 || i === imageIdsToPrefetch.length - 1) {
|
// 大小限制判断
|
||||||
let res = await Promise.all(taskPromises)
|
if (enableInitPrefetchLimit && (totalLoadedBytes >= InitPrefetchMaxBytes || (nextImageBytes > 0 && totalLoadedBytes + nextImageBytes > InitPrefetchMaxBytes))) {
|
||||||
if (modality === 'PT') {
|
console.info(`[Viewport] 初始化预取累计下载达到 ${this.formatBytes(totalLoadedBytes)},停止继续预取。`)
|
||||||
this.cachePTMetadata(res)
|
return
|
||||||
|
}
|
||||||
|
totalLoadedBytes += nextImageBytes
|
||||||
|
|
||||||
|
try {
|
||||||
|
const image = await cornerstoneDICOMImageLoader.wadouri.loadImage(imageId).promise
|
||||||
|
// PT模态缓存元数据(也可批量收集后统一缓存)
|
||||||
|
if (modality === 'PT') {
|
||||||
|
this.cachePTMetadata([image])
|
||||||
|
}
|
||||||
|
} catch (err) {
|
||||||
|
console.warn(`[Viewport] 预加载失败: ${imageId}`, err)
|
||||||
}
|
}
|
||||||
taskPromises = []
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// 启动 N 个并发,形成并发池
|
||||||
|
const workers = Array.from({ length: CONCURRENT_LIMIT }, () => runWorker())
|
||||||
|
await Promise.all(workers)
|
||||||
},
|
},
|
||||||
cachePTMetadata(images) {
|
cachePTMetadata(images) {
|
||||||
images.map(i => {
|
images.map(i => {
|
||||||
|
|||||||
Reference in New Issue
Block a user