package com.gingersoft.gsa.cloud.table.mvp.presenter;

import android.app.Activity;
import android.app.Application;
import android.widget.TextView;

import com.billy.cc.core.component.CC;
import com.gingersoft.gsa.cloud.base.application.GsaCloudApplication;
import com.gingersoft.gsa.cloud.base.common.bean.BaseResult;
import com.gingersoft.gsa.cloud.base.common.bean.OrderBean;
import com.gingersoft.gsa.cloud.base.common.bean.OrderDetail;
import com.gingersoft.gsa.cloud.base.common.bean.mealManage.MyOrderManage;
import com.gingersoft.gsa.cloud.base.common.bean.mealManage.OpenTableManage;
import com.gingersoft.gsa.cloud.table.R;
import com.gingersoft.gsa.cloud.table.mvp.contract.BaseOrderContract;
import com.gingersoft.gsa.cloud.table.mvp.model.bean.BillOrderMoney;
import com.gingersoft.gsa.cloud.table.mvp.model.bean.request.AddOrderRequest;
import com.gingersoft.gsa.cloud.table.mvp.model.bean.request.CreateOrderRequest;
import com.gingersoft.gsa.cloud.table.mvp.ui.activity.OrderContentActivity;
import com.gingersoft.gsa.cloud.table.mvp.ui.adapter.OrderMoneyAdapter;
import com.gingersoft.gsa.cloud.table.mvp.ui.adapter.meal.SelectMealAdapter;
import com.jess.arms.di.scope.ActivityScope;
import com.jess.arms.http.imageloader.ImageLoader;
import com.jess.arms.integration.AppManager;
import com.jess.arms.mvp.BasePresenter;
import com.jess.arms.utils.RxLifecycleUtils;
import com.qmuiteam.qmui.widget.dialog.QMUIDialog;
import com.qmuiteam.qmui.widget.dialog.QMUIDialogAction;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.inject.Inject;

import io.reactivex.android.schedulers.AndroidSchedulers;
import io.reactivex.schedulers.Schedulers;
import me.jessyan.rxerrorhandler.core.RxErrorHandler;
import me.jessyan.rxerrorhandler.handler.ErrorHandleSubscriber;
import okhttp3.FormBody;
import okhttp3.RequestBody;

/**
 * 作者：ELEGANT_BIN
 * 版本：1.6.0
 * 创建日期：2020-01-11
 * 修订历史：2020-01-11
 * 描述：
 */

@ActivityScope
public class BaseOrderPresenter<M extends BaseOrderContract.Model, V extends BaseOrderContract.View> extends BasePresenter<BaseOrderContract.Model, BaseOrderContract.View> {

    @Inject
    RxErrorHandler mErrorHandler;
    @Inject
    Application mApplication;
    @Inject
    ImageLoader mImageLoader;
    @Inject
    AppManager mAppManager;

    protected M mModel;
    protected V mRootView;

    private Activity IActivity;
    private OrderContentActivity mOrderContentActivity;
    private MealStandPresenter mMealStandPresenter;
    private OrderContentPresenter mOrderContentPresenter;
    private OrderPayPresenter mOrderPayPresenter;

    //订单数据管理类
    protected MyOrderManage myOrderManage;

    //訂單食品適配器
    protected SelectMealAdapter mSelectMealAdapter;
    protected List<OrderDetail> orderFoodList;

    //整單相關金額適配器
    protected OrderMoneyAdapter mOrderMoneyAdapter;
    protected List<BillOrderMoney> mOrderMoneyList = new ArrayList<>();

    //選中操作的食品下標
    protected int orderSelectPosition = -1;

    //食品數量
    protected int foodCount;
    //總金額
    protected double totalMoney;
    //币種
    public String cashStr = "$";

    private final String noFoodDeliveryTip = "賬單沒有食品，是否開台?";

