/********************
 * 流程控制
 * *****************/

#ifndef FLOWCONTROL_H
#define FLOWCONTROL_H

//#include <QObject>
#include "Network/billSocket.h"
#include "Model/orderObject.h"
#include "Model/dishesObject.h"
#include "alertForm.h"
#include <QMap>
#include <JQHttpServer.h>
#include <QMutex>
#include <QDateTime>
#include <QJsonArray>
#include <QTimer>
#include <QPair>
#include <QSemaphore>

class FlowControl : public QObject
{
    Q_OBJECT
public:
    static FlowControl& GetInstance();

private:
    FlowControl();
    FlowControl(FlowControl const&);
    FlowControl& operator=(FlowControl const&);

    typedef struct TOPULL_ORDER
    {
        int pageSize;
        int pageNumber;
        QString channel;
        QString orderId;
    }PullOrderInfo;

    typedef struct ORDER_OPERATION
    {
        int operation;//1:接单,0:取消订单
        int result;//1:成功,0:失败
        QString orderId;

    }OrderOperation;

private:
    // 门店信息
    QString m_storeId;
    QString m_password;
    QString m_posId;
    QString m_cashierId;
    QDateTime m_bDate;
    QString m_storeName;
    int m_orderCount;
    //订单清除定时器
    QTimer *m_clearTimer;
    QTimer *m_heartTimer;
    QTimer *m_pullTimer;
    QTimer *m_loginTimer;
    // 网络通信
    BillSocket *m_loginSocket;
    BillSocket *m_pullOrderSocket;
    BillSocket *m_pullOrderListSocket;
    BillSocket *m_procOrderSocket;
    BillSocket *m_pullDishesSocket;
    // 为Simphony在FM外卖插件中维护<有效待拉取订单>的容器
    QMap<QString, OrderObject*> m_simValidOrderMapQueue;
    // 是否第一次获取到门店信息
    bool m_bFirstRecvInfo;
    bool m_bLoginResult;
    bool m_bOperateResult;
    // HttpServer
    JQHttpServer::TcpServerManage* m_tcpServerManage;

    QMap<QString,  QMultiMap<QString, dishesObject> >m_dishesMap;
    // 入账list
    QStringList m_ordersEntryList;
    //订单号与pos短号映射
    QMap<QString,QString> m_orderIdToPosSalesIdMap;
    //记录当前订单操作
    QMap<QString, int> m_orderOperatePair;
    //订单拉取记录
    QList<PullOrderInfo> m_orderPullList;
    //订单操作互斥信号
    //QSemaphore semaphore;

    QMutex m_OrderEntryMutex;
signals:
    // 发送信号给自己 做登陆
    void doLogin();

    /* 功能:隐藏通知窗口
     * 参数:NULL
     * 返回:NULL
     * */
    void hideAlert();
    /* 功能:显示通知窗口
     * 参数:[1]窗口类型[2]显示信息
     * 返回:NULL
     * */
    void showAlert(AlertForm::Type type, const QString& msg);
    /* 功能:设置主界面门店信息
     * 参数:[1]门店号
     * 返回:NULL
     * */
    void setStoreInfo(const QString& storeId);
    /* 功能:设置主界收银员信息
     * 参数:[1]收银员信息
     * 返回:NULL
     * */
    void setCashierInfo(const QString& cashierInfo);
    /* 功能:设置门店营业状态
     * 参数:[1]营业状态
     * 返回:NULL
     * */
    void setOpeStatus(const QString& status);
    /* 功能:设置门店网络状态
     * 参数:[1]网络状态
     * 返回:NULL
     * */
    void setNetStatus(const QString& status);
    /* 功能:更改订单显示表
     * 参数:[1]订单对象[2]旧订单的状态
     * 返回:NULL
     * */
    void changeOrderStatus(OrderObject* orderObject, int oldStatus=-100);
    /* 功能:显示订单详情界面
     * 参数:[1]收银员信息
     * 返回:NULL
     * */
    void showOrderDetails(OrderObject* orderObject);
    /* 功能:显示订单搜索结果
     * 参数:[1]搜索结果
     * 返回:NULL
     * */
    void showSearchOrderResult(const QMap<QString,QString>& orderMap);

    // 通知菜品管理界面初始化菜品信息
    void iniDishesData(QMap< QString, QMultiMap<QString, dishesObject> >);

    // 通知门店营业管理界面初始化信息
    void initChannelsData(QStringList);


    // 通知菜品管理界面操作成功刷新界面 [1]菜品所属分类 [2]具体菜品
    void processDishiesSuccssful(QString, QMap<QString, int>);

    // 通知营业状态管理界面操作成功
    void setStoreOperatingStatusFinsh(QString);

    /* 功能:通知界面清空订单
     * 参数:[1]订单号[2]订单状态
     * 返回:NULL
     * */
    void clearorder(const QString& orderId,const int& oldstatus);
    /* 功能:通知界面展示日结
     * 参数:[1]日结数据JSON
     * 返回:NULL
     * */
    void showDailyReportData(QJsonObject);

    void doPullOrder(const QString& orderId = QString(),const QString& channel = QString());
    /* 功能:通知开始提醒
     * 参数:[1]提醒类型
     * 返回:NULL
     * */
    void startRemind(int);

    void setStoreStatusChanged(QJsonArray);

