
const { ccclass, property } = cc._decorator;

@ccclass
export default class Util {
    /**
        * 打乱数组
        * @param arr 要打乱的数组
        * @returns 打乱后的数组
        */
    static Shuffle<T>(arr: Array<T>): Array<T> {
        var len = arr.length;
        for (var i = len - 1; i >= 0; i--) {
            var j = Math.floor(Math.random() * len);
            var temp = arr[i];
            arr[i] = arr[j];
            arr[j] = temp;
        }

        return arr;
    }

    /**
     * 获取固定长度字符串  用于太长名字截断
     * @param str 原字符串
     * @param len 取字符长度
     * @returns 返回的字符串
     */
    public static cutStr(str: string, len: number): string {
        var str_length = 0;
        var str_len = 0;
        let str_cut = "";
        str_len = str.length;
        for (var i = 0; i < str_len; i++) {
            let a = str.charAt(i);
            str_length++;
            if (escape(a).length > 4) {
                //中文字符的长度经编码之后大于4
                str_length++;
            }
            str_cut = str_cut.concat(a);
            if (str_length >= len) {
                str_cut = str_cut.concat("...");
                return str_cut;
            }
        }
        //如果给定字符串小于指定长度，则返回源字符串；
        if (str_length < len) {
            return str;
        }
    }

    /**
     * 取一个区间内随机整数
     * @param n 开始位置
     * @param m 结束位置
     * @returns 返回的随机整数
     */
    public static rnd(n, m): number {
        var random = Math.floor(Math.random() * (m - n + 1) + n);
        return random;
    }

    static _hasOwnProperty = Object.prototype.hasOwnProperty;
    /**
     * 一个对象是否有prop属性
     * @param obj 对象
     * @param prop 属性
     * @returns 返回是否有
     */
    static has(obj: any, prop: any) {
        return Util._hasOwnProperty.call(obj, prop);
    }

    /**
     * 对比两个对象的大小
     * @param a 对象a
     * @param b 对象b
     * @returns 返回值 a < b : -1, a == b : 0, a > b : 1
     */
    static defaultCompare<T>(a: T, b: T): number {
        if (a < b) {
            return -1;
        } else if (a === b) {
            return 0;
        } else {
            return 1;
        }
    }

    /**根据key给对象排序
     * @param obj
     * @param key 
     */
    static objSortByKey(obj: any, key: string) {

        if (!obj.length) {
            mk.console.log("该对象不是数组或者元素个数为零");
            return;
        }
        let compare = (a, b) => {
            let a_value = a[key];
            let b_value = b[key];
            if (a_value < b_value) {
                return -1;
            } else if (a_value === b_value) {
                return 0;
            } else {
                return 1;
            }
        }
        obj.sort(compare);
    }

    /**
     * 将一个对象转为字符串
     * @param item 传入对象
     * @returns 返回值 字符串
     */
    static defaultToString(item: any): string {
        if (item === null) {
            return 'COLLECTION_NULL';
        } else if (Util.isUndefined(item)) {
            return 'COLLECTION_UNDEFINED';
        } else if (Util.isString(item)) {
            return '$s ' + item;
        } else {
            return '$o ' + item.toString();
        }
    }

    /**
    * 将所有属性用字符串格式拼接起来
    * @param item 要拼接属性的对象
    * @param join 拼接字符
    * @returns 返回值
    */
    static makeString<T>(item: T, join: string = ','): string {
        if (item === null) {
            return 'COLLECTION_NULL';
        } else if (Util.isUndefined(item)) {
            return 'COLLECTION_UNDEFINED';
        } else if (Util.isString(item)) {
            return item.toString();
        } else {
            let toret = '{';
            let first = true;
            for (const prop in item) {
                if (Util.has(item, prop)) {
                    if (first) {
                        first = false;
                    } else {
                        toret = toret + join;
                    }
                    toret = toret + prop + ':' + (<any>item)[prop];
                }
            }
            return toret + '}';
        }
    }

    /**
     * 检查func是否是一个函数
     * @param func 传入的参数
     * @returns 返回值 bool
     */
    static isFunction(func: any): boolean {
        return (typeof func) === 'function';
    }

    /**
     * 检查obj是否是undefined
     * @param obj 传入参数
     * @returns 返回值 bool
     */
    static isUndefined(obj: any): boolean {
        return (typeof obj) === 'undefined';
    }

    /**
     * 检查一个对象是否是字符串
     * @param obj 要检查的对象
     * @param 返回值 true : 是, false : 不是
     */
    static isString(obj: any): boolean {
        return Object.prototype.toString.call(obj) === '[object String]';
    }

    /**
     * 倒计时转换为时间格式（h:m:s） ，可自定义
     * @param t 秒
     * @param f 格式
     */
    public static ParseTime2Format(t: number, f: string = "h:m:s"): string {
        var d: number = Math.floor(t / 24 / 3600);
        var h: number = Math.floor((t / 3600) % 24);
        var m: number = Math.floor((t % 3600) / 60);
        var s: number = (t % 3600) % 60;

        function parse_format(t: number): string {
            var s: string = t.toString();
            if (t < 10) {
                s = "0" + t;
            }
            return s;
        }
        if (f.indexOf("d") != -1) {
            f = f.replace(/d/g, parse_format(d));
        }
        else {
            h += d * 24;
        }
        if (f.indexOf("h") != -1) {
            f = f.replace(/h/g, parse_format(h));
        } else {
            m += h * 60;
        }
        if (f.indexOf("m") != -1) {
            f = f.replace(/m/g, parse_format(m));
        } else {
            if (f.indexOf("h") != -1) {
                s += m * 60;
            } else {
                s = t;
            }
        }
        if (f.indexOf("s") != -1) {
            f = f.replace(/s/g, parse_format(s));
        }
        return f;
    }

