优化图片解密

This commit is contained in:
xuncha
2026-02-04 21:54:48 +08:00
committed by xuncha
parent 551995df68
commit ab15190c44
4 changed files with 21 additions and 20 deletions

View File

@@ -11,7 +11,16 @@ import { wcdbService } from './wcdbService'
// 获取 ffmpeg-static 的路径 // 获取 ffmpeg-static 的路径
function getStaticFfmpegPath(): string | null { function getStaticFfmpegPath(): string | null {
try { try {
// 方法1: 直接 require ffmpeg-static // 优先处理打包后的路径
if (app.isPackaged) {
const resourcesPath = process.resourcesPath
const packedPath = join(resourcesPath, 'app.asar.unpacked', 'node_modules', 'ffmpeg-static', 'ffmpeg.exe')
if (existsSync(packedPath)) {
return packedPath
}
}
// 方法1: 直接 require ffmpeg-static开发环境
// eslint-disable-next-line @typescript-eslint/no-var-requires // eslint-disable-next-line @typescript-eslint/no-var-requires
const ffmpegStatic = require('ffmpeg-static') const ffmpegStatic = require('ffmpeg-static')
@@ -19,21 +28,12 @@ function getStaticFfmpegPath(): string | null {
return ffmpegStatic return ffmpegStatic
} }
// 方法2: 手动构建路径(开发环境) // 方法2: 手动构建路径(开发环境备用
const devPath = join(process.cwd(), 'node_modules', 'ffmpeg-static', 'ffmpeg.exe') const devPath = join(process.cwd(), 'node_modules', 'ffmpeg-static', 'ffmpeg.exe')
if (existsSync(devPath)) { if (existsSync(devPath)) {
return devPath return devPath
} }
// 方法3: 打包后的路径
if (app.isPackaged) {
const resourcesPath = process.resourcesPath
const packedPath = join(resourcesPath, 'app.asar.unpacked', 'node_modules', 'ffmpeg-static', 'ffmpeg.exe')
if (existsSync(packedPath)) {
return packedPath
}
}
return null return null
} catch { } catch {
return null return null

4
package-lock.json generated
View File

@@ -1,12 +1,12 @@
{ {
"name": "weflow", "name": "weflow",
"version": "1.5.0", "version": "1.5.2",
"lockfileVersion": 3, "lockfileVersion": 3,
"requires": true, "requires": true,
"packages": { "packages": {
"": { "": {
"name": "weflow", "name": "weflow",
"version": "1.5.0", "version": "1.5.2",
"hasInstallScript": true, "hasInstallScript": true,
"dependencies": { "dependencies": {
"better-sqlite3": "^12.5.0", "better-sqlite3": "^12.5.0",

View File

@@ -1,6 +1,6 @@
{ {
"name": "weflow", "name": "weflow",
"version": "1.5.0", "version": "1.5.2",
"description": "WeFlow", "description": "WeFlow",
"main": "dist-electron/main.js", "main": "dist-electron/main.js",
"author": "cc", "author": "cc",
@@ -115,7 +115,8 @@
], ],
"asarUnpack": [ "asarUnpack": [
"node_modules/silk-wasm/**/*", "node_modules/silk-wasm/**/*",
"node_modules/sherpa-onnx-node/**/*" "node_modules/sherpa-onnx-node/**/*",
"node_modules/ffmpeg-static/**/*"
], ],
"extraFiles": [ "extraFiles": [
{ {

View File

@@ -1604,7 +1604,7 @@ function MessageBubble({ message, session, showTime, myAvatarUrl, isGroupChat, o
// 视频相关状态 // 视频相关状态
const [videoLoading, setVideoLoading] = useState(false) const [videoLoading, setVideoLoading] = useState(false)
const [videoInfo, setVideoInfo] = useState<{ videoUrl?: string; coverUrl?: string; thumbUrl?: string; exists: boolean } | null>(null) const [videoInfo, setVideoInfo] = useState<{ videoUrl?: string; coverUrl?: string; thumbUrl?: string; exists: boolean } | null>(null)
const videoContainerRef = useRef<HTMLDivElement>(null) const videoContainerRef = useRef<HTMLElement>(null)
const [isVideoVisible, setIsVideoVisible] = useState(false) const [isVideoVisible, setIsVideoVisible] = useState(false)
const [videoMd5, setVideoMd5] = useState<string | null>(null) const [videoMd5, setVideoMd5] = useState<string | null>(null)
@@ -2359,7 +2359,7 @@ function MessageBubble({ message, session, showTime, myAvatarUrl, isGroupChat, o
// 未进入可视区域时显示占位符 // 未进入可视区域时显示占位符
if (!isVideoVisible) { if (!isVideoVisible) {
return ( return (
<div className="video-placeholder" ref={videoContainerRef}> <div className="video-placeholder" ref={videoContainerRef as React.RefObject<HTMLDivElement>}>
<svg width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2"> <svg width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" strokeWidth="2">
<polygon points="23 7 16 12 23 17 23 7"></polygon> <polygon points="23 7 16 12 23 17 23 7"></polygon>
<rect x="1" y="5" width="15" height="14" rx="2" ry="2"></rect> <rect x="1" y="5" width="15" height="14" rx="2" ry="2"></rect>
@@ -2371,7 +2371,7 @@ function MessageBubble({ message, session, showTime, myAvatarUrl, isGroupChat, o
// 加载中 // 加载中
if (videoLoading) { if (videoLoading) {
return ( return (
<div className="video-loading" ref={videoContainerRef}> <div className="video-loading" ref={videoContainerRef as React.RefObject<HTMLDivElement>}>
<Loader2 size={20} className="spin" /> <Loader2 size={20} className="spin" />
</div> </div>
) )
@@ -2382,7 +2382,7 @@ function MessageBubble({ message, session, showTime, myAvatarUrl, isGroupChat, o
return ( return (
<button <button
className={`video-unavailable ${videoClicked ? 'clicked' : ''}`} className={`video-unavailable ${videoClicked ? 'clicked' : ''}`}
ref={videoContainerRef} ref={videoContainerRef as React.RefObject<HTMLButtonElement>}
onClick={() => { onClick={() => {
setVideoClicked(true) setVideoClicked(true)
setTimeout(() => setVideoClicked(false), 800) setTimeout(() => setVideoClicked(false), 800)
@@ -2404,7 +2404,7 @@ function MessageBubble({ message, session, showTime, myAvatarUrl, isGroupChat, o
// 默认显示缩略图,点击打开独立播放窗口 // 默认显示缩略图,点击打开独立播放窗口
const thumbSrc = videoInfo.thumbUrl || videoInfo.coverUrl const thumbSrc = videoInfo.thumbUrl || videoInfo.coverUrl
return ( return (
<div className="video-thumb-wrapper" ref={videoContainerRef} onClick={handlePlayVideo}> <div className="video-thumb-wrapper" ref={videoContainerRef as React.RefObject<HTMLDivElement>} onClick={handlePlayVideo}>
{thumbSrc ? ( {thumbSrc ? (
<img src={thumbSrc} alt="视频缩略图" className="video-thumb" /> <img src={thumbSrc} alt="视频缩略图" className="video-thumb" />
) : ( ) : (