    @Inject
    public BaseOrderPresenter(BaseOrderContract.Model model, BaseOrderContract.View rootView) {
        super(model, rootView);
        this.mModel = (M) model;
        this.mRootView = (V) rootView;
        this.IActivity = (Activity) mRootView;
        this.myOrderManage = MyOrderManage.getInstance();
        this.orderFoodList = myOrderManage.getOrderFoodList();

        if (IActivity instanceof OrderContentActivity) {
            mOrderContentActivity = (OrderContentActivity) IActivity;
        }
        if (this instanceof MealStandPresenter) {
            mMealStandPresenter = (MealStandPresenter) this;
        } else if (this instanceof OrderContentPresenter) {
            mOrderContentPresenter = (OrderContentPresenter) this;
        } else if (this instanceof OrderPayPresenter) {
            mOrderPayPresenter = (OrderPayPresenter) this;
        }

        recalcOrderMoneyCount();
        resetSelected();
        initOrderAdapter();
    }

    private void recalcOrderMoneyCount() {
        foodCount = initFoodCount();
        totalMoney = initFoodTotalMoney();
    }

    @Override
    public void onDestroy() {
        super.onDestroy();
        this.mErrorHandler = null;
        this.mAppManager = null;
        this.mImageLoader = null;
        this.mApplication = null;
    }

    private void initOrderAdapter() {
        if (mSelectMealAdapter == null) {
            mSelectMealAdapter = new SelectMealAdapter(IActivity, orderFoodList, this);
            //設置子父級下標
            mSelectMealAdapter.setIndex();
        }
        if (mOrderMoneyAdapter == null) {
            mOrderMoneyAdapter = new OrderMoneyAdapter(IActivity, mOrderMoneyList, cashStr);
        }
        initItemClickListener();
    }

    private void initItemClickListener() {
        mSelectMealAdapter.setOnItemClickListener(new SelectMealAdapter.OnItemClickListener() {

            @Override
            public void onItemClick(OrderDetail datasBean, int position) {
                orderSelectPosition = position;
                mSelectMealAdapter.setMyOrderManageSelectPosition();
            }

            @Override
            public void onMealCountDelete(OrderDetail datasBean, int position) {
                if (datasBean.getNumber() == 1) {
                    mSelectMealAdapter.removeFoodItem();
                } else {
                    changeNumber(datasBean.getNumber() - 1);
                }
                mSelectMealAdapter.notifyDataSetChanged();
                recalcOrderMoneyCount();
                if (mOrderContentActivity != null) {
                    mOrderContentActivity.initOrderDetail();
                }
            }

            @Override
            public void onMealCountAdd(OrderDetail datasBean, int position) {
                changeNumber(datasBean.getNumber() + 1);
                recalcOrderMoneyCount();
                if (mOrderContentActivity != null) {
                    mOrderContentActivity.initOrderDetail();
                }
            }

            @Override
            public void onCurrentOrderDetail(OrderDetail datasBean, int position) {
            }
        });
    }

    /**
     * 修改訂單
     *
     * @param //orderId 訂單號
     * @param //person  人數
     */
    public void updateOrderPerson(String peopleNumber, TextView textView) {
        RequestBody requestBody = new FormBody.Builder()
                .add("orderId", String.valueOf(MyOrderManage.getInstance().getOrderId()))
                .add("person", String.valueOf(peopleNumber))
                .build();
        mModel.updateOrder(requestBody)
                .subscribeOn(Schedulers.io())
                .subscribeOn(AndroidSchedulers.mainThread())
                .observeOn(AndroidSchedulers.mainThread())
                .compose(RxLifecycleUtils.bindToLifecycle(mRootView))
                .subscribe(new ErrorHandleSubscriber<BaseResult>(mErrorHandler) {
                    @Override
                    public void onNext(BaseResult baseResult) {
                        if (baseResult.isSuccess()) {
                            if (mOrderContentActivity != null) {
                                textView.setText(peopleNumber);
                            } else {
                                textView.setText("人數:" + peopleNumber);
                            }
                            OpenTableManage.getDefault().setPeopleNumber(Integer.parseInt(peopleNumber));
                        }
                    }
                });
    }

    public void changeNumber(int number) {
        if (!changeNumberCondition(number)) {
            return;
        }
        myOrderManage.changeNumber(number);
        if (mMealStandPresenter != null) {
            mMealStandPresenter.updateOrderFoodNumber();
        }
        mSelectMealAdapter.notifyDataSetChanged();
    }

