class commonUtils {
|
serverUrl
|
audioContext // 全局音频实例
|
requestLock // 请求控制锁(同步)
|
constructor() {
|
this.serverUrl = uni.getStorageSync('serverUrl') || 'http://47.96.97.237/API/';
|
this.audioContext = null;
|
this.requestLock = false
|
}
|
|
setServerUrl(url) {
|
this.serverUrl = url
|
}
|
|
getServerUrl() {
|
return this.serverUrl
|
}
|
|
|
|
// 防抖函数
|
debounce(func, delay, immediate = false) {
|
let timer = null;
|
return function() {
|
const context = this;
|
const args = arguments;
|
|
const callNow = immediate && !timer;
|
// 如果定时器已经存在,清除它
|
if (timer) {
|
clearTimeout(timer);
|
}
|
|
// 设置一个新的定时器
|
timer = setTimeout(() => {
|
if (!immediate) {
|
func.apply(context, args);
|
}
|
timer = null;
|
}, delay);
|
|
// 配置立即执行
|
if (callNow == true) {
|
func.apply(context, args)
|
}
|
};
|
}
|
|
// 判空函数
|
isEmpty(value, zeroIsEmpty = false, falseIsEmpty = false) {
|
let val = value
|
// 检查是否为null 或者 undefind
|
if (val === null || val === undefined) {
|
return true;
|
}
|
//如果字符串全部是由数字构成的,则转化为数字型
|
if (this.isAllDigits(val) === true) {
|
val = Number(val)
|
}
|
|
// 是否是字符串类型
|
if (typeof val === 'string') {
|
return val.trim().length === 0;
|
}
|
|
// 是否是数组
|
if (Array.isArray(val)) {
|
return val.length === 0;
|
}
|
|
//是否是对象
|
if (typeof val === 'object') {
|
return Object.keys(val).length === 0;
|
}
|
|
// 数字类型默认不为空
|
if (typeof val === 'number') {
|
// 数字为0视为空
|
if (zeroIsEmpty == true) {
|
if (val === 0) {
|
return true
|
}
|
}
|
return false
|
}
|
|
// 布尔类型默认不为空
|
if (typeof val === 'boolean') {
|
// false值视为空
|
if (falseIsEmpty == true) {
|
if (val === 0) {
|
return true
|
}
|
}
|
return false;
|
}
|
}
|
|
// 判断是否全是数字
|
isAllDigits(str) {
|
return /^\d+$/.test(str);
|
}
|
|
isJson(str) {
|
try {
|
JSON.parse(str)
|
return true
|
} catch {
|
return false
|
}
|
}
|
|
timeClock(callback, delay) {
|
let timeoutId;
|
let isRunning = false;
|
|
function interval() {
|
timeoutId = setTimeout(() => {
|
callback();
|
clearTimeout(timeoutId); // 立即清除当前定时器ID
|
if (isRunning) {
|
interval();
|
}
|
}, delay);
|
}
|
|
return {
|
start() {
|
if (!isRunning) {
|
isRunning = true;
|
interval();
|
}
|
},
|
stop() {
|
if (isRunning) {
|
isRunning = false;
|
clearTimeout(timeoutId);
|
}
|
}
|
};
|
}
|
|
deepClone(target, map = new WeakMap()) {
|
// 处理原始值和函数(typeof 数组会返回object)
|
if (typeof target !== 'object' || target === null) {
|
return target;
|
}
|
|
// 处理循环引用
|
if (map.has(target)) {
|
return map.get(target);
|
}
|
|
let clone;
|
|
// 处理数组
|
if (Array.isArray(target)) {
|
clone = [];
|
map.set(target, clone);
|
target.forEach((item, index) => {
|
clone[index] = deepClone(item, map);
|
});
|
return clone;
|
}
|
|
// 处理日期对象
|
if (target instanceof Date) {
|
clone = new Date(target.getTime());
|
map.set(target, clone);
|
return clone;
|
}
|
|
// 处理正则表达式
|
if (target instanceof RegExp) {
|
clone = new RegExp(target);
|
map.set(target, clone);
|
return clone;
|
}
|
|
// 处理函数 (直接使用函数的引用)
|
if (typeof target === 'function') {
|
return target;
|
}
|
|
// 处理其他对象(普通对象、类实例等)
|
clone = Object.create(Object.getPrototypeOf(target));
|
map.set(target, clone);
|
|
// 获取所有属性(包括 Symbol 类型)
|
const allKeys = [...Object.getOwnPropertyNames(target), ...Object.getOwnPropertySymbols(target)];
|
|
allKeys.forEach(key => {
|
const descriptor = Object.getOwnPropertyDescriptor(target, key);
|
if (descriptor && descriptor.enumerable) {
|
// 递归复制属性值
|
clone[key] = deepClone(target[key], map);
|
}
|
});
|
|
return clone;
|
}
|
|
// uni-app 使用 封装请求函数 使用传统函数当作回调需要传that,箭头函数不需要
|
doRequest(url, data, resFunction, errFunction, method, that) {
|
that = that || this;
|
let errorTip = null;
|
uni.showLoading({
|
title: '加载中...'
|
})
|
uni.request({
|
method: method || "GET",
|
url: this.serverUrl + url,
|
data: data || "",
|
success: (res) => {
|
if (typeof resFunction === 'function') {
|
resFunction.call(that, res)
|
} else if (typeof errFunction === 'undefined' || errFunction === null) {
|
return
|
} else {
|
throw new TypeError("访问成功回调函数类型不为函数或者空!")
|
}
|
},
|
fail: (err) => {
|
console.error(err)
|
errorTip = () => {
|
uni.showToast({
|
icon: "none",
|
title: err.errMsg || err.data.message || "接口异常!",
|
duration: 2000
|
})
|
}
|
if (typeof errFunction === 'function') {
|
errFunction.call(that, err)
|
} else if (typeof errFunction === 'undefined' || errFunction === null) {
|
return
|
} else {
|
throw new TypeError("访问失败回调函数类型不为函数或者空!")
|
}
|
|
},
|
complete() {
|
setTimeout(() => {
|
uni.hideLoading()
|
if (errorTip != null) {
|
errorTip()
|
}
|
}, 1000)
|
}
|
})
|
}
|
|
doRequest2({
|
url,
|
data,
|
resFunction,
|
errFunction,
|
method,
|
that
|
}) {
|
that = that || this;
|
let errorTip = null;
|
uni.showLoading({
|
title: '加载中...'
|
})
|
uni.request({
|
method: method || "GET",
|
url: this.serverUrl + url,
|
data: data || "",
|
success: (res) => {
|
if (typeof resFunction === 'function') {
|
resFunction.call(that, res)
|
} else if (typeof errFunction === 'undefined' || errFunction === null) {
|
return
|
} else {
|
throw new TypeError("访问成功回调函数类型不为函数或者空!")
|
}
|
},
|
fail: (err) => {
|
console.error(err)
|
errorTip = () => {
|
uni.showToast({
|
icon: "none",
|
title: err.errMsg || err.data.message || "接口异常!",
|
duration: 2000
|
})
|
}
|
if (typeof errFunction === 'function') {
|
errFunction.call(that, err)
|
} else if (typeof errFunction === 'undefined' || errFunction === null) {
|
return
|
} else {
|
throw new TypeError("访问失败回调函数类型不为函数或者空!")
|
}
|
|
},
|
complete: () => {
|
|
setTimeout(() => {
|
uni.hideLoading()
|
if (errorTip != null) {
|
errorTip()
|
}
|
}, 1000)
|
}
|
})
|
}
|
|
// 同步执行请求 (配合await或者then)
|
async doRequest2Sync({
|
url,
|
data,
|
method,
|
}) {
|
if (this.requestLock) {
|
console.log("该请求被锁定,不能重复请求!!!")
|
return
|
}
|
this.requestLock = true
|
return new Promise((resolve, reject) => {
|
// that = that || this;
|
let errorTip = null;
|
uni.showLoading({
|
title: '加载中...'
|
})
|
uni.request({
|
method: method || "GET",
|
url: this.serverUrl + url,
|
data: data || "",
|
success: (res) => {
|
resolve(res)
|
},
|
fail: (err) => {
|
reject(err)
|
},
|
complete: () => {
|
// 释放请求锁
|
this.requestLock = false
|
uni.hideLoading()
|
}
|
})
|
})
|
}
|
//没有添加锁的异步查询
|
async doRequest2Async({
|
url,
|
data,
|
method,
|
}) {
|
return new Promise((resolve, reject) => {
|
// that = that || this;
|
let errorTip = null;
|
uni.showLoading({
|
title: '加载中...'
|
})
|
uni.request({
|
method: method || "GET",
|
url: this.serverUrl + url,
|
data: data || "",
|
success: (res) => {
|
resolve(res)
|
},
|
fail: (err) => {
|
reject(err)
|
},
|
complete: () => {
|
uni.hideLoading()
|
}
|
})
|
})
|
}
|
|
stringToBoolean(str) {
|
// 忽略大小写的转换
|
return str?.toLowerCase() === "true";
|
}
|
|
// uni-app 播放音频封装
|
playSound(e) {
|
const innerAudioContext = uni.createInnerAudioContext();
|
if (e == 1) {
|
innerAudioContext.src = '/static/success.wav';
|
} else {
|
innerAudioContext.src = '/static/jingbao.wav';
|
}
|
innerAudioContext.play(); // 播放音频
|
|
innerAudioContext.onPlay(() => {
|
console.log('开始播放');
|
});
|
innerAudioContext.onError((res) => {
|
console.log(res.errMsg);
|
console.log(res.errCode);
|
});
|
innerAudioContext.onPause(function() {
|
console.log('播放暂停,销毁');
|
innerAudioContext.destroy();
|
});
|
|
}
|
// playSound(e) {
|
// // 全局维护一个音频实例,防止缓存溢出
|
// if (this.audioContext) {
|
// this.audioContext.destroy();
|
// }
|
// this.audioContext = uni.createInnerAudioContext();
|
// if (e == 1) {
|
// this.audioContext.src = '/static/success.wav';
|
// } else {
|
// this.audioContext.src = '/static/jingbao.wav';
|
// }
|
// this.audioContext.play(); // 播放音频
|
//
|
// // 播放结束后销毁实例
|
// this.audioContext.onEnded(() => {
|
// this.audioContext.destroy();
|
// this.audioContext = null;
|
// });
|
//
|
// // 错误处理
|
// this.audioContext.onError((err) => {
|
// uni.showToast({
|
// icon: 'none',
|
// title: `音频播放错误: ${err}`
|
// })
|
//
|
// this.audioContext.destroy();
|
// this.audioContext = null;
|
// });
|
// }
|
|
|
showTips({
|
type,
|
message,
|
title,
|
duration
|
}) {
|
if (!message) {
|
return
|
}
|
|
if (message.length < 20) {
|
return uni.showToast({
|
icon: type || 'none',
|
title: message
|
})
|
}
|
|
return uni.showModal({
|
title: title,
|
content: message,
|
showCancel: false
|
})
|
}
|
|
replaceWithFunction(str, handler) {
|
return str.replace(/\{(.+?)\}/g, (match, key) => {
|
// 调用处理函数,传入匹配到的键
|
return handler(key, match);
|
});
|
}
|
|
fieldListFilterRole({FieldList, ExcludeKeys = [] ,RoleList = null}) {
|
if(!RoleList) {
|
RoleList = [
|
/^[a-zA-Z]+$/,
|
/id$/i
|
]
|
}
|
if(!Array.isArray(RoleList)){
|
return {
|
status: false,
|
data: null,
|
Message: "过滤字段列表失败,规则必须是数组。"
|
}
|
}
|
|
let FieldListCache = Array(...FieldList)
|
|
RoleList.forEach(role => {
|
FieldListCache = FieldListCache.filter(elem => !role.test(elem.ColmCols))
|
})
|
|
FieldListCache = FieldListCache.filter(elem => !ExcludeKeys.includes(elem.ColmCols))
|
return {
|
status: true,
|
data: FieldListCache,
|
Message: ""
|
}
|
}
|
|
emptyValueFilter(item, fieldList){
|
return fieldList.filter(e => {
|
return item[e.ColmCols]
|
})
|
}
|
}
|
|
export const CommonUtils = new commonUtils()
|