/**
 * DocumentOutline.tsx - 文档大纲组件
 * 
 * 显示文档的层级结构,支持:
 * - 展开/折叠子标题
 * - 点击跳转到对应位置
 * - 高亮当前激活的标题
 * 
 * @module components/Editor
 */

import React, { useState, useMemo, useCallback } from 'react';
import { Tree } from 'antd';
import type { DataNode } from 'antd/es/tree';
import {
  FileTextOutlined,
  CaretDownOutlined,
  CaretRightOutlined,
} from '@ant-design/icons';
import type { HeadingBlock } from '../../types/editor';
import { useEditorStore } from '../../stores/editorStore';
import { useShallow } from 'zustand/react/shallow';
import './DocumentOutline.css';
import { getHeadingNumberMap } from '../../utils/headingNumbering';

// ══════════════════════════════════════════════════════════════════════════════
// Types
// ══════════════════════════════════════════════════════════════════════════════

interface OutlineNode extends DataNode {
  key: string;
  title: string;
  level: number;
  blockId: string;
  children?: OutlineNode[];
}

// ══════════════════════════════════════════════════════════════════════════════
// Component Props
// ══════════════════════════════════════════════════════════════════════════════

export interface DocumentOutlineProps {
  /** 是否显示大纲 */
  visible?: boolean;
  /** 关闭回调 */
  onClose?: () => void;
}

// ══════════════════════════════════════════════════════════════════════════════
// Helper Functions
// ══════════════════════════════════════════════════════════════════════════════

/**
 * 构建大纲树结构
 */
function buildOutlineTree(headings: HeadingBlock[]): OutlineNode[] {
  const root: OutlineNode[] = [];
  const stack: OutlineNode[] = [];

  headings.forEach((heading) => {
    const content = typeof heading.content === 'string'
      ? heading.content
      : heading.content.map(seg => seg.text).join('');

    const node: OutlineNode = {
      key: heading.id,
      title: content || `标题 ${heading.level}`,
      level: heading.level,
      blockId: heading.id,
      children: [],
    };

    // 找到合适的父节点
    while (stack.length > 0 && stack[stack.length - 1].level >= heading.level) {
      stack.pop();
    }

    if (stack.length === 0) {
      // 顶层节点
      root.push(node);
    } else {
      // 子节点
      const parent = stack[stack.length - 1];
      if (!parent.children) {
        parent.children = [];
      }
      parent.children.push(node);
    }

    stack.push(node);
  });

  return root;
}

function addHeadingNumbers(
  node: OutlineNode,
  numberMap: Map<string, string>,
): OutlineNode {
  return {
    ...node,
    title: `${numberMap.get(node.blockId) || ''} ${node.title}`.trim(),
    children: node.children?.map((child) => addHeadingNumbers(child, numberMap)),
  };
}

// ══════════════════════════════════════════════════════════════════════════════
// Component
// ══════════════════════════════════════════════════════════════════════════════

/**
 * DocumentOutline - 文档大纲
 */
export const DocumentOutline: React.FC<DocumentOutlineProps> = ({
  visible = true,
}) => {
  const headings = useEditorStore(
    useShallow((state) =>
      state.blocks
        .filter((block): block is HeadingBlock => block.type === 'heading')
        .sort((left, right) => left.block_order - right.block_order)
    )
  );
  const selectedBlockId = useEditorStore((state) => state.selectedBlockId);
  const [expandedKeys, setExpandedKeys] = useState<React.Key[]>([]);
  const [autoExpandParent, setAutoExpandParent] = useState(true);

  // 构建树结构
  const treeData = useMemo(() => {
    const numberMap = getHeadingNumberMap(headings);
    return buildOutlineTree(headings).map((node) => addHeadingNumbers(node, numberMap));
  }, [headings]);

  // 获取所有节点的key
  const allKeys = useMemo(() => {
    const keys: string[] = [];
    const traverse = (nodes: OutlineNode[]) => {
      nodes.forEach(node => {
        keys.push(node.key);
        if (node.children) {
          traverse(node.children);
        }
      });
    };
    traverse(treeData);
    return keys;
  }, [treeData]);

  // 处理节点点击
  const handleSelect = useCallback((selectedKeys: React.Key[]) => {
    if (selectedKeys.length === 0) return;

    const blockId = selectedKeys[0] as string;
    const element = document.querySelector(`[data-block-id="${blockId}"]`);
    
    if (element) {
      element.scrollIntoView({ behavior: 'smooth', block: 'center' });
      // 可以添加高亮效果
      element.classList.add('block-highlight');
      setTimeout(() => {
        element.classList.remove('block-highlight');
      }, 2000);
    }
  }, []);

  // 处理展开/折叠
  const handleExpand = useCallback((expandedKeys: React.Key[]) => {
    setExpandedKeys(expandedKeys);
    setAutoExpandParent(false);
  }, []);

  // 全部展开
  const handleExpandAll = useCallback(() => {
    setExpandedKeys(allKeys);
  }, [allKeys]);

  // 全部折叠
  const handleCollapseAll = useCallback(() => {
    setExpandedKeys([]);
  }, []);

  // 自定义标题渲染
  const titleRender = useCallback((node: DataNode) => {
    const outlineNode = node as OutlineNode;
    const levelClass = `outline-title-level-${outlineNode.level}`;
    
    return (
      <span className={`outline-title ${levelClass}`}>
        {outlineNode.title}
      </span>
    );
  }, []);

  if (!visible) return null;

  if (headings.length === 0) {
    return (
      <div className="document-outline empty">
        <div className="outline-header">
          <FileTextOutlined />
          <span>文档大纲</span>
        </div>
        <div className="outline-empty">
          <p>暂无标题</p>
          <p className="outline-hint">添加标题后将显示文档结构</p>
        </div>
      </div>
    );
  }

  return (
    <div className="document-outline">
      {/* 头部 */}
      <div className="outline-header">
        <div className="outline-header-left">
          <FileTextOutlined />
          <span>文档结构图</span>
        </div>
        <div className="outline-header-actions">
          <button
            className="outline-action-btn"
            onClick={handleExpandAll}
            title="全部展开"
          >
            +
          </button>
          <button
            className="outline-action-btn"
            onClick={handleCollapseAll}
            title="全部折叠"
          >
            −
          </button>
        </div>
      </div>

      {/* 树形结构 */}
      <div className="outline-content">
        <Tree
          showLine={false}
          showIcon={false}
          switcherIcon={({ expanded }) =>
            expanded ? <CaretDownOutlined /> : <CaretRightOutlined />
          }
          treeData={treeData}
          selectedKeys={selectedBlockId ? [selectedBlockId] : []}
          expandedKeys={expandedKeys}
          autoExpandParent={autoExpandParent}
          onSelect={handleSelect}
          onExpand={handleExpand}
          titleRender={titleRender}
        />
      </div>
    </div>
  );
};

export default DocumentOutline;
