UNPKG

fastlion-amis

Version:

一种MIS页面生成工具

385 lines (359 loc) 11.3 kB
import FileSaver from "file-saver"; import { Shell } from "../../../utils/shell"; // 用于生成唯一id以关联主从表 const uuid = () => { const temp_url = URL.createObjectURL(new Blob()); const uuid = temp_url.toString(); URL.revokeObjectURL(temp_url); return uuid.substr(uuid.lastIndexOf("/") + 1); } // 用于添加并合并多个className const classNames = (...names: any[]) => { let currentNames: string[] = []; names.forEach((name) => { if (name) currentNames.push(name) }); return currentNames.join(' '); } const extractTemplate = (str: {}) => { const regex: RegExp = /\$\{([^}]+)\}/g; return Object.values(str).map((_str: string) => { return _str.replace(regex, (match: any, item: any) => { return item }) }) } // 单双击同时存在的情况,直接使用ondblclick会同时触发两次单击事件,延迟单击执行时间 const singleAndDoubleClick = (() => { let isClick = false, clickNum = 0; return (obj: { singleClick?: Function, doubleClick?: Function, params?: any }) => { const { singleClick, doubleClick, params } = obj if (!doubleClick) { return singleClick && singleClick(params) } clickNum++ if (isClick) return isClick = true setTimeout(() => { if (clickNum > 1) { doubleClick && doubleClick(params) } else { singleClick && singleClick(params) } clickNum = 0 isClick = false }, 300); } })() // 是否是图片格式 const IMG_SUFFIX = ['jpg', 'jpeg', 'png', 'bmp', 'gif', 'tif', 'heic', 'webp'] const isImg = (fileName: string) => { if (!fileName || !fileName.includes('.')) return true const suffix = fileName.split('.').pop() || '' return IMG_SUFFIX.includes(suffix.toLocaleLowerCase()) } // 是否是视频格式 const right_typ = ["wav", "mp4", "avi", "mp3"] const isCon = (fileName: string) => { if (!fileName || !fileName.includes('.')) return true const suffix = fileName.split('.').pop() || '' return right_typ.includes(suffix.toLocaleLowerCase()) } // 是否是pdf格式 const isPdf = (str: string) => { return /^\S+(.pdf)$/i.test(str) } // 是否是Excel文件 const isExcel = (str: string) => { return /^\S+(.xls|.xlsx)$/i.test(str) } // 是否xls(x)文件 const isXlsx = (str: string) => { return /^\S+(.xls|.xlsx|.csv)$/i.test(str) } // 是否媒体文件 const isMedia = (str: string) => { return /^\S+(.mp4|.avi|.mp3|.wav)$/i.test(str); } // 文件格式地址 const iconMap = { // annex: './public/images/icon-annex-fill.png', doc: ['#icon-toolword', '#14A9DA'], excel: ['#icon-toolexcel', '#13B478'], img: ['#icon-toolimage', '#DC3119'], music: ['#icon-toolaudio', '#8C181A'], pdf: ['#icon-toolpdf', '#8C181A'], ppt: ['#icon-toolppt', '#E34221'], txt: ['#icon-tooltxt', '#14A9DA'], video: ['#icon-toolmp', ''], zip: ['#icon-toolzip', ''], unknown: ['#icon-toolunknown', ''], // annex: './public/images/icon-annex-fill.png', // doc: './public/images/icon-doc-fill.png', // excel: './public/images/icon-excel-fill.png', // img: './public/images/icon-img-fill.png', // music: './public/images/icon-music-fill.png', // pdf: './public/images/icon-pdf-fill.png', // ppt: './public/images/icon-ppt-fill.png', // txt: './public/images/icon-txt-fill.png', // video: './public/images/icon-video-fill.png', // zip: './public/images/icon-zip-fill.png', } const getFileType = (fileName) => { const type = fileName?.split('.')?.pop() ?? ''; return type; } const getMediaIcon = (fileName: string) => { let icon = iconMap.doc; // let fileType = fileName?.split('.')?.pop() ?? ''; const fileType = getFileType(fileName); switch (fileType.toLocaleLowerCase()) { case 'doc': case 'docx': icon = iconMap.doc; break; case 'xls': case 'xlsx': icon = iconMap.excel; break; case 'ppt': case 'pptx': icon = iconMap.ppt; break; case 'zip': case 'rar': icon = iconMap.zip; break; case 'jpg': case 'jpeg': case 'png': case 'gif': case 'tif': case 'bmp': case 'webp': icon = iconMap.img; break; case 'txt': icon = iconMap.txt; break; case 'wav': case 'mp4': case 'avi': case 'mp3': icon = iconMap.video; break; case 'pdf': icon = iconMap.pdf; break; default: icon = iconMap.unknown; break; } return icon } // 文件夹大小,路径,文件夹名字,获取文件夹大小,导航条, const downFile = async (chunk: any, url: any, name: string | undefined | null, percent: any,) => { // 路径。分流大小3M const chunkSize: number = 3145728 chunk(url, chunkSize, name).then((res: any) => { if (res) { download(url, res, percent, chunkSize, name) .then(buffers => { const mime = "application/" + name?.split(".").pop() saveAs(buffers as Uint8Array, name as string, mime) }) } else { if (Shell.hasShell()) { Shell.download(url, name || ''); } else { downloadFile(url, name || '', true) } } }); } //下载不同源的图片 const downloadImage = async (url: string, filename: string | null | undefined) => { const response = await fetch(url, { method: 'GET', mode: 'cors' }); const blob = await response.blob(); const urlObject = URL.createObjectURL(blob); const link = document.createElement('a'); link.href = urlObject; link.download = filename || ''; link.click(); URL.revokeObjectURL(urlObject); // 清理工作 } // 文件下载--自lioncellfile迁徙 const downloadFile = (url: any, name: string | undefined | null, crossDomain?: boolean) => { return new Promise((resolve, reject) => { resolve('') }).then(res => { if(crossDomain) { downloadImage(url, name) } else { if (typeof url == 'object' && url instanceof Blob) { url = URL.createObjectURL(url); // 创建blob地址 } var aLink = document.createElement('a'); aLink.href = url; aLink.download = name || ''; // HTML5新增的属性,指定保存文件名,可以不要后缀,注意,file:///模式下不会生效 var event; if (window.MouseEvent) event = new MouseEvent('click'); else { event = document.createEvent('MouseEvents'); event.initMouseEvent('click', true, false, window, 0, 0, 0, 0, 0, false, false, false, false, 0, null); } aLink.dispatchEvent(event); } }) } // // 路径,文件大小,默认下载分流的大小,最大下载次数 const download = async (url: string, datacontent: number, percent: any, chunkSize = 524288, name: string | undefined | null, poolLimit = 5) => { const chunks = typeof chunkSize === "number" ? Math.ceil(datacontent / chunkSize) : 1; const results = await asyncPool( poolLimit, chunks, (i: number) => { let start = i * chunkSize; let end = i + 1 == chunks ? datacontent - 1 : (i + 1) * chunkSize - 1; return getBinaryContent(url, start, end, i, name, percent); }) const sortedBuffers = results.map((item: any) => { const Buffers = item.buffer return new Uint8Array(Buffers) }) return concatenate(sortedBuffers); } const asyncPool = async (poolLimit: number, array: any, iteratorFn: any,) => { const ret: any = []; // 存储所有的异步任务 const executing: any = []; // 存储正在执行的异步任务 for (let i = 0; i < array; i++) { // 调用iteratorFn函数创建异步任务 const p = Promise.resolve().then(() => iteratorFn(i)); ret.push(p); // 保存新的异步任务 // 当poolLimit值小于或等于总任务个数时,进行并发控制 if (poolLimit <= array) { // 当任务完成后,从正在执行的任务数组中移除已完成的任务 const e: any = p.then(() => executing.splice(executing.indexOf(e), 1)); executing.push(e); // 保存正在执行的异步任务 if (executing.length >= poolLimit) { await Promise.race(executing); // 等待较快的任务执行完成 } } } return Promise.all(ret); } const getBinaryContent = (url: string, start: number, end: number, i: number, name: any, percent?: any,) => { return new Promise((resolve, reject) => { try { const xhr = new XMLHttpRequest(); xhr.open("GET", url, true); xhr.setRequestHeader("range", `bytes=${start}-${end}`); // 请求头上设置范围请求信息 xhr.responseType = "arraybuffer"; // 设置返回的类型为arraybuffer xhr.onload = function () { percent(name); resolve({ index: i, // 文件块的索引 buffer: xhr.response, // 范围请求对应的数据 }); }; xhr.send(); } catch (err) { reject(new Error(err)); } }); } const concatenate = (arrays: any) => { if (!arrays.length) return null; const totalLength = arrays.reduce((acc: any, value: any) => acc + value.length, 0); const result = new Uint8Array(totalLength); let length = 0; for (let array of arrays) { result.set(array, length); length += array.length; } return result; } const saveAs = (buffers: Uint8Array, name: string, mime = "application/octet-stream") => { const blob = new Blob([buffers], { type: mime }); // const blobUrl = URL.createObjectURL(blob); // const a = document.createElement("a"); // a.download = name || ""; // a.href = blobUrl; // a.style.display = 'none' // document.body.appendChild(a) // a.click(); // a.remove(); // URL.revokeObjectURL(blobUrl); FileSaver.saveAs(blob, name); } const copy = async (text: string) => { const execCommandCopay = () => { let input = document.createElement("textarea"); input.style.cssText = 'position: absolute;top: -1px;height: 1px;width: 1px;'; input.value = text; document.body.appendChild(input); input.select(); document.execCommand("Copy"); document.body.removeChild(input); return; } if (!navigator.clipboard) { execCommandCopay() } else { // 如果出现错误 try { await navigator.clipboard.writeText(text).catch(() => { execCommandCopay() }) } catch { execCommandCopay() } } } const createRandomValue = () => { let r, v, n; n = 'yyxxxxxx-yyxx-'.replace(/[xy]/g, (c) => { (r = (Math.random() * 16) | 0), (v = c == 'x' ? r : (r & 0x3) | 0x8); return v.toString(16); }); return n + Date.now().toString(16); } const byteSize = (limit: number) => { var size = ""; if (limit < 0.1 * 1024) { size = limit.toFixed(2) + "B" } else if (limit < 0.1 * 1024 * 1024) { size = (limit / 1024).toFixed(2) + "KB" } else if (limit < 0.1 * 1024 * 1024 * 1024) { size = (limit / (1024 * 1024)).toFixed(2) + "MB" } else { size = (limit / (1024 * 1024 * 1024)).toFixed(2) + "GB" } var sizeStr = size + ""; var index = sizeStr.indexOf("."); var dou = sizeStr.substr(index + 1, 2) if (dou == "00") { return sizeStr.substring(0, index) + sizeStr.substr(index + 3, 2) } return size; } export { extractTemplate, classNames, singleAndDoubleClick, isImg, getMediaIcon, downloadFile, uuid, copy, isCon, isPdf, isExcel, isXlsx, isMedia, downFile, createRandomValue, byteSize, getFileType }