"use client" import type React from "react" import { useState, useEffect, use } from "react" import { useRouter } from "next/navigation" import { ChevronLeft, Plus, X, Image as ImageIcon, UploadCloud, Link, Video, FileText, Layers, CalendarDays, ChevronDown } from "lucide-react" import { Card } from "@/components/ui/card" import { Button } from "@/components/ui/button" import { Textarea } from "@/components/ui/textarea" import { Label } from "@/components/ui/label" import { toast } from "@/components/ui/use-toast" import { api } from "@/lib/api" import { showToast } from "@/lib/toast" import Image from "next/image" import { Input } from "@/components/ui/input" import { cn } from "@/lib/utils" interface ApiResponse { code: number msg: string data: T } interface Material { id: number type: string title: string content: string coverImage: string | null resUrls: string[] urls: ({ desc?: string; image?: string; url?: string } | string)[] createTime: string createMomentTime: number time: string wechatId: string friendId: string | null wechatChatroomId: number senderNickname: string location: string | null lat: string lng: string comment: string | null icon: string | null videoUrl?: string sendTime: string contentType: string } const isImageUrl = (url: string) => { return /\.(jpg|jpeg|png|gif|webp)$/i.test(url) || url.includes('oss-cn-shenzhen.aliyuncs.com') } // 素材类型枚举 const MATERIAL_TYPES = [ { id: 1, name: "图片", icon: ImageIcon }, { id: 2, name: "链接", icon: Link }, { id: 3, name: "视频", icon: Video }, { id: 4, name: "文本", icon: FileText }, { id: 5, name: "小程序", icon: Layers } ] export default function EditMaterialPage({ params }: { params: Promise<{ id: string, materialId: string }> }) { const resolvedParams = use(params) const router = useRouter() const [isLoading, setIsLoading] = useState(true) const [content, setContent] = useState("") const [images, setImages] = useState([]) const [previewUrls, setPreviewUrls] = useState([]) const [originalMaterial, setOriginalMaterial] = useState(null) const [sendTime, setSendTime] = useState("") const [contentType, setContentType] = useState(1) const [url, setUrl] = useState("") const [desc, setDesc] = useState("") const [image, setImage] = useState("") const [title, setTitle] = useState("") const [iconUrl, setIconUrl] = useState("") const [videoUrl, setVideoUrl] = useState("") const [comment, setComment] = useState("") // 获取素材详情 useEffect(() => { const fetchMaterialDetail = async () => { setIsLoading(true) try { const response = await api.get>(`/v1/content/library/get-item-detail?id=${resolvedParams.materialId}`) if (response.code === 200 && response.data) { const material = response.data setOriginalMaterial(material) setContent(material.content) setComment(material.comment || "") setSendTime(material.sendTime || "") setContentType(Number(material.contentType) || 1) // 链接类型 if (Number(material.contentType) === 2 && material.urls && material.urls.length > 0) { const first = material.urls[0]; if (typeof first === "object" && first !== null) { setDesc(first.desc || ""); setImage(first.image || ""); setUrl(first.url || ""); } else { setDesc(""); setImage(""); setUrl(typeof first === "string" ? first : ""); } } // 视频类型 if (Number(material.contentType) === 3 && material.urls && material.urls.length > 0) { const first = material.urls[0]; if (typeof first === "string") { setVideoUrl(first); } else if (typeof first === "object" && first !== null && first.url) { setVideoUrl(first.url); } else { setVideoUrl(""); } } // 处理图片 const imageUrls: string[] = [] // 检查内容本身是否为图片链接 if (isImageUrl(material.content)) { if (!imageUrls.includes(material.content)) { imageUrls.push(material.content) } } // 添加资源URL中的图片 material.resUrls.forEach(url => { if (isImageUrl(url) && !imageUrls.includes(url)) { imageUrls.push(url) } }) setImages(imageUrls) setPreviewUrls(imageUrls) } else { showToast(response.msg || "获取素材详情失败", "error") router.back() } } catch (error: any) { console.error("Failed to fetch material detail:", error) showToast(error?.message || "请检查网络连接", "error") router.back() } finally { setIsLoading(false) } } fetchMaterialDetail() }, [resolvedParams.materialId, router]) // 模拟上传图片 const handleUploadImage = () => { // 这里应该是真实的图片上传逻辑 // 为了演示,这里模拟添加一些示例图片URL const mockImageUrls = [ "https://picsum.photos/id/237/200/300", "https://picsum.photos/id/238/200/300", "https://picsum.photos/id/239/200/300" ] const randomIndex = Math.floor(Math.random() * mockImageUrls.length) const newImage = mockImageUrls[randomIndex] if (!images.includes(newImage)) { setImages([...images, newImage]) setPreviewUrls([...previewUrls, newImage]) } } const handleRemoveImage = (indexToRemove: number) => { setImages(images.filter((_, index) => index !== indexToRemove)) setPreviewUrls(previewUrls.filter((_, index) => index !== indexToRemove)) } const handleSubmit = async (e: React.FormEvent) => { e.preventDefault() // 根据不同类型校验不同字段 if (contentType === 1 && images.length === 0) { showToast("请上传图片", "error") return } else if (contentType === 2 && (!url || !desc)) { showToast("请输入描述和链接地址", "error") return } else if ((contentType === 4 || contentType === 6) && !content) { showToast("请输入文本内容", "error") return } const loadingToast = showToast("正在更新素材...", "loading", true) try { const payload: any = { id: resolvedParams.materialId, contentType: contentType, content: content, comment: comment, sendTime: sendTime, } // 根据类型添加不同的字段 if (contentType === 1) { payload.resUrls = images } else if (contentType === 2) { payload.urls = [{ desc, image, url }] } else if (contentType === 3) { payload.urls = videoUrl ? [videoUrl] : [] } const response = await api.post('/v1/content/library/update-item', payload) if (response.code === 200) { showToast("素材更新成功", "success") router.push(`/content/${resolvedParams.id}/materials`) } else { showToast(response.msg || "更新失败", "error") } } catch (error: any) { console.error("Failed to update material:", error) showToast(error?.message || "更新失败", "error") } finally { loadingToast.remove && loadingToast.remove() } } if (isLoading) { return (
加载中...
) } return (

编辑素材

{/* 基础信息分组 */}
基础信息
setSendTime(e.target.value)} className="w-full h-12 rounded-2xl border-gray-300 focus:border-blue-500 focus:ring-2 focus:ring-blue-100 px-4 text-base placeholder:text-gray-300" placeholder="请选择发布时间" style={{ width: 'auto' }} />
{/* 内容信息分组 */}
内容信息