131 lines
4.7 KiB
Vue
131 lines
4.7 KiB
Vue
<template>
|
|
<view class="page">
|
|
<fy-header title="同事资料" back />
|
|
<view v-if="p" class="body">
|
|
<view class="card profile">
|
|
<image v-if="p.avatar" class="av img" :src="p.avatar" mode="aspectFill" />
|
|
<view v-else class="av">{{ p.name.slice(0, 1) }}</view>
|
|
<view class="info">
|
|
<view class="nm">
|
|
<text class="n">{{ p.name }}</text>
|
|
<text class="tag">{{ p.employeeStatus || '在职' }}</text>
|
|
</view>
|
|
<text class="s">{{ p.title }} · {{ p.department }}</text>
|
|
<view class="ph" @click="copyPhone">
|
|
<text>☎ {{ masked }}</text>
|
|
<text class="copy">复制</text>
|
|
</view>
|
|
</view>
|
|
</view>
|
|
|
|
<view class="acts">
|
|
<view class="act" @click="chat">
|
|
<text class="ai">💬</text>
|
|
<text>发消息</text>
|
|
</view>
|
|
<view class="act" @click="call">
|
|
<text class="ai">☎</text>
|
|
<text>语音通话</text>
|
|
</view>
|
|
<view class="act" @click="video">
|
|
<text class="ai">▷</text>
|
|
<text>视频通话</text>
|
|
</view>
|
|
</view>
|
|
|
|
<view class="card rows">
|
|
<view class="row">
|
|
<text class="k">所属部门</text>
|
|
<text class="v">{{ p.department || '—' }}</text>
|
|
</view>
|
|
<view class="row">
|
|
<text class="k">工号</text>
|
|
<text class="v">{{ p.jobId || '—' }}</text>
|
|
</view>
|
|
</view>
|
|
|
|
<view class="card rows">
|
|
<view class="row" @click="toggle('pinned')" v-if="conv">
|
|
<text class="k">置顶聊天</text>
|
|
<text class="v brand">{{ conv.pinned ? '已置顶' : '未置顶' }}</text>
|
|
</view>
|
|
<view class="row" @click="toggle('muted')" v-if="conv">
|
|
<text class="k">消息免打扰</text>
|
|
<text class="v brand">{{ conv.muted ? '已开启' : '未开启' }}</text>
|
|
</view>
|
|
</view>
|
|
</view>
|
|
</view>
|
|
</template>
|
|
|
|
<script>
|
|
import FyHeader from '../../components/fy-header.vue'
|
|
import { store } from '../../utils/store.js'
|
|
import { dmId, maskPhone, toast } from '../../utils/format.js'
|
|
|
|
export default {
|
|
components: { FyHeader },
|
|
data() { return { id: '', tick: 0 } },
|
|
computed: {
|
|
p() { return store.person(this.id) },
|
|
masked() { return maskPhone(this.p && this.p.phone) },
|
|
conv() {
|
|
this.tick
|
|
if (!this.p || !store.me) return null
|
|
return store.findConv(dmId(store.me.id, this.p.id))
|
|
}
|
|
},
|
|
onLoad(q) { this.id = decodeURIComponent(q.id || '') },
|
|
methods: {
|
|
chat() {
|
|
if (!this.p) return
|
|
const conv = store.openDirect(this.p)
|
|
uni.navigateTo({ url: '/pages/chat/chat?sid=' + encodeURIComponent(conv.id) })
|
|
},
|
|
call() {
|
|
if (!this.p) return
|
|
store.startCall(this.p.id, { video: false }).catch((e) => toast((e && e.message) || '无法发起通话'))
|
|
},
|
|
async video() {
|
|
if (!this.p) return
|
|
try {
|
|
await store.startCall(this.p.id, { video: true })
|
|
} catch (e) {
|
|
toast((e && e.message) || '暂无法发起视频通话')
|
|
}
|
|
},
|
|
copyPhone() {
|
|
if (!this.p || !this.p.phone) return
|
|
uni.setClipboardData({ data: String(this.p.phone) })
|
|
},
|
|
toggle(field) {
|
|
if (!this.conv) return
|
|
store.setSession(this.conv, { [field]: !this.conv[field] })
|
|
this.tick += 1
|
|
}
|
|
}
|
|
}
|
|
</script>
|
|
|
|
<style scoped>
|
|
.body { padding: 16rpx 24rpx 48rpx; }
|
|
.profile { padding: 32rpx 24rpx; display: flex; align-items: center; }
|
|
.av { width: 112rpx; height: 112rpx; border-radius: 24rpx; background: #E8F1FF; color: #1677FF; display: flex; align-items: center; justify-content: center; font-size: 44rpx; font-weight: 650; }
|
|
.av.img { border-radius: 24rpx; }
|
|
.info { margin-left: 20rpx; flex: 1; min-width: 0; }
|
|
.nm { display: flex; align-items: center; gap: 12rpx; }
|
|
.n { font-size: 36rpx; font-weight: 650; color: #111827; }
|
|
.tag { font-size: 22rpx; background: #E8F8EF; color: #16A34A; padding: 2rpx 10rpx; border-radius: 8rpx; }
|
|
.s, .ph { display: block; font-size: 24rpx; color: #6B7280; margin-top: 6rpx; }
|
|
.copy { color: #1677FF; margin-left: 12rpx; }
|
|
.acts { display: flex; gap: 16rpx; margin: 20rpx 0; }
|
|
.act { flex: 1; background: #fff; border-radius: 20rpx; border: 1rpx solid rgba(17,24,39,0.06); padding: 20rpx 8rpx; display: flex; flex-direction: column; align-items: center; font-size: 22rpx; font-weight: 600; color: #111827; }
|
|
.ai { font-size: 36rpx; color: #1677FF; margin-bottom: 8rpx; }
|
|
.rows { overflow: hidden; margin-bottom: 20rpx; }
|
|
.row { display: flex; justify-content: space-between; align-items: center; padding: 28rpx 24rpx; font-size: 28rpx; }
|
|
.row + .row { border-top: 1rpx solid #F0F2F5; }
|
|
.k { color: #6B7280; }
|
|
.v { color: #111827; }
|
|
.brand { color: #1677FF; font-weight: 600; }
|
|
</style>
|