    /**计算两点之间的弧度值 */
    static countHuBetweenToPos(startPos: cc.Vec2, endPos: cc.Vec2) {
        var hu: number = Math.atan2(endPos.y - startPos.y, endPos.x - startPos.x);
        //拥挤城市 +90 这边是 -90 可能跟引擎的原始坐标系有关
        return hu;
    }

    /**转换成年月日 2020-10-10 */
    static parseTimestamp(date: Date): string {

        // let year = date.getFullYear();
        // let month = date.getMonth()+1;
        // let day = date.getDay();
        // return 

        var date = new Date(date);
        var YY = date.getFullYear() + '-';
        var MM = (date.getMonth() + 1 < 10 ? '0' + (date.getMonth() + 1) : date.getMonth() + 1) + '-';
        var DD = (date.getDate() < 10 ? '0' + (date.getDate()) : date.getDate());
        return YY + MM + DD;
    }

    /**将时间戳转换为 20xx.10.xx 11:20:00 */
    static timestampToTime(timestamp: number): string {
        var date = new Date(timestamp * 1000);//时间戳为10位需*1000，时间戳为13位的话不需乘1000
        var Y = date.getFullYear() + '.';
        var M = (date.getMonth() + 1 < 10 ? '0' + (date.getMonth() + 1) : date.getMonth() + 1) + '.';
        var D = (date.getDate() < 10 ? '0' + date.getDate() : date.getDate()) + ' ';
        var h = (date.getHours() < 10 ? '0' + date.getHours() : date.getHours()) + ':';
        var m = (date.getMinutes() < 10 ? '0' + date.getMinutes() : date.getMinutes()) + ':';
        var s = date.getSeconds() < 10 ? '0' + date.getSeconds() : date.getSeconds();
        return Y + M + D + h + m + s;
    }

    /**数值保留小数
     * @param num 具体得数值
     * @param fixedNum 所保留的位数
     */
    static numberFixed(num: number, fixedNum: number): number {
        return Number(num.toFixed(fixedNum));

        //土方法实现保留小数位数
        //    let num = Math.round((PlayerConst.cashNum * 100)) / 100;
    }

    /** 版本对比 */
    static versionCompareHandle(versionA, versionB) {
        console.log("JS Custom Version Compare: version A is " + versionA + ', version B is ' + versionB);
        var vA = versionA.split('.');
        var vB = versionB.split('.');
        for (var i = 0; i < vA.length; ++i) {
            var a = parseInt(vA[i]);
            var b = parseInt(vB[i] || 0);
            if (a === b) {
                continue;
            }
            else {
                return a - b;
            }
        }
        if (vB.length > vA.length) {
            return -1;
        }
        else {
            return 0;
        }
    }

    //安装相关-----------------------------------------------------------------------------------------
    /** 是否有apk安装包 */
    static checkHasApk(fileName) {
        var fullPath = jsb.fileUtils.getWritablePath() + fileName

        if (jsb.fileUtils.isFileExist(fullPath)) {
            return fullPath
        }
        else {
            return ''
        }
    }

    /** 下载文件
    * @param url 下载地址
    * @param fileName 存储文件名称
    * @param successCb 成功回调
    * @param failCb 失败回调
    * @param progressCb 下载进度回调
    */
    static downFile2Local(url, fileName, successCb, failCb, progressCb): any {
        var fullPath = jsb.fileUtils.getWritablePath() + fileName
        // showModelLoadingDialog();//显示加载中模态框
        if (jsb) {
            var downloader = new jsb.Downloader();
            downloader.setOnFileTaskSuccess(function () {
                // removeModelLoadingDialog();//删除加载中模态框
                console.log("DownLoadM setOnFileTaskSuccess", "")
                if (successCb) {
                    console.log("DownLoadM result... ", jsb.fileUtils.isFileExist(fullPath))
                    console.log("DownLoadM setOnFileTaskSuccess fullPath...", fullPath)
                    successCb(fullPath);
                    // AdM.installApp()
                }
            });
            downloader.setOnTaskError(function (task: any, errorCode: number, errorCodeInternal: number, errorStr: string) {
                // removeModelLoadingDialog();
                // showTips("文件下载失败！！！");
                console.log("DownLoadM setOnTaskError", errorCode + " ; " + errorCodeInternal + " ; " + errorStr)
                if (failCb) {
                    failCb(fullPath);
                }
            });
            downloader.setOnTaskProgress(function (task: any, bytesReceived: number, totalBytesReceived: number, totalBytesExpected: number) {
                // removeModelLoadingDialog();
                // showTips("文件下载失败！！！");
                console.log("DownLoadM", bytesReceived + " ; " + totalBytesReceived + " ; " + totalBytesExpected)
                if (progressCb) {
                    progressCb(bytesReceived, totalBytesReceived, totalBytesExpected)
                }
            });
            downloader.createDownloadFileTask(url, fullPath);//创建下载任务
            return downloader
        }
    }

}
