<?php

namespace App\Http\Controllers;

use App\Models\Quotation;
use App\Models\OrderConfirmation;
use App\Models\Inquiry;
use App\Models\Info\Brand;
use App\Models\Info\ItemDescription;
use App\Models\Info\SizeRange;
use App\Models\Info\Color;
use App\Models\Info\FabricComposition;
use App\Models\Info\FabricType;
use App\Models\Info\YarnCount;
use App\Models\Info\FabricWeight;
use App\Models\Info\PortOfLanding;
use App\Models\Info\CountryOfOrigin;
use App\Models\Info\PortOfDischarge;
use App\Models\Info\FinalDestination;
use App\Models\Info\DeliveryTerm;
use App\Models\Info\ShipmentMode;
use Illuminate\Http\Request;
use App\Models\Buyer;
use App\Models\GarmentAddon;
use App\Models\FabricAddon;
use App\Models\DyeingType;
use App\Models\KnittingType;
use App\Models\YarnType;
use App\Models\Accessory;
use App\Models\OtherCost;
use App\Models\CommercialRate;
use App\Models\Cost;
use Illuminate\Support\Facades\Validator;

class QuotationController extends Controller
{
    public function index(Request $request)
    {
        $query = Quotation::with('inquiry.itemDescription', 'inquiry.buyer');

        // Filter by status
        if ($request->filled('status')) {
            $query->where('status', $request->status);
        }

        // Search functionality
        if ($request->filled('search')) {
            $search = $request->search;
            $query->where(function($q) use ($search) {
                $q->where('quotation_number', 'like', "%{$search}%")
                  ->orWhereHas('inquiry', function($iq) use ($search) {
                      $iq->whereHas('buyer', function($bq) use ($search) {
                          $bq->where('company_name', 'like', "%{$search}%");
                      });
                  });
            });
        }

        $quotations = $query->latest()->paginate(10);

        // Get status counts for dashboard
        $statusCounts = [
            'pending' => Quotation::where('status', 'pending')->count(),
            'won' => Quotation::where('status', 'won')->count(),
            'lost' => Quotation::where('status', 'lost')->count(),
            'draft' => Quotation::where('status', 'draft')->count(),
            'submitted' => Quotation::where('status', 'submitted')->count(),
        ];

        return view('admin.quotation.index', compact('quotations', 'statusCounts'));
    }

    public function create(Request $request)
    {
        $inquiry_id = $request->query('inquiry_id');
        if (!$inquiry_id) {
            return redirect()->route('admin.inquiries.index')->with('error', 'Inquiry ID is required to create a quotation.');
        }

        $inquiry = Inquiry::with([
            'itemDescription', 'brand', 'sizeRange', 'color',
            'fabricComposition', 'fabricType', 'yarnCount', 'fabricWeight',
            'portOfLanding', 'countryOfOrigin', 'portOfDischarge', 'finalDestination',
            'deliveryTerm', 'shipmentMode', 'buyer'
        ])->find($inquiry_id);

        if (!$inquiry) {
            return redirect()->route('admin.inquiries.index')->with('error', 'Inquiry not found.');
        }

        $garments = GarmentAddon::all(); 
        $fabric = FabricAddon::all(); 
        $yarn = YarnType::all();  
        $knitting = KnittingType::all(); 
        $dyeing = DyeingType::all(); 
        $accessories = Accessory::all(); 
        $other = OtherCost::all(); 
        $commercial = CommercialRate::all(); 
        $cost = Cost::all();

        return view('admin.quotation.create', compact('inquiry','garments','fabric','yarn','knitting','dyeing','accessories','other', 'commercial','cost'));
    }

