工具方法合集-utils.js

通用

import get from 'lodash.get'
import cloneDeep from 'lodash.clonedeep'
// 深度clone
export function deepClone(obj) {
  return obj ? cloneDeep(obj) : obj
}
export function lodashGet(obj, key, defaultValue = '') {
  //这个 defaultValue  不能给默认 值 会报错;
  return get(obj, key, defaultValue);
}
/**
 * 生成 通用唯一编码
 * @param len 指定长度
 * @param radix 基数
*/
export const createUuid = (len, radix) => {
  var chars = '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz'.split('')
  var uuid = []
  var i
  radix = radix || chars.length

  if (len) {
    // Compact form
    for (i = 0; i < len; i++) uuid[i] = chars[0 | Math.random() * radix]
  } else {
    // rfc4122, version 4 form
    var r

    // rfc4122 requires these characters
    uuid[8] = uuid[13] = uuid[18] = uuid[23] = '-'
    uuid[14] = '4'

    // Fill in random data.  At i==19 set the high bits of clock sequence as
    // per rfc4122, sec. 4.1.5
    for (i = 0; i < 36; i++) {
      if (!uuid[i]) {
        r = 0 | Math.random() * 16
        uuid[i] = chars[(i === 19) ? (r & 0x3) | 0x8 : r]
      }
    }
  }

  return uuid.join('')
}
// 获取对象的具体类型
export function getDataType(data) {
  if (data === null) {
    return 'null';
  }
  if (data instanceof Array) {
    return 'Array';
  }
  if (data instanceof Object) {
    return 'Object';
  }
  return 'param is no object type';
}

// tree扁平化处理
export function treeTraversal(treeList) {
  let list = [];
  const loop = (tree) => {
    tree.map((item) => {
      const children = item.children ? item.children : '';
      delete item.children;
      list = [...list, item];
      return children ? loop(children) : '';
    });
  };
  loop(deepClone(treeList));
  return list;
}

//根据dbid返回指定的字段 可满足filed的格式'cycleTime'或多级'processSegment.cycleTime'
export function findFiled(val, filed, data = []) {
  if (!val) {
    return '';
  }
  const list = data[0] && data[0].children ? treeTraversal(data) : data;
  const nameArr = list.filter(({ dbid }) => dbid === val);
  if (!nameArr.length) {
    return '';
  }

  return lodashGet(nameArr[0], filed);
}

// 设置URL上的querystring
export function setQueryString(val) {
  let querystring = JSON.parse(localStorage.getItem('queryString'))
  querystring = querystring || {}
  const { query, hash } = router.app.$route
  const { name } = router.currentRoute
  const newQuery = { ...query, ...val }
  querystring[name] = newQuery
  localStorage.setItem('queryString', JSON.stringify(querystring))
  router.replace({ query: newQuery, hash })
}

// 获取URL上querystring 格式化成对象格式(vue-router)
export function getQueryString(data) {
  const { currentRoute, app } = router;
  const { name } = currentRoute;
  const val = deepClone(data);
  const { query } = app.$route;
  const queryKeys = Object.keys(query);
  if (queryKeys.length) {
    Object.keys(val)
      .forEach((key) => {
        if (queryKeys.find(queryKey => queryKey === key)) {
          const item = query[key];
          if (getDataType(val[key]) === 'Array' && getDataType(item) !== 'Array') {
            val[key] = !item ? [] : [item];
          } else if (item === 'true') {
            val[key] = true;
          } else if (item === 'false') {
            val[key] = false;
          } else if (item) {
            val[key] = item;
          }
        }
      });
    return JSON.parse(JSON.stringify(val), (k, v) => {
      v = v && typeof v === 'string' && !Number.isNaN(Number(v)) ? Number(v) : v;
      return v;
    });
  }

  return val;
}

