/**
 * CAN 通信完整使用示例
 * 包括：基础通信、AGV 运动控制、数据监控等场景
 */

#include <iostream>
#include <thread>
#include <chrono>
#include <iomanip>
#include "can/CANController.h"

using namespace std;

// AGV CAN 协议定义
namespace AGV_Protocol {
    // CAN ID 定义
    const UINT ID_MOTOR_CONTROL = 0x200;      // 电机控制指令
    const UINT ID_MOTOR_FEEDBACK = 0x201;     // 电机反馈
    const UINT ID_AGV_STATUS = 0x300;         // AGV 状态
    const UINT ID_SENSOR_DATA = 0x400;        // 传感器数据

    // 命令类型
    const BYTE CMD_VELOCITY = 0x10;           // 速度控制
    const BYTE CMD_POSITION = 0x20;           // 位置控制
    const BYTE CMD_STOP = 0x30;               // 停止
    const BYTE CMD_RESET = 0x40;              // 复位
}

/**
 * 打印 CAN 帧信息
 */
void PrintCANFrame(const VCI_CAN_OBJ& frame) {
    cout << "[接收] ID=0x" << hex << setw(3) << setfill('0') << frame.ID << dec;
    cout << " (" << (frame.ExternFlag ? "扩展帧" : "标准帧");
    cout << (frame.RemoteFlag ? ", 远程帧" : ", 数据帧") << ")";
    cout << " 长度=" << (int)frame.DataLen << " 数据=[";

    for (int i = 0; i < frame.DataLen; i++) {
        cout << hex << setw(2) << setfill('0') << (int)frame.Data[i];
        if (i < frame.DataLen - 1) cout << " ";
    }
    cout << "]" << dec << endl;
}

/**
 * 示例1：基本 CAN 通信测试
 */
void Example1_BasicCommunication() {
    cout << "\n========== 示例1：基本 CAN 通信测试 ==========" << endl;

    CANController can;

    // 初始化（波特率 500Kbps）
    if (!can.Initialize(0x00, 0x1C, 0)) {
        return;
    }

    // 读取设备信息
    VCI_BOARD_INFO info;
    if (can.GetDeviceInfo(info)) {
        cout << "\n设备信息：" << endl;
        cout << "  硬件版本: 0x" << hex << info.hw_Version << dec << endl;
        cout << "  固件版本: 0x" << hex << info.fw_Version << dec << endl;
        cout << "  CAN 通道数: " << (int)info.can_Num << endl;
        cout << "  序列号: " << info.str_Serial_Num << endl;
    }

    // 发送测试数据
    cout << "\n发送测试数据..." << endl;
    BYTE test_data[] = {0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88};
    if (can.SendStandardFrame(0x123, test_data, 8)) {
        cout << "发送成功：ID=0x123, 数据=[11 22 33 44 55 66 77 88]" << endl;
    }

    // 接收数据（持续3秒）
    cout << "\n开始接收数据（3秒）..." << endl;
    auto start = chrono::steady_clock::now();
    int total_received = 0;

    while (true) {
        auto now = chrono::steady_clock::now();
        auto elapsed = chrono::duration_cast<chrono::seconds>(now - start).count();
        if (elapsed >= 3) break;

        vector<VCI_CAN_OBJ> frames;
        DWORD count = can.Receive(frames, 100);

        if (count > 0) {
            for (const auto& frame : frames) {
                PrintCANFrame(frame);
                total_received++;
            }
        }

        this_thread::sleep_for(chrono::milliseconds(10));
    }

    cout << "接收完成，共接收 " << total_received << " 帧数据" << endl;
}

/**
 * 示例2：AGV 速度控制
 */
void Example2_AGVVelocityControl() {
    cout << "\n========== 示例2：AGV 速度控制 ==========" << endl;

    CANController can;

    // 初始化（波特率 250Kbps）
    if (!can.Initialize(0x01, 0x1C, 0)) {
        return;
    }

    // 设置接收回调（处理电机反馈）
    can.SetReceiveCallback([](const VCI_CAN_OBJ& frame) {
        if (frame.ID == AGV_Protocol::ID_MOTOR_FEEDBACK) {
            // 解析电机反馈数据
            int16_t speed = (frame.Data[0] << 8) | frame.Data[1];
            int16_t current = (frame.Data[2] << 8) | frame.Data[3];
            cout << "  [反馈] 速度=" << speed << " RPM, 电流=" << current << " mA" << endl;
        }
    });

    // AGV 速度控制函数
    auto sendVelocityCommand = [&can](int16_t left_speed, int16_t right_speed) {
        BYTE data[8] = {0};
        data[0] = AGV_Protocol::CMD_VELOCITY;  // 命令类型
        data[1] = 0x00;                         // 保留
        data[2] = (left_speed >> 8) & 0xFF;     // 左轮速度高字节
        data[3] = left_speed & 0xFF;            // 左轮速度低字节
        data[4] = (right_speed >> 8) & 0xFF;    // 右轮速度高字节
        data[5] = right_speed & 0xFF;           // 右轮速度低字节
        data[6] = 0x00;                         // 保留
        data[7] = 0x00;                         // 校验和（简化）

        return can.SendStandardFrame(AGV_Protocol::ID_MOTOR_CONTROL, data, 8);
    };

    // 场景1：直行
    cout << "\n场景1：AGV 直行（速度 100 RPM）" << endl;
    if (sendVelocityCommand(100, 100)) {
        cout << "发送成功：左轮=100, 右轮=100" << endl;
    }
    this_thread::sleep_for(chrono::seconds(2));

    // 场景2：左转
    cout << "\n场景2：AGV 左转" << endl;
    if (sendVelocityCommand(50, 100)) {
        cout << "发送成功：左轮=50, 右轮=100" << endl;
    }
    this_thread::sleep_for(chrono::seconds(2));

    // 场景3：右转
    cout << "\n场景3：AGV 右转" << endl;
    if (sendVelocityCommand(100, 50)) {
        cout << "发送成功：左轮=100, 右轮=50" << endl;
    }
    this_thread::sleep_for(chrono::seconds(2));

    // 场景4：停止
    cout << "\n场景4：AGV 停止" << endl;
    BYTE stop_data[] = {AGV_Protocol::CMD_STOP, 0, 0, 0, 0, 0, 0, 0};
    if (can.SendStandardFrame(AGV_Protocol::ID_MOTOR_CONTROL, stop_data, 8)) {
        cout << "发送停止命令" << endl;
    }

    // 接收反馈数据
    cout << "\n接收反馈数据..." << endl;
    for (int i = 0; i < 10; i++) {
        vector<VCI_CAN_OBJ> frames;
        can.Receive(frames, 100);
        this_thread::sleep_for(chrono::milliseconds(100));
    }
}

