import React, { createContext, useContext } from "react";
import { Hotspot } from "../../types/annotations";
import {
    ClickEvent,
    SessionMetadata,
    SessionStep,
    SessionStepRecord,
    TimelineMarker,
    Transcript,
} from "../../lib/api";

export type MediaTab = "video" | "terminal" | "both";
export type ExportKind = "markdown" | "mp4";
export type EditorMode = "edit" | "preview";

export interface ExportFeedback {
    status: "success" | "error";
    kind: ExportKind;
    path: string | null;
    message: string;
}

export interface AutoStepsFeedback {
    status: "success" | "error";
    message: string;
}

interface EditorContextType {
    sessionId: string | undefined;
    metadata: SessionMetadata | null;
    videoUrl: string | null;
    terminalUrl: string | null;
    playing: boolean;
    setPlaying: (playing: boolean) => void;
    activeTab: MediaTab;
    setActiveTab: (tab: MediaTab) => void;
    hasTerminal: boolean;
    fps: number;
    markers: TimelineMarker[];
    allHotspots: Hotspot[];
    hotspots: Hotspot[];
    selectedHotspotId: string | null;
    setSelectedHotspotId: (id: string | null) => void;
    editingHotspots: boolean;
    setEditingHotspots: React.Dispatch<React.SetStateAction<boolean>>;
    placingHotspot: boolean;
    setPlacingHotspot: React.Dispatch<React.SetStateAction<boolean>>;
    placingHotspotStyle: Hotspot["style"];
    setPlacingHotspotStyle: React.Dispatch<React.SetStateAction<Hotspot["style"]>>;
    walkthroughMode: boolean;
    setWalkthroughMode: (mode: boolean) => void;
    walkthroughSteps: SessionStep[];
    walkthroughLoading: boolean;
    exporting: boolean;
    lastExportPath: string | null;
    exportFeedback: ExportFeedback | null;
    autoStepsFeedback: AutoStepsFeedback | null;
    isProcessing: boolean;
    isAnalyzing: boolean;
    transcript: Transcript | null;
    transcribing: boolean;
    transcriptError: string | null;
    steps: SessionStepRecord[];
    selectedStepId: string | null;
    selectedStep: SessionStepRecord | null;

    // Actions
    togglePlay: () => void;
    undo: () => void;
    redo: () => void;
    canUndo: boolean;
    canRedo: boolean;
    startWalkthrough: () => Promise<void>;
    handleAnalyzeSession: () => Promise<void>;
    handleGenerateStepsFromActivity: () => void;
    handleMarkStep: () => Promise<void>;
    handleTranscribe: () => Promise<void>;
    handleExportMarkdown: () => Promise<void>;
    handleExportMp4: (includeChapterCards: boolean) => Promise<void>;
    clearExportFeedback: () => void;
    clearAutoStepsFeedback: () => void;
    handleVideoLoadError: () => void | Promise<void>;
    handleStageClick: (position: { x: number; y: number }) => void;
    handleAddHotspot: (hotspot: Hotspot, stepId?: string | null) => void;
    handleUpdateHotspot: (id: string, updater: (hotspot: Hotspot) => Hotspot) => void;
    handleDeleteHotspot: (id: string) => void;
    handleSelectStep: (stepId: string) => void;
    handleRenameStep: (stepId: string, title: string) => void;
    updateStepConfig: (
        stepId: string,
        updater: (step: SessionStepRecord) => SessionStepRecord
    ) => void;
    moveStepUp: (stepId: string) => void;
    moveStepDown: (stepId: string) => void;
    duplicateStep: (stepId: string) => void;
    deleteStep: (stepId: string) => void;
    splitSelectedStepAtCurrentFrame: () => void;
    mergeSelectedStepWithNext: () => void;
    applyHotspotStylePreset: (
        scope: "step" | "session",
        target: "hotspot" | "callout",
        patch: { backgroundColor?: string; textColor?: string }
    ) => void;

    // Video Hooks State
    currentFrame: number;
    currentTime: number;
    duration: number;
    totalFrames: number;
    seekToFrame: (frame: number) => void;
    seekToTimestamp: (time: number) => void;
    stepFrames: (frames: number) => void;

    // UI state
    editorMode: EditorMode;
    setEditorMode: (mode: EditorMode) => void;
    setSharing: (sharing: boolean) => void;

    // Click highlights
    clicks: ClickEvent[];
    showClickRipples: boolean;
    setShowClickRipples: (show: boolean) => void;
}

const EditorContext = createContext<EditorContextType | undefined>(undefined);

export const EditorProvider: React.FC<{ value: EditorContextType; children: React.ReactNode }> = ({
    value,
    children,
}) => {
    return <EditorContext.Provider value={value}>{children}</EditorContext.Provider>;
};

export const useEditor = () => {
    const context = useContext(EditorContext);
    if (!context) {
        throw new Error("useEditor must be used within an EditorProvider");
    }
    return context;
};
