import React, { useState, useEffect, useCallback } from 'react';
import {
  Image,
  FolderOpen,
  Play,
  Settings,
  Clock,
  List,
  Grid,
  RefreshCw,
  Download,
  Eye,
  Trash2,
  CheckCircle,
  AlertCircle,
  Info
} from 'lucide-react';
import { invoke } from '@tauri-apps/api/core';
import { open } from '@tauri-apps/plugin-dialog';

import {
  FrameExtractionConfig,
  VideoFileInfo,
  FrameExtractionResult,
  FrameType,
  ImageFormat,
  ExtractionTaskStatus,
  DEFAULT_FRAME_EXTRACTION_CONFIG,
  SUPPORTED_VIDEO_FORMATS,
  FRAME_EXTRACTION_PRESETS
} from '../../types/frame-extractor';

import { FrameExtractionConfigPanel } from '../../components/frame-extractor/FrameExtractionConfigPanel';
import { VideoFileList } from '../../components/frame-extractor/VideoFileList';
import { ExtractionProgress } from '../../components/frame-extractor/ExtractionProgress';
import { FramePreview } from '../../components/frame-extractor/FramePreview';
import { ExtractionResults } from '../../components/frame-extractor/ExtractionResults';
import { VideoPlayer } from '../../components/frame-extractor/VideoPlayer';

/**
 * 视频关键帧提取工具主组件
 * 遵循 Tauri 开发规范和 UI/UX 设计标准
 */
