Files
medical-mall/pages/mall/admin/marketing/live/anchor.uvue

377 lines
9.1 KiB
Plaintext
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
<template>
<view class="marketing-live-anchor">
<view class="action-bar">
<button class="btn-add" @click="showModal = true">添加主播</button>
</view>
<view class="table-card border-shadow">
<view class="table-container">
<view class="table-head">
<view class="th cell-id">ID</view>
<view class="th cell-name">名称</view>
<view class="th cell-phone">电话</view>
<view class="th cell-wechat">微信号</view>
<view class="th cell-op">操作</view>
</view>
<view class="table-body">
<view v-for="item in anchorList" :key="item.id" class="table-row">
<view class="td cell-id"><text class="td-txt">{{ item.id }}</text></view>
<view class="td cell-name"><text class="td-txt">{{ item.name }}</text></view>
<view class="td cell-phone"><text class="td-txt">{{ item.phone }}</text></view>
<view class="td cell-wechat"><text class="td-txt">{{ item.wechat }}</text></view>
<view class="td cell-op">
<view class="op-links">
<text class="op-link" @click="handleEdit(item)">修改</text>
<text class="op-split">|</text>
<text class="op-link" @click="handleDelete(item)">删除</text>
</view>
</view>
</view>
</view>
</view>
<!-- 分页 -->
<CommonPagination
v-if="anchorList.length > 0"
:total="anchorList.length"
:loading="false"
:currentPage="currentPage"
:pageSize="pageSize"
:pageSizeOptionLabels="pageSizeOptionLabels"
:pageSizeIndex="pageSizeIndex"
:visiblePages="visiblePages"
:totalPage="totalPage"
:jumpPageInput="jumpPageInput"
@page-size-change="handlePageSizeChange"
@page-change="handlePageChange"
@update:jumpPageInput="(val : string) => { jumpPageInput = val }"
@jump-page="handleJumpPage"
/>
</view>
<!-- Modal Overlay -->
<view v-if="showModal" class="modal-mask" @click="showModal = false"></view>
<!-- Modal Panel -->
<view v-if="showModal" class="modal-panel">
<view class="modal-header">
<text class="modal-title">添加主播</text>
<text class="modal-close" @click="showModal = false">×</text>
</view>
<view class="modal-content">
<view class="form-item">
<text class="form-label required">主播名称:</text>
<input class="form-input" placeholder="请输入主播名称" />
</view>
<view class="form-item">
<text class="form-label required">主播微信号:</text>
<input class="form-input" placeholder="请输入主播微信号" />
</view>
<view class="form-item">
<text class="form-label required">主播手机号:</text>
<input class="form-input" v-model="formData.phone" placeholder="请输入主播手机号" />
</view>
<view class="form-item">
<text class="form-label">主播图像:</text>
<view class="upload-mock" @click="handleUpload">
<image v-if="formData.avatar" :src="formData.avatar" mode="aspectFill" class="avatar-preview" />
<text v-else class="upload-ic">🖼️</text>
</view>
</view>
</view>
<view class="modal-footer">
<button class="btn-cancel" @click="showModal = false">取消</button>
<button class="btn-confirm" @click="handleSubmit">确定</button>
</view>
</view>
</view>
</template>
<script setup lang="uts">
import { ref, computed } from 'vue'
import CommonPagination from '@/components/CommonPagination/CommonPagination.uvue'
const showModal = ref(false)
const formData = ref({
id: 0,
name: '',
wechat: '',
phone: '',
avatar: ''
})
const anchorList = ref([
{
id: 11,
name: '万万',
phone: '15012341234',
wechat: 'xiao112032014'
},
{
id: 10,
name: '打羽毛球',
phone: '13333333333',
wechat: 'evoxwht'
}
])
const handleEdit = (item: any) => {
formData.value = { ...item, avatar: '' }
showModal.value = true
}
const handleDelete = (item: any) => {
uni.showModal({
title: '提示',
content: '确定要删除该主播吗?',
success: (res) => {
if (res.confirm) {
anchorList.value = anchorList.value.filter(i => i.id !== item.id)
uni.showToast({ title: '删除成功' })
}
}
})
}
const handleUpload = () => {
uni.chooseImage({
count: 1,
success: (res) => {
formData.value.avatar = res.tempFilePaths[0]
}
})
}
const handleSubmit = () => {
uni.showToast({ title: '操作成功', icon: 'success' })
showModal.value = false
}
// 分页适配状态
const currentPage = ref(1)
const pageSize = ref(15)
let jumpPageInput = ''
const pageSizeOptions = [10, 15, 20, 30, 50]
const pageSizeOptionLabels = computed(() => pageSizeOptions.map((n: number) => `${n}条/页`))
const pageSizeIndex = computed(() => {
const idx = pageSizeOptions.indexOf(pageSize.value)
return idx >= 0 ? idx : 0
})
const totalPage = computed(() => Math.max(1, Math.ceil(anchorList.value.length / pageSize.value)))
const visiblePages = computed(() => {
const t = totalPage.value
const cur = currentPage.value
if (t <= 7) return Array.from({ length: t }, (_: any, i: number) => i + 1)
if (cur <= 4) return [1, 2, 3, 4, 5, -1, t]
if (cur >= t - 3) return [1, -1, t - 4, t - 3, t - 2, t - 1, t]
return [1, -1, cur - 1, cur, cur + 1, -1, t]
})
const handlePageChange = (p: number) => { currentPage.value = p }
const handlePageSizeChange = (e: any) => {
const idx = Number(e.detail.value)
pageSize.value = pageSizeOptions[idx] ?? pageSizeOptions[0]
currentPage.value = 1
}
const handleJumpPage = () => {
const p = parseInt(jumpPageInput)
if (!isNaN(p) && p >= 1 && p <= totalPage.value) currentPage.value = p
}
</script>
<style scoped lang="scss">
.marketing-live-anchor {
min-height: auto;
background: transparent;
padding: 0;
}
.border-shadow {
background: #fff;
border-radius: 4px;
box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.05);
}
/* 操作栏 */
.action-bar {
margin-bottom: 16px;
}
.btn-add {
width: auto;
padding: 0 16px;
height: 32px;
background-color: #1890ff;
color: #fff;
font-size: 14px;
border: none;
border-radius: 4px;
display: inline-flex;
align-items: center;
justify-content: center;
cursor: pointer;
}
/* 表格区域 */
.table-card {
padding: 24px;
}
.table-head {
display: flex;
flex-direction: row;
background-color: #f8f8f9;
border-bottom: 1px solid #e8eaec;
}
.th {
padding: 12px 8px;
font-size: 13px;
color: #515a6e;
font-weight: bold;
}
.table-row {
display: flex;
flex-direction: row;
border-bottom: 1px solid #e8eaec;
align-items: center;
}
.td {
padding: 16px 8px;
}
.td-txt { font-size: 13px; color: #515a6e; }
/* 各列宽度 */
.cell-id { width: 80px; }
.cell-name { flex: 1; min-width: 150px; }
.cell-phone { width: 180px; }
.cell-wechat { width: 180px; }
.cell-op { width: 120px; text-align: right; }
.op-links {
display: flex;
flex-direction: row;
justify-content: flex-end;
align-items: center;
}
.op-link { color: #1890ff; font-size: 13px; cursor: pointer; }
.op-split { color: #e8eaec; margin: 0 8px; }
/* 分页区域已迁至 CommonPagination 组件 */
/* Modal Styles */
.modal-mask {
position: fixed;
top: 0;
left: 0;
right: 0;
bottom: 0;
background-color: rgba(0, 0, 0, 0.45);
z-index: 1000;
}
.modal-panel {
position: fixed;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
width: 520px;
background-color: #fff;
z-index: 1001;
border-radius: 4px;
box-shadow: 0 4px 12px rgba(0, 0, 0, 0.15);
display: flex;
flex-direction: column;
}
.modal-header {
padding: 16px 24px;
border-bottom: 1px solid #f0f0f0;
display: flex;
flex-direction: row;
justify-content: space-between;
align-items: center;
}
.modal-title {
font-size: 16px;
font-weight: 600;
color: #262626;
}
.modal-close {
font-size: 24px;
color: #bfbfbf;
cursor: pointer;
}
.modal-content {
padding: 24px;
}
.form-item {
margin-bottom: 24px;
}
.form-label {
display: block;
font-size: 14px;
color: #262626;
margin-bottom: 8px;
}
.required::before {
content: '*';
color: #ff4d4f;
margin-right: 4px;
}
.form-input {
width: 100%;
height: 32px;
border: 1px solid #d9d9d9;
border-radius: 4px;
padding: 0 12px;
font-size: 14px;
}
.upload-mock {
width: 80px;
height: 80px;
border: 1px dashed #d9d9d9;
border-radius: 4px;
display: flex;
align-items: center;
justify-content: center;
background-color: #fafafa;
}
.upload-ic { font-size: 24px; color: #bfbfbf; }
.modal-footer {
padding: 10px 16px;
border-top: 1px solid #f0f0f0;
display: flex;
flex-direction: row;
justify-content: flex-end;
gap: 8px;
}
.btn-cancel, .btn-confirm {
width: auto;
padding: 0 15px;
height: 32px;
font-size: 14px;
border-radius: 4px;
cursor: pointer;
}
.btn-cancel {
background-color: #fff;
border: 1px solid #d9d9d9;
color: #595959;
}
.btn-confirm {
background-color: #1890ff;
border: 1px solid #1890ff;
color: #fff;
}
</style>