//判断是否为浅色
export function isLight(color) {
  if (!color) {
    return false;
  }
  const colorRgb = () => {
    // 16进制颜色值的正则
    const reg = /^#([0-9a-fA-f]{3}|[0-9a-fA-f]{6})$/;
    // 把颜色值变成小写
    color = color.toLowerCase();
    if (reg.test(color)) {
      // 如果只有三位的值,需变成六位,如:#fff => #ffffff
      if (color.length === 4) {
        let colorNew = '#';
        for (let i = 1; i < 4; i += 1) {
          colorNew += color.slice(i, i + 1)
            .concat(color.slice(i, i + 1));
        }
        color = colorNew;
      }
      // 处理六位的颜色值,转为RGB
      const colorChange = [];
      for (let i = 1; i < 7; i += 2) {
        colorChange.push(parseInt(`0x${color.slice(i, i + 2)}`, 0));
      }
      return colorChange;
    }
    const list = [];
    color.replace(/[0-9]*(\.[0-9]*)?/g, (e) => {
      if (e !== '') {
        list.push(Number(e));
      }
    });

    return list;
  };
  const [r, g, b] = colorRgb();

  return r * 0.299 + g * 0.578 + b * 0.114 >= 192;
}

/**
 * 根据对象中的一个字段分组
 * @param groupType:Array|Object返回值格式(数组型数组或者对象型数组)
 * @param objModel model1|model2 对象型数组的格式
 * 数组型数组返回值格式为
 * [
 * [{x:0.1,y:0.3},{x:0.1,y:0.5}]
 * ...
 * ]
 *
 * 对象型数组model1返回值格式为
 * [
 *  {code:'0.1',valueList:[{x:0.1,y:0.3},{x:0.1,y:0.5}]}
 * ...
 * ]
 *  对象型数组model2返回值格式为
 * [
 *  {code:'0.1',valueList:[0.3,0.5]}
 * ...
 * ]
 * @returns {Array}
 */

export function grouping(data, key, groupType = 'Array', objModel = 'model1') {
  const newArray = []
  data
    .map((item) => [item])
    .forEach(([{ ...item }]) => {
      const flag = newArray.find(([{ ...o }]) => xeGet(o, key) === xeGet(item, key))
      if (!flag) {
        newArray.push([{ ...item }])
      } else {
        newArray.forEach(([{ ...y }], index) => {
          if (xeGet(y, key) === xeGet(item, key)) {
            newArray[index].push(item)
          }
        })
      }
    })
  if (groupType !== 'Array') {
    // 返回对象型数组
    const ObjArray = []
    newArray.forEach((item) => {
      const obj = {}
      obj.groupName = xeGet(item[0], key)
      if (objModel === 'model1') {
        obj.valueList = item
      } else {
        obj.valueList = item.map((item) => item.y)
      }
      ObjArray.push(obj)
    })
    // console.log('ObjArray===', ObjArray)
    return ObjArray
  }
  // console.log("newArray===", newArray);
  // 返回数组型数组
  return newArray
}

/**
 *  字节单位动态转换
 * @param bytes 字节数值
 * @returns {String}
 *  */
export function bytesUnitTransfer(bytes) {
  if (bytes) {
    if (String(bytes) === '0') return '0 B'
    const k = 1024
    const sizes = ['B', 'KB', 'MB', 'GB', 'TB', 'PB', 'EB', 'ZB', 'YB']
    const i = Math.floor(Math.log(bytes) / Math.log(k))
    if (isNaN(i)) {
      return '-'
    } else {
      return (bytes / Math.pow(k, i)).toFixed(2) + ' ' + sizes[i]
    }
  } else {
    return '-'
  }
}

function getDigit(integer) {
  let digit = -1
  while (integer >= 1) {
    digit++
    integer = integer / 10
  }
  return digit
}
// 数字过大 进行单位转换
function addWan(integer, number, mutiple, decimalDigit) {
  const digit = getDigit(integer)
  if (digit > 3) {
    var remainder = digit % 8
    if (remainder >= 5) {
      // ‘十万’、‘百万’、‘千万’显示为‘万’
      remainder = 4
    }
    return Math.round(number / Math.pow(10, remainder + mutiple - decimalDigit)) / Math.pow(10, decimalDigit) + '万'
  } else {
    return Math.round(number / Math.pow(10, mutiple - decimalDigit)) / Math.pow(10, decimalDigit)
  }
}
/**
 *  数字单位动态转换
 * @param number 数值
 * @param decimalDigit 小数位
 * @returns {string}
 *  */
