import SwiftUI
import UniformTypeIdentifiers

public struct DropZoneView: View {
    @State private var isDragging = false
    @State private var uploadResult: UploadResult?
    @State private var error: String?
    @State private var isUploading = false
    @State private var uploadProgress: Double = 0
    
    public let uploadManager: UploadManager
    
    public init(uploadManager: UploadManager) {
        self.uploadManager = uploadManager
    }
    
    public var body: some View {
        VStack(spacing: 20) {
            Image(systemName: "arrow.up.doc.fill")
                .font(.system(size: 48))
                .foregroundColor(isDragging ? .blue : .secondary)
            
            Text("Drop files here")
                .font(.title2)
            
            if isUploading {
                ProgressView(value: uploadProgress)
                    .frame(width: 180)
                Text("\(Int(uploadProgress * 100))%")
                    .font(.caption)
                    .foregroundColor(.secondary)
            } else if let result = uploadResult {
                VStack(spacing: 8) {
                    Image(systemName: "checkmark.circle.fill")
                        .font(.system(size: 32))
                        .foregroundColor(.green)
                    
                    Text("Uploaded \(result.filename)")
                        .font(.headline)
                    
                    Text("URL copied to clipboard")
                        .font(.caption)
                        .foregroundColor(.secondary)
                    
                    Text(result.url.absoluteString)
                        .font(.caption2)
                        .foregroundColor(.blue)
                        .lineLimit(1)
                        .truncationMode(.middle)
                        .padding(.horizontal)
                }
            } else if let error = error {
                VStack(spacing: 8) {
                    Image(systemName: "xmark.circle.fill")
                        .font(.system(size: 32))
                        .foregroundColor(.red)
                    
                    Text("Upload failed")
                        .font(.headline)
                    
                    Text(error)
                        .font(.caption)
                        .foregroundColor(.secondary)
                }
            }
        }
        .frame(width: 300, height: 250)
        .background(
            RoundedRectangle(cornerRadius: 12)
                .fill(isDragging ? Color.blue.opacity(0.1) : Color.secondary.opacity(0.1))
                .overlay(
                    RoundedRectangle(cornerRadius: 12)
                        .strokeBorder(isDragging ? Color.blue : Color.secondary.opacity(0.3), style: StrokeStyle(lineWidth: 2, dash: [8]))
                )
        )
        .onDrop(of: [.fileURL], isTargeted: $isDragging) { providers in
            guard let provider = providers.first else { return false }
            
            _ = provider.loadObject(ofClass: URL.self) { url, error in
                guard let url = url else { return }
                
                Task {
                    await MainActor.run {
                        isUploading = true
                        uploadProgress = 0
                        self.error = nil
                        self.uploadResult = nil
                    }
                    
                    do {
                        let result = try await uploadFileResolvingDuplicates(url, onProgress: { progress in
                            Task { @MainActor in
                                uploadProgress = min(max(progress, 0), 1)
                            }
                        })
                        await MainActor.run {
                            uploadResult = result
                            isUploading = false
                            uploadProgress = 0
                        }
                    } catch {
                        await MainActor.run {
                            self.error = error.localizedDescription
                            isUploading = false
                            uploadProgress = 0
                        }
                    }
                }
            }
            
            return true
        }
    }

    private func uploadFileResolvingDuplicates(
        _ url: URL,
        onProgress: UploadProgressHandler?
    ) async throws -> UploadResult {
        var duplicateAction: UploadDuplicateAction?

        while true {
            do {
                return try await uploadManager.uploadFile(
                    url,
                    duplicateAction: duplicateAction,
                    onProgress: onProgress
                )
            } catch let error as APIError where error.isUploadConflict {
                guard let action = promptForUploadDuplicate(error, filename: url.lastPathComponent) else {
                    throw UploadCancelledError()
                }
                duplicateAction = action
            }
        }
    }
}

#Preview {
    // This preview won't work without a real UploadManager
    Text("DropZoneView Preview")
}