    public boolean changeNumberCondition(int i) {
        if (MyOrderManage.getInstance().getSize() <= 0) {
            return false;
        }
        if (mSelectMealAdapter.getSelect_start_position() == -1 || mSelectMealAdapter.getSelect_start_position() >= mSelectMealAdapter.getInfos().size()) {
            return false;
        }
        if (myOrderManage.getOrderFoodList().get(mSelectMealAdapter.getSelect_start_position()).isIsfood() == false) {
            return false;
        }
        //旧食品不可以修改数量
        if (i != 0 && myOrderManage.getOrderFoodList().get(mSelectMealAdapter.getSelect_start_position()).isNew() == false) {
            return false;
        }
        if (mSelectMealAdapter.getSelect_position() == -1) {
            return false;
        }
        return true;
    }

    /**
     * 送單
     * @param isPrint 是否印單
     */
    public void sendOrder(boolean isPrint) {
        if (MyOrderManage.getInstance().getOrderId() == -1) {
            if (getFoodCount() == 0) {
                showTip2Dialog(IActivity, noFoodDeliveryTip,isPrint);
            } else {
                if (mMealStandPresenter != null) {
                    mMealStandPresenter.createOrder();
                } else if (mOrderContentPresenter != null) {
                    mOrderContentPresenter.createOrder(isPrint);
                } else if (mOrderPayPresenter != null) {
                    mOrderPayPresenter.createOrder();
                }
            }
        } else {
            if (mMealStandPresenter != null) {
                mMealStandPresenter.addOrderFood();
            } else if (mOrderContentPresenter != null) {
                mOrderContentPresenter.addOrderFood(isPrint);
            } else if (mOrderPayPresenter != null) {
                mOrderPayPresenter.addOrderFood();
            }
        }
    }

    /**
     * 創建訂單后保存OrderId
     *
     * @param orderId
     */
    protected void setOrderId(double orderId) {
        MyOrderManage.getInstance().setOrderId(orderId);
    }

    /**
     * 重置選中狀態
     */
    public void resetSelected() {
        for (int i = 0; i < orderFoodList.size(); i++) {
            OrderDetail datasBean = orderFoodList.get(i);
            datasBean.setSelected(0);
        }
    }

    public double initFoodTotalMoney() {
        double total = 0.0;
        for (OrderDetail food : myOrderManage.getOrderFoodList()) {
            total += food.getPrice();
        }
        return total;
    }

    private int initFoodCount() {
        int cout = 0;
        for (OrderDetail food : myOrderManage.getOrderFoodList()) {
            cout += food.getNumber();
        }
        return cout;
    }

    protected String getDeleteFoodIds() {
        StringBuilder builder = new StringBuilder();
        List<OrderDetail> orderDetails = getOldOrderFoodLists();
        int start_position = mSelectMealAdapter.getSelect_full_start_position() + 1;
        int end_position = mSelectMealAdapter.getSelect_full_end_position() + 1;
        for (int i = orderDetails.size() - 1; i >= 0; i--) {
            int my_index = orderDetails.get(i).getMyIndex();
            if (start_position <= my_index && my_index <= end_position) {
                OrderDetail orderDetail1 = orderDetails.get(i);
                builder.append(orderDetail1.getId());
                builder.append(",");
            }
        }
        String str = builder.toString();
        if (str.endsWith(",")) {
            str = str.substring(0, str.length() - 1);
        }
        return str;
    }

    protected CreateOrderRequest getCreateOrderRequest(List<OrderDetail> foodList) {
        int restaurantId = GsaCloudApplication.getRestaurantId(mApplication);
        CreateOrderRequest request = new CreateOrderRequest();
        request.setOrderDetails(orderDetailBeanToFoodRequest(foodList));
        request.setPerson(OpenTableManage.getDefault().getPeopleNumber());
        request.setTableId(OpenTableManage.getDefault().getTableBean().getId());
        request.setRestaurantId(restaurantId);
        return request;
    }

