package com.bonait.bnframework;


import android.annotation.SuppressLint;
import android.app.Activity;
import android.app.Application;
import android.content.Context;
import android.util.Log;

import com.bonait.bnframework.business.ConfigData;
import com.bonait.bnframework.common.constant.ConfigName;
import com.bonait.bnframework.common.constant.DataBus;
import com.bonait.bnframework.common.db.QueryDB;
import com.bonait.bnframework.common.db.mode.BPA_ALERTLOG;
import com.bonait.bnframework.common.db.mode.BPA_GOODS;
import com.bonait.bnframework.common.db.mode.BPA_LOG;
import com.bonait.bnframework.common.db.mode.BPA_PROCESS;
import com.bonait.bnframework.common.db.mode.BPA_PROCESSModel;
import com.bonait.bnframework.common.db.mode.BPA_SILOS;
import com.bonait.bnframework.common.db.mode.BPA_SILOSANDMATERIAL;
import com.bonait.bnframework.common.db.mode.BPA_USER;
import com.bonait.bnframework.common.db.res.AlertLogEnum;
import com.bonait.bnframework.common.db.res.UserLogEnum;
import com.bonait.bnframework.common.helper.CrashHandler;
import com.bonait.bnframework.common.helper.I.IMessageLogNotify;
import com.bonait.bnframework.common.helper.MessageLog;
import com.bonait.bnframework.common.helper.SdCart;
import com.bonait.bnframework.manager.ActivityLifecycleManager;
import com.bonait.bnframework.common.constant.Constants;
import com.bonait.bnframework.common.notification.MainNotification;
import com.bonait.bnframework.common.utils.AppUtils;
import com.bonait.bnframework.common.utils.PreferenceUtils;
import com.lzy.okgo.OkGo;
import com.lzy.okgo.cache.CacheEntity;
import com.lzy.okgo.cache.CacheMode;
import com.lzy.okgo.interceptor.HttpLoggingInterceptor;
import com.orhanobut.logger.AndroidLogAdapter;
import com.orhanobut.logger.FormatStrategy;
import com.orhanobut.logger.Logger;
import com.orhanobut.logger.PrettyFormatStrategy;
import com.qmuiteam.qmui.arch.QMUISwipeBackActivityManager;
import com.squareup.leakcanary.LeakCanary;

import org.litepal.LitePal;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.IdentityHashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.TimeUnit;
import java.util.logging.Level;

import okhttp3.OkHttpClient;

/**
 * Created by FYF on 2019/3/19.
 */
public class MainApplication extends Application {

    @SuppressLint("StaticFieldLeak")
    private static Context context;

    public static Context getContext() {
        return context;
    }

    @Override
    public void onCreate() {
        super.onCreate();
        context = getApplicationContext();
        //0.全局异常捕获,保存为SD卡本级目录 crash
        CrashHandler.getInstance().init(this);

        //1.设置程序active,初始化Main函数进程,初始化消息日志
        InitMsgLog();
        ConfigName.getInstance().dishesCon = this;

        //2.初始化SD卡,数据库DB
        SdCart.getInstance().initSD();

        //4.初始化Main,并且增加本地图片库
        ConfigData.getInstance().AddImage(context);
        // activity生命周期管理
        ActivityLifecycleManager.get().init(this);

        // QMUI 框架初始化
        QMUISwipeBackActivityManager.init(this);

        // LitePal 数据库初始化
        LitePal.initialize(this);

        // 全局配置OkGo
        initOkGo();

        // 配置sharedPreferences
        PreferenceUtils.initPreference(this, AppUtils.getAppName(this), Activity.MODE_PRIVATE);

        // 初始化通知栏消息渠道
        MainNotification.initNotificationChannel(this);

        // 内存泄漏检测
        initLeakCanary(false);

        // Log日志打印框架
        initLogCat();

        // SmartShow Toast框架，暂时不用，先使用ToastUtils工具类的
        //SmartShow.init(this);

        //初始化DB数据
        InitDBdata();
        DataBus.getInstance().GetLc();//获取料仓数据

    }