const FrameExtractorTool: React.FC = () => {
  // 状态管理
  const [selectedVideos, setSelectedVideos] = useState<VideoFileInfo[]>([]);
  const [config, setConfig] = useState<FrameExtractionConfig>(DEFAULT_FRAME_EXTRACTION_CONFIG);
  const [isExtracting, setIsExtracting] = useState(false);
  const [isScanning, setIsScanning] = useState(false);
  const [extractionResults, setExtractionResults] = useState<FrameExtractionResult[]>([]);
  const [currentProgress, setCurrentProgress] = useState(0);
  const [currentFile, setCurrentFile] = useState<string>('');
  const [viewMode, setViewMode] = useState<'config' | 'progress' | 'results'>('config');
  const [selectedFolder, setSelectedFolder] = useState<string>('');
  const [ffmpegAvailable, setFfmpegAvailable] = useState<boolean | null>(null);
  const [selectedVideoForPreview, setSelectedVideoForPreview] = useState<VideoFileInfo | null>(null);
  const [currentPlayTime, setCurrentPlayTime] = useState<number>(0);
  const [recursiveScan, setRecursiveScan] = useState<boolean>(true);

  // 检查 FFmpeg 可用性
  useEffect(() => {
    checkFFmpegAvailability();
  }, []);

  const checkFFmpegAvailability = useCallback(async () => {
    try {
      const available = await invoke<boolean>('check_ffmpeg_availability');
      setFfmpegAvailable(available);
      if (!available) {
        console.warn('FFmpeg 不可用，某些功能可能无法正常工作');
      }
    } catch (error) {
      console.error('检查 FFmpeg 可用性失败:', error);
      setFfmpegAvailable(false);
    }
  }, []);

  // 选择单个视频文件
  const handleSelectFiles = useCallback(async () => {
    try {
      const selected = await open({
        multiple: true,
        filters: [{
          name: '视频文件',
          extensions: SUPPORTED_VIDEO_FORMATS
        }],
        title: '选择视频文件',
      });

      if (selected && Array.isArray(selected)) {
        await loadVideoFiles(selected);
      } else if (selected && typeof selected === 'string') {
        await loadVideoFiles([selected]);
      }
    } catch (error) {
      console.error('选择文件失败:', error);
    }
  }, []);

  // 选择文件夹
  const handleSelectFolder = useCallback(async () => {
    try {
      const selected = await open({
        directory: true,
        multiple: false,
        title: '选择视频文件夹',
      });

      if (selected && typeof selected === 'string') {
        setSelectedFolder(selected);
        await scanVideoFiles(selected, recursiveScan);
      }
    } catch (error) {
      console.error('选择文件夹失败:', error);
    }
  }, []);

  // 扫描视频文件
  const scanVideoFiles = useCallback(async (folderPath: string, recursive: boolean) => {
    setIsScanning(true);
    setCurrentFile(`正在扫描文件夹: ${folderPath}${recursive ? ' (递归)' : ''}`);

    try {
      const files = await invoke<VideoFileInfo[]>('scan_video_files', {
        request: {
          folder_path: folderPath,
          recursive,
          supported_formats: SUPPORTED_VIDEO_FORMATS,
        }
      });

      const validFiles = files.filter(f => f.is_valid);
      setSelectedVideos(validFiles);

      // 显示扫描结果
      const totalFiles = files.length;
      const validCount = validFiles.length;
      const invalidCount = totalFiles - validCount;

      console.log(`扫描完成: 找到 ${totalFiles} 个文件，其中 ${validCount} 个有效，${invalidCount} 个无效`);
      setCurrentFile(`扫描完成: 找到 ${validCount} 个有效视频文件`);

      // 2秒后清除状态信息
      setTimeout(() => {
        setCurrentFile('');
      }, 2000);

    } catch (error) {
      console.error('扫描视频文件失败:', error);
      setCurrentFile('扫描失败，请重试');
      setTimeout(() => {
        setCurrentFile('');
      }, 3000);
    } finally {
      setIsScanning(false);
    }
  }, []);

  // 加载视频文件信息
  const loadVideoFiles = useCallback(async (filePaths: string[]) => {
    setIsScanning(true);
    const videoInfos: VideoFileInfo[] = [];

    try {
      for (const filePath of filePaths) {
        try {
          const info = await invoke<VideoFileInfo>('get_video_info', {
            videoPath: filePath
          });
          videoInfos.push(info);
        } catch (error) {
          console.error(`获取视频信息失败 ${filePath}:`, error);
        }
      }

      setSelectedVideos(videoInfos.filter(info => info.is_valid));
    } finally {
      setIsScanning(false);
    }
  }, []);

  // 开始提取
  const handleStartExtraction = useCallback(async () => {
    if (selectedVideos.length === 0) {
      alert('请先选择视频文件');
      return;
    }

    if (!config.output_directory) {
      alert('请设置输出目录');
      return;
    }

    setIsExtracting(true);
    setViewMode('progress');
    setCurrentProgress(0);
    setExtractionResults([]);

    try {
      const videoPaths = selectedVideos.map(v => v.path);
      const results = await invoke<FrameExtractionResult[]>('extract_frames_batch', {
        request: {
          video_files: videoPaths,
          config: config,
        }
      });

      setExtractionResults(results);
      setViewMode('results');
      
      const successCount = results.filter(r => r.success).length;
      console.log(`提取完成: ${successCount}/${results.length} 成功`);
    } catch (error) {
      console.error('批量提取失败:', error);
      alert(`提取失败: ${error}`);
    } finally {
      setIsExtracting(false);
    }
  }, [selectedVideos, config]);

  // 清除选择
  const handleClearSelection = useCallback(() => {
    setSelectedVideos([]);
    setSelectedFolder('');
    setExtractionResults([]);
    setCurrentProgress(0);
    setCurrentFile('');
  }, []);

  // 应用预设配置
  const handleApplyPreset = useCallback((presetId: string) => {
    const preset = FRAME_EXTRACTION_PRESETS.find(p => p.id === presetId);
    if (preset) {
      setConfig({ ...preset.config });
    }
  }, []);

  return (
    <div className="space-y-6">
      {/* 页面标题 */}
      <div className="page-header flex items-center justify-between">
        <div className="flex items-center gap-3">
          <div className="w-12 h-12 bg-gradient-to-br from-blue-500 to-blue-600 rounded-xl flex items-center justify-center shadow-lg hover:shadow-xl transition-all duration-300">
            <Image className="w-6 h-6 text-white" />
          </div>
          <div>
            <h1 className="text-3xl font-bold bg-gradient-to-r from-gray-900 to-blue-600 bg-clip-text text-transparent">
              视频关键帧提取工具
            </h1>
            <p className="text-gray-600 text-lg">快速提取视频的第一帧、最后帧或自定义位置的帧</p>
          </div>
        </div>

        {/* FFmpeg 状态指示器 */}
        <div className="flex items-center gap-2">
          {ffmpegAvailable === null ? (
            <div className="flex items-center gap-2 text-gray-500">
              <RefreshCw className="w-4 h-4 animate-spin" />
              <span className="text-sm">检查中...</span>
            </div>
          ) : ffmpegAvailable ? (
            <div className="flex items-center gap-2 text-green-600">
              <CheckCircle className="w-4 h-4" />
              <span className="text-sm">FFmpeg 可用</span>
            </div>
          ) : (
            <div className="flex items-center gap-2 text-red-600">
              <AlertCircle className="w-4 h-4" />
              <span className="text-sm">FFmpeg 不可用</span>
            </div>
          )}
        </div>
      </div>

      {/* 工具栏 */}
      <div className="flex items-center justify-between bg-white rounded-lg p-4 shadow-sm border">
        <div className="flex items-center gap-3">
          <button
            onClick={handleSelectFiles}
            disabled={isScanning || isExtracting}
            className="flex items-center gap-2 px-4 py-2 bg-blue-500 text-white rounded-lg hover:bg-blue-600 disabled:opacity-50 disabled:cursor-not-allowed transition-colors"
          >
            <Image className="w-4 h-4" />
            选择文件
          </button>
          
          <button
            onClick={handleSelectFolder}
            disabled={isScanning || isExtracting}
            className="flex items-center gap-2 px-4 py-2 bg-green-500 text-white rounded-lg hover:bg-green-600 disabled:opacity-50 disabled:cursor-not-allowed transition-colors"
            title={recursiveScan ? "选择文件夹并递归扫描所有子文件夹中的视频文件" : "选择文件夹并扫描其中的视频文件"}
          >
            <FolderOpen className="w-4 h-4" />
            选择文件夹{recursiveScan ? ' (递归)' : ''}
          </button>

          <button
            onClick={handleClearSelection}
            disabled={isScanning || isExtracting}
            className="flex items-center gap-2 px-4 py-2 bg-gray-500 text-white rounded-lg hover:bg-gray-600 disabled:opacity-50 disabled:cursor-not-allowed transition-colors"
          >
            <Trash2 className="w-4 h-4" />
            清除选择
          </button>

          {/* 递归扫描选项 */}
          <div className="flex items-center gap-2 ml-4 pl-4 border-l border-gray-200">
            <label className="flex items-center gap-2 text-sm text-gray-700 cursor-pointer">
              <input
                type="checkbox"
                checked={recursiveScan}
                onChange={(e) => setRecursiveScan(e.target.checked)}
                className="rounded border-gray-300 text-blue-600 focus:ring-blue-500"
              />
              <span>递归扫描子文件夹</span>
            </label>
          </div>
        </div>

        <div className="flex items-center gap-3">
          <div className="text-sm text-gray-600">
            已选择 {selectedVideos.length} 个视频文件
          </div>
          
          <button
            onClick={handleStartExtraction}
            disabled={selectedVideos.length === 0 || isExtracting || !ffmpegAvailable}
            className="flex items-center gap-2 px-6 py-2 bg-purple-500 text-white rounded-lg hover:bg-purple-600 disabled:opacity-50 disabled:cursor-not-allowed transition-colors"
          >
            {isExtracting ? (
              <>
                <RefreshCw className="w-4 h-4 animate-spin" />
                提取中...
              </>
            ) : (
              <>
                <Play className="w-4 h-4" />
                开始提取
              </>
            )}
          </button>
        </div>
      </div>

      {/* 状态显示区域 */}
      {(isScanning || currentFile) && (
        <div className="bg-blue-50 border border-blue-200 rounded-lg p-3">
          <div className="flex items-center gap-2">
            {isScanning && <RefreshCw className="w-4 h-4 text-blue-600 animate-spin" />}
            <span className="text-sm text-blue-800">
              {currentFile || '正在处理...'}
            </span>
          </div>
        </div>
      )}

      {/* 视图切换 */}
      <div className="flex items-center gap-2 bg-white rounded-lg p-1 shadow-sm border w-fit">
        <button
          onClick={() => setViewMode('config')}
          className={`px-4 py-2 rounded-md transition-colors ${
            viewMode === 'config'
              ? 'bg-blue-100 text-blue-600'
              : 'text-gray-600 hover:text-gray-800'
          }`}
        >
          <Settings className="w-4 h-4 inline mr-2" />
          配置
        </button>
        <button
          onClick={() => setViewMode('progress')}
          className={`px-4 py-2 rounded-md transition-colors ${
            viewMode === 'progress'
              ? 'bg-blue-100 text-blue-600'
              : 'text-gray-600 hover:text-gray-800'
          }`}
        >
          <Clock className="w-4 h-4 inline mr-2" />
          进度
        </button>
        <button
          onClick={() => setViewMode('results')}
          className={`px-4 py-2 rounded-md transition-colors ${
            viewMode === 'results'
              ? 'bg-blue-100 text-blue-600'
              : 'text-gray-600 hover:text-gray-800'
          }`}
        >
          <List className="w-4 h-4 inline mr-2" />
          结果
        </button>
      </div>

      {/* 主要内容区域 */}
      <div className="grid grid-cols-1 lg:grid-cols-3 gap-6">
        {/* 左侧：视频文件列表 */}
        <div className="lg:col-span-1">
          <VideoFileList
            videos={selectedVideos}
            isScanning={isScanning}
            onRemoveVideo={(index: number) => {
              const newVideos = [...selectedVideos];
              newVideos.splice(index, 1);
              setSelectedVideos(newVideos);
              // 如果删除的是当前预览的视频，清除预览
              if (selectedVideoForPreview && selectedVideos[index]?.path === selectedVideoForPreview.path) {
                setSelectedVideoForPreview(null);
              }
            }}
            onPreviewVideo={(video: VideoFileInfo) => {
              setSelectedVideoForPreview(video);
              setViewMode('config'); // 切换到配置视图以显示预览
            }}
          />
        </div>

        {/* 右侧：主要内容 */}
        <div className="lg:col-span-2 space-y-6">
          {viewMode === 'config' && (
            <>
              {/* 视频预览播放器 */}
              {selectedVideoForPreview && (
                <div className="bg-white rounded-lg shadow-sm border p-4">
                  <div className="flex items-center justify-between mb-4">
                    <h3 className="font-semibold text-gray-900">视频预览</h3>
                    <button
                      onClick={() => setSelectedVideoForPreview(null)}
                      className="text-gray-400 hover:text-gray-600"
                    >
                      <Eye className="w-5 h-5" />
                    </button>
                  </div>
                  <VideoPlayer
                    video={selectedVideoForPreview}
                    currentTime={currentPlayTime}
                    onTimeUpdate={setCurrentPlayTime}
                    className="w-full h-64"
                  />
                </div>
              )}

              {/* 配置面板 */}
              <FrameExtractionConfigPanel
                config={config}
                onConfigChange={setConfig}
                onApplyPreset={handleApplyPreset}
                presets={FRAME_EXTRACTION_PRESETS}
                currentVideo={selectedVideoForPreview || undefined}
                currentTime={currentPlayTime}
                onTimeChange={setCurrentPlayTime}
              />
            </>
          )}

          {viewMode === 'progress' && (
            <ExtractionProgress
              isExtracting={isExtracting}
              progress={currentProgress}
              currentFile={currentFile}
              totalFiles={selectedVideos.length}
            />
          )}

          {viewMode === 'results' && (
            <ExtractionResults
              results={extractionResults}
              onOpenResult={(result: FrameExtractionResult) => {
                // 打开结果文件所在目录
                invoke('open_file_directory', { path: result.output_path });
              }}
            />
          )}
        </div>
      </div>
    </div>
  );
};

export default FrameExtractorTool;
