修改前端推荐搜素样式,链接推荐搜索前后端

Change-Id: I76d3be2a2cb6f553fc6c4512e11b6de3341ad0c4
diff --git a/JWLLL/API_front/src/components/UploadPage.jsx b/JWLLL/API_front/src/components/UploadPage.jsx
new file mode 100644
index 0000000..e6db861
--- /dev/null
+++ b/JWLLL/API_front/src/components/UploadPage.jsx
@@ -0,0 +1,200 @@
+import React, { useState } from 'react'
+import { Image, Video } from 'lucide-react'
+
+
+export default function UploadPage() {
+  const [activeTab, setActiveTab]         = useState('image')
+  const [isDragOver, setIsDragOver]       = useState(false)
+  const [isUploading, setIsUploading]     = useState(false)
+  const [uploadedFiles, setUploadedFiles] = useState([])
+  const [uploadProgress, setUploadProgress] = useState(0)
+
+  const validateFiles = files => {
+    const imgTypes = ['image/jpeg','image/jpg','image/png','image/webp']
+    const vidTypes = ['video/mp4','video/mov','video/avi']
+    const types = activeTab==='video'? vidTypes : imgTypes
+    const max   = activeTab==='video'? 2*1024*1024*1024 : 32*1024*1024
+
+    const invalid = files.filter(f => !types.includes(f.type) || f.size > max)
+    if (invalid.length) {
+      alert(`发现 ${invalid.length} 个无效文件,请检查文件格式和大小`)
+      return false
+    }
+    return true
+  }
+
+  const simulateUpload = files => {
+    setIsUploading(true)
+    setUploadProgress(0)
+    setUploadedFiles(files)
+    const iv = setInterval(() => {
+      setUploadProgress(p => {
+        if (p >= 100) {
+          clearInterval(iv)
+          setIsUploading(false)
+          alert(`成功上传了 ${files.length} 个文件`)
+          return 100
+        }
+        return p + 10
+      })
+    }, 200)
+  }
+
+  const handleFileUpload = () => {
+    if (isUploading) return
+    const input = document.createElement('input')
+    input.type = 'file'
+    input.accept = activeTab==='video'? 'video/*' : 'image/*'
+    input.multiple = activeTab==='image'
+    input.onchange = e => {
+      const files = Array.from(e.target.files)
+      if (files.length > 0 && validateFiles(files)) simulateUpload(files)
+    }
+    input.click()
+  }
+
+  const handleDragOver  = e => { e.preventDefault(); e.stopPropagation(); setIsDragOver(true) }
+  const handleDragLeave = e => { e.preventDefault(); e.stopPropagation(); setIsDragOver(false) }
+  const handleDrop      = e => {
+    e.preventDefault(); e.stopPropagation(); setIsDragOver(false)
+    if (isUploading) return
+    const files = Array.from(e.dataTransfer.files)
+    if (files.length > 0 && validateFiles(files)) simulateUpload(files)
+  }
+
+  const clearFiles = () => setUploadedFiles([])
+  const removeFile = idx => setUploadedFiles(f => f.filter((_,i) => i!==idx))
+
+  return (
+    <>
+      <div className="upload-tabs">
+        <button
+          className={`upload-tab${activeTab==='video'?' active':''}`}
+          onClick={() => setActiveTab('video')}
+        >上传视频</button>
+        <button
+          className={`upload-tab${activeTab==='image'?' active':''}`}
+          onClick={() => setActiveTab('image')}
+        >上传图文</button>
+      </div>
+
+      <div
+        className={`upload-area${isDragOver?' drag-over':''}`}
+        onDragOver={handleDragOver}
+        onDragLeave={handleDragLeave}
+        onDrop={handleDrop}
+      >
+        <div className="upload-icon">
+          {activeTab==='video'? <Video/> : <Image/>}
+        </div>
+        <h2 className="upload-title">
+          {activeTab==='video'
+            ? '拖拽视频到此处或点击上传'
+            : '拖拽图片到此处或点击上传'
+          }
+        </h2>
+        <p className="upload-subtitle">(需支持上传格式)</p>
+        <button
+          className={`upload-btn${isUploading?' uploading':''}`}
+          onClick={handleFileUpload}
+          disabled={isUploading}
+        >
+          {isUploading
+            ? `上传中... ${uploadProgress}%`
+            : activeTab==='video'
+              ? '上传视频'
+              : '上传图片'
+          }
+        </button>
+
+        {isUploading && (
+          <div className="progress-container">
+            <div className="progress-bar">
+              <div
+                className="progress-fill"
+                style={{ width: `${uploadProgress}%` }}
+              />
+            </div>
+            <div className="progress-text">{uploadProgress}%</div>
+          </div>
+        )}
+      </div>
+
+      {uploadedFiles.length > 0 && (
+        <div className="file-preview-area">
+          <div className="preview-header">
+            <h3 className="preview-title">已上传文件 ({uploadedFiles.length})</h3>
+            <button className="clear-files-btn" onClick={clearFiles}>
+              清除所有
+            </button>
+          </div>
+          <div className="file-grid">
+            {uploadedFiles.map((file, i) => (
+              <div key={i} className="file-item">
+                <button
+                  className="remove-file-btn"
+                  onClick={() => removeFile(i)}
+                  title="删除文件"
+                >×</button>
+                {file.type.startsWith('image/') ? (
+                  <div className="file-thumbnail">
+                    <img src={URL.createObjectURL(file)} alt={file.name} />
+                  </div>
+                ) : (
+                  <div className="file-thumbnail video-thumbnail">
+                    <Video size={24} />
+                  </div>
+                )}
+                <div className="file-info">
+                  <div className="file-name" title={file.name}>
+                    {file.name.length > 20
+                      ? file.name.slice(0,17) + '...'
+                      : file.name
+                    }
+                  </div>
+                  <div className="file-size">
+                    {(file.size/1024/1024).toFixed(2)} MB
+                  </div>
+                </div>
+              </div>
+            ))}
+          </div>
+        </div>
+      )}
+
+      <div className="upload-info fade-in">
+        {activeTab==='image' ? (
+          <>
+            <div className="info-item">
+              <h3 className="info-title">图片大小</h3>
+              <p className="info-desc">最大32MB</p>
+            </div>
+            <div className="info-item">
+              <h3 className="info-title">图片格式</h3>
+              <p className="info-desc">png/jpg/jpeg/webp</p>
+            </div>
+            <div className="info-item">
+              <h3 className="info-title">分辨率</h3>
+              <p className="info-desc">建议720×960及以上</p>
+            </div>
+          </>
+        ) : (
+          <>
+            <div className="info-item">
+              <h3 className="info-title">视频大小</h3>
+              <p className="info-desc">最大2GB,时长≤5分钟</p>
+            </div>
+            <div className="info-item">
+              <h3 className="info-title">视频格式</h3>
+              <p className="info-desc">mp4/mov</p>
+            </div>
+            <div className="info-item">
+              <h3 className="info-title">分辨率</h3>
+              <p className="info-desc">建议720P及以上</p>
+            </div>
+          </>
+        )}
+      </div>
+    </>
+  )
+}
\ No newline at end of file