    public function store(Request $request)
    {
        $validatedData = $request->validate([
            'inquiry_id' => 'required|exists:inquiries,id',
            'costing_details' => 'required|json',
            'calculated_total_fabric_consumption' => 'required|numeric|min:0',
            'calculated_total_fabric_cost' => 'required|numeric|min:0',
            'calculated_accessories_cost' => 'required|numeric|min:0',
            'calculated_additional_costs_total' => 'required|numeric|min:0',
            'calculated_total_cost' => 'required|numeric|min:0',
            'quoted_price' => 'required|numeric|min:0',
            'remarks' => 'nullable|string',
            'status' => 'sometimes|string|in:draft,submitted,approved,rejected,pending,won,lost',
        ]);

        $lastQuotation = Quotation::latest('id')->first();
        $nextNumber = $lastQuotation ? $lastQuotation->id + 1 : 1;
        $validatedData['quotation_number'] = 'Q-' . str_pad($nextNumber, 5, '0', STR_PAD_LEFT);

        // Set default status if not provided
        if (!isset($validatedData['status'])) {
            $validatedData['status'] = 'draft';
        }

        Quotation::create($validatedData);

        return redirect()->route('admin.quotations.index')->with('success', 'Quotation created successfully.');
    }

    public function show(Quotation $quotation)
    {
        $quotation->load([
            'inquiry.itemDescription', 
            'inquiry.brand', 
            'inquiry.buyer',
            'orderConfirmation',
            'statusUpdatedBy'
        ]);
        
        return view('admin.quotation.show', compact('quotation'));
    }

    public function edit(Quotation $quotation)
    {
        $quotation->load('inquiry');
        $inquiry = $quotation->inquiry;

        if (!$inquiry) {
            return redirect()->route('admin.quotations.index')->with('error', 'Associated Inquiry not found.');
        }

        $inquiry->load([
            'itemDescription', 'brand', 'sizeRange', 'color',
            'fabricComposition', 'fabricType', 'yarnCount', 'fabricWeight',
            'portOfLanding', 'countryOfOrigin', 'portOfDischarge', 'finalDestination',
            'deliveryTerm', 'shipmentMode'
        ]);

        return view('admin.quotation.edit', compact('quotation', 'inquiry'));
    }

    public function update(Request $request, Quotation $quotation)
    {
        $validatedData = $request->validate([
            'costing_details' => 'required|json',
            'calculated_total_fabric_consumption' => 'required|numeric|min:0',
            'calculated_total_fabric_cost' => 'required|numeric|min:0',
            'calculated_accessories_cost' => 'required|numeric|min:0',
            'calculated_additional_costs_total' => 'required|numeric|min:0',
            'calculated_total_cost' => 'required|numeric|min:0',
            'quoted_price' => 'required|numeric|min:0',
            'remarks' => 'nullable|string',
            'status' => 'sometimes|string|in:draft,submitted,approved,rejected,pending,won,lost',
        ]);

        $quotation->update($validatedData);

        return redirect()->route('admin.quotations.index')->with('success', 'Quotation updated successfully.');
    }

    public function destroy(Quotation $quotation)
    {
        // Check if quotation has an associated order
        if ($quotation->orderConfirmation) {
            return redirect()->back()->with('error', 'Cannot delete quotation with associated order confirmation.');
        }

        $quotation->delete();
        return redirect()->route('admin.quotations.index')->with('success', 'Quotation deleted successfully.');
    }

    /**
     * Update quotation status with notes
     */
    public function updateStatus(Request $request, Quotation $quotation)
    {
        $validator = Validator::make($request->all(), [
            'status' => 'required|in:draft,submitted,approved,rejected,pending,won,lost',
            'notes' => 'nullable|string|max:1000',
        ]);

        if ($validator->fails()) {
            if ($request->expectsJson()) {
                return response()->json(['errors' => $validator->errors()], 422);
            }
            return redirect()->back()->withErrors($validator)->withInput();
        }

        $quotation->updateStatus($request->status, $request->notes);

        $message = "Quotation status updated to " . ucfirst($request->status) . " successfully.";

        if ($request->expectsJson()) {
            return response()->json([
                'success' => true,
                'message' => $message,
                'status' => $quotation->status,
                'status_label' => $quotation->status_label,
                'status_badge_color' => $quotation->status_badge_color,
                'can_convert_to_order' => $quotation->can_convert_to_order,
            ]);
        }

        return redirect()->back()->with('success', $message);
    }

