import React, { useState, useEffect, useRef } from 'react';
import { Plus, Pencil, Trash2, Pin, FileText, LayoutTemplate, FileSpreadsheet } from 'lucide-react';
import api from '@/lib/api';
import ThumbnailImage from './ThumbnailImage';

interface FileItem {
  name: string;
  path: string;
  is_dir: boolean;
  size: number;
  mime_type: string;
  is_pinned: boolean;
  is_trashed: boolean;
  mod_time: string;
  checksum?: string;
}

interface OfficeHomeProps {
  type: 'docs' | 'slides' | 'sheets';
  onFileSelect: (file: FileItem) => void;
  onCreateBlank: (file: FileItem) => void;
  onPinChange?: () => void;
}

// Custom Word icon (blue)
function WordIcon({ className }: { className?: string }) {
  return (
    <div className={`flex items-center justify-center text-white bg-[#2B579A] rounded-lg ${className || ''}`}>
      <FileText className="w-[55%] h-[55%]" />
    </div>
  );
}

// Custom PowerPoint icon (orange)
function PptIcon({ className }: { className?: string }) {
  return (
    <div className={`flex items-center justify-center text-white bg-[#D24726] rounded-lg ${className || ''}`}>
      <LayoutTemplate className="w-[55%] h-[55%]" />
    </div>
  );
}

// Custom Excel icon (green)
function SheetIcon({ className }: { className?: string }) {
  return (
    <div className={`flex items-center justify-center text-white bg-[#107C41] rounded-lg ${className || ''}`}>
      <FileSpreadsheet className="w-[55%] h-[55%]" />
    </div>
  );
}

interface ContextMenuState {
  x: number;
  y: number;
  file: FileItem;
}