/**
 * 示例3：CAN 数据监控
 */
void Example3_CANMonitor() {
    cout << "\n========== 示例3：CAN 总线监控 ==========" << endl;

    CANController can;

    // 初始化为只听模式（不影响总线）
    if (!can.Initialize(0x00, 0x1C, 1)) {  // mode=1 只听模式
        return;
    }

    cout << "开始监控 CAN 总线（10秒）..." << endl;
    cout << "提示：只听模式，不会影响总线通信" << endl;

    // 统计信息
    map<UINT, int> id_count;  // 每个 ID 的帧数统计
    int total_frames = 0;

    auto start = chrono::steady_clock::now();

    while (true) {
        auto now = chrono::steady_clock::now();
        auto elapsed = chrono::duration_cast<chrono::seconds>(now - start).count();
        if (elapsed >= 10) break;

        vector<VCI_CAN_OBJ> frames;
        DWORD count = can.Receive(frames, 100);

        if (count > 0) {
            for (const auto& frame : frames) {
                PrintCANFrame(frame);
                id_count[frame.ID]++;
                total_frames++;
            }
        }

        this_thread::sleep_for(chrono::milliseconds(50));
    }

    // 显示统计信息
    cout << "\n========== 统计信息 ==========" << endl;
    cout << "总帧数: " << total_frames << endl;
    cout << "不同 ID 数量: " << id_count.size() << endl;
    cout << "\nID 分布：" << endl;
    for (const auto& pair : id_count) {
        cout << "  ID 0x" << hex << setw(3) << setfill('0') << pair.first
             << dec << ": " << pair.second << " 帧" << endl;
    }
}

/**
 * 示例4：周期性发送和接收
 */
void Example4_PeriodicTransmit() {
    cout << "\n========== 示例4：周期性发送和接收 ==========" << endl;

    CANController can;

    if (!can.Initialize(0x00, 0x1C, 0)) {
        return;
    }

    cout << "开始周期性通信（10秒）..." << endl;

    bool running = true;

    // 发送线程：每100ms发送一次心跳
    thread send_thread([&can, &running]() {
        int counter = 0;
        while (running) {
            BYTE data[8] = {0};
            data[0] = 0xAA;  // 心跳标识
            data[1] = (counter >> 8) & 0xFF;
            data[2] = counter & 0xFF;
            data[3] = 0x55;

            can.SendStandardFrame(0x100, data, 4);
            counter++;

            this_thread::sleep_for(chrono::milliseconds(100));
        }
    });

    // 接收线程
    thread recv_thread([&can, &running]() {
        while (running) {
            vector<VCI_CAN_OBJ> frames;
            DWORD count = can.Receive(frames, 100);

            if (count > 0) {
                for (const auto& frame : frames) {
                    PrintCANFrame(frame);
                }
            }

            this_thread::sleep_for(chrono::milliseconds(10));
        }
    });

    // 运行10秒
    this_thread::sleep_for(chrono::seconds(10));
    running = false;

    send_thread.join();
    recv_thread.join();

    cout << "周期性通信结束" << endl;
}

/**
 * 主程序
 */
int main() {
    cout << "================================================" << endl;
    cout << "       CAN 通信完整示例程序" << endl;
    cout << "================================================" << endl;

    int choice = 0;
    cout << "\n请选择示例：" << endl;
    cout << "1. 基本 CAN 通信测试" << endl;
    cout << "2. AGV 速度控制" << endl;
    cout << "3. CAN 总线监控（只听模式）" << endl;
    cout << "4. 周期性发送和接收" << endl;
    cout << "0. 运行所有示例" << endl;
    cout << "\n请输入选择 (0-4): ";
    cin >> choice;

    switch (choice) {
        case 1:
            Example1_BasicCommunication();
            break;
        case 2:
            Example2_AGVVelocityControl();
            break;
        case 3:
            Example3_CANMonitor();
            break;
        case 4:
            Example4_PeriodicTransmit();
            break;
        case 0:
            Example1_BasicCommunication();
            Example2_AGVVelocityControl();
            Example3_CANMonitor();
            Example4_PeriodicTransmit();
            break;
        default:
            cout << "无效选择！" << endl;
    }

    cout << "\n程序执行完成！" << endl;
    return 0;
}