    void doConfirmOrder(const QString& orderId);
    void doRefundOrder(const QString& orderId, int reasonCode, const QString &reason);
    void doStartOperateTimer();

private slots:
    bool _GetStoreInfo();
    /* 功能:登录
     * 参数:NULL
     * 返回:是否成功
     * */
    bool _Login();
    /* 功能:拉取订单
     * 参数:[1]订单编号
     * 返回:是否成功
     * */
    void _PullOrder();
    /* 功能:拉取指定订单
     * 参数:[1]订单编号
     * 返回:是否成功
     * */
    bool _PullOrderDetail(const QString &orderId);
    /* 功能:拉取订单
     * 参数:NULL
     * 返回:是否成功
     * */
    bool _PullOrderList(const int &pageSize, const int &pageNo);
    /* 功能:发送心跳
     * 参数:NULL
     * 返回:是否成功
     * */
    bool _SendHeart();
    /* 功能:确认订单
     * 参数:[1]订单编号[2]配送员信息
     * 返回:是否成功
     * */
    bool _ConfirmOrder(const QString& orderId);
    /* 功能:拒绝订单
     * 参数:[1]订单编号[2]拒单原因
     * 返回:是否成功
     * */
    bool _RefuseOrder(const QString& orderId, int refuseCode, const QString reason);
    /* 功能:送出订单
     * 参数:[1]订单编号
     * 返回:是否成功
     * */
    bool _SendOrder(const QString& orderId);
    /* 功能:完成订单
     * 参数:NULL
     * 返回:是否成功
     * */
    bool _CompleteOrder(const QString& orderId);
    /* 功能:拒绝退单
     * 参数:NULL
     * 返回:是否成功
     * */
    bool _RefuseRefund(const QString& orderId);
    /* 功能:退单
     * 参数:NULL
     * 返回:是否成功
     * */
    bool _RefundOrder(const QString& orderId, int reasonCode, const QString &reason);
    /* 功能:获取Json对象的字符
     * 参数:NULL
     * 返回:Json字符串
     * */
    QString _GetJsonStr(const QJsonObject& json);
    /* 功能:获取Http返回Json数据
     * 参数:NULL
     * 返回:Json对象
     * */
    QJsonObject _PackHttpReplyJson(const int status, const QString& msg, const QJsonObject& data, const int &iscontinue);
    /**
    *功能:清空订单Map里的订单
    *参数:无
    *返回:无
    **/
    void _ClearOrder();
    bool _GetReplyJson(const QJsonObject &content, QJsonObject &data,QString &error);
    bool _Get01ReplyJson(const QJsonObject &content, QJsonObject &data,QString &error);
    bool _Get02ReplyJson(const QJsonObject &content, QJsonObject &data,QString &error);
    bool _Get03ReplyJson(const QJsonObject &content, QJsonObject &data,QString &error);
    bool _Get04ReplyJson(const QJsonObject &content, QJsonObject &data,QString &error);
    bool _Get11ReplyJson(const QJsonObject &content, QJsonObject &data,QString &error);
    bool _Get12ReplyJson(const QJsonObject &content, QJsonObject &data,QString &error);
    bool _GetLoginReplyJson(const QJsonObject &content, QString &error);
    bool _GetQueryReplyJson(QJsonObject &data,QString &error, const QString &orderId);

    // 单位转换
    QString _Penny2Dollar(int penny);

    QString _GetIpAddress();
    void _AddOrderPull(const QString& orderId=0,const QString& channel=0,const int& pageNumber=1,const int& pageSize=100);
    void _GetOrder(const QString& orderId,const QString& channel);
    //点击屏幕指定区域
    void _ClickOMSAssignArea();
    void _ClickToLogin();
    void _OrderAnalysis(const QJsonObject &jsonObject);



public slots:
    /* 功能:获取到新的门店信息
     * 参数:[1]操作员ID[2]POS机ID
     *      [3]门店ID[4]营业日
     * 返回:NULL
     * */
    void onGetNewStoreInfo();
    /* 功能:处理订单
     * 参数:[1]操作动作名[2]订单编号[3]配送员姓名
     * 返回:NULL
     * */
    void onProcessOrder(const QString& operation, const QString& orderId);
    /* 功能:获取订单详情
     * 参数:NULL
     * 返回:NULL
     * */
    void onGetOrderDetails(const QString &orderId);
    /* 功能:搜索订单
     * 参数:[1]搜索内容
     * 返回:NULL
     * */
    void onSerachOrder(const QString& text);
    void onProcessRejectOrder(const QString& orderId, const int& reasonCode,const QString &reason);
    void onProcessRepealOrder(const QString& orderId, const int& reasonCode,const QString &reason);

    /* 功能:获取门店营业状态
     * 参数:NULL
     * 返回:NULL
     * */
    void onGetBusinessStatus();
    /* 功能:获取菜品信息
     * 参数:NULL
     * 返回:NULL
     * */
    void onPullDishes();
    /* 功能:获取菜品信息
     * 参数:NULL
     * 返回:NULL
     * */
    void onUpdDishes(QString channelCode, QMap<QString, int> dishes);

    /* 功能:获取菜品信息
     * 参数:NULL
     * 返回:NULL
     * */
    void onUpdDishesForRef(QString channelCode, QMap<QString, int> dishes);
    /* 功能:设置门店营业状态
     * 参数:NULL
     * 返回:NULL
     * */
    void onSetStoreOperatingStatus(const QString& channelCode, const QString& channelName,int business_status);
    /* 功能:向服务端获取日结数据
     * 参数:NULL
     * 返回:NULL
     * */
    void onDailyReport();

};

#endif // FLOWCONTROL_H
