feat: 支持配置微信用户已通关关卡
This commit is contained in:
@@ -1,10 +1,9 @@
|
||||
'use client'
|
||||
|
||||
import { useState, useRef, useEffect } from 'react'
|
||||
import { useState, useEffect } from 'react'
|
||||
import { Button } from '@/components/ui/button'
|
||||
import { Input } from '@/components/ui/input'
|
||||
import { Label } from '@/components/ui/label'
|
||||
import { Textarea } from '@/components/ui/textarea'
|
||||
import {
|
||||
Dialog,
|
||||
DialogContent,
|
||||
@@ -16,7 +15,6 @@ import {
|
||||
import { Spinner } from '@/components/ui/spinner'
|
||||
import { Level, LevelFormData } from '@/types'
|
||||
import { ImageUploader } from './image-uploader'
|
||||
import { Upload } from 'lucide-react'
|
||||
|
||||
interface LevelDialogProps {
|
||||
open: boolean
|
||||
@@ -26,8 +24,12 @@ interface LevelDialogProps {
|
||||
}
|
||||
|
||||
const defaultFormData: LevelFormData = {
|
||||
imageUrl: '',
|
||||
image1Url: '',
|
||||
image1Description: '',
|
||||
image2Url: '',
|
||||
image2Description: '',
|
||||
answer: '',
|
||||
punchline: '',
|
||||
hint1: '',
|
||||
hint2: '',
|
||||
hint3: '',
|
||||
@@ -37,15 +39,18 @@ export function LevelDialog({ open, onOpenChange, level, onSubmit }: LevelDialog
|
||||
const [formData, setFormData] = useState<LevelFormData>(defaultFormData)
|
||||
const [isLoading, setIsLoading] = useState(false)
|
||||
const [error, setError] = useState('')
|
||||
const fileInputRef = useRef<HTMLInputElement>(null)
|
||||
|
||||
// Reset form when dialog opens/closes or level changes
|
||||
useEffect(() => {
|
||||
if (open) {
|
||||
if (level) {
|
||||
setFormData({
|
||||
imageUrl: level.imageUrl,
|
||||
image1Url: level.image1Url,
|
||||
image1Description: level.image1Description || '',
|
||||
image2Url: level.image2Url,
|
||||
image2Description: level.image2Description || '',
|
||||
answer: level.answer,
|
||||
punchline: level.punchline || '',
|
||||
hint1: level.hint1 || '',
|
||||
hint2: level.hint2 || '',
|
||||
hint3: level.hint3 || '',
|
||||
@@ -57,16 +62,25 @@ export function LevelDialog({ open, onOpenChange, level, onSubmit }: LevelDialog
|
||||
}
|
||||
}, [open, level])
|
||||
|
||||
const handleImageUpload = (url: string) => {
|
||||
setFormData((prev) => ({ ...prev, imageUrl: url }))
|
||||
const handleImage1Upload = (url: string) => {
|
||||
setFormData((prev) => ({ ...prev, image1Url: url }))
|
||||
}
|
||||
|
||||
const handleImage2Upload = (url: string) => {
|
||||
setFormData((prev) => ({ ...prev, image2Url: url }))
|
||||
}
|
||||
|
||||
const handleSubmit = async (e: React.FormEvent) => {
|
||||
e.preventDefault()
|
||||
setError('')
|
||||
|
||||
if (!formData.imageUrl) {
|
||||
setError('请上传关卡图片')
|
||||
if (!formData.image1Url) {
|
||||
setError('请上传图片1')
|
||||
return
|
||||
}
|
||||
|
||||
if (!formData.image2Url) {
|
||||
setError('请上传图片2')
|
||||
return
|
||||
}
|
||||
|
||||
@@ -75,6 +89,11 @@ export function LevelDialog({ open, onOpenChange, level, onSubmit }: LevelDialog
|
||||
return
|
||||
}
|
||||
|
||||
if (formData.answer.trim().length > 4) {
|
||||
setError('答案最多4个字')
|
||||
return
|
||||
}
|
||||
|
||||
setIsLoading(true)
|
||||
try {
|
||||
await onSubmit(formData)
|
||||
@@ -88,7 +107,7 @@ export function LevelDialog({ open, onOpenChange, level, onSubmit }: LevelDialog
|
||||
|
||||
return (
|
||||
<Dialog open={open} onOpenChange={onOpenChange}>
|
||||
<DialogContent className="sm:max-w-[500px]">
|
||||
<DialogContent className="sm:max-w-2xl max-h-[85vh] overflow-y-auto">
|
||||
<DialogHeader>
|
||||
<DialogTitle>{level ? '编辑关卡' : '添加关卡'}</DialogTitle>
|
||||
<DialogDescription>
|
||||
@@ -102,12 +121,39 @@ export function LevelDialog({ open, onOpenChange, level, onSubmit }: LevelDialog
|
||||
</div>
|
||||
)}
|
||||
|
||||
<div className="space-y-2">
|
||||
<Label>关卡图片 *</Label>
|
||||
<ImageUploader
|
||||
value={formData.imageUrl}
|
||||
onChange={handleImageUpload}
|
||||
/>
|
||||
{/* 双图上传区域 */}
|
||||
<div className="grid grid-cols-2 gap-4">
|
||||
{/* 图片1 */}
|
||||
<div className="space-y-2">
|
||||
<Label>图片1 *</Label>
|
||||
<ImageUploader
|
||||
value={formData.image1Url}
|
||||
onChange={handleImage1Upload}
|
||||
/>
|
||||
<Input
|
||||
value={formData.image1Description}
|
||||
onChange={(e) =>
|
||||
setFormData((prev) => ({ ...prev, image1Description: e.target.value }))
|
||||
}
|
||||
placeholder="图片1描述 (可选)"
|
||||
/>
|
||||
</div>
|
||||
|
||||
{/* 图片2 */}
|
||||
<div className="space-y-2">
|
||||
<Label>图片2 *</Label>
|
||||
<ImageUploader
|
||||
value={formData.image2Url}
|
||||
onChange={handleImage2Upload}
|
||||
/>
|
||||
<Input
|
||||
value={formData.image2Description}
|
||||
onChange={(e) =>
|
||||
setFormData((prev) => ({ ...prev, image2Description: e.target.value }))
|
||||
}
|
||||
placeholder="图片2描述 (可选)"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="space-y-2">
|
||||
@@ -118,9 +164,25 @@ export function LevelDialog({ open, onOpenChange, level, onSubmit }: LevelDialog
|
||||
onChange={(e) =>
|
||||
setFormData((prev) => ({ ...prev, answer: e.target.value }))
|
||||
}
|
||||
placeholder="请输入答案"
|
||||
placeholder="请输入答案(最多4个字)"
|
||||
maxLength={4}
|
||||
required
|
||||
/>
|
||||
<p className="text-xs text-muted-foreground text-right">
|
||||
{formData.answer.length}/4
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<div className="space-y-2">
|
||||
<Label htmlFor="punchline">谐音梗说明 (可选)</Label>
|
||||
<Input
|
||||
id="punchline"
|
||||
value={formData.punchline}
|
||||
onChange={(e) =>
|
||||
setFormData((prev) => ({ ...prev, punchline: e.target.value }))
|
||||
}
|
||||
placeholder="请输入谐音梗说明"
|
||||
/>
|
||||
</div>
|
||||
|
||||
<div className="space-y-2">
|
||||
|
||||
Reference in New Issue
Block a user