    protected AddOrderRequest getAddOrderRequest(List<OrderDetail> foodList) {
        AddOrderRequest request = new AddOrderRequest();
        request.setMaps(orderDetailBeanToAddFoodRequest(foodList));
        request.setOrderId(MyOrderManage.getInstance().getOrderId());
        return request;
    }

    protected Map<Long, List<OrderBean.OrderDetailsBean>> orderDetailBeanToFoodRequest(List<OrderDetail> foodList) {
        Map<Long, List<OrderBean.OrderDetailsBean>> orderDetails = new HashMap<>();
        if (foodList != null) {
            //套餐明細ID
            long mapIndex = 0;
            List<OrderBean.OrderDetailsBean> orderItems = null;
            for (int i = 0; i < foodList.size(); i++) {
                OrderDetail food = foodList.get(i);
                if (food.getItemType() == 1) {
                    orderItems = new ArrayList<>();
                    mapIndex += 1;
                }

                OrderBean.OrderDetailsBean request = new OrderBean.OrderDetailsBean();
                request.setProductName(food.getProductName());
                request.setProductId(food.getProductId());
                request.setParentId(food.getParentId());
                request.setNumber(food.getNumber());
                request.setPrice(food.getUnit_price());
                request.setType(food.getType());
                request.setLunchboxPrice(0);
                if (food.isNew()) {
                    //這裡只添加新食品
                    orderItems.add(request);
                }
                int nextIndex = i + 1;
                if (foodList.size() > nextIndex) {
                    if (foodList.get(nextIndex).getItemType() == 1 && orderItems != null && orderItems.size() > 0) {
                        //下一個食品是不是主食品
                        orderDetails.put(mapIndex, orderItems);
                    }
                } else if (foodList.size() == nextIndex) {
                    //最後
                    if (orderItems != null && orderItems.size() > 0) {
                        orderDetails.put(mapIndex, orderItems);
                    }
                }
            }
        }
        return orderDetails;
    }

    protected Map<String, List<OrderBean.OrderDetailsBean>> orderDetailBeanToAddFoodRequest(List<OrderDetail> foodList) {
        /**
         * 1#主食品（完全新點）
         * 2#主食品+子食品+細項（主食品基礎上新加）
         */
        long type1 = 1;
        long type2 = 2;
        //打印用到，清理掉之前保存的食品
        MyOrderManage.getInstance().getNewFoodList().clear();
        //可重複的map
        Map<String, List<OrderBean.OrderDetailsBean>> orderDetails = new HashMap<>();
        if (foodList != null) {
            //套餐明細ID
            String mapIndex = "1-1";
            int indexCount = 0;
            List<OrderBean.OrderDetailsBean> orderItems = null;
            for (int i = 0; i < foodList.size(); i++) {
                OrderDetail food = foodList.get(i);
                if (food.getItemType() == 1) {
                    orderItems = new ArrayList<>();
                    indexCount += 1;
                    if (food.isNew()) {
                        //完全新點的一個食品
                        mapIndex = indexCount + "-" + type1;
                    } else {
                        //基礎上新加
                        mapIndex = indexCount + "-" + type2;
                    }
                }

                OrderBean.OrderDetailsBean request = new OrderBean.OrderDetailsBean();
                request.setOrderId(MyOrderManage.getInstance().getOrderId());
                request.setProductName(food.getProductName());
                request.setProductId(food.getProductId());
                request.setParentId(food.getParentId());
                request.setNumber(food.getNumber());
                request.setPrice(food.getUnit_price());
                request.setType(food.getType());
                request.setLunchboxPrice(0);
                if (food.isNew()) {
                    //這裡只添加新食品
                    orderItems.add(request);
                    //保存新食品，打印用到
                    MyOrderManage.getInstance().getNewFoodList().add(food);
                }
                int nextIndex = i + 1;
                if (foodList.size() > nextIndex) {
                    if (foodList.get(nextIndex).getItemType() == 1 && orderItems != null && orderItems.size() > 0) {
                        //下一個食品是不是主食品
                        orderDetails.put(mapIndex, orderItems);
                    }
                } else if (foodList.size() == nextIndex) {
                    //最後
                    if (orderItems != null && orderItems.size() > 0) {
                        orderDetails.put(mapIndex, orderItems);
                    }
                }
            }
        }
        return orderDetails;
    }

