chore:认领码正常
This commit is contained in:
@@ -1,13 +1,17 @@
|
||||
<template>
|
||||
<view class="card-detail">
|
||||
<view class="card-detail" :style="designVars" :class="{ 'qs-square': ds.quickStyle === 'square' }">
|
||||
<view class="page-layer">
|
||||
<!-- 名片区: 蓝色背景 + 白卡。蓝色自导航栏下沿一路向下延伸到卡片内部后渐隐 -->
|
||||
<view class="card-wrap" v-if="relation">
|
||||
<!-- 蓝色背景层: 下沿锚定在卡片底部上方, 故卡片高度变化时蓝色下沿跟着走 -->
|
||||
<view class="card-wrap-bg"></view>
|
||||
<view class="card-wrap-bg" :style="cardWrapStyle"></view>
|
||||
|
||||
<!-- 名片卡: 对齐设计稿 —— 姓名/职位/公司与全部联系方式都收在同一张白卡内, 不再拆成上下两块 -->
|
||||
<view class="detail-card">
|
||||
<view class="detail-card" :class="['layout-' + ds.layout, ds.cover && ds.layout !== 'classic' ? 'has-cover' : '']">
|
||||
<!-- 封面(hero/compact): 有 cover 时全幅主视觉, 身份信息压在其下沿; classic 不展示封面 -->
|
||||
<view v-if="ds.cover && ds.layout !== 'classic'" class="dc-cover" :class="ds.layout === 'compact' ? 'dc-cover-compact' : 'dc-cover-hero'">
|
||||
<image class="dc-cover-img" :src="$util.img(ds.cover)" mode="aspectFill"></image>
|
||||
</view>
|
||||
<view class="dc-name">{{ relation.name || '未命名名片' }}</view>
|
||||
<view class="dc-job" v-if="relation.job_title">{{ relation.job_title }}</view>
|
||||
<view class="dc-company" v-if="relation.company">{{ relation.company }}</view>
|
||||
@@ -171,12 +175,36 @@
|
||||
</template>
|
||||
|
||||
<script>
|
||||
/**
|
||||
* 把两个 hex 颜色按比例混合(返回 hex)。t=0 取 a, t=1 取 b。
|
||||
* 用于从后端下发的主色/文字色派生浅色调(提示条底色、次级文字色等),
|
||||
* 避免在前端硬编码与主题色脱节的灰色。
|
||||
*/
|
||||
function mixHex(a, b, t) {
|
||||
const toRgb = h => {
|
||||
h = (h || '').replace('#', '');
|
||||
if (h.length === 3) h = h.split('').map(c => c + c).join('');
|
||||
const n = parseInt(h, 16);
|
||||
if (isNaN(n)) return [0, 0, 0];
|
||||
return [(n >> 16) & 255, (n >> 8) & 255, n & 255];
|
||||
};
|
||||
const [r1, g1, b1] = toRgb(a);
|
||||
const [r2, g2, b2] = toRgb(b);
|
||||
const r = Math.round(r1 + (r2 - r1) * t);
|
||||
const g = Math.round(g1 + (g2 - g1) * t);
|
||||
const bl = Math.round(b1 + (b2 - b1) * t);
|
||||
return '#' + [r, g, bl].map(x => x.toString(16).padStart(2, '0')).join('');
|
||||
}
|
||||
|
||||
export default {
|
||||
data() {
|
||||
return {
|
||||
cardId: '',
|
||||
relation: null,
|
||||
source: null,
|
||||
// 名片设计摘要(后端 /card/api/card/detail 顶层 design, 旧后端无此键时为 null)
|
||||
// 仅做有限主题化(色/字/圆角/布局/封面), 不渲染画布块
|
||||
design: null,
|
||||
shareList: [],
|
||||
isLoading: true,
|
||||
errorMsg: '',
|
||||
@@ -234,6 +262,76 @@ export default {
|
||||
|
||||
return rows;
|
||||
},
|
||||
/* ============ 名片设计摘要(后端下发, 仅做有限主题化) ============ */
|
||||
/**
|
||||
* 归一化 design: 字段缺失/非法一律回落文档默认值, 任何异常都不应阻断页面。
|
||||
* 后端已对颜色 safeColor 校验、cover 转绝对地址、layout/font_family/font_scale 钳位,
|
||||
* 这里再做一层前端兜底(旧后端无 design 键时 all-default)。
|
||||
*/
|
||||
ds() {
|
||||
const d = this.design || {};
|
||||
const FONTS = {
|
||||
system: '-apple-system,BlinkMacSystemFont,"PingFang SC","Helvetica Neue",Arial,sans-serif',
|
||||
sans: '"Source Han Sans SC","Noto Sans SC","PingFang SC",Helvetica,Arial,sans-serif',
|
||||
serif: '"Source Han Serif SC","Songti SC",SimSun,Georgia,serif',
|
||||
rounded: '"Yuanti SC","YouYuan","Quicksand",-apple-system,sans-serif'
|
||||
};
|
||||
const isHex = v => /^#[0-9a-fA-F]{3,8}$/.test(v || '');
|
||||
const theme = isHex(d.theme_color) ? d.theme_color : '#119dff';
|
||||
const text = isHex(d.text_color) ? d.text_color : '#1f2329';
|
||||
const bg = isHex(d.bg_color) ? d.bg_color : '#ffffff';
|
||||
const fontKey = FONTS[d.font_family] ? d.font_family : 'system';
|
||||
const fontScale = Math.min(160, Math.max(60, Number(d.font_scale) || 100));
|
||||
const cardRadius = Number(d.card_radius) || 16;
|
||||
const layout = ['hero', 'compact', 'classic'].includes(d.layout) ? d.layout : 'classic';
|
||||
const headerEnd = typeof d.header_gradient_end === 'string' ? d.header_gradient_end : '';
|
||||
const headerAngle = Number(d.header_gradient_angle) || 150;
|
||||
return {
|
||||
themeColor: theme,
|
||||
textColor: text,
|
||||
bgColor: bg,
|
||||
layout: layout,
|
||||
cover: d.cover || '',
|
||||
fontFamily: FONTS[fontKey],
|
||||
fontScale: fontScale,
|
||||
cardRadius: cardRadius,
|
||||
headerGradientEnd: headerEnd,
|
||||
headerGradientAngle: headerAngle,
|
||||
quickStyle: d.quick_style || '',
|
||||
templateId: d.template_id || '',
|
||||
source: d.source || 'none',
|
||||
// 派生(前端按主题色/文字色混合得到, 避免硬编码脱节灰)
|
||||
textSoft: mixHex(text, bg, 0.55),
|
||||
themeSoft: mixHex(theme, '#ffffff', 0.85),
|
||||
fontScaleNum: fontScale / 100
|
||||
};
|
||||
},
|
||||
/** 根节点注入的 CSS 变量(所有卡片视觉从变量取值) */
|
||||
designVars() {
|
||||
const s = this.ds;
|
||||
return {
|
||||
'--card-theme': s.themeColor,
|
||||
'--card-theme-end': s.headerGradientEnd || s.themeColor,
|
||||
'--card-text': s.textColor,
|
||||
'--card-text-soft': s.textSoft,
|
||||
'--card-bg': s.bgColor,
|
||||
'--card-radius': s.cardRadius + 'px',
|
||||
'--card-font': s.fontFamily,
|
||||
'--card-font-scale': s.fontScaleNum
|
||||
};
|
||||
},
|
||||
/** 头部蓝色背景层: 主题色渐变(header_gradient_end 为空时按文档算法向黑加深 28%) */
|
||||
headerBg() {
|
||||
const s = this.ds;
|
||||
if (s.headerGradientEnd) {
|
||||
return 'linear-gradient(' + s.headerGradientAngle + 'deg, ' + s.themeColor + ', ' + s.headerGradientEnd + ')';
|
||||
}
|
||||
return 'linear-gradient(150deg, ' + s.themeColor + ' 0%, ' + s.themeColor + ' 62%, rgba(0,0,0,0.28) 160%)';
|
||||
},
|
||||
/** 头部背景层内联样式(覆盖静态 background-color) */
|
||||
cardWrapStyle() {
|
||||
return { background: this.headerBg };
|
||||
},
|
||||
// 是否「待处理请求」(决定头部文案与是否显示忽略/同意)
|
||||
exchangeIsRequest() {
|
||||
return this.exchangeList.length > 0;
|
||||
@@ -314,6 +412,8 @@ export default {
|
||||
this.isLoading = false;
|
||||
this.relation = data.relation || null;
|
||||
this.source = data.source || null;
|
||||
// 名片设计摘要: 旧后端无 design 键时为 null, 全页面按默认值渲染(不报错/不阻断)
|
||||
this.design = data.design || null;
|
||||
this.shareList = data.share_list || [];
|
||||
// 公开页/二维码地址由后端统一拼装返回(含 site_id/域名), 前端不自行拼接
|
||||
this.shareUrl = data.wap_url || '';
|
||||
@@ -648,6 +748,8 @@ export default {
|
||||
background-color: #ffffff;
|
||||
padding: 0 0 60rpx;
|
||||
box-sizing: border-box;
|
||||
// 设计摘要: 全局字体键(后端 font_family → CSS 字体栈)
|
||||
font-family: var(--card-font, -apple-system, "PingFang SC", "Helvetica Neue", Arial, sans-serif);
|
||||
}
|
||||
|
||||
// 内容层
|
||||
@@ -672,7 +774,7 @@ export default {
|
||||
right: 0;
|
||||
bottom: 48rpx;
|
||||
z-index: 0;
|
||||
background-color: #2aa5ff;
|
||||
background-color: var(--card-theme, #2aa5ff);
|
||||
border-bottom-left-radius: 240rpx 44rpx;
|
||||
border-bottom-right-radius: 240rpx 44rpx;
|
||||
pointer-events: none;
|
||||
@@ -684,30 +786,48 @@ export default {
|
||||
position: relative;
|
||||
z-index: 1;
|
||||
margin: 0 24rpx;
|
||||
background-color: #ffffff;
|
||||
border-radius: 20rpx;
|
||||
// 设计摘要: 名片底色 + 圆角(后端 bg_color / card_radius)
|
||||
background-color: var(--card-bg, #ffffff);
|
||||
border-radius: var(--card-radius, 20rpx);
|
||||
padding: 40rpx 36rpx 32rpx;
|
||||
box-shadow: 0 6rpx 20rpx rgba(0, 30, 80, 0.06);
|
||||
|
||||
// 封面(hero/compact): 顶部全幅出血, 身份信息压在其下沿; classic 不展示
|
||||
.dc-cover {
|
||||
margin: -40rpx -36rpx 24rpx;
|
||||
border-top-left-radius: var(--card-radius, 20rpx);
|
||||
border-top-right-radius: var(--card-radius, 20rpx);
|
||||
overflow: hidden;
|
||||
|
||||
.dc-cover-img {
|
||||
display: block;
|
||||
width: 100%;
|
||||
}
|
||||
}
|
||||
.dc-cover-hero .dc-cover-img { height: 200rpx; }
|
||||
.dc-cover-compact .dc-cover-img { height: 90rpx; }
|
||||
|
||||
.dc-name {
|
||||
font-size: 44rpx;
|
||||
font-weight: 700;
|
||||
color: #1a1a1a;
|
||||
// 设计摘要: 正文字色(姓名保持固定字号, 不随 font_scale 放大, 避免溢出)
|
||||
color: var(--card-text, #1a1a1a);
|
||||
line-height: 1.3;
|
||||
}
|
||||
|
||||
.dc-job {
|
||||
margin-top: 6rpx;
|
||||
font-size: 28rpx;
|
||||
// 设计摘要: 次级文字 = 文字色向底色混合; 字号随 font_scale 缩放(正文)
|
||||
font-size: calc(28rpx * var(--card-font-scale, 1));
|
||||
line-height: 1.3;
|
||||
color: #4a4a4a;
|
||||
color: var(--card-text-soft, #4a4a4a);
|
||||
}
|
||||
|
||||
.dc-company {
|
||||
margin-top: 2rpx;
|
||||
font-size: 26rpx;
|
||||
font-size: calc(26rpx * var(--card-font-scale, 1));
|
||||
line-height: 1.3;
|
||||
color: #9aa4b2;
|
||||
color: var(--card-text-soft, #9aa4b2);
|
||||
}
|
||||
|
||||
.dc-rows {
|
||||
@@ -715,6 +835,15 @@ export default {
|
||||
margin-top: 56rpx;
|
||||
}
|
||||
|
||||
// 紧凑布局: 间距收紧(封面压扁由 .dc-cover-compact 控制)
|
||||
&.layout-compact {
|
||||
padding-top: 28rpx;
|
||||
|
||||
.dc-rows { margin-top: 28rpx; }
|
||||
.field-row { padding: 8rpx 0; }
|
||||
.dc-name { font-size: 40rpx; }
|
||||
}
|
||||
|
||||
// 资料行: 全局 view{line-height:1.8} 会把每行撑高, 这里显式收紧到参考图行距
|
||||
.field-row {
|
||||
display: flex;
|
||||
@@ -731,7 +860,7 @@ export default {
|
||||
margin-right: 18rpx;
|
||||
font-size: 32rpx;
|
||||
line-height: 1;
|
||||
color: #8a94a6;
|
||||
color: var(--card-text-soft, #8a94a6);
|
||||
text-align: center;
|
||||
flex-shrink: 0;
|
||||
}
|
||||
@@ -739,18 +868,18 @@ export default {
|
||||
.field-tag {
|
||||
min-width: 40rpx;
|
||||
margin-right: 18rpx;
|
||||
font-size: 26rpx;
|
||||
font-size: calc(26rpx * var(--card-font-scale, 1));
|
||||
line-height: 1.2;
|
||||
color: #9aa4b2;
|
||||
color: var(--card-text-soft, #9aa4b2);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.field-value {
|
||||
flex: 1;
|
||||
min-width: 0;
|
||||
font-size: 28rpx;
|
||||
font-size: calc(28rpx * var(--card-font-scale, 1));
|
||||
line-height: 1.25;
|
||||
color: #333333;
|
||||
color: var(--card-text, #333333);
|
||||
word-break: break-all;
|
||||
}
|
||||
|
||||
@@ -808,7 +937,7 @@ export default {
|
||||
.eg-icon {
|
||||
font-size: 52rpx;
|
||||
line-height: 1;
|
||||
color: #2aa5ff;
|
||||
color: var(--card-theme, #2aa5ff);
|
||||
}
|
||||
|
||||
.eg-text {
|
||||
@@ -834,7 +963,8 @@ export default {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
padding: 12rpx 24rpx;
|
||||
background-color: #eaf3ff;
|
||||
// 设计摘要: 提示条底色 = 主题色向白混合的浅色调
|
||||
background-color: var(--card-theme-soft, #eaf3ff);
|
||||
}
|
||||
|
||||
// 参考图: 蓝色喇叭图标(替换原来的小圆点)
|
||||
@@ -842,7 +972,7 @@ export default {
|
||||
margin-right: 10rpx;
|
||||
font-size: 26rpx;
|
||||
line-height: 1;
|
||||
color: #2aa5ff;
|
||||
color: var(--card-theme, #2aa5ff);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
@@ -861,7 +991,7 @@ export default {
|
||||
font-size: 26rpx;
|
||||
line-height: 1.2;
|
||||
font-weight: 600;
|
||||
color: #2aa5ff;
|
||||
color: var(--card-theme, #2aa5ff);
|
||||
}
|
||||
|
||||
.eb-arrow {
|
||||
@@ -920,7 +1050,7 @@ export default {
|
||||
.eb-badge {
|
||||
margin-left: 8rpx;
|
||||
font-size: 24rpx;
|
||||
color: #2aa5ff;
|
||||
color: var(--card-theme, #2aa5ff);
|
||||
}
|
||||
|
||||
// 参考图: 职位一行、公司一行
|
||||
@@ -985,7 +1115,7 @@ export default {
|
||||
|
||||
// 同意: 蓝底实心圆 + 白色 ✓
|
||||
&.eb-act-agree {
|
||||
background-color: #2aa5ff;
|
||||
background-color: var(--card-theme, #2aa5ff);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1034,7 +1164,7 @@ export default {
|
||||
|
||||
// 参考图: 「同意」文字为蓝色, 「忽略」为灰色
|
||||
.eb-act-text-main {
|
||||
color: #2aa5ff;
|
||||
color: var(--card-theme, #2aa5ff);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1147,8 +1277,8 @@ export default {
|
||||
}
|
||||
|
||||
.ss-btn-main {
|
||||
background-color: var(--main-color, #0054a5);
|
||||
border-color: var(--main-color, #0054a5);
|
||||
background-color: var(--card-theme, #119dff);
|
||||
border-color: var(--card-theme, #119dff);
|
||||
color: #ffffff;
|
||||
}
|
||||
}
|
||||
@@ -1177,9 +1307,9 @@ export default {
|
||||
font-size: 34rpx;
|
||||
font-weight: 600;
|
||||
color: #ffffff;
|
||||
// 设计稿: 亮蓝渐变胶囊
|
||||
background: linear-gradient(135deg, #2aa5ff 0%, #0d7bf0 100%);
|
||||
box-shadow: 0 10rpx 24rpx rgba(13, 123, 240, 0.35);
|
||||
// 设计摘要: 主题色渐变胶囊(135° 由主题色 → 头部渐变第二色)
|
||||
background: linear-gradient(135deg, var(--card-theme, #2aa5ff) 0%, var(--card-theme-end, #0d7bf0) 100%);
|
||||
box-shadow: 0 10rpx 24rpx rgba(0, 0, 0, 0.12);
|
||||
border-radius: 48rpx;
|
||||
// 小程序原生 <button> 自带 margin/padding/背景/::after 边框, 需清掉才能当普通块用
|
||||
margin: 0;
|
||||
@@ -1192,6 +1322,11 @@ export default {
|
||||
}
|
||||
}
|
||||
|
||||
/* 快捷操作区: quick_style=square → 方形快捷图标(设计摘要 §3 / 自测矩阵) */
|
||||
.qs-square .eb-act {
|
||||
border-radius: 20%;
|
||||
}
|
||||
|
||||
.detail-loading {
|
||||
text-align: center;
|
||||
color: #999999;
|
||||
|
||||
@@ -51,6 +51,31 @@
|
||||
<ns-empty v-if="!isLoading && list.length === 0" :isIndex="false"
|
||||
:text="emptyText"></ns-empty>
|
||||
</view>
|
||||
|
||||
<!-- 认领弹层: 支持领取码/名片编号 + 扫码带参预填(与 card_claim_api 文档同步) -->
|
||||
<view v-if="showClaim" class="claim-mask" @tap="closeClaim">
|
||||
<view class="claim-pop" @tap.stop>
|
||||
<view class="claim-pop-title">认领名片</view>
|
||||
<view class="claim-pop-tabs">
|
||||
<view class="claim-tab" :class="{ active: claimMode === 'code' }" @tap="claimMode = 'code'">领取码</view>
|
||||
<view class="claim-tab" :class="{ active: claimMode === 'id' }" @tap="claimMode = 'id'">名片编号</view>
|
||||
</view>
|
||||
<view class="claim-input-wrap">
|
||||
<input class="claim-input" :value="claimInput"
|
||||
:placeholder="claimMode === 'code' ? '输入 8 位领取码(大写字母数字)' : '输入名片编号'"
|
||||
@input="onClaimInput" confirm-type="done" @confirm="submitClaim" />
|
||||
<text v-if="claimInput" class="claim-clear" @tap="claimInput = ''">✕</text>
|
||||
</view>
|
||||
<view class="claim-scan" @tap="scanClaim">
|
||||
<text class="iconfont icon-saomafu"></text>
|
||||
<text>扫码认领(自动识别领取码 / 编号)</text>
|
||||
</view>
|
||||
<view class="claim-pop-actions">
|
||||
<view class="claim-btn-cancel" @tap="closeClaim">取消</view>
|
||||
<view class="claim-btn-confirm" @tap="submitClaim">确认认领</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
@@ -66,10 +91,21 @@ export default {
|
||||
keyword: '',
|
||||
onlyFav: false,
|
||||
isLoading: false,
|
||||
emptyText: '暂无名片,可点击右上角「新建」或「认领」添加'
|
||||
emptyText: '暂无名片,可点击右上角「新建」或「认领」添加',
|
||||
// 认领弹层状态(与 card_claim_api 文档同步)
|
||||
showClaim: false,
|
||||
claimInput: '',
|
||||
claimMode: 'code', // code=领取码(主通道), id=名片编号(旧入口兼容)
|
||||
pendingClaimCode: '' // 扫码带参预填的码
|
||||
};
|
||||
},
|
||||
onLoad() {
|
||||
onLoad(options) {
|
||||
// 扫码带参预填(文档 §5): 二维码/链接带 claim_code 或 card_id 直接进入认领
|
||||
if (options && (options.claim_code || options.card_id)) {
|
||||
this.pendingClaimCode = (options.claim_code || options.card_id || '')
|
||||
.toUpperCase().replace(/\s+/g, '');
|
||||
this.claimMode = options.claim_code ? 'code' : 'id';
|
||||
}
|
||||
this.refresh();
|
||||
},
|
||||
onPullDownRefresh() {
|
||||
@@ -206,35 +242,78 @@ export default {
|
||||
url: '/pages_tool/card/edit'
|
||||
});
|
||||
},
|
||||
// 认领: 打开弹层(支持领取码/名片编号 + 扫码带参预填, 与 card_claim_api 文档同步)
|
||||
onClaimTap() {
|
||||
uni.showModal({
|
||||
title: '认领名片',
|
||||
editable: true,
|
||||
placeholderText: '粘贴商家提供的名片编号(card_id)',
|
||||
success: res => {
|
||||
if (!res.confirm) return;
|
||||
const cardId = (res.content || '').trim();
|
||||
if (!cardId) {
|
||||
uni.showToast({ title: '请输入名片编号', icon: 'none' });
|
||||
this.claimInput = this.pendingClaimCode || '';
|
||||
this.showClaim = true;
|
||||
},
|
||||
onClaimInput(e) {
|
||||
// 输入框自动转大写并过滤空格(文档 §5 checklist)
|
||||
this.claimInput = (e.detail.value || '').toUpperCase().replace(/\s+/g, '');
|
||||
},
|
||||
closeClaim() {
|
||||
this.showClaim = false;
|
||||
},
|
||||
submitClaim() {
|
||||
const code = (this.claimInput || '').trim().toUpperCase().replace(/\s+/g, '');
|
||||
this.claimInput = code;
|
||||
if (!code) {
|
||||
uni.showToast({
|
||||
title: this.claimMode === 'code' ? '请输入领取码' : '请输入名片编号',
|
||||
icon: 'none'
|
||||
});
|
||||
return;
|
||||
}
|
||||
this.doClaim(code);
|
||||
this.closeClaim();
|
||||
},
|
||||
// 扫码认领: 解析二维码(URL 参数或整串), 自动识别领取码/名片编号
|
||||
scanClaim() {
|
||||
// #ifndef H5
|
||||
uni.scanCode({
|
||||
success: r => {
|
||||
const code = this.parseClaimParam(r.result);
|
||||
if (!code) {
|
||||
uni.showToast({ title: '二维码未包含领取码或名片编号', icon: 'none' });
|
||||
return;
|
||||
}
|
||||
this.doClaim(cardId);
|
||||
}
|
||||
this.claimInput = code;
|
||||
this.claimMode = /^\d+$/.test(code) ? 'id' : 'code';
|
||||
this.doClaim(code);
|
||||
this.closeClaim();
|
||||
},
|
||||
fail: () => {}
|
||||
});
|
||||
// #endif
|
||||
// #ifdef H5
|
||||
uni.showToast({ title: '请在微信/小程序内扫码', icon: 'none' });
|
||||
// #endif
|
||||
},
|
||||
doClaim(cardId) {
|
||||
parseClaimParam(val) {
|
||||
const s = (val || '').trim();
|
||||
if (!s) return '';
|
||||
const m = s.match(/[?&](claim_code|card_id)=([^&]+)/i);
|
||||
if (m) return decodeURIComponent(m[2]).toUpperCase().replace(/\s+/g, '');
|
||||
return s.toUpperCase().replace(/\s+/g, '');
|
||||
},
|
||||
doClaim(code) {
|
||||
uni.showLoading({ title: '认领中…' });
|
||||
// 文档 §2: claim_code 主通道, card_id 旧入口兼容; 二者二选一
|
||||
const payload = this.claimMode === 'code'
|
||||
? { claim_code: code }
|
||||
: { card_id: code };
|
||||
this.$cardApi.cardClaim({
|
||||
data: { card_id: cardId },
|
||||
data: payload,
|
||||
success: res => {
|
||||
uni.hideLoading();
|
||||
if (res.code == 0) {
|
||||
const claimed = res.data && res.data.claimed === false;
|
||||
// claimed=true=新认领; false=早已是自己的(幂等)
|
||||
const isNew = res.data && res.data.claimed === true;
|
||||
uni.showToast({
|
||||
title: claimed ? '该名片已在您的名片夹中' : '认领成功',
|
||||
title: isNew ? '认领成功' : '该名片已在您名下',
|
||||
icon: 'success'
|
||||
});
|
||||
this.refresh();
|
||||
this.refresh(); // 认领后与员工自建/扫描卡同池展示
|
||||
} else {
|
||||
this.handleApiError(res);
|
||||
}
|
||||
@@ -441,4 +520,122 @@ export default {
|
||||
text-overflow: ellipsis;
|
||||
white-space: nowrap;
|
||||
}
|
||||
|
||||
/* 认领弹层(与 card_claim_api 文档同步) */
|
||||
.claim-mask {
|
||||
position: fixed;
|
||||
left: 0;
|
||||
right: 0;
|
||||
top: 0;
|
||||
bottom: 0;
|
||||
background-color: rgba(0, 0, 0, 0.45);
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
z-index: 999;
|
||||
}
|
||||
|
||||
.claim-pop {
|
||||
width: 600rpx;
|
||||
background-color: #ffffff;
|
||||
border-radius: 24rpx;
|
||||
padding: 40rpx 36rpx;
|
||||
box-sizing: border-box;
|
||||
|
||||
.claim-pop-title {
|
||||
font-size: 34rpx;
|
||||
font-weight: 600;
|
||||
color: #1f2329;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.claim-pop-tabs {
|
||||
display: flex;
|
||||
margin: 32rpx 0 24rpx;
|
||||
background-color: #f3f4f6;
|
||||
border-radius: 14rpx;
|
||||
padding: 6rpx;
|
||||
|
||||
.claim-tab {
|
||||
flex: 1;
|
||||
text-align: center;
|
||||
font-size: 28rpx;
|
||||
color: #6b7280;
|
||||
padding: 16rpx 0;
|
||||
border-radius: 10rpx;
|
||||
|
||||
&.active {
|
||||
background-color: #ffffff;
|
||||
color: var(--main-color, #0054a5);
|
||||
font-weight: 600;
|
||||
box-shadow: 0 2rpx 8rpx rgba(0, 0, 0, 0.06);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.claim-input-wrap {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
background-color: #f7f8fa;
|
||||
border: 2rpx solid #e5e7eb;
|
||||
border-radius: 14rpx;
|
||||
padding: 0 20rpx;
|
||||
height: 84rpx;
|
||||
|
||||
.claim-input {
|
||||
flex: 1;
|
||||
height: 84rpx;
|
||||
font-size: 30rpx;
|
||||
color: #1f2329;
|
||||
letter-spacing: 2rpx;
|
||||
}
|
||||
|
||||
.claim-clear {
|
||||
color: #bbb;
|
||||
font-size: 30rpx;
|
||||
padding: 0 8rpx;
|
||||
}
|
||||
}
|
||||
|
||||
.claim-scan {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
margin-top: 24rpx;
|
||||
color: var(--main-color, #0054a5);
|
||||
font-size: 26rpx;
|
||||
|
||||
.iconfont {
|
||||
margin-right: 10rpx;
|
||||
font-size: 32rpx;
|
||||
}
|
||||
}
|
||||
|
||||
.claim-pop-actions {
|
||||
display: flex;
|
||||
margin-top: 36rpx;
|
||||
|
||||
.claim-btn-cancel,
|
||||
.claim-btn-confirm {
|
||||
flex: 1;
|
||||
height: 84rpx;
|
||||
line-height: 84rpx;
|
||||
text-align: center;
|
||||
border-radius: 14rpx;
|
||||
font-size: 30rpx;
|
||||
}
|
||||
|
||||
.claim-btn-cancel {
|
||||
background-color: #f3f4f6;
|
||||
color: #6b7280;
|
||||
margin-right: 20rpx;
|
||||
}
|
||||
|
||||
.claim-btn-confirm {
|
||||
background-color: var(--main-color, #0054a5);
|
||||
color: #ffffff;
|
||||
font-weight: 600;
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
||||
|
||||
Reference in New Issue
Block a user