    /**
     * Convert won quotation to order confirmation
     */
    public function convertToOrder(Request $request, Quotation $quotation)
    {
        if (!$quotation->can_convert_to_order) {
            $message = 'This quotation cannot be converted to an order.';
            if ($request->expectsJson()) {
                return response()->json(['error' => $message], 400);
            }
            return redirect()->back()->with('error', $message);
        }

        try {
            $orderData = [];
            
            // If additional data is provided in request
            if ($request->filled('customer_po_number')) {
                $orderData['customer_po_number'] = $request->customer_po_number;
            }
            if ($request->filled('delivery_date')) {
                $orderData['delivery_date'] = $request->delivery_date;
            }
            if ($request->filled('payment_terms')) {
                $orderData['payment_terms'] = $request->payment_terms;
            }
            if ($request->filled('special_instructions')) {
                $orderData['special_instructions'] = $request->special_instructions;
            }

            $orderConfirmation = $quotation->convertToOrder($orderData);

            $message = 'Quotation converted to order confirmation successfully.';
            
            if ($request->expectsJson()) {
                return response()->json([
                    'success' => true,
                    'message' => $message,
                    'order_id' => $orderConfirmation->id,
                    'order_number' => $orderConfirmation->order_number,
                    'redirect_url' => route('admin.order-confirmations.show', $orderConfirmation),
                ]);
            }

            return redirect()->route('admin.order-confirmations.show', $orderConfirmation)
                           ->with('success', $message);

        } catch (\Exception $e) {
            $message = 'Error converting quotation to order: ' . $e->getMessage();
            
            if ($request->expectsJson()) {
                return response()->json(['error' => $message], 500);
            }
            
            return redirect()->back()->with('error', $message);
        }
    }

    /**
     * Show form to convert quotation to order
     */
    public function showConvertToOrderForm(Quotation $quotation)
    {
        if (!$quotation->can_convert_to_order) {
            return redirect()->back()->with('error', 'This quotation cannot be converted to an order.');
        }

        $quotation->load(['inquiry.itemDescription', 'inquiry.buyer']);

        return view('admin.quotation.convert_to_order', compact('quotation'));
    }

    /**
     * Get quotations by status for dashboard
     */
    public function getByStatus($status)
    {
        $quotations = Quotation::with(['inquiry.itemDescription', 'inquiry.buyer'])
                              ->where('status', $status)
                              ->latest()
                              ->paginate(10);

        $statusCounts = [
            'pending' => Quotation::where('status', 'pending')->count(),
            'won' => Quotation::where('status', 'won')->count(),
            'lost' => Quotation::where('status', 'lost')->count(),
        ];

        return view('admin.quotation.index', compact('quotations', 'statusCounts'))
               ->with('currentStatus', $status);
    }

    /**
     * Bulk update quotation status
     */
    public function bulkUpdateStatus(Request $request)
    {
        $validator = Validator::make($request->all(), [
            'quotation_ids' => 'required|array',
            'quotation_ids.*' => 'exists:quotations,id',
            'status' => 'required|in:pending,won,lost',
            'notes' => 'nullable|string|max:1000',
        ]);

        if ($validator->fails()) {
            return redirect()->back()->withErrors($validator);
        }

        $updated = 0;
        foreach ($request->quotation_ids as $quotationId) {
            $quotation = Quotation::find($quotationId);
            if ($quotation) {
                $quotation->updateStatus($request->status, $request->notes);
                $updated++;
            }
        }

        return redirect()->back()->with('success', "Successfully updated {$updated} quotation(s) to " . ucfirst($request->status) . ".");
    }
}

