9.16下午更新 包含im
This commit is contained in:
+79
@@ -0,0 +1,79 @@
|
||||
import { V2NIMConst, NIM } from '../dist/nim.js'
|
||||
let appConfig = {
|
||||
// 用户的appkey
|
||||
// 用于在web demo中注册账号异步请求demo 服务器中使用
|
||||
test: {
|
||||
appkey: 'fe416640c8e8a72734219e1847ad2547',
|
||||
postUrl: 'https://apptest.netease.im'
|
||||
},
|
||||
online: {
|
||||
appkey: '885dea390870814acf3ba8558c717572',//885dea390870814acf3ba8558c717572 //45c6af3c98409b18a84451215d0bdd6e
|
||||
postUrl: 'https://app.netease.im'
|
||||
}
|
||||
}
|
||||
|
||||
const imLogin = async ()=>{
|
||||
let storage_token='';
|
||||
let storage_accid='';
|
||||
if (process.env.UNI_PLATFORM == "h5") {
|
||||
if (window.location.href.indexOf('dev') > -1) {
|
||||
storage_accid=uni.getetStorageSync('AUTH_YX_ACCID_App');
|
||||
storage_token=uni.setStorageSync('AUTH_YX_TOKEN_App');
|
||||
} else {
|
||||
storage_accid=uni.getStorageSync('DEV_AUTH_YX_ACCID_App');
|
||||
storage_token=uni.getStorageSync('DEV_AUTH_YX_TOKEN_App');
|
||||
}
|
||||
} else if(process.env.UNI_PLATFORM == "mp-weixin") {
|
||||
const {
|
||||
envVersion
|
||||
} = uni.getAccountInfoSync().miniProgram;
|
||||
if (envVersion == "release") {
|
||||
storage_accid=uni.getetStorageSync('AUTH_YX_ACCID_App');
|
||||
storage_token=uni.setStorageSync('AUTH_YX_TOKEN_App');
|
||||
} else {
|
||||
storage_accid=uni.getStorageSync('DEV_AUTH_YX_ACCID_App');
|
||||
storage_token=uni.getStorageSync('DEV_AUTH_YX_TOKEN_App');
|
||||
}
|
||||
}else{
|
||||
if (BASE_URL.indexOf('dev') == -1) {
|
||||
storage_accid=uni.getStorageSync('DEV_AUTH_YX_ACCID_App');
|
||||
storage_token=uni.getStorageSync('DEV_AUTH_YX_TOKEN_App');
|
||||
|
||||
} else {
|
||||
storage_accid=uni.getetStorageSync('AUTH_YX_ACCID_App');
|
||||
storage_token=uni.setStorageSync('AUTH_YX_TOKEN_App');
|
||||
}
|
||||
}
|
||||
const account =storage_accid;
|
||||
const token = storage_token;
|
||||
const appkey = appConfig.online.appkey
|
||||
const params1 = {
|
||||
appkey: appkey,
|
||||
debugLevel: 'log',
|
||||
apiVersion: 'v2'
|
||||
}
|
||||
|
||||
console.log('NIM', NIM)
|
||||
const nim = NIM.getInstance(params1)
|
||||
console.log('V2NIMConst', V2NIMConst.V2NIMTeamUpdateInfoMode.V2NIM_TEAM_UPDATE_INFO_MODE_MANAGER)
|
||||
console.log('V2NIMConst', V2NIMConst.V2NIMConversationType.V2NIM_CONVERSATION_TYPE_P2P)
|
||||
|
||||
try {
|
||||
console.log('正在 login...')
|
||||
|
||||
await nim.V2NIMLoginService.login(account, token, {
|
||||
retryCount: 3,
|
||||
timeout: 60000,
|
||||
forceMode: false,
|
||||
authType: 0
|
||||
})
|
||||
|
||||
console.log('login 成功')
|
||||
|
||||
|
||||
}catch(error){
|
||||
console.log('login 失败', error)
|
||||
}
|
||||
|
||||
}
|
||||
export default imLogin
|
||||
@@ -0,0 +1,90 @@
|
||||
import { t } from './i18n'
|
||||
import { V2NIMConst } from './nim'
|
||||
|
||||
// 自定义的一些事件常量
|
||||
export const events = {
|
||||
// 自己发出一条消息
|
||||
SEND_MSG: 'sendMsg',
|
||||
// 发送消息失败
|
||||
SEND_MSG_FAILED: 'sendMsgFailed',
|
||||
// 收到一条消息
|
||||
ON_MSG: 'onMsg',
|
||||
// 加载更多
|
||||
ON_LOAD_MORE: 'onLoadMore',
|
||||
// 首次进入聊天页并获取历史记录
|
||||
ON_CHAT_MOUNTED: 'onChatMounted',
|
||||
// 重新编辑撤回消息
|
||||
ON_REEDIT_MSG: 'onReEditMsg',
|
||||
// 页面触底
|
||||
ON_REACH_BOTTOM: 'onReachBottom',
|
||||
// 页面触顶
|
||||
ON_REACH_TOP: 'onReactTop',
|
||||
// 回复消息
|
||||
REPLY_MSG: 'replyMsg',
|
||||
// input框聚焦
|
||||
ON_INPUT_FOCUS_CHANGE: 'onInputFocusChange',
|
||||
// input框失焦
|
||||
ON_INPUT_BLUR: 'onInputBlur',
|
||||
// 滚动到底部
|
||||
ON_SCROLL_BOTTOM: 'onScrollBottom',
|
||||
// @群成员
|
||||
AIT_TEAM_MEMBER: 'aitTeamMember',
|
||||
// 表情框弹起与收起变化
|
||||
EMOJI_AREA_CHANGE: 'emojiAreaChange',
|
||||
// 获取历史消息
|
||||
GET_HISTORY_MSG: 'getHistoryMsg',
|
||||
// 取消转发消息
|
||||
CANCEL_FORWARD_MSG: 'cancelForwardMsg',
|
||||
// 确认转发消息
|
||||
CONFIRM_FORWARD_MSG: 'confirmForwardMsg',
|
||||
// @消息 @群成员
|
||||
HANDLE_AIT_MEMBER: 'handleAitMember',
|
||||
// 关闭@弹窗
|
||||
CLOSE_AIT_POPUP: 'closeAitPopup',
|
||||
// 表情点击
|
||||
EMOJI_CLICK: 'emojiClick',
|
||||
// 表情删除
|
||||
EMOJI_DELETE: 'emojiDelete',
|
||||
// 表情发送
|
||||
EMOJI_SEND: 'emojiSend',
|
||||
// 好友选择
|
||||
FRIEND_SELECT: 'friendSelect',
|
||||
// 处理滚动穿透
|
||||
HANDLE_MOVE_THROUGH: 'handleMoveThrough',
|
||||
// 关闭表情、语音面板
|
||||
CLOSE_PANEL: 'closePanel',
|
||||
// 语音消息url改变
|
||||
AUDIO_URL_CHANGE: 'audioUrlChange',
|
||||
}
|
||||
|
||||
export const HISTORY_LIMIT = 15
|
||||
|
||||
export const MSG_ID_FLAG = 'message-item-'
|
||||
|
||||
export const AT_ALL_ACCOUNT = 'ait_all'
|
||||
|
||||
export const ALLOW_AT = 'yxAllowAt'
|
||||
|
||||
export const REPLY_MSG_TYPE_MAP = {
|
||||
[V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_IMAGE]: t('imgMsgText'),
|
||||
[V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_AUDIO]: t('audioMsgText'),
|
||||
[V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_VIDEO]: t('videoMsgText'),
|
||||
[V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_FILE]: t('fileMsgText'),
|
||||
}
|
||||
|
||||
export const STORAGE_KEY = '__yx_im_options__'
|
||||
|
||||
export const callTypeMap = {
|
||||
audio: '1',
|
||||
video: '2',
|
||||
}
|
||||
|
||||
export const g2StatusMap= {
|
||||
1: t('callDurationText'),
|
||||
2: t('callCancelText'),
|
||||
3: t('callRejectedText'),
|
||||
4: t('callTimeoutText'),
|
||||
5: t('callBusyText'),
|
||||
}
|
||||
|
||||
export const msgRecallTime = 2 * 60 * 1000
|
||||
@@ -0,0 +1,17 @@
|
||||
const preUrl = ''
|
||||
|
||||
export function customNavigateTo(options) {
|
||||
uni.navigateTo({ ...options, url: preUrl + options.url })
|
||||
}
|
||||
|
||||
export function customRedirectTo(options) {
|
||||
uni.redirectTo({ ...options, url: preUrl + options.url })
|
||||
}
|
||||
|
||||
export function customSwitchTab(options) {
|
||||
uni.switchTab({ ...options, url: preUrl + options.url })
|
||||
}
|
||||
|
||||
export function customReLaunch(options) {
|
||||
uni.reLaunch({ ...options, url: preUrl + options.url })
|
||||
}
|
||||
@@ -0,0 +1,58 @@
|
||||
import { t } from './i18n'
|
||||
|
||||
export function caculateTimeago(dateTimeStamp) {
|
||||
const minute = 1000 * 60 // 把分,时,天,周,半个月,一个月用毫秒表示
|
||||
const hour = minute * 60
|
||||
const day = hour * 24
|
||||
const week = day * 7
|
||||
const now = new Date().getTime() // 获取当前时间毫秒
|
||||
const diffValue = now - dateTimeStamp // 时间差
|
||||
let result = ''
|
||||
|
||||
if (diffValue < 0) {
|
||||
return t('nowText')
|
||||
}
|
||||
const minC = Math.floor(diffValue / minute) // 计算时间差的分,时,天,周,月
|
||||
const hourC = Math.floor(diffValue / hour)
|
||||
const dayC = Math.floor(diffValue / day)
|
||||
const weekC = Math.floor(diffValue / week)
|
||||
if (weekC >= 1 && weekC <= 4) {
|
||||
result = ` ${weekC}${t('weekText')}`
|
||||
} else if (dayC >= 1 && dayC <= 6) {
|
||||
result = ` ${dayC}${t('dayText')}`
|
||||
} else if (hourC >= 1 && hourC <= 23) {
|
||||
result = ` ${hourC}${t('hourText')}`
|
||||
} else if (minC >= 1 && minC <= 59) {
|
||||
result = ` ${minC}${t('minuteText')}`
|
||||
} else if (diffValue >= 0 && diffValue <= minute) {
|
||||
result = t('nowText')
|
||||
} else {
|
||||
const datetime = new Date()
|
||||
datetime.setTime(dateTimeStamp)
|
||||
const Nyear = datetime.getFullYear()
|
||||
const Nmonth =
|
||||
datetime.getMonth() + 1 < 10
|
||||
? `0${datetime.getMonth() + 1}`
|
||||
: datetime.getMonth() + 1
|
||||
const Ndate =
|
||||
datetime.getDate() < 10 ? `0${datetime.getDate()}` : datetime.getDate()
|
||||
result = `${Nyear}-${Nmonth}-${Ndate}`
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
export const formatDateRange = (type) => {
|
||||
const date = new Date()
|
||||
let year = date.getFullYear()
|
||||
let month= date.getMonth() + 1
|
||||
let day= date.getDate()
|
||||
|
||||
if (type === 'start') {
|
||||
year = year - 100
|
||||
} else if (type === 'end') {
|
||||
year = year
|
||||
}
|
||||
month = month > 9 ? month : '0' + month
|
||||
day = day > 9 ? day : '0' + day
|
||||
return `${year}-${month}-${day}`
|
||||
}
|
||||
@@ -0,0 +1,160 @@
|
||||
import { t } from './i18n'
|
||||
|
||||
|
||||
export const EMOJI_ICON_MAP_CONFIG = {
|
||||
'[大笑]': 'icon-a-1',
|
||||
'[开心]': 'icon-a-2',
|
||||
'[色]': 'icon-a-3',
|
||||
'[酷]': 'icon-a-4',
|
||||
'[奸笑]': 'icon-a-5',
|
||||
'[亲]': 'icon-a-6',
|
||||
'[伸舌头]': 'icon-a-7',
|
||||
'[眯眼]': 'icon-a-8',
|
||||
'[可爱]': 'icon-a-9',
|
||||
'[鬼脸]': 'icon-a-10',
|
||||
'[偷笑]': 'icon-a-11',
|
||||
'[喜悦]': 'icon-a-12',
|
||||
'[狂喜]': 'icon-a-13',
|
||||
'[惊讶]': 'icon-a-14',
|
||||
'[流泪]': 'icon-a-15',
|
||||
'[流汗]': 'icon-a-16',
|
||||
'[天使]': 'icon-a-17',
|
||||
'[笑哭]': 'icon-a-18',
|
||||
'[尴尬]': 'icon-a-19',
|
||||
'[惊恐]': 'icon-a-20',
|
||||
'[大哭]': 'icon-a-21',
|
||||
'[烦躁]': 'icon-a-22',
|
||||
'[恐怖]': 'icon-a-23',
|
||||
'[两眼冒星]': 'icon-a-24',
|
||||
'[害羞]': 'icon-a-25',
|
||||
'[睡着]': 'icon-a-26',
|
||||
'[冒星]': 'icon-a-27',
|
||||
'[口罩]': 'icon-a-28',
|
||||
'[OK]': 'icon-a-29',
|
||||
'[好吧]': 'icon-a-30',
|
||||
'[鄙视]': 'icon-a-31',
|
||||
'[难受]': 'icon-a-32',
|
||||
'[不屑]': 'icon-a-33',
|
||||
'[不舒服]': 'icon-a-34',
|
||||
'[愤怒]': 'icon-a-35',
|
||||
'[鬼怪]': 'icon-a-36',
|
||||
'[发怒]': 'icon-a-37',
|
||||
'[生气]': 'icon-a-38',
|
||||
'[不高兴]': 'icon-a-39',
|
||||
'[皱眉]': 'icon-a-40',
|
||||
'[心碎]': 'icon-a-41',
|
||||
'[心动]': 'icon-a-42',
|
||||
'[好的]': 'icon-a-43',
|
||||
'[低级]': 'icon-a-44',
|
||||
'[赞]': 'icon-a-45',
|
||||
'[鼓掌]': 'icon-a-46',
|
||||
'[给力]': 'icon-a-47',
|
||||
'[打你]': 'icon-a-48',
|
||||
'[阿弥陀佛]': 'icon-a-49',
|
||||
'[拜拜]': 'icon-a-50',
|
||||
'[第一]': 'icon-a-51',
|
||||
'[拳头]': 'icon-a-52',
|
||||
'[手掌]': 'icon-a-53',
|
||||
'[剪刀]': 'icon-a-54',
|
||||
'[招手]': 'icon-a-55',
|
||||
'[不要]': 'icon-a-56',
|
||||
'[举着]': 'icon-a-57',
|
||||
'[思考]': 'icon-a-58',
|
||||
'[猪头]': 'icon-a-59',
|
||||
'[不听]': 'icon-a-60',
|
||||
'[不看]': 'icon-a-61',
|
||||
'[不说]': 'icon-a-62',
|
||||
'[猴子]': 'icon-a-63',
|
||||
'[炸弹]': 'icon-a-64',
|
||||
'[睡觉]': 'icon-a-65',
|
||||
'[筋斗云]': 'icon-a-66',
|
||||
'[火箭]': 'icon-a-67',
|
||||
'[救护车]': 'icon-a-68',
|
||||
'[便便]': 'icon-a-70',
|
||||
}
|
||||
|
||||
export const emojiMap = {
|
||||
[t('Laugh')]: 'icon-a-1',
|
||||
[t('Happy')]: 'icon-a-2',
|
||||
[t('Sexy')]: 'icon-a-3',
|
||||
[t('Cool')]: 'icon-a-4',
|
||||
[t('Mischievous')]: 'icon-a-5',
|
||||
[t('Kiss')]: 'icon-a-6',
|
||||
[t('Spit')]: 'icon-a-7',
|
||||
[t('Squint')]: 'icon-a-8',
|
||||
[t('Cute')]: 'icon-a-9',
|
||||
[t('Grimace')]: 'icon-a-10',
|
||||
[t('Snicker')]: 'icon-a-11',
|
||||
[t('Joy')]: 'icon-a-12',
|
||||
[t('Ecstasy')]: 'icon-a-13',
|
||||
[t('Surprise')]: 'icon-a-14',
|
||||
[t('Tears')]: 'icon-a-15',
|
||||
[t('Sweat')]: 'icon-a-16',
|
||||
[t('Angle')]: 'icon-a-17',
|
||||
[t('Funny')]: 'icon-a-18',
|
||||
[t('Awkward')]: 'icon-a-19',
|
||||
[t('Thrill')]: 'icon-a-20',
|
||||
[t('Cry')]: 'icon-a-21',
|
||||
[t('Fretting')]: 'icon-a-22',
|
||||
[t('Terrorist')]: 'icon-a-23',
|
||||
[t('Halo')]: 'icon-a-24',
|
||||
[t('Shame')]: 'icon-a-25',
|
||||
[t('Sleep')]: 'icon-a-26',
|
||||
[t('Tired')]: 'icon-a-27',
|
||||
[t('Mask')]: 'icon-a-28',
|
||||
[t('ok')]: 'icon-a-29',
|
||||
[t('AllRight')]: 'icon-a-30',
|
||||
[t('Despise')]: 'icon-a-31',
|
||||
[t('Uncomfortable')]: 'icon-a-32',
|
||||
[t('Disdain')]: 'icon-a-33',
|
||||
[t('ill')]: 'icon-a-34',
|
||||
[t('Mad')]: 'icon-a-35',
|
||||
[t('Ghost')]: 'icon-a-36',
|
||||
[t('Angry')]: 'icon-a-37',
|
||||
[t('Angry')]: 'icon-a-38',
|
||||
[t('Unhappy')]: 'icon-a-39',
|
||||
[t('Frown')]: 'icon-a-40',
|
||||
[t('Broken')]: 'icon-a-41',
|
||||
[t('Beckoning')]: 'icon-a-42',
|
||||
[t('Ok')]: 'icon-a-43',
|
||||
[t('Low')]: 'icon-a-44',
|
||||
[t('Nice')]: 'icon-a-45',
|
||||
[t('Applause')]: 'icon-a-46',
|
||||
[t('GoodJob')]: 'icon-a-47',
|
||||
[t('Hit')]: 'icon-a-48',
|
||||
[t('Please')]: 'icon-a-49',
|
||||
[t('Bye')]: 'icon-a-50',
|
||||
[t('First')]: 'icon-a-51',
|
||||
[t('Fist')]: 'icon-a-52',
|
||||
[t('GiveMeFive')]: 'icon-a-53',
|
||||
[t('Knife')]: 'icon-a-54',
|
||||
[t('Hi')]: 'icon-a-55',
|
||||
[t('No')]: 'icon-a-56',
|
||||
[t('Hold')]: 'icon-a-57',
|
||||
[t('Think')]: 'icon-a-58',
|
||||
[t('Pig')]: 'icon-a-59',
|
||||
[t('NoListen')]: 'icon-a-60',
|
||||
[t('NoLook')]: 'icon-a-61',
|
||||
[t('NoWords')]: 'icon-a-62',
|
||||
[t('Monkey')]: 'icon-a-63',
|
||||
[t('Bomb')]: 'icon-a-64',
|
||||
[t('Sleep')]: 'icon-a-65',
|
||||
[t('Cloud')]: 'icon-a-66',
|
||||
[t('Rocket')]: 'icon-a-67',
|
||||
[t('Ambulance')]: 'icon-a-68',
|
||||
[t('Poop')]: 'icon-a-70',
|
||||
}
|
||||
|
||||
export const emojiRegExp = new RegExp(
|
||||
'(' +
|
||||
Object.keys(EMOJI_ICON_MAP_CONFIG)
|
||||
.map((item) => {
|
||||
const left = `\\${item.slice(0, 1)}`
|
||||
const right = `\\${item.slice(-1)}`
|
||||
const mid = item.slice(1, -1)
|
||||
return `${left}${mid}${right}`
|
||||
})
|
||||
.join('|') +
|
||||
')',
|
||||
'g'
|
||||
)
|
||||
@@ -0,0 +1,26 @@
|
||||
export default (data)=> {
|
||||
let text = ''
|
||||
for (let i = 0; i < data.length; i++) {
|
||||
switch (data.charCodeAt(i)) {
|
||||
case 34: // "
|
||||
text += '"'
|
||||
break
|
||||
case 38: // &
|
||||
text += '&'
|
||||
break
|
||||
case 39: // '
|
||||
text += ''' // modified from escape-html; used to be '''
|
||||
break
|
||||
case 60: // <
|
||||
text += '<'
|
||||
break
|
||||
case 62: // >
|
||||
text += '>'
|
||||
break
|
||||
default:
|
||||
text += data[i]
|
||||
break
|
||||
}
|
||||
}
|
||||
return text
|
||||
}
|
||||
@@ -0,0 +1,72 @@
|
||||
// #ifdef APP-PLUS
|
||||
import pinyin from 'pinyin'
|
||||
// #endif
|
||||
|
||||
export const friendGroupByPy = (
|
||||
arr,
|
||||
keys,
|
||||
isLowerCase = true
|
||||
) => {
|
||||
const res = {}
|
||||
const OTHER_TAG = '#'
|
||||
|
||||
const add = (k, v) => {
|
||||
const _k = isLowerCase ? k.toLowerCase() : k.toUpperCase()
|
||||
if (!res[_k]) {
|
||||
res[_k] = [v]
|
||||
} else {
|
||||
res[_k].push(v)
|
||||
}
|
||||
}
|
||||
|
||||
arr.forEach((item) => {
|
||||
const v =
|
||||
item[keys.firstKey] ||
|
||||
item[keys.secondKey || ''] ||
|
||||
item[keys.thirdKey || '']
|
||||
if (!!v && typeof v === 'string') {
|
||||
const str = v[0]
|
||||
if (/^[a-zA-Z]$/.test(str)) {
|
||||
add(str.toLowerCase(), item)
|
||||
} else if (/^[\u4e00-\u9fa5]$/.test(str)) {
|
||||
const en = '*abcdefghjklmnopqrstwxyz'.split('')
|
||||
let resolvedK
|
||||
// #ifdef APP-PLUS
|
||||
// @ts-ignore
|
||||
resolvedK = en.find((k) => {
|
||||
const py = pinyin(str, {
|
||||
style: 'FIRST_LETTER',
|
||||
})
|
||||
return py[0][0] === k
|
||||
})
|
||||
// #endif
|
||||
// #ifndef APP-PLUS
|
||||
const zh = '阿八嚓哒妸发旮哈讥咔垃痳拏噢妑七呥扨它穵夕丫帀'.split('')
|
||||
// @ts-ignore
|
||||
resolvedK = en.find(
|
||||
(currentK, ki) =>
|
||||
(!zh[ki - 1] || zh[ki - 1].localeCompare(str, 'zh') <= 0) &&
|
||||
str.localeCompare(zh[ki], 'zh') == -1
|
||||
)
|
||||
// #endif
|
||||
if (resolvedK && resolvedK !== '*') {
|
||||
add(resolvedK, item)
|
||||
} else {
|
||||
add(OTHER_TAG, item)
|
||||
}
|
||||
} else {
|
||||
add(OTHER_TAG, item)
|
||||
}
|
||||
} else {
|
||||
add(OTHER_TAG, item)
|
||||
}
|
||||
})
|
||||
|
||||
const data = Object.keys(res).map((k) => ({ key: k, data: res[k] }))
|
||||
const sortData = data
|
||||
.filter((item) => item.key !== OTHER_TAG)
|
||||
.sort((a, b) => a.key.localeCompare(b.key, 'en'))
|
||||
const otherData = data.filter((item) => item.key === OTHER_TAG)
|
||||
|
||||
return sortData.concat(otherData)
|
||||
}
|
||||
@@ -0,0 +1,16 @@
|
||||
import en from '../../locale/en'
|
||||
import zh from '../../locale/zh-Hans'
|
||||
const i18nData = {
|
||||
en,
|
||||
zh,
|
||||
}
|
||||
|
||||
let currentLanguage= 'zh'
|
||||
|
||||
export function setLanguage(language) {
|
||||
currentLanguage = language
|
||||
}
|
||||
|
||||
export const t = (key) => {
|
||||
return i18nData[currentLanguage][key] || key
|
||||
}
|
||||
@@ -0,0 +1,442 @@
|
||||
import { events } from './constants'
|
||||
|
||||
export const getUniPlatform = () => {
|
||||
// @ts-ignore
|
||||
return uni.getSystemInfoSync().uniPlatform
|
||||
}
|
||||
|
||||
export const getPlatform = () => {
|
||||
// @ts-ignore
|
||||
return uni.getSystemInfoSync().platform
|
||||
}
|
||||
// 是否是android app
|
||||
export const isAndroidApp =
|
||||
uni.getSystemInfoSync().platform == 'android' &&
|
||||
uni.getSystemInfoSync().uniPlatform == 'app'
|
||||
|
||||
// 是否是Ios app
|
||||
export const isIosApp =
|
||||
uni.getSystemInfoSync().platform == 'ios' &&
|
||||
uni.getSystemInfoSync().uniPlatform == 'app'
|
||||
|
||||
// 是否是鸿蒙app
|
||||
export const isHarmonyOs =
|
||||
uni.getSystemInfoSync().platform == 'harmonyos' &&
|
||||
uni.getSystemInfoSync().uniPlatform === 'app'
|
||||
|
||||
// 是否是Android app 或者 Ios app
|
||||
export const isAndroidOrIosApp =
|
||||
uni.getSystemInfoSync().uniPlatform == 'app' &&
|
||||
(uni.getSystemInfoSync().platform == 'android' ||
|
||||
uni.getSystemInfoSync().platform == 'ios')
|
||||
|
||||
// 是否是Ios web
|
||||
export const isIosWeb =
|
||||
uni.getSystemInfoSync().uniPlatform === 'web' &&
|
||||
uni.getSystemInfoSync().platform === 'ios'
|
||||
|
||||
// 是否是App
|
||||
export const isApp = uni.getSystemInfoSync().uniPlatform == 'app'
|
||||
|
||||
// 是否是微信小程序
|
||||
export const isWxApp = uni.getSystemInfoSync().uniPlatform == 'mp-weixin'
|
||||
|
||||
// 是否是web
|
||||
export const isWeb = uni.getSystemInfoSync().uniPlatform === 'web'
|
||||
|
||||
// @ts-ignore
|
||||
export function deepClone(source, visited = new WeakMap()) {
|
||||
if (source === null || typeof source !== 'object') {
|
||||
return source
|
||||
}
|
||||
|
||||
if (visited.has(source)) {
|
||||
return visited.get(source)
|
||||
}
|
||||
// @ts-ignore
|
||||
let clone
|
||||
|
||||
if (source instanceof Date) {
|
||||
clone = new Date(source.getTime())
|
||||
} else if (source instanceof RegExp) {
|
||||
clone = new RegExp(source)
|
||||
} else if (source instanceof Map) {
|
||||
clone = new Map()
|
||||
visited.set(source, clone)
|
||||
source.forEach((value, key) => {
|
||||
// @ts-ignore
|
||||
clone.set(key, deepClone(value, visited))
|
||||
})
|
||||
} else if (source instanceof Set) {
|
||||
clone = new Set()
|
||||
visited.set(source, clone)
|
||||
source.forEach((value) => {
|
||||
// @ts-ignore
|
||||
clone.add(deepClone(value, visited))
|
||||
})
|
||||
} else if (Array.isArray(source)) {
|
||||
clone = []
|
||||
// @ts-ignore
|
||||
visited.set(source, clone)
|
||||
for (let i = 0; i < source.length; i++) {
|
||||
clone[i] = deepClone(source[i], visited)
|
||||
}
|
||||
} else {
|
||||
clone = Object.create(Object.getPrototypeOf(source))
|
||||
visited.set(source, clone)
|
||||
for (const prop in source) {
|
||||
if (source.hasOwnProperty(prop)) {
|
||||
clone[prop] = deepClone(source[prop], visited)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return clone
|
||||
}
|
||||
|
||||
export function stopAllAudio() {
|
||||
uni.$emit(events.AUDIO_URL_CHANGE, '')
|
||||
}
|
||||
|
||||
/**
|
||||
* 秒转换为时分秒
|
||||
*/
|
||||
export const convertSecondsToTime = (seconds)=> {
|
||||
if (!seconds) {
|
||||
return null
|
||||
}
|
||||
const hours = Math.floor(seconds / 3600)
|
||||
const minutes = Math.floor((seconds - hours * 3600) / 60)
|
||||
const remainingSeconds= seconds - hours * 3600 - minutes * 60
|
||||
|
||||
let timeString = ''
|
||||
|
||||
const includeHours = seconds >= 3600
|
||||
if (includeHours) {
|
||||
if (hours < 10) {
|
||||
timeString += '0'
|
||||
}
|
||||
timeString += hours.toString() + ':'
|
||||
}
|
||||
|
||||
if (minutes < 10) {
|
||||
timeString += '0'
|
||||
}
|
||||
timeString += minutes.toString() + ':'
|
||||
|
||||
if (remainingSeconds < 10) {
|
||||
timeString += '0'
|
||||
}
|
||||
timeString += remainingSeconds.toString()
|
||||
|
||||
return timeString
|
||||
}
|
||||
|
||||
export const startCall = (options) => {
|
||||
try {
|
||||
// @ts-ignore
|
||||
uni.$UIKitCallKit.toCallPage(
|
||||
{
|
||||
calledAccount: options.remoteUserAccid,
|
||||
// currentUserAccid: options.currentUserAccid,
|
||||
type: options.type,
|
||||
calledShowName: options.remoteShowName,
|
||||
},
|
||||
() => {
|
||||
console.log('toCallPage: ', {
|
||||
remoteUserAccid: options.remoteUserAccid,
|
||||
currentUserAccid: options.currentUserAccid,
|
||||
type: options.type,
|
||||
remoteShowName: options.remoteShowName,
|
||||
})
|
||||
}
|
||||
)
|
||||
} catch (error) {
|
||||
console.log('handleVideoCall error', error)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
export const EMOJI_ICON_MAP_CONFIG= {
|
||||
'[大笑]': 'icon-a-1',
|
||||
'[开心]': 'icon-a-2',
|
||||
'[色]': 'icon-a-3',
|
||||
'[酷]': 'icon-a-4',
|
||||
'[奸笑]': 'icon-a-5',
|
||||
'[亲]': 'icon-a-6',
|
||||
'[伸舌头]': 'icon-a-7',
|
||||
'[眯眼]': 'icon-a-8',
|
||||
'[可爱]': 'icon-a-9',
|
||||
'[鬼脸]': 'icon-a-10',
|
||||
'[偷笑]': 'icon-a-11',
|
||||
'[喜悦]': 'icon-a-12',
|
||||
'[狂喜]': 'icon-a-13',
|
||||
'[惊讶]': 'icon-a-14',
|
||||
'[流泪]': 'icon-a-15',
|
||||
'[流汗]': 'icon-a-16',
|
||||
'[天使]': 'icon-a-17',
|
||||
'[笑哭]': 'icon-a-18',
|
||||
'[尴尬]': 'icon-a-19',
|
||||
'[惊恐]': 'icon-a-20',
|
||||
'[大哭]': 'icon-a-21',
|
||||
'[烦躁]': 'icon-a-22',
|
||||
'[恐怖]': 'icon-a-23',
|
||||
'[两眼冒星]': 'icon-a-24',
|
||||
'[害羞]': 'icon-a-25',
|
||||
'[睡着]': 'icon-a-26',
|
||||
'[冒星]': 'icon-a-27',
|
||||
'[口罩]': 'icon-a-28',
|
||||
'[OK]': 'icon-a-29',
|
||||
'[好吧]': 'icon-a-30',
|
||||
'[鄙视]': 'icon-a-31',
|
||||
'[难受]': 'icon-a-32',
|
||||
'[不屑]': 'icon-a-33',
|
||||
'[不舒服]': 'icon-a-34',
|
||||
'[愤怒]': 'icon-a-35',
|
||||
'[鬼怪]': 'icon-a-36',
|
||||
'[发怒]': 'icon-a-37',
|
||||
'[生气]': 'icon-a-38',
|
||||
'[不高兴]': 'icon-a-39',
|
||||
'[皱眉]': 'icon-a-40',
|
||||
'[心碎]': 'icon-a-41',
|
||||
'[心动]': 'icon-a-42',
|
||||
'[好的]': 'icon-a-43',
|
||||
'[低级]': 'icon-a-44',
|
||||
'[赞]': 'icon-a-45',
|
||||
'[鼓掌]': 'icon-a-46',
|
||||
'[给力]': 'icon-a-47',
|
||||
'[打你]': 'icon-a-48',
|
||||
'[阿弥陀佛]': 'icon-a-49',
|
||||
'[拜拜]': 'icon-a-50',
|
||||
'[第一]': 'icon-a-51',
|
||||
'[拳头]': 'icon-a-52',
|
||||
'[手掌]': 'icon-a-53',
|
||||
'[剪刀]': 'icon-a-54',
|
||||
'[招手]': 'icon-a-55',
|
||||
'[不要]': 'icon-a-56',
|
||||
'[举着]': 'icon-a-57',
|
||||
'[思考]': 'icon-a-58',
|
||||
'[猪头]': 'icon-a-59',
|
||||
'[不听]': 'icon-a-60',
|
||||
'[不看]': 'icon-a-61',
|
||||
'[不说]': 'icon-a-62',
|
||||
'[猴子]': 'icon-a-63',
|
||||
'[炸弹]': 'icon-a-64',
|
||||
'[睡觉]': 'icon-a-65',
|
||||
'[筋斗云]': 'icon-a-66',
|
||||
'[火箭]': 'icon-a-67',
|
||||
'[救护车]': 'icon-a-68',
|
||||
'[便便]': 'icon-a-70',
|
||||
}
|
||||
|
||||
export function replaceEmoji(text, emojiMap) {
|
||||
const defaultEmojiMap = {
|
||||
'[Laugh]': '[大笑]',
|
||||
'[Happy]': '[开心]',
|
||||
'[Sexy]': '[色]',
|
||||
'[Cool]': '[酷]',
|
||||
'[Mischievous]': '[奸笑]',
|
||||
'[Kiss]': '[亲]',
|
||||
'[Spit]': '[伸舌头]',
|
||||
'[Squint]': '[眯眼]',
|
||||
'[Cute]': '[可爱]',
|
||||
'[Grimace]': '[鬼脸]',
|
||||
'[Snicker]': '[偷笑]',
|
||||
'[Joy]': '[喜悦]',
|
||||
'[Ecstasy]': '[狂喜]',
|
||||
'[Surprise]': '[惊讶]',
|
||||
'[Tears]': '[流泪]',
|
||||
'[Sweat]': '[流汗]',
|
||||
'[Angle]': '[天使]',
|
||||
'[Funny]': '[笑哭]',
|
||||
'[Awkward]': '[尴尬]',
|
||||
'[Thrill]': '[惊恐]',
|
||||
'[Cry]': '[大哭]',
|
||||
'[Fretting]': '[烦躁]',
|
||||
'[Terrorist]': '[恐怖]',
|
||||
'[Halo]': '[两眼冒星]',
|
||||
'[Shame]': '[害羞]',
|
||||
'[Sleep]': '[睡着]',
|
||||
'[Tired]': '[睡觉]',
|
||||
'[Mask]': '[口罩]',
|
||||
'[Ok]': '[OK]',
|
||||
'[All right]': '[好吧]',
|
||||
'[Despise]': '[鄙视]',
|
||||
'[Uncomfortable]': '[难受]',
|
||||
'[Disdain]': '[不屑]',
|
||||
'[ill]': '[不舒服]',
|
||||
'[Mad]': '[愤怒]',
|
||||
'[Ghost]': '[鬼怪]',
|
||||
'[Huff]': '[发怒]',
|
||||
'[Angry]': '[生气]',
|
||||
'[Unhappy]': '[不高兴]',
|
||||
'[Frown]': '[皱眉]',
|
||||
'[Broken]': '[心碎]',
|
||||
'[Beckoning]': '[心动]',
|
||||
'[Low]': '[低级]',
|
||||
'[Nice]': '[赞]',
|
||||
'[Applause]': '[鼓掌]',
|
||||
'[Good job]': '[给力]',
|
||||
'[Hit]': '[打你]',
|
||||
'[Please]': '[阿弥陀佛]',
|
||||
'[Bye]': '[拜拜]',
|
||||
'[First]': '[第一]',
|
||||
'[Fist]': '[拳头]',
|
||||
'[Give me five]': '[招手]',
|
||||
'[Knife]': '[剪刀]',
|
||||
'[Hi]': '[招手]',
|
||||
'[No]': '[不要]',
|
||||
'[Hold]': '[举着]',
|
||||
'[Think]': '[思考]',
|
||||
'[Pig]': '[猪头]',
|
||||
'[No listen]': '[不听]',
|
||||
'[No look]': '[不看]',
|
||||
'[No words]': '[不说]',
|
||||
'[Monkey]': '[猴子]',
|
||||
'[Bomb]': '[炸弹]',
|
||||
'[Sleeping]': '[睡觉]',
|
||||
'[Cloud]': '[筋斗云]',
|
||||
'[Rocket]': '[火箭]',
|
||||
'[Ambulance]': '[救护车]',
|
||||
'[Poop]': '[便便]',
|
||||
}
|
||||
|
||||
const emojiMapConfig = emojiMap || defaultEmojiMap
|
||||
const emojiMapRegex = new RegExp(
|
||||
'(' +
|
||||
Object.keys(emojiMapConfig)
|
||||
.map((item) => {
|
||||
const left = `\\${item.slice(0, 1)}`
|
||||
const right = `\\${item.slice(-1)}`
|
||||
const mid = item.slice(1, -1)
|
||||
|
||||
return `${left}${mid}${right}`
|
||||
})
|
||||
.join('|') +
|
||||
')',
|
||||
'g'
|
||||
)
|
||||
|
||||
return text.replace(emojiMapRegex, function (matched) {
|
||||
return emojiMapConfig[matched]
|
||||
})
|
||||
}
|
||||
|
||||
export const handleEmojiTranslate = (t) => {
|
||||
const SHOW_EMOJI_ICON_MAP_CONFIG = {
|
||||
[t('Laugh')]: 'icon-a-1',
|
||||
[t('Happy')]: 'icon-a-2',
|
||||
[t('Sexy')]: 'icon-a-3',
|
||||
[t('Cool')]: 'icon-a-4',
|
||||
[t('Mischievous')]: 'icon-a-5',
|
||||
[t('Kiss')]: 'icon-a-6',
|
||||
[t('Spit')]: 'icon-a-7',
|
||||
[t('Squint')]: 'icon-a-8',
|
||||
[t('Cute')]: 'icon-a-9',
|
||||
[t('Grimace')]: 'icon-a-10',
|
||||
[t('Snicker')]: 'icon-a-11',
|
||||
[t('Joy')]: 'icon-a-12',
|
||||
[t('Ecstasy')]: 'icon-a-13',
|
||||
[t('Surprise')]: 'icon-a-14',
|
||||
[t('Tears')]: 'icon-a-15',
|
||||
[t('Sweat')]: 'icon-a-16',
|
||||
[t('Angle')]: 'icon-a-17',
|
||||
[t('Funny')]: 'icon-a-18',
|
||||
[t('Awkward')]: 'icon-a-19',
|
||||
[t('Thrill')]: 'icon-a-20',
|
||||
[t('Cry')]: 'icon-a-21',
|
||||
[t('Fretting')]: 'icon-a-22',
|
||||
[t('Terrorist')]: 'icon-a-23',
|
||||
[t('Halo')]: 'icon-a-24',
|
||||
[t('Shame')]: 'icon-a-25',
|
||||
[t('Sleep')]: 'icon-a-26',
|
||||
[t('Tired')]: 'icon-a-27',
|
||||
[t('Mask')]: 'icon-a-28',
|
||||
[t('ok')]: 'icon-a-29',
|
||||
[t('AllRight')]: 'icon-a-30',
|
||||
[t('Despise')]: 'icon-a-31',
|
||||
[t('Uncomfortable')]: 'icon-a-32',
|
||||
[t('Disdain')]: 'icon-a-33',
|
||||
[t('ill')]: 'icon-a-34',
|
||||
[t('Mad')]: 'icon-a-35',
|
||||
[t('Ghost')]: 'icon-a-36',
|
||||
[t('huff')]: 'icon-a-37',
|
||||
[t('Angry')]: 'icon-a-38',
|
||||
[t('Unhappy')]: 'icon-a-39',
|
||||
[t('Frown')]: 'icon-a-40',
|
||||
[t('Broken')]: 'icon-a-41',
|
||||
[t('Beckoning')]: 'icon-a-42',
|
||||
[t('Ok')]: 'icon-a-43',
|
||||
[t('Low')]: 'icon-a-44',
|
||||
[t('Nice')]: 'icon-a-45',
|
||||
[t('Applause')]: 'icon-a-46',
|
||||
[t('GoodJob')]: 'icon-a-47',
|
||||
[t('Hit')]: 'icon-a-48',
|
||||
[t('Please')]: 'icon-a-49',
|
||||
[t('Bye')]: 'icon-a-50',
|
||||
[t('First')]: 'icon-a-51',
|
||||
[t('Fist')]: 'icon-a-52',
|
||||
[t('GiveMeFive')]: 'icon-a-53',
|
||||
[t('Knife')]: 'icon-a-54',
|
||||
[t('Hi')]: 'icon-a-55',
|
||||
[t('No')]: 'icon-a-56',
|
||||
[t('Hold')]: 'icon-a-57',
|
||||
[t('Think')]: 'icon-a-58',
|
||||
[t('Pig')]: 'icon-a-59',
|
||||
[t('NoListen')]: 'icon-a-60',
|
||||
[t('NoLook')]: 'icon-a-61',
|
||||
[t('NoWords')]: 'icon-a-62',
|
||||
[t('Monkey')]: 'icon-a-63',
|
||||
[t('Bomb')]: 'icon-a-64',
|
||||
[t('Sleeping')]: 'icon-a-65',
|
||||
[t('Cloud')]: 'icon-a-66',
|
||||
[t('Rocket')]: 'icon-a-67',
|
||||
[t('Ambulance')]: 'icon-a-68',
|
||||
[t('Poop')]: 'icon-a-70',
|
||||
}
|
||||
|
||||
const INPUT_EMOJI_SYMBOL_REG = new RegExp(
|
||||
'(' +
|
||||
Object.keys(EMOJI_ICON_MAP_CONFIG)
|
||||
.map((item) => {
|
||||
const left = `\\${item.slice(0, 1)}`
|
||||
const right = `\\${item.slice(-1)}`
|
||||
const mid = item.slice(1, -1)
|
||||
|
||||
return `${left}${mid}${right}`
|
||||
})
|
||||
.join('|') +
|
||||
')',
|
||||
'g'
|
||||
)
|
||||
|
||||
return {
|
||||
SHOW_EMOJI_ICON_MAP_CONFIG,
|
||||
INPUT_EMOJI_SYMBOL_REG,
|
||||
}
|
||||
}
|
||||
|
||||
// emoji正则
|
||||
export const emojiRegExp = new RegExp(
|
||||
'(' +
|
||||
Object.keys(EMOJI_ICON_MAP_CONFIG)
|
||||
.map((item) => {
|
||||
const left = `\\${item.slice(0, 1)}`
|
||||
const right = `\\${item.slice(-1)}`
|
||||
const mid = item.slice(1, -1)
|
||||
return `${left}${mid}${right}`
|
||||
})
|
||||
.join('|') +
|
||||
')',
|
||||
'g'
|
||||
)
|
||||
|
||||
/** 是否是讨论组 */
|
||||
export const isDiscussionFunc = (serverExtension) => {
|
||||
try {
|
||||
return JSON.parse(serverExtension || '{}').im_ui_kit_group
|
||||
} catch (error) {
|
||||
console.warn('parse serverExtension error', error)
|
||||
return false
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,16 @@
|
||||
export const calculateMatrix =(arr, colNum)=> {
|
||||
if (colNum < 1) {
|
||||
throw Error('colNum cound not be smaller than 1')
|
||||
}
|
||||
const len = arr.length
|
||||
const rowNum = Math.ceil(len / colNum)
|
||||
let curIndex = 0
|
||||
let curRow = 0
|
||||
const res = []
|
||||
while (curIndex <= len && curRow < rowNum) {
|
||||
res[curRow] = arr.slice(curIndex, curIndex + colNum)
|
||||
curIndex += colNum
|
||||
curRow++
|
||||
}
|
||||
return res
|
||||
}
|
||||
+123
@@ -0,0 +1,123 @@
|
||||
import { V2NIMConst } from './nim'
|
||||
import { t } from './i18n'
|
||||
|
||||
const translate = (key)=> {
|
||||
const text =
|
||||
{
|
||||
textMsgText: t('textMsgText'),
|
||||
customMsgText: t('customMsgText'),
|
||||
audioMsgText: t('audioMsgText'),
|
||||
videoMsgText: t('videoMsgText'),
|
||||
fileMsgText: t('fileMsgText'),
|
||||
callMsgText: t('callMsgText'),
|
||||
geoMsgText: t('geoMsgText'),
|
||||
imgMsgText: t('imgMsgText'),
|
||||
notiMsgText: t('notiMsgText'),
|
||||
robotMsgText: t('robotMsgText'),
|
||||
tipMsgText: t('tipMsgText'),
|
||||
unknowMsgText: t('unknowMsgText'),
|
||||
}[key] || ''
|
||||
return `[${text}]`
|
||||
}
|
||||
|
||||
export const getMsgContentTipByType = (msg)=> {
|
||||
const { messageType, text } = msg
|
||||
switch (messageType) {
|
||||
case V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_TEXT:
|
||||
return text || translate('textMsgText')
|
||||
case V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_FILE:
|
||||
return translate('fileMsgText')
|
||||
case V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_IMAGE:
|
||||
return translate('imgMsgText')
|
||||
case V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_CUSTOM:
|
||||
return text || translate('customMsgText')
|
||||
case V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_AUDIO:
|
||||
return translate('audioMsgText')
|
||||
case V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_CALL:
|
||||
return translate('callMsgText')
|
||||
case V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_LOCATION:
|
||||
return translate('geoMsgText')
|
||||
case V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_NOTIFICATION:
|
||||
return translate('notiMsgText')
|
||||
case V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_ROBOT:
|
||||
return translate('robotMsgText')
|
||||
case V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_TIPS:
|
||||
return translate('tipMsgText')
|
||||
case V2NIMConst.V2NIMMessageType.V2NIM_MESSAGE_TYPE_VIDEO:
|
||||
return translate('videoMsgText')
|
||||
default:
|
||||
return translate('unknowMsgText')
|
||||
}
|
||||
}
|
||||
|
||||
export const setTabUnread = ()=> {
|
||||
const routes = getCurrentPages()
|
||||
const curRoute = routes[routes.length - 1].route
|
||||
const tabPaths = [
|
||||
'pages/User/my/index',
|
||||
'pages/Contact/index',
|
||||
'pages/Conversation/index',
|
||||
]
|
||||
if (curRoute && !tabPaths.includes(curRoute)) {
|
||||
// 不是首页和聊天页,不需要设置tabbar的badge
|
||||
return
|
||||
}
|
||||
|
||||
const store = uni.$UIKitStore
|
||||
/**是否是云端会话 */
|
||||
const enableV2CloudConversation = store?.sdkOptions?.enableV2CloudConversation
|
||||
const unread =
|
||||
(enableV2CloudConversation
|
||||
? store?.conversationStore?.totalUnreadCount
|
||||
: store?.localConversationStore?.totalUnreadCount) || 0
|
||||
if (unread === 0) {
|
||||
uni.hideTabBarRedDot({
|
||||
//隐藏数字
|
||||
index: 0, //tabbar下标
|
||||
})
|
||||
} else {
|
||||
uni.showTabBarRedDot({
|
||||
index: 0, //tabbar下标
|
||||
})
|
||||
}
|
||||
/**
|
||||
* 此为展示tabbar的未读消息数字的写法
|
||||
if (unread === 0) {
|
||||
uni.removeTabBarBadge({
|
||||
//隐藏数字
|
||||
index: 0, //tabbar下标
|
||||
})
|
||||
} else {
|
||||
uni.setTabBarBadge({
|
||||
//显示数字
|
||||
index: 0, //tabbar下标
|
||||
text: unread > 99 ? '99+' : unread.toString(), //显示的数字
|
||||
})
|
||||
}
|
||||
*/
|
||||
}
|
||||
|
||||
export const setContactTabUnread = ()=> {
|
||||
const routes = getCurrentPages()
|
||||
const curRoute = routes[routes.length - 1].route
|
||||
const tabPaths = [
|
||||
'pages/User/my/index',
|
||||
'pages/Contact/index',
|
||||
'pages/Conversation/index',
|
||||
]
|
||||
if (curRoute && !tabPaths.includes(curRoute)) {
|
||||
// 不是首页和聊天页,不需要设置tabbar的badge
|
||||
return
|
||||
}
|
||||
const unread = uni.$UIKitStore?.sysMsgStore?.getTotalUnreadMsgsCount()
|
||||
if (unread === 0) {
|
||||
uni.hideTabBarRedDot({
|
||||
//隐藏数字
|
||||
index: 1, //tabbar下标
|
||||
})
|
||||
} else {
|
||||
uni.showTabBarRedDot({
|
||||
index: 1, //tabbar下标
|
||||
})
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,15 @@
|
||||
// 常规集成的V2NIMConst
|
||||
import { V2NIMConst } from "nim-web-sdk-ng/dist/esm/nim";
|
||||
|
||||
// ESM 版本集成的V2NIMConst
|
||||
|
||||
/**
|
||||
* NIM SDK 默认导出 UMD(Universal Module Definition)格式的产物,这种格式的文件可以在多种环境中使用。
|
||||
* 当应用对包体积有更严格的要求,例如小程序应用,则可以使用 ESM(ECMAScript Module)格式的 SDK。ESM 是 JavaScript 的原生模块系统,
|
||||
* 允许更细粒度的模块控制和更有效的打包。再配合 webpack 实现 tree-shaking(一种去除代码中未引用部分的方式),从而进一步降低 NIM SDK 产物体积。
|
||||
* 具体参考文档 https://doc.yunxin.163.com/messaging2/guide/DcyMjA1Njk?platform=client
|
||||
*/
|
||||
//@ts-ignore
|
||||
// import { V2NIMConst } from '../esmNim.js'
|
||||
|
||||
export { V2NIMConst };
|
||||
@@ -0,0 +1,160 @@
|
||||
import { emojiRegExp } from './emoji'
|
||||
|
||||
|
||||
|
||||
/* eslint-disable vars-on-top, no-var, prefer-template */
|
||||
// @ts-nocheck
|
||||
var isRegExp = function (re) {
|
||||
return re instanceof RegExp
|
||||
}
|
||||
var escapeRegExp = function escapeRegExp(string) {
|
||||
var reRegExpChar = /[\\^$.*+?()[\]{}|]/g,
|
||||
reHasRegExpChar = RegExp(reRegExpChar.source)
|
||||
|
||||
return string && reHasRegExpChar.test(string)
|
||||
? string.replace(reRegExpChar, '\\$&')
|
||||
: string
|
||||
}
|
||||
var isString = function (value) {
|
||||
return typeof value === 'string'
|
||||
}
|
||||
var flatten = function (array) {
|
||||
var newArray= []
|
||||
|
||||
array.forEach(function (item) {
|
||||
if (Array.isArray(item)) {
|
||||
newArray = newArray.concat(item)
|
||||
} else {
|
||||
newArray.push(item)
|
||||
}
|
||||
})
|
||||
|
||||
return newArray
|
||||
}
|
||||
|
||||
/**
|
||||
* Given a string, replace every substring that is matched by the `match` regex
|
||||
* with the result of calling `fn` on matched substring. The result will be an
|
||||
* array with all odd indexed elements containing the replacements. The primary
|
||||
* use case is similar to using String.prototype.replace except for React.
|
||||
*
|
||||
* React will happily render an array as children of a react element, which
|
||||
* makes this approach very useful for tasks like surrounding certain text
|
||||
* within a string with react elements.
|
||||
*
|
||||
* Example:
|
||||
* matchReplace(
|
||||
* 'Emphasize all phone numbers like 884-555-4443.',
|
||||
* /([\d|-]+)/g,
|
||||
* (number, i) => <strong key={i}>{number}</strong>
|
||||
* );
|
||||
* // => ['Emphasize all phone numbers like ', <strong>884-555-4443</strong>, '.'
|
||||
*
|
||||
* @param {string} str
|
||||
* @param {RegExp|str} match Must contain a matching group
|
||||
* @param {function} fn
|
||||
* @return {array}
|
||||
*/
|
||||
|
||||
function replaceString(str, match, fn) {
|
||||
var curCharStart = 0
|
||||
var curCharLen = 0
|
||||
|
||||
if (str === '') {
|
||||
return str
|
||||
} else if (!str || !isString(str)) {
|
||||
throw new TypeError(
|
||||
'First argument to react-string-replace#replaceString must be a string'
|
||||
)
|
||||
}
|
||||
|
||||
var re = match
|
||||
|
||||
if (!isRegExp(re)) {
|
||||
// @ts-ignore
|
||||
re = new RegExp('(' + escapeRegExp(re) + ')', 'gi')
|
||||
}
|
||||
// @ts-ignore
|
||||
var result = str.split(re)
|
||||
|
||||
// Apply fn to all odd elements
|
||||
for (var i = 1, length = result.length; i < length; i += 2) {
|
||||
/** @see {@link https://github.com/iansinnott/react-string-replace/issues/74} */
|
||||
if (result[i] === undefined || result[i - 1] === undefined) {
|
||||
console.warn(
|
||||
'reactStringReplace: Encountered undefined value during string replacement. Your RegExp may not be working the way you expect.'
|
||||
)
|
||||
continue
|
||||
}
|
||||
|
||||
curCharLen = result[i].length
|
||||
curCharStart += result[i - 1].length
|
||||
result[i] = fn(result[i], i, curCharStart)
|
||||
curCharStart += curCharLen
|
||||
}
|
||||
|
||||
return result
|
||||
}
|
||||
|
||||
// 字符串替换
|
||||
function stringReplace(source, match, fn) {
|
||||
if (!Array.isArray(source)) source = [source]
|
||||
|
||||
return flatten(
|
||||
source.map(function (x) {
|
||||
return isString(x) ? replaceString(x, match, fn) : x
|
||||
})
|
||||
)
|
||||
}
|
||||
|
||||
export function parseText(text, ext){
|
||||
if (!text) return []
|
||||
const regexLink = /(https?:\/\/\S+)/gi
|
||||
const yxAitMsg = ext ? JSON.parse(ext).yxAitMsg : null
|
||||
const emojiArr = stringReplace(text, emojiRegExp, (item) => {
|
||||
return {
|
||||
type: 'emoji',
|
||||
value: item,
|
||||
}
|
||||
})
|
||||
|
||||
const emojiAndLinkArr = stringReplace(emojiArr, regexLink, (item) => {
|
||||
return {
|
||||
type: 'link',
|
||||
value: item,
|
||||
}
|
||||
})
|
||||
|
||||
let emojiAndLinkAndAitArr = emojiAndLinkArr
|
||||
if (yxAitMsg) {
|
||||
Object.keys(yxAitMsg)?.forEach((key) => {
|
||||
const item = yxAitMsg[key]
|
||||
emojiAndLinkAndAitArr = stringReplace(
|
||||
emojiAndLinkAndAitArr,
|
||||
item.text,
|
||||
(item) => {
|
||||
return {
|
||||
type: 'Ait',
|
||||
value: item,
|
||||
}
|
||||
}
|
||||
)
|
||||
})
|
||||
}
|
||||
|
||||
const result = emojiAndLinkAndAitArr.map((item, index) => {
|
||||
if (typeof item == 'string') {
|
||||
return {
|
||||
type: 'text',
|
||||
value: item,
|
||||
key: index + 'text',
|
||||
}
|
||||
} else {
|
||||
return {
|
||||
...item,
|
||||
key: index + item.type,
|
||||
}
|
||||
}
|
||||
})
|
||||
return result
|
||||
}
|
||||
@@ -0,0 +1,27 @@
|
||||
import { t } from './i18n'
|
||||
|
||||
export const handleNoPermission = (res)=> {
|
||||
if (
|
||||
uni.getSystemInfoSync().platform == 'android' ||
|
||||
uni.getSystemInfoSync().platform == 'ios'
|
||||
) {
|
||||
const appAuthorizeSetting = uni.getAppAuthorizeSetting()
|
||||
//点击取消时不出现弹窗
|
||||
const isCameraDenied = appAuthorizeSetting.cameraAuthorized === 'denied'
|
||||
const isUserCancelled =
|
||||
res.errMsg === 'chooseImage:fail User cancelled' ||
|
||||
res.errMsg === 'chooseImage:fail cancel' ||
|
||||
res.errMsg === 'chooseVideo:fail cancel' ||
|
||||
res.errMsg === 'chooseVideo:fail User cancelled'
|
||||
if (
|
||||
(res.code === 11 && isCameraDenied && !isUserCancelled) ||
|
||||
(res.code === 12 && isCameraDenied && !isUserCancelled) ||
|
||||
(res.code === 2 && !isUserCancelled)
|
||||
) {
|
||||
uni.showToast({
|
||||
icon: 'none',
|
||||
title: t('addPermissionText'),
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,23 @@
|
||||
import { EventTracking } from '@xkit-yx/utils/dist/uniapp'
|
||||
//@ts-ignore
|
||||
import imPkg from 'nim-web-sdk-ng/package.json'
|
||||
|
||||
export const trackInit = (
|
||||
component
|
||||
) => {
|
||||
if (uni.$UIKitNIM?.options?.appkey) {
|
||||
const eventTracking = new EventTracking({
|
||||
appKey: uni.$UIKitNIM.options.appkey,
|
||||
version: '10.4.0',
|
||||
component,
|
||||
imVersion: imPkg.version,
|
||||
platform: 'UniApp',
|
||||
os: uni.getSystemInfoSync().platform.toUpperCase(),
|
||||
framework: 'UniApp',
|
||||
language: 'Vue3',
|
||||
container: uni.getSystemInfoSync().uniPlatform.toUpperCase(),
|
||||
})
|
||||
|
||||
eventTracking.track('init', '')
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
let vueVersion
|
||||
// #ifndef VUE3
|
||||
export * from '@vue/composition-api'
|
||||
vueVersion = 2
|
||||
// #endif
|
||||
|
||||
// #ifdef VUE3
|
||||
export * from 'vue'
|
||||
vueVersion = 3
|
||||
// #endif
|
||||
console.log(`vue version is ${vueVersion}`)
|
||||
export { vueVersion }
|
||||
+1808
File diff suppressed because it is too large
Load Diff
Reference in New Issue
Block a user