修改提示框样式、完成付费片单、推荐跳转

Change-Id: Ie84c53d4e306435144b1f26ceb39cc182e99d57a
diff --git a/src/pages/SeedList/Recommend/Recommend.jsx b/src/pages/SeedList/Recommend/Recommend.jsx
index 8270145..f58c73d 100644
--- a/src/pages/SeedList/Recommend/Recommend.jsx
+++ b/src/pages/SeedList/Recommend/Recommend.jsx
@@ -2,48 +2,205 @@
 import axios from 'axios';
 import './Recommend.css';
 import { useUser } from '../../../context/UserContext';
+import { useLocation } from 'wouter';
+import toast from 'react-hot-toast';
+import CreatePlaylistModal from './CreatePlaylistModal';
+import { confirmAlert } from 'react-confirm-alert';
+import 'react-confirm-alert/src/react-confirm-alert.css';
 
 const Recommend = () => {
   const { user } = useUser();
+  const [paidLists, setPaidLists] = useState([]);
   const [popularSeeds, setPopularSeeds] = useState([]);
-  const [recommendedSeeds, setRecommendedSeeds] = useState([]);
+  const [recommendedSeeds, setRecommendedSeeds] = useState({
+    movie: [],
+    tv: [],
+    anime: []
+  });
+
+  const [showModal, setShowModal] = useState(false);
+  const [, navigate] = useLocation();
 
   useEffect(() => {
-    // 获取热门资源
+    axios
+      .get('/playlist/page', { params: { page: 1, size: 8 } })
+      .then((res) => {
+        if (res.data.code === 0) {
+          setPaidLists(res.data.data);
+        } else {
+          toast.error(`获取片单失败:${res.data.msg}`);
+        }
+      })
+      .catch((err) => {
+        console.error('请求片单失败', err);
+        toast.error('请求片单失败,请稍后重试');
+      });
+
     axios
       .get('/echo/recommendation/popular', { params: { limit: 16 } })
       .then((res) => setPopularSeeds(res.data))
-      .catch((err) => console.error('获取热门资源失败', err));
+      .catch((err) => {
+        console.error('获取热门资源失败', err);
+        toast.error('获取热门资源失败');
+      });
   }, []);
 
   useEffect(() => {
-    // 获取个性化推荐
-    if (user && user.userId) {
+    if (user?.userId) {
       axios
         .get(`/echo/recommendation/seeds/${user.userId}`)
-        .then((res) => setRecommendedSeeds(res.data))
-        .catch((err) => console.error('获取个性化推荐失败', err));
+        .then((res) => {
+          const categorized = { movie: [], tv: [], anime: [] };
+          res.data.forEach((seed) => {
+            if (seed.category === 'movie') categorized.movie.push(seed);
+            else if (seed.category === 'tv') categorized.tv.push(seed);
+            else if (seed.category === 'anime') categorized.anime.push(seed);
+          });
+          setRecommendedSeeds(categorized);
+        })
+        .catch((err) => {
+          console.error('获取个性化推荐失败', err);
+          toast.error('获取个性化推荐失败');
+        });
     }
   }, [user]);
 
-  const renderSeedCard = (seed) => (
-    <div className="seed-card" key={seed.id}>
-      <img src={seed.coverUrl || '/default-cover.jpg'} alt={seed.title} />
-      <div className="title">{seed.title}</div>
-    </div>
+  const handleDelete = (id) => {
+    confirmAlert({
+      title: '确认删除',
+      message: '确定删除此片单吗?',
+      buttons: [
+        {
+          label: '确定',
+          onClick: async () => {
+            const toastId = toast.loading('正在删除...');
+            try {
+              await axios.delete('/playlist', {
+                params: { ids: id },
+                paramsSerializer: (params) =>
+                  `ids=${Array.isArray(params.ids) ? params.ids.join(',') : params.ids}`
+              });
+              setPaidLists(paidLists.filter((list) => list.id !== id));
+              toast.success('删除成功', { id: toastId });
+            } catch (error) {
+              console.error('删除失败', error);
+              toast.error('删除失败,请稍后重试', { id: toastId });
+            }
+          }
+        },
+        { label: '取消' }
+      ]
+    });
+  };
+
+  const handlePurchase = (id) => {
+    confirmAlert({
+      title: '确认购买',
+      message: '确定支付该片单?',
+      buttons: [
+        {
+          label: '确定',
+          onClick: async () => {
+            const toastId = toast.loading('购买中...');
+            try {
+              const res = await axios.post(`/playlist/${id}/pay`);
+              if (res.data.code === 0) {
+                toast.success('购买成功', { id: toastId });
+                navigate(`/playlist/${id}`);
+              } else {
+                toast.error(`购买失败:${res.data.msg}`, { id: toastId });
+              }
+            } catch (err) {
+              console.error('支付失败', err);
+              toast.error('购买失败,请稍后重试', { id: toastId });
+            }
+          }
+        },
+        { label: '取消' }
+      ]
+    });
+  };
+
+const renderSeedCard = (seed) => (
+  <div
+    className="seed-card"
+    key={seed.id}
+    onClick={() => navigate(`/seed/${seed.id}`)}
+    style={{ cursor: 'pointer' }}
+  >
+    <img src={seed.imageUrl || '/default-cover.jpg'} alt={seed.title} />
+    <div className="title">{seed.title}</div>
+  </div>
+);
+
+
+  const renderSection = (title, seeds) => (
+    <>
+      <h2>{title}</h2>
+      <div className="seed-list">{seeds.map(renderSeedCard)}</div>
+    </>
   );
 
   return (
     <div className="recommendation-page">
-      <h2>🎬 正在热映</h2>
-      <div className="seed-list">{popularSeeds.map(renderSeedCard)}</div>
+      <h2>💰 付费片单</h2>
+      {user && user.role === 'admin' && (
+        <button className="create-button" onClick={() => setShowModal(true)}>
+          ➕ 创建片单
+        </button>
+      )}
 
-      <h2>🎯 个性化推荐</h2>
+      <div className="recommend-paid-row">
+        {paidLists.map((list) => (
+          <div className="paid-card" key={list.id}>
+            <img
+              className="paid-cover"
+              src={list.coverUrl || '/default-cover.jpg'}
+              alt={list.title}
+            />
+            <div className="paid-title">{list.title}</div>
+
+            {user && user.role === 'admin' ? (
+              <div className="admin-actions">
+                <button onClick={() => handleDelete(list.id)}>删除</button>
+              </div>
+            ) : list.isPaid ? (
+              <button onClick={() => navigate(`/playlist/${list.id}`)}>详情</button>
+            ) : (
+              <button onClick={() => handlePurchase(list.id)}>购买</button>
+            )}
+          </div>
+        ))}
+      </div>
+
+      <h2>🎬 正在热映</h2>
+      <div className="seed-list popular-row">
+        {popularSeeds.slice(0, 8).map(renderSeedCard)}
+      </div>
+
+      <h2>🎯 猜你喜欢</h2>
       {user ? (
-        <div className="seed-list">{recommendedSeeds.map(renderSeedCard)}</div>
+        <>
+          {recommendedSeeds.movie.length > 0 &&
+            renderSection('🎞️ 电影推荐', recommendedSeeds.movie)}
+          {recommendedSeeds.tv.length > 0 &&
+            renderSection('📺 电视剧推荐', recommendedSeeds.tv)}
+          {recommendedSeeds.anime.length > 0 &&
+            renderSection('🎌 动漫推荐', recommendedSeeds.anime)}
+        </>
       ) : (
         <div className="login-reminder">请登录以获取个性化推荐</div>
       )}
+
+      {showModal && (
+        <CreatePlaylistModal
+          onClose={() => setShowModal(false)}
+          onSuccess={(newPlaylist) => {
+            setPaidLists([newPlaylist, ...paidLists]);
+            setShowModal(false);
+          }}
+        />
+      )}
     </div>
   );
 };