    protected List<OrderDetail> getNewOrderFoodLists() {
        List<OrderDetail> orderDetails = new ArrayList<>();
        for (int i = 0; i < getOrderFoodLists().size(); i++) {
            OrderDetail orderDetail = getOrderFoodLists().get(i);
            if (orderDetail.isNew()) {
                orderDetails.add(orderDetail);
            }
        }
        return orderDetails;
    }

    protected List<OrderDetail> getOldOrderFoodLists() {
        List<OrderDetail> orderDetails = new ArrayList<>();
        for (int i = 0; i < getOrderFoodLists().size(); i++) {
            OrderDetail orderDetail = getOrderFoodLists().get(i);
            if (!orderDetail.isNew()) {
                orderDetails.add(orderDetail);
            }
        }
        return orderDetails;
    }

    protected boolean hasNesOrderFoods() {
        if (getNewOrderFoodLists().size() > 0) {
            return true;
        }
        return false;
    }

    protected boolean hasOldOrderFoods() {
        if (getOldOrderFoodLists().size() > 0) {
            return true;
        }
        return false;
    }

    public List<OrderDetail> getOrderFoodLists() {
        return myOrderManage.getOrderFoodList();
    }

    protected void sortSelectMealByIsNew() {
        List<OrderDetail> orderDetail = orderFoodList;
        List<OrderDetail> sortOrderList = new ArrayList<>();
        for (int i = 0; i < orderDetail.size(); i++) {
            sortOrderList.add(orderDetail.get(i));
        }
        Comparator c = new Comparator<OrderDetail>() {
            @Override
            public int compare(OrderDetail o1, OrderDetail o2) {
                Boolean isnew1 = o1.isNew();
                Boolean isnew2 = o2.isNew();
                return isnew1.compareTo(isnew2);
            }
        };
        Collections.sort(sortOrderList, c);
        orderDetail.clear();
        for (int i = 0; i < sortOrderList.size(); i++) {
            orderDetail.add(sortOrderList.get(i));
        }
    }

    protected String getTableName() {
        String tablename = "";
        if (OpenTableManage.getDefault().isSplite()) {
            tablename = OpenTableManage.getDefault().getTableBean().getTableName() + "-" + OpenTableManage.getDefault().getSplitNo();
        } else {
            tablename = OpenTableManage.getDefault().getTableBean().getTableName();
        }
        return tablename;
    }

    protected void showTipDialog(Activity context, String msg) {
        QMUIDialog.MessageDialogBuilder dialogBuilder = new QMUIDialog.MessageDialogBuilder(context);
        dialogBuilder.setTitle("溫馨提示");
        dialogBuilder.setMessage(msg);
        dialogBuilder.addAction("確定", (dialog, index) -> dialog.dismiss());
        dialogBuilder.create(R.style.MyDialogTheme2).show();
    }

    protected void showTip2Dialog(Activity context, String msg,boolean isPrint) {
        QMUIDialog.MessageDialogBuilder dialogBuilder = new QMUIDialog.MessageDialogBuilder(context);
        dialogBuilder.setTitle("溫馨提示");
        dialogBuilder.setMessage(msg);
        dialogBuilder.addAction("取消", (dialog, index) -> dialog.dismiss());
        dialogBuilder.addAction(0, "確認", QMUIDialogAction.ACTION_PROP_NEGATIVE, (dialog, index) -> {
            if (mMealStandPresenter != null) {
                mMealStandPresenter.createOrder();
            } else if (mOrderContentPresenter != null) {
                mOrderContentPresenter.createOrder(isPrint);
            } else if (mOrderPayPresenter != null) {
                mOrderPayPresenter.createOrder();
            }
            dialog.dismiss();
        });
        dialogBuilder.create(R.style.MyDialogTheme2).show();
    }

    public int getFoodCount() {
        return getOrderFoodLists().size();
    }

    public void setFoodCount(int foodCount) {
        this.foodCount = foodCount;
    }

    public double getTotalMoney() {
        return totalMoney;
    }

    public void setTotalMoney(double totalMoney) {
        this.totalMoney = totalMoney;
    }
}