export function numberUnitTransfer(number, decimalDigit) {
  decimalDigit = decimalDigit == null ? 2 : decimalDigit
  const integer = Math.floor(number)
  const digit = getDigit(integer)
  // ['个', '十', '百', '千', '万', '十万', '百万', '千万'];
  const unit = []
  if (digit > 3) {
    var multiple = Math.floor(digit / 8)
    if (multiple >= 1) {
      const tmp = Math.round(integer / Math.pow(10, 8 * multiple))
      unit.push(addWan(tmp, number, 8 * multiple, decimalDigit))
      for (let i = 0; i < multiple; i++) {
        unit.push('亿')
      }
      return unit.join('')
    } else {
      return addWan(integer, number, 0, decimalDigit)
    }
  } else {
    return number
  }
}

// 数字取整
export const numRevise = (num, type) => {
  // if (!isNull(num) && /^[0-9]+(\.[0-9]+)?$/.test(num)) {
  if (!isNull(num) && !isNaN(num)) {
    if (isNull(type)) {
      // 丢弃小数部分,保留整数部分
      return parseInt(num)
    }
    if (type === 'ceil' || type === 'floor' || type === 'round') {
      // ceil向上取整; floor向下取整; round四舍五入
      return Math[type](num)
    }
  }
  return undefined
}

文件处理

// 获取file格式图片的宽高
export const getImgWidthAndH = function (file) {
  return new Promise((resolve, reject) => {
    const reader = new FileReader()
    reader.readAsDataURL(file)
    reader.onload = function (event) {
      const base64 = event.target.result
      const img = new Image()
      img.src = base64
      img.onload = function () {
        resolve({ width: img.width, height: img.height })
      }
    }
  })
}


// 文件转base64
export function getBase64(file) {
  return new Promise(function (resolve, reject) {
    const reader = new FileReader()
    let imgResult = ''
    reader.readAsDataURL(file)
    reader.onload = function () {
      imgResult = reader.result
    }
    reader.onerror = function (error) {
      reject(error)
    }
    reader.onloadend = function () {
      resolve(imgResult)
    }
  })
}
// 图片base64转图片
export function getBase64ToUrl(base64) {
  const changebase64 = 'data:image/jpg;base64,' + base64.replace(/[\r\n]/g, '')
  return changebase64
}

// 下载文件流处理
export function blobToFile(res, fileName, type = 'application/vnd.ms-excel') {
  const link = document.createElement('a')
  const blob = new Blob([res.data], {
    type
  })
  link.style.display = 'none'
  link.href = URL.createObjectURL(blob)
  if (fileName) {
    link.download = fileName // 下载的文件名
  } else {
    link.download = res.headers['content-disposition']
    const name = decodeURI(escape(link.download.split('=')[1])) // 乱码转义
    link.download = name // 下载的文件名
  }
  document.body.appendChild(link)
  link.click()
  document.body.removeChild(link)
}

// 获取文件(流)头信息
export const getFileMIME = file => new Promise((resolve) => {
  const reader = new FileReader()
  reader.readAsArrayBuffer(file)
  reader.onload = (e) => {
    const typeHex = (new Uint8Array(reader.result)).subarray(0, 4).reduce((str, index) => str + index.toString(16), '').toLowerCase()
    resolve(typeHex ? FILE_MIME_HEX[typeHex] : '')
  }
})

tree合集

// 根据指定字段获取符合的项
export function getChildren(val, tree, key = 'dbid') {
  let hasFound = false; // 表示是否有找到id值
  let result = null;
  const fn = (data) => {
    if (Array.isArray(data) && !hasFound) {
      // 判断是否是数组并且没有的情况下,
      data.forEach((item) => {
        if (item[key] === val) {
          // 数据循环每个子项,并且判断子项下边是否有id值
          result = item; // 返回的结果等于每一项
          hasFound = true; // 并且找到id值
        } else if (item.children) {
          fn(item.children); // 递归调用下边的子项
        }
      });
    }
  };
  fn(tree); // 调用一下
  return result;
}