    //========================================================================//
    /**
     * 初始化数据库数据(默认数据)
     */
    public void InitDBdata() {
        //1.没有用户数据 默认写一个admin
        if (QueryDB.GetUserALL().size() <= 0) {
            BPA_USER user = new BPA_USER();
            user.id = "20230415-fyf";
            user.name = "管理员";
            user.account = "admin";
            user.pass = "123456";
            user.deviceID = ConfigName.getInstance().DeviceId;
            user.userID = "20230415-fyf";
            user.exp = "管理员";
            QueryDB.AddUser(user);
            //10个料仓
            if (QueryDB.GetSilosALL().size() == 0) {
                for (int i = 0; i < 10; i++) {
                    BPA_SILOS silo = new BPA_SILOS();
                    silo.id = java.util.UUID.randomUUID().toString();
                    silo.num = i + 1;
                    silo.thrsoleValue=ConfigName.getInstance().SiloAlarmThreshold;
                    silo.warningValue=ConfigName.getInstance().SiloFeedThreshold;
                    BPA_SILOSANDMATERIAL sm = new BPA_SILOSANDMATERIAL();
                    sm.silosID = silo.id;
                    sm.materialID = "";
                    QueryDB.AddSilos(silo);
                    QueryDB.AddSilosAndMaterial(sm);
                }
            }

            //20个测试商品
            for (int i=0;i<20;i++)
            {
                BPA_GOODS good=new BPA_GOODS();
                good.name="回锅肉"+i;
                good.status=1;
                good.sort=i+1;
                good.maketime=1605+i;
                good.issc=0;
                QueryDB.AddGoods(good);
            }

            //工序模型表
            InitProcessData();

        }
    }

    /**
     * 初始化工序模型表
     */
    public void InitProcessData()
    {
        List<String> mxname=Arrays.asList("搅拌","热油","主料","加热","液体料","延迟","勾芡","出菜","热锅");
        Map<String,List<String>> mx=new IdentityHashMap<>();
        mx.put("搅拌",Arrays.asList("搅拌动作","正转速度","反转速度","正转(秒)","反转(秒)","停止(秒)","延迟(秒)"));
        mx.put("热油",Arrays.asList("加热功率","热油(克)"));
        mx.put("主料",Arrays.asList("主料名称","主料重量","烹饪(秒)","投料动作"));
        mx.put("加热",Arrays.asList("加热功率","延迟(秒)"));

        mx.put("液体料",new ArrayList<>());
        mx.put("延迟",Arrays.asList("延迟(秒)"));
        mx.put("勾芡",Arrays.asList("勾芡(克)"));
        mx.put("出菜",Arrays.asList("时间(秒)"));
        mx.put("热锅",Arrays.asList("热锅功率"));

        int index=1;
        for (String key:mxname)
        {
            List<String> values= mx.get(key);
            BPA_PROCESS process=new BPA_PROCESS();
            process.sort=index;
            process.name=key;
            QueryDB.AddProcess(process);//增加模型

            int chidindex=1;
            for (String item:values)//模型
            {
                BPA_PROCESSModel processModel=new BPA_PROCESSModel();
                processModel.processid=process.id;
                processModel.name=item;
                processModel.sort=chidindex;
                if (item.equals("搅拌动作"))
                {
                    processModel.datatype=2;
                    processModel.data="正转反转、一直正转、一直反转";
                }
                else if (item.equals("投料动作"))
                {
                    processModel.datatype=2;
                    processModel.data="投出抖动三次、投出等待三秒、直接投出、手动投料";
                }
                else if (item.equals("正转速度") || item.equals("反转速度"))
                {
                    processModel.datatype=2;
                    processModel.data="停止、最低、低速、中速、高速、最高、极高";
                }else if (item.equals("加热功率") || item.equals("热锅功率"))
                {
                    processModel.datatype=2;
                    processModel.data="停止、一档、二档、三档、四档、五档";
                }else if (item.equals("主料名称"))
                {
                    processModel.datatype=1;
                }else
                {
                    processModel.datatype=0;
                }
                QueryDB.AddProcessModel(processModel);
                chidindex++;
            }
            index++;
        }
    }
    /**
     * 初始化消息日志接收打印
     */
    public void InitMsgLog(){
        MessageLog.MsgNotify = new IMessageLogNotify() {
            @Override
            public void ErrorMsg(String msg) {
                Log.e("Error", msg);
            }
            @Override
            public void InfoMsg(String msg) {
                Log.i("Info", msg);
            }
            @Override
            public void WarnMsg(String msg) {
                Log.w("Warn", msg);
            }
            @Override
            public void UserMsg(UserLogEnum type, String msg) {
                BPA_LOG log = new BPA_LOG();
                log.userID = ConfigName.getInstance().user.userID;
                switch (type.toString())
                {
                    case "登录日志":log.type=1;
                        break;
                    case "角色操作日志":log.type=2;
                        break;
                    case "数据接收":log.type=3;
                        break;
                    case "上传日志":log.type=4;
                        break;
                    case "订单处理日志":log.type=5;
                        break;
                }
                log.text = msg;
                QueryDB.Addlog(log);
            }

            @Override
            public void AlertMsg(AlertLogEnum type, String msg) {
                BPA_ALERTLOG log = new BPA_ALERTLOG();
                log.userID = ConfigName.getInstance().user.userID;
                switch (type.toString())
                {
                    case "异常订单未制作日志":log.type=1;
                        break;
                    case "料仓缺料日志":log.type=2;
                        break;
                    case "传感器异常日志":log.type=3;
                        break;
                    case "其他":log.type=4;
                        break;
                }
                log.text = msg;
                QueryDB.AddAlertlog(log);
            }
        };
    }
    /**
     * 内存泄漏检测，根据flag来判断要不要初始化
     */
    private void initLeakCanary(boolean flag) {
        if (flag) {
            // leak 内存检测注册
            if (LeakCanary.isInAnalyzerProcess(this)) {
                return;
            }
            LeakCanary.install(this);
        }
    }

