153 lines
		
	
	
		
			5.5 KiB
		
	
	
	
		
			TypeScript
		
	
	
	
	
	
			
		
		
	
	
			153 lines
		
	
	
		
			5.5 KiB
		
	
	
	
		
			TypeScript
		
	
	
	
	
	
import React from 'react';
 | 
						||
import { Mark } from '../mock/collection';
 | 
						||
import './modal.css';
 | 
						||
 | 
						||
interface DetailModalProps {
 | 
						||
  visible: boolean;
 | 
						||
  data: Mark | null;
 | 
						||
  onClose: () => void;
 | 
						||
}
 | 
						||
 | 
						||
export const DetailModal: React.FC<DetailModalProps> = ({ visible, data, onClose }) => {
 | 
						||
  if (!visible || !data) return null;
 | 
						||
 | 
						||
  return (
 | 
						||
    <div className="modal-overlay" onClick={onClose}>
 | 
						||
      <div className="modal-content" onClick={e => e.stopPropagation()}>
 | 
						||
        <div className="modal-header">
 | 
						||
          <h3>详情信息</h3>
 | 
						||
          <button className="modal-close" onClick={onClose}>×</button>
 | 
						||
        </div>
 | 
						||
        
 | 
						||
        <div className="modal-body">
 | 
						||
          <div className="detail-section">
 | 
						||
            <h4>基本信息</h4>
 | 
						||
            <div className="detail-grid">
 | 
						||
              <div className="detail-item">
 | 
						||
                <label>标题:</label>
 | 
						||
                <span>{data.title}</span>
 | 
						||
              </div>
 | 
						||
              <div className="detail-item">
 | 
						||
                <label>类型:</label>
 | 
						||
                <span className={`type-badge type-${data.markType}`}>{data.markType}</span>
 | 
						||
              </div>
 | 
						||
              <div className="detail-item">
 | 
						||
                <label>创建者:</label>
 | 
						||
                <span>{data.uname}</span>
 | 
						||
              </div>
 | 
						||
              <div className="detail-item">
 | 
						||
                <label>可见性:</label>
 | 
						||
                <span className={`visibility-badge visibility-${data.config.visibility}`}>
 | 
						||
                  {data.config.visibility === 'public' ? '公开' : 
 | 
						||
                   data.config.visibility === 'private' ? '私有' : '受限'}
 | 
						||
                </span>
 | 
						||
              </div>
 | 
						||
            </div>
 | 
						||
          </div>
 | 
						||
 | 
						||
          <div className="detail-section">
 | 
						||
            <h4>描述</h4>
 | 
						||
            <p>{data.description}</p>
 | 
						||
          </div>
 | 
						||
 | 
						||
          <div className="detail-section">
 | 
						||
            <h4>标签</h4>
 | 
						||
            <div className="tags-container">
 | 
						||
              {data.tags.map((tag, index) => (
 | 
						||
                <span key={index} className="tag">{tag}</span>
 | 
						||
              ))}
 | 
						||
            </div>
 | 
						||
          </div>
 | 
						||
 | 
						||
          <div className="detail-section">
 | 
						||
            <h4>时间信息</h4>
 | 
						||
            <div className="detail-grid">
 | 
						||
              <div className="detail-item">
 | 
						||
                <label>标记时间:</label>
 | 
						||
                <span>{new Date(data.markedAt).toLocaleString('zh-CN')}</span>
 | 
						||
              </div>
 | 
						||
              <div className="detail-item">
 | 
						||
                <label>创建时间:</label>
 | 
						||
                <span>{new Date(data.createdAt).toLocaleString('zh-CN')}</span>
 | 
						||
              </div>
 | 
						||
              <div className="detail-item">
 | 
						||
                <label>更新时间:</label>
 | 
						||
                <span>{new Date(data.updatedAt).toLocaleString('zh-CN')}</span>
 | 
						||
              </div>
 | 
						||
              <div className="detail-item">
 | 
						||
                <label>版本:</label>
 | 
						||
                <span>v{data.version}</span>
 | 
						||
              </div>
 | 
						||
            </div>
 | 
						||
          </div>
 | 
						||
 | 
						||
          {data.fileList.length > 0 && (
 | 
						||
            <div className="detail-section">
 | 
						||
              <h4>附件文件 ({data.fileList.length})</h4>
 | 
						||
              <div className="file-list">
 | 
						||
                {data.fileList.map((file, index) => (
 | 
						||
                  <div key={index} className="file-item">
 | 
						||
                    <div className="file-info">
 | 
						||
                      <span className="file-name">{file.name}</span>
 | 
						||
                      <span className="file-size">{formatFileSize(file.size)}</span>
 | 
						||
                    </div>
 | 
						||
                    <span className={`file-type file-type-${file.type}`}>{file.type}</span>
 | 
						||
                  </div>
 | 
						||
                ))}
 | 
						||
              </div>
 | 
						||
            </div>
 | 
						||
          )}
 | 
						||
 | 
						||
          <div className="detail-section">
 | 
						||
            <h4>数据摘要</h4>
 | 
						||
            <p className="summary-text">{data.data.summary || data.summary}</p>
 | 
						||
          </div>
 | 
						||
 | 
						||
          {data.config.allowComments !== undefined && (
 | 
						||
            <div className="detail-section">
 | 
						||
              <h4>权限设置</h4>
 | 
						||
              <div className="permission-grid">
 | 
						||
                <div className="permission-item">
 | 
						||
                  <label>允许评论:</label>
 | 
						||
                  <span className={data.config.allowComments ? 'enabled' : 'disabled'}>
 | 
						||
                    {data.config.allowComments ? '是' : '否'}
 | 
						||
                  </span>
 | 
						||
                </div>
 | 
						||
                <div className="permission-item">
 | 
						||
                  <label>允许下载:</label>
 | 
						||
                  <span className={data.config.allowDownload ? 'enabled' : 'disabled'}>
 | 
						||
                    {data.config.allowDownload ? '是' : '否'}
 | 
						||
                  </span>
 | 
						||
                </div>
 | 
						||
                {data.config.expiredAt && (
 | 
						||
                  <div className="permission-item">
 | 
						||
                    <label>过期时间:</label>
 | 
						||
                    <span>{new Date(data.config.expiredAt).toLocaleString('zh-CN')}</span>
 | 
						||
                  </div>
 | 
						||
                )}
 | 
						||
              </div>
 | 
						||
            </div>
 | 
						||
          )}
 | 
						||
        </div>
 | 
						||
 | 
						||
        <div className="modal-footer">
 | 
						||
          <button className="btn btn-default" onClick={onClose}>关闭</button>
 | 
						||
          <button className="btn btn-primary" onClick={() => {
 | 
						||
            alert('编辑功能待实现');
 | 
						||
          }}>编辑</button>
 | 
						||
        </div>
 | 
						||
      </div>
 | 
						||
    </div>
 | 
						||
  );
 | 
						||
};
 | 
						||
 | 
						||
// 格式化文件大小
 | 
						||
function formatFileSize(bytes: number): string {
 | 
						||
  if (bytes === 0) return '0 B';
 | 
						||
  
 | 
						||
  const k = 1024;
 | 
						||
  const sizes = ['B', 'KB', 'MB', 'GB'];
 | 
						||
  const i = Math.floor(Math.log(bytes) / Math.log(k));
 | 
						||
  
 | 
						||
  return parseFloat((bytes / Math.pow(k, i)).toFixed(1)) + ' ' + sizes[i];
 | 
						||
} |