// 获取指定项tree轨迹
export const getTrajectory = function (tree, itemIndex = 0, key = 'id') {
  const treePath = []
  const mapTree = (node, innerVal, innerKey) => {
    innerVal.push(node[innerKey])
    if (node.children) {
      mapTree(node.children[itemIndex], innerVal, innerKey)
    }
  }
  mapTree(tree[itemIndex], treePath, key)

  return treePath
}

//  根据具体值,找tree轨迹
export const getPathByKey = (val, data, key = 'id') => {
  let result = [] // 记录路径结果
  const traverse = (curVal, path, data) => {
    if (data.length === 0) {
      return
    }
    for (const item of data) {
      path.push(item)
      if (item[key] === curVal) {
        result = JSON.parse(JSON.stringify(path))
        return
      }
      const children = Array.isArray(item.children) ? item.children : []
      traverse(curVal, path, children) // 遍历
      path.pop() // 回溯
    }
  }
  traverse(val, [], data)
  return result
}

//获取tree叶子节点
export function getAllLeafNode(tree, key = 'dbid') {
  const val = [];
  const mapTree = (node, innerVal, innerKey) => {
    node.forEach((item) => {
      if (!item.children) {
        innerVal.push(item[innerKey]);
      } else {
        mapTree(item.children, innerVal, innerKey);
      }
    });
  };
  mapTree(tree, val, key);
  return val;
}
//获取tree 的指定字段(所有层级)
export function getTreeAppointField(tree, key = 'dbid') {
  const val = [];
  const mapTree = (node, innerVal, innerKey) => {
    node.forEach((item) => {
      innerVal.push(item[innerKey]);
      if (item.children) {
        mapTree(item.children, innerVal, innerKey);
      }
    });
  };
  mapTree(tree, val, key);
  return val;
}

// 向tree中的每一项添加指定数据
/**
 * @param newData:向每一项填加的属性
 * @param uuid:是否要向每一项填加唯一标识
 * @param childrenField: 下级的字段名标识
 */
export function treeTraversalToAdd(treeList, newData, uuid = true, childrenField = 'children') {
  const addKey = (arr) => {
    if (uuid) {
      return arr?.map((item) => ({
        uuid: createUuid(),
        ...item,
        ...newData,
        [childrenField]: item[childrenField] ? addKey(item[childrenField]) : []
      }))
    }
    return arr?.map((item) => ({
      ...item,
      ...newData,
      [childrenField]: item[childrenField] ? addKey(item[childrenField]) : []
    }))
  }
  const newTree = addKey(deepClone(treeList))

  return newTree
}

/**
 * 向tree数据符合条件的子项前添加
 * @param newData:要添加的新数据
 * @param type:level添加平级、sub添加下级
 * @param first:是否是第一个元素
 */

export function addTreeChildren(val, tree, newData = {}, type = 'level', key = 'aid', first = false) {
  const newTree = deepClone(tree)
  let hasFound = false // 表示是否有找到值
  const traversal = data => {
    for (let i = 0; i < data.length; i++) {
      if (hasFound) return
      const info = data[i]
      if (lodashGet(info, key) !== val && info.children) {
        traversal(info.children)
      } else if (lodashGet(info, key) === val) {
        hasFound = true // 找到值
        const index = data.findIndex(item => val === lodashGet(item, key))
        if (type === 'level') {
          // 向平级添加
          if (first) {
            data.splice(index, 0, newData)
            return
          }
          data.splice(index + 1, 0, newData)
        } else {
          // 向下级添加(实则是替换当前项,向子级添加项)
          const dealData = { ...data[index], children: [newData, ...data[index]?.children] }
          data.splice(index, 1, dealData)
        }
      }
    }
  }
  traversal(newTree)
  return newTree
}

