feat: add puzzle residence configuration and reflection progress logic

- Introduced `puzzleResidences.ts` to define puzzle residence configurations including properties like display name, position, and puzzle availability.
- Added `reflectionProgress.ts` to manage badge unlocking logic based on place completion, including functions to determine unlocked badges and video sources for scenes.
This commit is contained in:
zhongyidian committed 2026-04-27 11:49:30 +08:00
1 parent e0fa47d21a
commit f5f36f75b5
153 files changed
+3846 -2352

No files matched your search

+40 -4
View File
@@ -1,5 +1,5 @@
import { useEffect, useMemo, useRef, useState } from 'react'
import { Image } from '@/components'
import { ExhibitFlipOverlay, FlipActionButton, Image } from '@/components'
import { cn, getBackgroundImage, getStaticImage } from '@/lib/utils'
import { useNavigate, useParams } from 'react-router-dom'
import { saveZhanglepingStore, useZhanglepingStore } from '@/store/zhanglepingStore'
@@ -17,6 +17,10 @@ import {
sidebarBlocks,
} from './draw1.config'
import { TopMenuPanel } from './TopMenuPanel'
import { SanmaoDialogueItem, SanmaoDialogueSteps } from '@/pages/zhangleping/components'
const COMPLETION_DIALOGUE =
'太好啦!我的记忆都回来啦,还拥有了新时代的模样!爷爷画的我,藏着善良、勇敢与热爱;你画的我,让这些美好品质在今天继续发光!谢谢你,让三毛精神一直传承下去!'
const ZhanglepingDraw1 = () => {
const navigate = useNavigate()
@@ -30,6 +34,9 @@ const ZhanglepingDraw1 = () => {
const [showCaptionInput, setShowCaptionInput] = useState(false)
const [captionText, setCaptionText] = useState('')
const [isSubmitting, setIsSubmitting] = useState(false)
const [createdArtworkSrc, setCreatedArtworkSrc] = useState('')
const [showCreatedOverlay, setShowCreatedOverlay] = useState(false)
const [showCompletionDialogue, setShowCompletionDialogue] = useState(false)
const captionInputRef = useRef<HTMLInputElement>(null)
const compositionRef = useRef<HTMLDivElement>(null)
@@ -75,14 +82,15 @@ const ZhanglepingDraw1 = () => {
setShowCaptionInput(true)
return
}
if (isSubmitting) return
if (isSubmitting || !compositionRef.current) return
setIsSubmitting(true)
try {
const dataUrl = await buildCompositeDataUrl(compositionRef.current!)
const dataUrl = await buildCompositeDataUrl(compositionRef.current)
setDrawArtwork(dataUrl, captionText.trim())
saveZhanglepingStore()
navigate(`/${moduleName}/${STAR_NAME}/reflection5`)
setCreatedArtworkSrc(dataUrl)
setShowCreatedOverlay(true)
} catch (error) {
console.error('Failed to submit draw artwork', error)
} finally {
@@ -90,6 +98,10 @@ const ZhanglepingDraw1 = () => {
}
}
const handleCollectArtwork = () => {
navigate(`/${moduleName}/${STAR_NAME}/reflection5`)
}
const isPreviewVisible = activeBlock !== '任务提示'
if (!moduleName) return null
@@ -226,6 +238,30 @@ const ZhanglepingDraw1 = () => {
onClick={handleSubmitArtwork}
/>
</div>
{createdArtworkSrc && (
<ExhibitFlipOverlay
src={createdArtworkSrc}
visible={showCreatedOverlay}
// footerClassName="bottom-120"
onEnterComplete={() => {
setShowCompletionDialogue(true)
}}
onClose={() => {
setShowCreatedOverlay(false)
}}
footer={<FlipActionButton onClick={handleCollectArtwork}>收藏</FlipActionButton>}
/>
)}
<SanmaoDialogueSteps
visible={showCompletionDialogue}
onVisibleChange={setShowCompletionDialogue}
showMask={false}
zIndex={10020}
>
<SanmaoDialogueItem>{COMPLETION_DIALOGUE}</SanmaoDialogueItem>
</SanmaoDialogueSteps>
</div>
)
}