最新公告
  • 欢迎您光临起源地模板网,本站秉承服务宗旨 履行“站长”责任,销售只是起点 服务永无止境!立即加入钻石VIP
  • 值得收藏的前端开发必备工具类函数

    正文概述 掘金(CloudEmperor)   2020-11-27   410

    前言

    乘着空闲,整理一些平常项目开发中经常用到的工具类函数。每个都是亲测有效的,开箱即用。

    1.判断当前环境是否是手机端

    
    /**
     * 判断当前环境是否是手机端
     * 
     * @return {Boolean}  返回结果
     * 
     */
     export const isMobile=() =>{
         if(/Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(navigator.userAgent)) {
                return true
            } else {
                return false
          }
       }
       
    

    2.断当前环境是否是微信环境

    
    /**
     * 断当前环境是否是微信环境
     * 
     * @return {Boolean}  返回结果
     * 
     */
    export const isWeixin =() =>{      
          const ua = navigator.userAgent.toLowerCase();
          if(ua.match(/MicroMessenger/i)==="micromessenger") {
               return true;
         } else {
                return false;
          }
      }
    

    3.检测浏览器是否放大

    /**
     * 检测浏览器是否放大
     * 
     * @param {Boolean } rsize  是否返回具体放大数值,默认否
     * @return {Boolean | Number}  返回结果
     * 
     */
    export const detectZoom=rsize =>{
      let ratio = 0
      const screen = window.screen
      const ua = navigator.userAgent.toLowerCase()
    
      if (window.devicePixelRatio) {
        ratio = window.devicePixelRatio
      } else if (~ua.indexOf('msie')) {
        if (screen.deviceXDPI && screen.logicalXDPI) ratio = screen.deviceXDPI / screen.logicalXDPI
      } else if (window.outerWidth&& window.innerWidth) {
        ratio = window.outerWidth / window.innerWidth
      }
    
      if (ratio) ratio = Math.round(ratio * 100)
    
      return rsize ? ratio : ratio === 100
    }
    

    4.获取普通地址url参数

    /**
     * 获取普通地址url参数
     * 例如:http://localhost:8080/?token=rTyJ7bcRb7KU4DMcWo4216&roleId=512213631174180864
     * 
     * @param {String} name 
     * @return {Boolean | String} 返回获取值 
     * 
     */
    export const getUrlParam = name =>{
      const reg = new RegExp("(^|&)" + name + "=([^&]*)(&|$)"); 
      const r = window.location.search.substr(1).match(reg);  
      if (r != null) return decodeURI(r[2]); return false; 
    }
    

    5.获取hash模式地址url参数

    /**
     * 获取hash模式地址url参数
     * 例如:http://localhost:8080/#/?token=rTyJ7bcRb7KU4DMcWo4216&roleId=512213631174180864
     * 
     * @param {String} name 
     * @return {Boolean | String} 返回获取值 
     * 
     */
    export const getUrlHashParam =name =>{
      const w = window.location.hash.indexOf("?");
      const query = window.location.hash.substring(w + 1);
      const vars = query.split("&");
      for (let i = 0; i < vars.length; i++) {
        const pair = vars[i].split("=");
        if (pair[0] == name) {
          return pair[1];
        }
      }
    
      return false;
    }
    

    6.时间戳转换

    /**
     * 时间戳转换
     * 
     * @param {Number} date 时间戳
     * @param {String} fmt  时间显示格式,例如 yyyy-MM-dd HH:mm:ss
     * @return {String} fmt 返回转换后的时间 ,formatDate(value, "yyyy-MM-dd  hh: mm : ss")
     * 
     */
    export const formatDate = (date, fmt) => {
      date = new Date(date);
      if (isNaN(date.getDate())) return date;
      if (/(y+)/.test(fmt)) {
        fmt = fmt.replace(
          RegExp.$1,
          (date.getFullYear() + "").substr(4 - RegExp.$1.length)
        );
      }
      let o = {
        "M+": date.getMonth() + 1,
        "d+": date.getDate(),
        "h+": date.getHours(),
        "m+": date.getMinutes(),
        "s+": date.getSeconds()
      };
      for (let k in o) {
        if (new RegExp(`(${k})`).test(fmt)) {
          let str = o[k] + "";
          fmt = fmt.replace(
            RegExp.$1,
            RegExp.$1.length === 1 ? str : ("00" + str).substr(str.length)
          );
        }
      }
      return fmt;
    };
    

    7.时间戳转换成什么之前

    /**
     * 时间戳转换成什么之前
     * 
     * @param {Number} times 时间戳
     * @return {String} 返回结果,timeAgoLabel(1606273724459) 输出:刚刚
     * 
     */
    export const timeAgoLabel = times => {
      let nowTimes = new Date().getTime()
      let diffSecond = (nowTimes - times) / 1000
      let agoLabel = ''
      if (diffSecond < 60) {
        agoLabel = '刚刚'
      } else if (diffSecond < 60 * 60) {
        agoLabel = Math.floor(diffSecond / 60) + '分钟前'
      } else if (diffSecond < 60 * 60 * 24) {
        agoLabel = Math.floor(diffSecond / 3600) + '小时前'
      } else if (diffSecond < 60 * 60 * 24 * 30) {
        agoLabel = Math.floor(diffSecond / (3600 * 24)) + '天前'
      } else if (diffSecond < 3600 * 24 * 30 * 12) {
        agoLabel = Math.floor(diffSecond / (3600 * 24 * 30)) + '月前'
      } else {
        agoLabel = Math.floor(diffSecond / (3600 * 24 * 30 * 12)) + '年前'
      }
      return agoLabel
    }
    

    8.生成任意位数随机数(数字)

    /**
     * 生成任意位数随机数(数字)
     * 
     * @param {Number} n 可选长度位数
     * @return {Number} 返回随机值
     * 
     */
    export const randomNumber =n =>{
          let rnd = '';
          for (let i = 0; i < n; i++) {
            rnd += Math.floor(Math.random() * 10);
          }
          return rnd;
    }
    

    9.随机生成一个自定义长度,不重复的字母加数字组合,可用来做id标识

    /**
     * 随机生成一个自定义长度,不重复的字母加数字组合,可用来做id标识
     * 
     * @param {Number} randomLength 可选长度位数,默认10
     * @return {String} 返回随机值
     * 
     */
    export const randomId =(randomLength = 10) =>{
        return Number(Math.random().toString().substr(3,randomLength) + Date.now()).toString(36)
    },
    

    10.js数组去重(复杂数据有ID的情况下)

     /**
      * js数组去重(复杂数据有ID的情况下)
      * 方式一(hash)
      * 
      * @param {Array} repeatArray 含重复数据的数组
      * @return {Array} 返回去重后的数据
      * 
      */
     export const noRepeatArrayHash= repeatArray =>{
          const hash = {};
          const temp = [];
          for (let i = 0; i < repeatArray.length; i++) {
              if (!hash[repeatArray[i].id]) {
                  hash[repeatArray[i].id] = true;
                  temp.push(repeatArray[i]);
              }
          }
      
          return temp;
    }
    
     /**
      * js数组去重(复杂数据有ID的情况下)
      * 方式二(hash + reduce)
      * 
      * @param {Array} repeatArray 含重复数据的数组
      * @return {Array} 返回去重后的数据
      * 
      */
    export const noRepeatArrayReduce= repeatArray =>{
        const hash = {};
    	return repeatArray.reduce(function(accumulator, currentValue){
    	       if(!hash[currentValue.id]){
    		       hash[currentValue.id]=true;
    			   accumulator.push(currentValue)
               }  
               
            return accumulator		   
    	
    	}, []);
    }
    

    11.浅拷贝

    /**
     * 浅拷贝
     * 
     * @param {Array | Object} objOrArr 要拷贝的对象或数组
     * @return {Array | Object} 返回拷贝结果
     * 
     */
    export const shallowCopy = objOrArr =>{
        const type = objOrArr instanceof Array ? 'array' : 'object'
        let newObjOrArr = objOrArr instanceof Array ? [] : {}
        if(type === 'array'){
            newObjOrArr=[].concat(objOrArr)
        }else{
            for(let key in objOrArr){
                if(objOrArr.hasOwnProperty(key)){
                    newObjOrArr[key]= objOrArr[key]
                }
            }
        }
    
        return newObjOrArr
    }
    

    12.深拷贝

    /**
     * 深拷贝
     * 
     * @param {Array | Object} objOrArr 要拷贝的对象或数组
     * @return {Array | Object} 返回拷贝结果
     * 
     */
    export const deepCopy= objOrArr => {
        const type = objOrArr instanceof Array ? 'array' : 'object'
        let newObjOrArr = objOrArr instanceof Array ? [] : {}
        if (type === 'array') {
            newObjOrArr = JSON.parse(JSON.stringify(objOrArr))
        } else {
            for (let key in objOrArr) {
                if (objOrArr.hasOwnProperty(key)) {
                    newObjOrArr[key] = typeof objOrArr[key] === 'object' ? deepCopy(objOrArr[key]) : objOrArr[key]
                }
            }
        }
    
        return newObjOrArr
    }
    

    13.promise方式封装的ajax函数

    /**
     * promise方式封装的ajax函数
     * 
     * @param {String} method 请求方式
     * @param {String} url 请求地址
     * @param {Object} params 请求参数
     * 
     */
    export const ajax=(method,url, params) =>{		
        //兼容IE		 	
        const request= window.XMLHttpRequest ? 	new XMLHttpRequest() : new ActiveXObject("Microsoft.XMLHTTP")	
        return new Promise(function(resolve,reject){
                request.onreadystatechange=function(){
                        if(request.readyState===4){
                                if(request.status===200){
                                    resolve(JSON.parse(request.response));
                                }else{
                                    reject(request.status);
                                }
                        }
                };
                if(method.toUpperCase() === "GET"){
                    const arr = [];
                    for(let key in params){
                        arr.push(key + '=' + params[key]);
                    }
                    const getData=arr.join("&");					
                    request.open("GET",url +"?"+getData,true);
                    request.send(null);
                }else if(method.toUpperCase() === "POST"){
                    request.open("POST",url,true);
                    request.responseType="json";
                    request.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded;charset=utf-8');
                    request.send(params);
    
                }			
    
        })
    
    }
    

    14.js浮点数计算加减乘除精度损失解决方法

    /**
     * js浮点数计算加减乘除精度损失解决方法
     * 
     * @param {Number} a 数值a
     * @param {Number} b 数值b
     * @param {String} computeType 加减乘除类型 add加  subtract减  multiply乘  divide除
     * @return {Number} 返回计算结果,floatNumber(0.11, 0.03, 'add')
     * 
     */
    export const floatNumber = (a, b, computeType) =>{
        const isInteger= obj =>{
            return Math.floor(obj) === obj
        }
        const toInteger= floatNum =>{
            const ret = {times: 1, num: 0}
            if (isInteger(floatNum)) {
                ret.num = floatNum
                return ret
            }
            const strfi  = floatNum + ''
            const dotPos = strfi.indexOf('.')
            const len    = strfi.substr(dotPos+1).length
            const times  = Math.pow(10, len)
            const intNum = parseInt(floatNum * times + 0.5, 10)
            ret.times  = times
            ret.num    = intNum
            return ret
        }
        const operation=(a, b, computeType) =>{
            const o1 = toInteger(a)
            const o2 = toInteger(b)
            const n1 = o1.num
            const n2 = o2.num
            const t1 = o1.times
            const t2 = o2.times
            const max = t1 > t2 ? t1 : t2
            let result = null
            switch (computeType) {
                case 'add':
                    if (t1 === t2) { // 两个小数位数相同
                        result = n1 + n2
                    } else if (t1 > t2) { // o1 小数位 大于 o2
                        result = n1 + n2 * (t1 / t2)
                    } else { // o1 小数位 小于 o2
                        result = n1 * (t2 / t1) + n2
                    }
                    return result / max
                case 'subtract':
                    if (t1 === t2) {
                        result = n1 - n2
                    } else if (t1 > t2) {
                        result = n1 - n2 * (t1 / t2)
                    } else {
                        result = n1 * (t2 / t1) - n2
                    }
                    return result / max
                case 'multiply':
                    result = (n1 * n2) / (t1 * t2)
                    return result
                case 'divide':
                    result = (n1 / n2) * (t2 / t1)
                    return result
            }
    
        }
    
        return operation(a, b, computeType)
    }
    

    15.防抖 (debounce)

    /**
     * 防抖 (debounce)将多次高频操作优化为只在最后一次执行
     * 
     * @param {Function} fn 需要防抖函数
     * @param {Number} wait  需要延迟的毫秒数
     * @param {Boolean} immediate 可选参,设为true,debounce会在wait时间间隔的开始时立即调用这个函数
     * @return {Function}
     * 
     */
    export const debounce= (fn, wait, immediate) =>{
        let timer = null
    
        return function() {
            let args = arguments
            let context = this
    
            if (immediate && !timer) {
                fn.apply(context, args)
            }
    
            if (timer) clearTimeout(timer)
            timer = setTimeout(() => {
                fn.apply(context, args)
            }, wait)
        }
    }
    

    16.节流(throttle)

    /**
     * 节流(throttle)将高频操作优化成低频操作,每隔 100~500 ms执行一次即可
     * 
     * @param {Function} fn 需要防抖函数
     * @param {Number} wait  需要延迟的毫秒数
     * @param {Boolean} immediate 可选参立即执行,设为true,debounce会在wait时间间隔的开始时立即调用这个函数
     * @return {Function}
     * 
     */
    export const throttle =(fn, wait, immediate) =>{
        let timer = null
        let callNow = immediate
        
        return function() {
            let context = this,
                args = arguments
    
            if (callNow) {
                fn.apply(context, args)
                callNow = false
            }
    
            if (!timer) {
                timer = setTimeout(() => {
                    fn.apply(context, args)
                    timer = null
                }, wait)
            }
        }
    }
    

    17.文件大小换算成单位

    /** 
     * 文件大小换算成单位
     * 
     * @param {Number} bytes 大小
     * @param {String} units 可选单位,默认metric
     * @param {Number} precision 可选位数,数值精度保留几位小数点,默认1
     * @return {String} 返回带单位值,byteSize(1580),输出1.6 kB
     * 
    */
    export const byteSize = (bytes, units='metric', precision=1) => {
        let value='',
            unit=''
        const base = units === 'metric' || units === 'metric_octet' ? 1000 : 1024
        const table = [
            { expFrom: 0, expTo: 1, metric: 'B', iec: 'B', metric_octet: 'o', iec_octet: 'o' },
            { expFrom: 1, expTo: 2, metric: 'kB', iec: 'KiB', metric_octet: 'ko', iec_octet: 'Kio' },
            { expFrom: 2, expTo: 3, metric: 'MB', iec: 'MiB', metric_octet: 'Mo', iec_octet: 'Mio' },
            { expFrom: 3, expTo: 4, metric: 'GB', iec: 'GiB', metric_octet: 'Go', iec_octet: 'Gio' },
            { expFrom: 4, expTo: 5, metric: 'TB', iec: 'TiB', metric_octet: 'To', iec_octet: 'Tio' },
            { expFrom: 5, expTo: 6, metric: 'PB', iec: 'PiB', metric_octet: 'Po', iec_octet: 'Pio' },
            { expFrom: 6, expTo: 7, metric: 'EB', iec: 'EiB', metric_octet: 'Eo', iec_octet: 'Eio' },
            { expFrom: 7, expTo: 8, metric: 'ZB', iec: 'ZiB', metric_octet: 'Zo', iec_octet: 'Zio' },
            { expFrom: 8, expTo: 9, metric: 'YB', iec: 'YiB', metric_octet: 'Yo', iec_octet: 'Yio' }
        ]
    
        for (let i = 0; i < table.length; i++) {
            const lower = Math.pow(base, table[i].expFrom)
            const upper = Math.pow(base, table[i].expTo)
            if (bytes >= lower && bytes < upper) {
                const retUnit = table[i][units]
                if (i === 0) {
                    value = String(bytes)
                    unit = retUnit
                    break;
                } else {
                    value = (bytes / lower).toFixed(precision)
                    unit = retUnit
                    break;
                }
            }
        }
        return `${value} ${unit}`.trim()  
    }
    

    18.将一个字符串复制到剪贴板

    /**
     * 将一个字符串复制到剪贴板
     * @param {String} str 复制的内容
     * @return {String} 直接粘贴, copyToClipboard('将一个字符串复制到剪贴板')
     * 
     */
     export const copyToClipboard = str => {
          const el = document.createElement('textarea');
          el.value = str;
          el.setAttribute('readonly', '');
          el.style.position = 'absolute';
          el.style.left = '-9999px';
          document.body.appendChild(el);
          const selected =document.getSelection().rangeCount > 0 ? document.getSelection().getRangeAt(0) : false;
          el.select();
          document.execCommand('copy');
          document.body.removeChild(el);
          if (selected) {
              document.getSelection().removeAllRanges();
              document.getSelection().addRange(selected);
          }
    }
    

    19.平滑滚动到页面顶部

    /**
     * 平滑滚动到页面顶部
     * 
     */
    export const scrollToTop = () => {  
        const c = document.documentElement.scrollTop || document.body.scrollTop;  
        if (c > 0) {  
        window.requestAnimationFrame(scrollToTop);  
        window.scrollTo(0, c - c / 8);  
        }  
    }
    
    

    感谢阅读,更多内容请关注:

    • Github: Github Technology blog
    • juejin:juejin Technology blog
    • CSDN:CSDN Technology blog

    起源地下载网 » 值得收藏的前端开发必备工具类函数

    常见问题FAQ

    免费下载或者VIP会员专享资源能否直接商用?
    本站所有资源版权均属于原作者所有,这里所提供资源均只能用于参考学习用,请勿直接商用。若由于商用引起版权纠纷,一切责任均由使用者承担。更多说明请参考 VIP介绍。
    提示下载完但解压或打开不了?
    最常见的情况是下载不完整: 可对比下载完压缩包的与网盘上的容量,若小于网盘提示的容量则是这个原因。这是浏览器下载的bug,建议用百度网盘软件或迅雷下载。若排除这种情况,可在对应资源底部留言,或 联络我们.。
    找不到素材资源介绍文章里的示例图片?
    对于PPT,KEY,Mockups,APP,网页模版等类型的素材,文章内用于介绍的图片通常并不包含在对应可供下载素材包内。这些相关商业图片需另外购买,且本站不负责(也没有办法)找到出处。 同样地一些字体文件也是这种情况,但部分素材会在素材包内有一份字体下载链接清单。
    模板不会安装或需要功能定制以及二次开发?
    请QQ联系我们

    发表评论

    还没有评论,快来抢沙发吧!

    如需帝国cms功能定制以及二次开发请联系我们

    联系作者

    请选择支付方式

    ×
    迅虎支付宝
    迅虎微信
    支付宝当面付
    余额支付
    ×
    微信扫码支付 0 元