// 删除tree数据符合条件的子项
export function delTreeChildren(val, tree, key = 'aid') {
  const newTree = deepClone(tree)
  const traversal = data => {
    for (let i = 0; i < data.length; i++) {
      const info = data[i]
      if (lodashGet(info, key) !== val && info.children) {
        traversal(info.children)
      } else if (lodashGet(info, key) === val) {
        const index = data.findIndex(item => val === item[key])
        data.splice(index, 1)
        i--
      }
    }
  }
  traversal(newTree)
  return newTree
}

时间处理合集(moment.js)

//处理时间拼接毫秒和正八区和负八区
export function formatTime(timeStr, format = 'YYYY-MM-DDTHH:mm:ss.SSSZ') {
  const getFormatString = () => {
    switch (format) {
      case 'yyyy-MM-dd':
      case 'YYYY-MM-dd':
        return 'YYYY-MM-DD';
      case 'yyyy-MM-dd HH:mm:ss':
      case 'YYYY-MM-dd HH:mm:ss':
        return 'YYYY-MM-DDTHH:mm:ss.SSSZ';
      default:
        return format;
    }
  };
  if (!timeStr) {
    return '';
  } //当点击×的时候 传过来null
  if (timeStr[0] && timeStr[1]) {
    return [moment(timeStr[0])
      .format(getFormatString()), moment(timeStr[1])
      .format(getFormatString())];
  }
  return moment(timeStr)
    .format(getFormatString());
}
// 截取当前时间往前1(0,1,2,3,4....)个周(年years,月months,天days)
export function subtractCurrentTime(amount = 1, unit = 'weeks') {
  return [formatTime(moment()
    .subtract(amount, unit)), formatTime(moment())];
}

// 截取指定日期前或后或(前和后)1(0,1,2,3,4....)个周(年years,月months,天days)
// type :1前 2后 3前和后
export function getDatePreAndNext(amount = 1, unit = 'weeks', data = '', type = 1) {
  const date = !data
    ? moment()
      .format('YYYY-MM-DD')
    : moment(data)
      .format('YYYY-MM-DD')
  if (type === 0) {
    return [formatTime(moment(date)
      .subtract(amount, unit)), formatTime(moment(`${date} 23:59:59`))]
  } if (type === 1) {
    return [formatTime(moment(date)), formatTime(moment(`${date} 23:59:59`)
      .add(amount, unit))]
  }
  return [
    formatTime(moment(currentDate)
      .subtract(amount, unit)),
    formatTime(moment(`${currentDate} 23:59:59`)
      .add(amount, unit))
  ]
}

//根据时间和周期获取下一次时间
export function getTimeByDate(amount = 2, unit = 'Hours', date = new Date()) {
  const dDate = date || new Date();
  const currentDate = moment(dDate)
    .format('YYYY-MM-DD HH:mm:ss');
  return formatTime(moment(currentDate)
    .add(amount, unit));
}

//截取时间1(0,1,2,3,4....)个周(年years,月months,天days)开始时间0时至结束时间24时
export function subtractStartAndEnd(amount = 1, unit = 'weeks') {
  const [startDate, endDate] = subtractCurrentTime(amount, unit);
  return [formatTime(moment(startDate)
    .startOf(unit)), formatTime(moment(endDate)
    .endOf(unit))];
}
// 截取当天前后1(0,1,2,3,4....)个月(年years,周weeks,天days)
//前后时间间隔不同,第一个参数传array[1,2]:取时为1个月前2个月后
export function subtractPreAndNext(amount = 1, unit = 'months', format = 'YYYY-MM-DD HH:mm:ss') {
  const date = moment()
    .format('YYYY-MM-DD');
  if (Array.isArray(amount)) {
    return [
      formatTime(moment(date)
        .subtract(amount[0], unit), format),
      formatTime(moment(`${date} 23:59:59`)
        .add(amount[1], unit), format),
    ];
  }
  return [formatTime(moment(date)
    .subtract(amount, unit)), formatTime(moment(`${date} 23:59:59`)
    .add(amount, unit))];
}
// 获取一段日期的中间日期
export function enumerateDaysBetweenDates(startDate, endDate) {
  const dates = [];
  const currDate = moment(startDate)
    .startOf('day');
  const lastDate = moment(endDate)
    .startOf('day');

  while (currDate.add(1, 'days')
    .diff(lastDate) < 0) {
    dates.push(currDate.clone()
      .toDate());
  }
  const { length } = dates;
  const i = Math.ceil(length / 2 - 1);
  return formatTime(dates[i]);
}
//计算时间差
export function durationTime(startTime, endTime, unit = 'minute') {
  if (!startTime || !endTime) {
    return '';
  }
  const startDate = timeFormat(startTime);
  const seconds = moment(endTime, 'YYYY-MM-DD HH:mm:ss')
    .diff(startDate, 'seconds');
  let duration = '';
  switch (unit) {
    case 'minute':
      duration = `${seconds / 60} 分钟`;
      break;
    case 'hours':
      duration = `${seconds / 2600} 小时`;
      break;
    default:
      break;
  }
  return duration;
}