export default function OfficeHome({ type, onFileSelect, onCreateBlank, onPinChange }: OfficeHomeProps) {
  const [recentFiles, setRecentFiles] = useState<FileItem[]>([]);
  const [pinnedFiles, setPinnedFiles] = useState<FileItem[]>([]);
  const [allFiles, setAllFiles] = useState<FileItem[]>([]);
  const [loading, setLoading] = useState(true);
  const [loadingAll, setLoadingAll] = useState(true);
  const [contextMenu, setContextMenu] = useState<ContextMenuState | null>(null);
  const [renaming, setRenaming] = useState<string | null>(null); // path of file being renamed
  const [renameValue, setRenameValue] = useState('');
  const renameInputRef = useRef<HTMLInputElement>(null);
  const [downloadToken, setDownloadToken] = useState('');

  const ext = type === 'docs' ? '.docx' : type === 'slides' ? '.pptx' : '.xlsx';
  const fileTypeParam = type === 'docs' ? 'docx' : type === 'slides' ? 'pptx' : 'xlsx';

  const fetchFiles = () => {
    // Fetch recent files from root directory
    api.listDirectory('.')
      .then(data => {
        const files: FileItem[] = data.files || [];
        const filtered = files
          .filter(f => !f.is_dir && f.name.endsWith(ext) && !f.is_trashed)
          .sort((a, b) => new Date(b.mod_time).getTime() - new Date(a.mod_time).getTime())
          .slice(0, 12);
        setRecentFiles(filtered);
        setLoading(false);
      })
      .catch(err => {
        console.error(err);
        setLoading(false);
      });

    // Fetch pinned files
    api.listPinned()
      .then(data => {
        const files: FileItem[] = data.items || [];
        const filtered = files
          .filter(f => f.name.endsWith(ext) && !f.is_trashed)
          .sort((a, b) => new Date(b.mod_time).getTime() - new Date(a.mod_time).getTime());
        setPinnedFiles(filtered);
      })
      .catch(console.error);

    // Fetch ALL office files recursively
    api.listOfficeFiles(fileTypeParam)
      .then(data => {
        const files = (data.files || []).map((f: any) => ({
          ...f,
          is_dir: false,
          mime_type: '',
          is_pinned: false,
          is_trashed: false,
        }));
        // Sort by mod_time descending
        files.sort((a: FileItem, b: FileItem) => new Date(b.mod_time).getTime() - new Date(a.mod_time).getTime());
        setAllFiles(files);
        setLoadingAll(false);
      })
      .catch(err => {
        console.error(err);
        setLoadingAll(false);
      });
  };

  useEffect(() => {
    fetchFiles();
    api.createDownloadToken().then(setDownloadToken).catch(console.error);

    // Refresh files periodically to catch any debounced thumbnail updates from recent edits
    const timer = setInterval(() => {
      fetchFiles();
    }, 15000);
    return () => clearInterval(timer);
  }, [type]);

  // Close context menu on click elsewhere
  useEffect(() => {
    const handleClick = () => setContextMenu(null);
    if (contextMenu) {
      window.addEventListener('click', handleClick);
      return () => window.removeEventListener('click', handleClick);
    }
  }, [contextMenu]);

  // Focus rename input
  useEffect(() => {
    if (renaming && renameInputRef.current) {
      renameInputRef.current.focus();
      // Select the name without extension
      const dotIdx = renameValue.lastIndexOf('.');
      renameInputRef.current.setSelectionRange(0, dotIdx > 0 ? dotIdx : renameValue.length);
    }
  }, [renaming]);

  const handleCreateBlank = async () => {
    try {
      const res = await api.createOnlyOfficeFile(type === 'docs' ? 'word' : type === 'slides' ? 'slide' : 'cell');
      const { path, name } = res;
      
      const newFile: FileItem = {
        name,
        path,
        is_dir: false,
        size: 0,
        mime_type: type === 'docs' ? 'application/vnd.openxmlformats-officedocument.wordprocessingml.document' : 
                   type === 'slides' ? 'application/vnd.openxmlformats-officedocument.presentationml.presentation' :
                   'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet',
        is_pinned: false,
        is_trashed: false,
        mod_time: new Date().toISOString()
      };
      
      onCreateBlank(newFile);
    } catch (err) {
      console.error("Failed to create document", err);
    }
  };

  const handleContextMenu = (e: React.MouseEvent, file: FileItem) => {
    e.preventDefault();
    e.stopPropagation();
    setContextMenu({ x: e.clientX, y: e.clientY, file });
  };

  const handlePin = async (file: FileItem) => {
    try {
      await api.togglePin(file.path);
      fetchFiles();
      if (onPinChange) onPinChange();
    } catch (err) {
      console.error("Failed to pin", err);
    }
  };

  const handleRename = async () => {
    let trimmed = renameValue.trim();
    if (!renaming || !trimmed) {
      setRenaming(null);
      return;
    }

    // Determine the current file's extension to append
    const currentFile = recentFiles.find(f => f.path === renaming) || allFiles.find(f => f.path === renaming);
    if (currentFile) {
      const extMatch = currentFile.name.match(/\.[^.]+$/);
      const currentExt = extMatch ? extMatch[0] : '';
      if (!trimmed.toLowerCase().endsWith(currentExt.toLowerCase())) {
        trimmed += currentExt;
      }
    }

    try {
      await api.rename(renaming, trimmed);
      setRenaming(null);
      fetchFiles(); // Refresh
    } catch (err) {
      console.error("Failed to rename", err);
      setRenaming(null);
    }
  };

  const handleDelete = async (file: FileItem) => {
    try {
      await api.deleteFile(file.path);
      fetchFiles(); // Refresh
    } catch (err) {
      console.error("Failed to delete", err);
    }
  };

  const title = type === 'docs' ? 'Documents' : type === 'slides' ? 'Presentations' : 'Spreadsheets';
  const Icon = type === 'docs' ? WordIcon : type === 'slides' ? PptIcon : SheetIcon;
  const accentColor = type === 'docs' ? '#2B579A' : type === 'slides' ? '#D24726' : '#107C41';

  const renderFileCard = (file: FileItem) => {
    const isRenaming = renaming === file.path;
    const extMatch = file.name.match(/\.[^.]+$/);
    const baseName = extMatch ? file.name.slice(0, -extMatch[0].length) : file.name;

    return (
      <div key={file.path} className="flex flex-col gap-2 group">
        <button 
          onClick={() => !isRenaming && onFileSelect(file)}
          onContextMenu={(e) => handleContextMenu(e, file)}
          className={`w-full ${type === 'docs' ? 'aspect-[1/1.4]' : 'aspect-[1.4/1]'} rounded-lg border hover:border-blue-500 transition-colors flex items-center justify-center shadow-sm overflow-hidden relative`}
          style={{ backgroundColor: 'var(--color-bg-elevated)', borderColor: 'var(--color-border)' }}
        >
          {file.checksum ? (
            <div className="absolute inset-0 w-full h-full flex items-center justify-center z-0">
              <ThumbnailImage checksum={file.checksum} fallbackIcon={<Icon className="w-16 h-16 text-3xl opacity-30 group-hover:opacity-60 transition-opacity" />} downloadToken={downloadToken} isDocument={true} />
            </div>
          ) : (
            <Icon className="w-16 h-16 text-3xl opacity-30 group-hover:opacity-60 transition-opacity" />
          )}
        </button>
        <div className="flex items-start gap-2 min-w-0">
          <Icon className="w-4 h-4 flex-shrink-0 mt-0.5 text-[10px]" />
          {isRenaming ? (
            <input
              ref={renameInputRef}
              value={renameValue}
              onChange={(e) => setRenameValue(e.target.value)}
              onBlur={handleRename}
              onKeyDown={(e) => {
                if (e.key === 'Enter') handleRename();
                if (e.key === 'Escape') setRenaming(null);
              }}
              className="text-sm font-medium w-full bg-transparent border-b border-blue-500 outline-none"
              style={{ color: 'var(--color-text-primary)' }}
            />
          ) : (
            <span 
              className="text-sm font-medium leading-tight break-words" 
              style={{ color: 'var(--color-text-primary)', wordBreak: 'break-word' }} 
              title={file.name}
            >
              {baseName}
            </span>
          )}
        </div>
      </div>
    );
  };

  return (
    <div className="flex-1 overflow-y-auto" style={{ backgroundColor: 'var(--color-bg-primary)' }}>
      {/* Top Banner */}
      <div className="py-8 px-10" style={{ backgroundColor: 'var(--color-bg-secondary)' }}>
        <div className="max-w-6xl mx-auto">
          <h2 className="text-lg font-medium mb-4" style={{ color: 'var(--color-text-primary)' }}>Start a new {type === 'docs' ? 'document' : type === 'slides' ? 'presentation' : 'spreadsheet'}</h2>
          <div className="flex gap-4">
            <div className="flex flex-col gap-3">
              <button
                onClick={handleCreateBlank}
                className={`${type === 'docs' ? 'w-40 h-52' : 'w-52 h-40'} rounded-lg border hover:border-blue-500 transition-colors flex items-center justify-center shadow-sm group`}
                style={{ backgroundColor: 'var(--color-bg-elevated)', borderColor: 'var(--color-border)' }}
              >
                <Plus className="w-12 h-12 text-gray-300 group-hover:text-blue-500 transition-colors" />
              </button>
              <span className="text-sm font-medium" style={{ color: 'var(--color-text-primary)' }}>Blank</span>
            </div>
          </div>
        </div>
      </div>


      {/* Recent Documents */}
      <div className="py-8 px-10">
        <div className="max-w-6xl mx-auto">
          <h2 className="text-lg font-medium mb-6" style={{ color: 'var(--color-text-primary)' }}>Recent {title.toLowerCase()}</h2>
          
          {loading ? (
            <div className="text-sm text-gray-500">Loading...</div>
          ) : recentFiles.length === 0 ? (
            <div className="text-sm text-gray-500">No recent {title.toLowerCase()} found.</div>
          ) : (
            <div className={`grid ${type === 'slides' ? 'grid-cols-1 sm:grid-cols-2 md:grid-cols-3 lg:grid-cols-4 xl:grid-cols-5' : 'grid-cols-2 sm:grid-cols-3 md:grid-cols-4 lg:grid-cols-5 xl:grid-cols-6'} gap-6`}>
              {recentFiles.map(file => renderFileCard(file))}
            </div>
          )}
        </div>
      </div>

      {/* All Documents */}
      <div className="py-8 px-10 border-t" style={{ borderColor: 'var(--color-border)' }}>
        <div className="max-w-6xl mx-auto">
          <h2 className="text-lg font-medium mb-6" style={{ color: 'var(--color-text-primary)' }}>All {title.toLowerCase()}</h2>
          
          {loadingAll ? (
            <div className="text-sm text-gray-500">Loading...</div>
          ) : allFiles.length === 0 ? (
            <div className="text-sm text-gray-500">No {title.toLowerCase()} found in your drive.</div>
          ) : (
            <div className={`grid ${type === 'slides' ? 'grid-cols-1 sm:grid-cols-2 md:grid-cols-3 lg:grid-cols-4 xl:grid-cols-5' : 'grid-cols-2 sm:grid-cols-3 md:grid-cols-4 lg:grid-cols-5 xl:grid-cols-6'} gap-6`}>
              {allFiles.map(file => renderFileCard(file))}
            </div>
          )}
        </div>
      </div>

      {/* Context Menu */}
      {contextMenu && (
        <div 
          className="fixed z-50 min-w-[160px] py-1 rounded-lg shadow-lg border"
          style={{ 
            top: contextMenu.y, 
            left: contextMenu.x,
            backgroundColor: 'var(--color-bg-elevated, #fff)',
            borderColor: 'var(--color-border, #e5e7eb)',
          }}
          onClick={(e) => e.stopPropagation()}
        >
          <button
            className="w-full px-4 py-2 text-left text-sm flex items-center gap-3 hover:bg-black/5 transition-colors"
            style={{ color: 'var(--color-text-primary)' }}
            onClick={() => {
              handlePin(contextMenu.file);
              setContextMenu(null);
            }}
          >
            <Pin className="w-4 h-4" style={{ color: 'var(--color-text-secondary)' }} />
            {contextMenu.file.is_pinned || pinnedFiles.find(f => f.path === contextMenu.file.path) ? 'Unpin' : 'Pin'}
          </button>
          <button
            className="w-full px-4 py-2 text-left text-sm flex items-center gap-3 hover:bg-black/5 transition-colors"
            style={{ color: 'var(--color-text-primary)' }}
            onClick={() => {
              const extMatch = contextMenu.file.name.match(/\.[^.]+$/);
              const baseName = extMatch ? contextMenu.file.name.slice(0, -extMatch[0].length) : contextMenu.file.name;
              setRenaming(contextMenu.file.path);
              setRenameValue(baseName);
              setContextMenu(null);
            }}
          >
            <Pencil className="w-4 h-4" />
            Rename
          </button>
          <button
            className="w-full px-4 py-2 text-left text-sm flex items-center gap-3 hover:bg-black/5 transition-colors text-red-500"
            onClick={() => {
              handleDelete(contextMenu.file);
              setContextMenu(null);
            }}
          >
            <Trash2 className="w-4 h-4" />
            Delete
          </button>
        </div>
      )}
    </div>
  );
}