    /**
     * 初始化log日志框架
     */
    private void initLogCat() {
        FormatStrategy formatStrategy = PrettyFormatStrategy.newBuilder()
                .showThreadInfo(false)  // （可选）是否显示线程信息。 默认值为true
                .methodCount(2)         // （可选）要显示的方法行数。 默认2
                .build();
        Logger.addLogAdapter(new AndroidLogAdapter(formatStrategy) {
            @Override
            public boolean isLoggable(int priority, String tag) {
                return BuildConfig.DEBUG;
            }
        });
    }

    /**
     * 配置OkGo
     */
    private void initOkGo() {

        //---------这里给出的是示例代码,告诉你可以这么传,实际使用的时候,根据需要传,不需要就不传-------------//
        /*HttpHeaders headers = new HttpHeaders();
        headers.put("commonHeaderKey1", "commonHeaderValue1");    //header不支持中文，不允许有特殊字符
        headers.put("commonHeaderKey2", "commonHeaderValue2");
        HttpParams params = new HttpParams();
        params.put("commonParamsKey1", "commonParamsValue1");     //param支持中文,直接传,不要自己编码
        params.put("commonParamsKey2", "这里支持中文参数");*/
        //----------------------------------------------------------------------------------------//

        OkHttpClient.Builder builder = new OkHttpClient.Builder();

        //log相关
        HttpLoggingInterceptor loggingInterceptor = new HttpLoggingInterceptor("OkGo");
        //log打印级别，决定了log显示的详细程度
        loggingInterceptor.setPrintLevel(HttpLoggingInterceptor.Level.BODY);
        //log颜色级别，决定了log在控制台显示的颜色
        loggingInterceptor.setColorLevel(Level.INFO);
        //添加OkGo默认debug日志
        builder.addInterceptor(loggingInterceptor);

        //-------------------------配置超时时间，默认60000ms，60s------------------------------//
        //OkGo.DEFAULT_MILLISECONDS
        //全局的连接超时时间
        builder.connectTimeout(Constants.CONNECT_TIME_OUT, TimeUnit.MILLISECONDS);
        //全局的读取超时时间
        builder.readTimeout(Constants.CONNECT_TIME_OUT, TimeUnit.MILLISECONDS);
        //全局的写入超时时间
        builder.writeTimeout(OkGo.DEFAULT_MILLISECONDS, TimeUnit.MILLISECONDS);

        OkGo.getInstance().init(this)                           //必须调用初始化
                .setOkHttpClient(builder.build())               //建议设置OkHttpClient，不设置将使用默认的
                .setCacheMode(CacheMode.NO_CACHE)               //全局统一缓存模式，默认不使用缓存，可以不传
                .setCacheTime(CacheEntity.CACHE_NEVER_EXPIRE)   //全局统一缓存时间，默认永不过期，可以不传
                .setRetryCount(3);                               //全局统一超时重连次数，默认为三次，那么最差的情况会请求4次(一次原始请求，三次重连请求)，不需要可以设置为0
        //.addCommonParams(params);                       //全局公共参数

    }


}