//获取当前月初到月底
//获取当天,00:00:00到23:59:59,(unit=day)
//获取当前所在周,周一到到周日,(unit=week)
//获取当前所在月,月初到月底,(unit=month)
//获取当前所在年,年初到年末,(unit=year)
export function dateStartAndEnd(unit = 'month', date = new Date(), format = 'YYYY-MM-DDTHH:mm:ss.SSSZ') {
  const currentDate = moment(date)
    .format('YYYY-MM-DD');
  return [formatTime(moment(currentDate)
    .startOf(unit), format), formatTime(moment(currentDate)
    .endOf(unit), format)];
}

//获取当月初到当天23:59:59
export function monthStartAndSameDay() {
  const date = moment()
    .format('YYYY-MM-DD');

  return [formatTime(moment()
    .startOf('month')), formatTime(moment(`${date} 23:59:59`))];
}

//获取当前天的 日期格式 20200430 字符串
export function getStandardIntervalString(unit = 'month', date = undefined) {
  switch (unit) {
    case 'day': {
      return moment(date)
        .format('YYYYMMDD');
    }
    case 'month': {
      return moment(date)
        .format('YYYYMM');
    }
    case 'year': {
      return moment(date)
        .format('YYYY');
    }
  }
}

数组操作

// 对象数组根据某一个字段去重
export const getArrayUnique = function (arr, key) {
  const newArrId = []
  const newArrObj = []
  arr.forEach((item) => {
    if (!newArrId.includes(item[key])) {
      newArrId.push(item[key])
      newArrObj.push(item)
    }
  })
  return newArrObj
}
// 根据某一字段求arr2对象数组的差集
export const getArrayDifference = function (arr1, arr2, key) {
  const result = []
  for (let i = 0; i < arr2.length; i++) {
    const obj = arr2[i]
    const unique1 = obj[key]
    let isExist = false
    for (let j = 0; j < arr1.length; j++) {
      const aj = arr1[j]
      const unique2 = aj[key]
      if (unique2 === unique1) {
        isExist = true
        break
      }
    }
    if (!isExist) {
      result.push(obj)
    }
  }
  return result
}

// 将数组拼成tree
export function arrayToTree(arr) {
  const map = {}
  const result = []
  let node
  for (let i = 0; i < arr.length; i++) {
    map[arr[i].id] = arr[i]
    arr[i].children = []
  }
  for (let i = 0; i < arr.length; i++) {
    node = arr[i]
    if (node.parentId) {
      map[node.parentId].children.push(node)
    } else {
      result.push(node)
    }
  }
  return result
}

/**
 * 根据数组中对象的某个字段排序
 * @param props 进行排序的字段
 * @param type 排序规则 ascend 升序 descend降序
 * @returns {*}
 */
export function sortBy(props, type) {
  return function (a, b) {
    if (type === 'ascend') {
      return b[props] - a[props]
    } else if (type === 'descend') {
      return a[props] - b[props]
    }
  }
}
  • 5
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值