mirror of
https://gitee.com/beijing_hongye_huicheng/lilishop-ui.git
synced 2026-09-21 04:12:03 +08:00
feat(setting): 添加店铺H5和小程序二维码展示功能
This commit is contained in:
@@ -64,6 +64,14 @@
|
|||||||
<el-form-item label="wap站点地址" prop="staticPageWapAddress">
|
<el-form-item label="wap站点地址" prop="staticPageWapAddress">
|
||||||
<el-input v-model="formValidate.staticPageWapAddress" />
|
<el-input v-model="formValidate.staticPageWapAddress" />
|
||||||
</el-form-item>
|
</el-form-item>
|
||||||
|
<el-form-item label="展示店铺H5地址" prop="showStoreH5Address">
|
||||||
|
<el-switch v-model="formValidate.showStoreH5Address" active-text="开" inactive-text="关" />
|
||||||
|
<span class="desc">开启后,商家后台顶栏展示 H5 店铺首页二维码,需先填写上方「wap站点地址」</span>
|
||||||
|
</el-form-item>
|
||||||
|
<el-form-item label="展示店铺小程序地址" prop="showStoreMpAddress">
|
||||||
|
<el-switch v-model="formValidate.showStoreMpAddress" active-text="开" inactive-text="关" />
|
||||||
|
<span class="desc">开启后,商家后台顶栏展示小程序店铺首页码,需先配置微信小程序,且小程序已发布店铺页</span>
|
||||||
|
</el-form-item>
|
||||||
<div class="label-btns">
|
<div class="label-btns">
|
||||||
<el-button type="primary" @click="submit('formValidate')">保存</el-button>
|
<el-button type="primary" @click="submit('formValidate')">保存</el-button>
|
||||||
</div>
|
</div>
|
||||||
@@ -106,6 +114,8 @@ export default {
|
|||||||
siteName: "",
|
siteName: "",
|
||||||
staticPageAddress: "",
|
staticPageAddress: "",
|
||||||
staticPageWapAddress: "",
|
staticPageWapAddress: "",
|
||||||
|
showStoreH5Address: false,
|
||||||
|
showStoreMpAddress: false,
|
||||||
},
|
},
|
||||||
selected: "",
|
selected: "",
|
||||||
ruleValidate: {},
|
ruleValidate: {},
|
||||||
@@ -150,8 +160,16 @@ export default {
|
|||||||
},
|
},
|
||||||
init() {
|
init() {
|
||||||
this.result = JSON.parse(this.res);
|
this.result = JSON.parse(this.res);
|
||||||
this.formValidate = { ...this.result };
|
this.formValidate = {
|
||||||
|
...this.formValidate,
|
||||||
|
...this.result,
|
||||||
|
showStoreH5Address: this.result.showStoreH5Address === true,
|
||||||
|
showStoreMpAddress: this.result.showStoreMpAddress === true,
|
||||||
|
};
|
||||||
Object.keys(this.result).forEach((item) => {
|
Object.keys(this.result).forEach((item) => {
|
||||||
|
if (item === "showStoreH5Address" || item === "showStoreMpAddress") {
|
||||||
|
return;
|
||||||
|
}
|
||||||
this.ruleValidate[item] = [
|
this.ruleValidate[item] = [
|
||||||
{
|
{
|
||||||
required: true,
|
required: true,
|
||||||
|
|||||||
@@ -55,6 +55,11 @@ export const userInfo = params => {
|
|||||||
export const userMsg = params => {
|
export const userMsg = params => {
|
||||||
return getRequest('/settings/storeSettings', params)
|
return getRequest('/settings/storeSettings', params)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** 当前店铺首页小程序码 */
|
||||||
|
export const getStoreMpQrcode = () => {
|
||||||
|
return getRequest("/settings/storeSettings/mp-qrcode");
|
||||||
|
};
|
||||||
//验证短信验证码
|
//验证短信验证码
|
||||||
export const validateCode = params => {
|
export const validateCode = params => {
|
||||||
return postRequestWithNoToken("/passport/login/resetByMobile", params);
|
return postRequestWithNoToken("/passport/login/resetByMobile", params);
|
||||||
|
|||||||
@@ -20,6 +20,7 @@
|
|||||||
align="middle"
|
align="middle"
|
||||||
class="user-dropdown-innercon"
|
class="user-dropdown-innercon"
|
||||||
>
|
>
|
||||||
|
<store-qrcode />
|
||||||
<ul class="nav-list">
|
<ul class="nav-list">
|
||||||
<li class="nav-item" @click="im">
|
<li class="nav-item" @click="im">
|
||||||
<el-tooltip content="联系客服" placement="bottom">
|
<el-tooltip content="联系客服" placement="bottom">
|
||||||
@@ -84,6 +85,7 @@ import shrinkableMenu from "./main-components/shrinkable-menu/shrinkable-menu.vu
|
|||||||
import tagsPageOpened from "./main-components/tags-page-opened.vue";
|
import tagsPageOpened from "./main-components/tags-page-opened.vue";
|
||||||
import circleLoading from "@/views/my-components/lili/circle-loading.vue";
|
import circleLoading from "@/views/my-components/lili/circle-loading.vue";
|
||||||
import configDrawer from "@/views/main-components/config-drawer.vue";
|
import configDrawer from "@/views/main-components/config-drawer.vue";
|
||||||
|
import storeQrcode from "@/views/main-components/store-qrcode.vue";
|
||||||
import Cookies from "js-cookie";
|
import Cookies from "js-cookie";
|
||||||
import util from "@/libs/util.js";
|
import util from "@/libs/util.js";
|
||||||
import { logout } from "@/api/index";
|
import { logout } from "@/api/index";
|
||||||
@@ -100,6 +102,7 @@ export default {
|
|||||||
tagsPageOpened,
|
tagsPageOpened,
|
||||||
circleLoading,
|
circleLoading,
|
||||||
configDrawer,
|
configDrawer,
|
||||||
|
storeQrcode,
|
||||||
},
|
},
|
||||||
data() {
|
data() {
|
||||||
return {
|
return {
|
||||||
|
|||||||
202
seller/src/views/main-components/store-qrcode.vue
Normal file
202
seller/src/views/main-components/store-qrcode.vue
Normal file
@@ -0,0 +1,202 @@
|
|||||||
|
<template>
|
||||||
|
<div v-if="storeId && (showH5 || showMp)" class="store-qr-group">
|
||||||
|
<el-popover v-if="showH5" trigger="hover" placement="bottom" :width="220">
|
||||||
|
<template #reference>
|
||||||
|
<div class="store-qr-thumb">
|
||||||
|
<vue-qr v-if="h5Url" :text="h5Url" :margin="0" color-dark="#000" color-light="#fff" :size="40" />
|
||||||
|
<el-icon v-else class="store-qr-empty"><Picture /></el-icon>
|
||||||
|
<span>H5</span>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
<div class="store-qr-panel">
|
||||||
|
<vue-qr v-if="h5Url" :text="h5Url" :margin="0" color-dark="#000" color-light="#fff" :size="160" />
|
||||||
|
<div v-else class="store-qr-tip">请先在系统设置中填写 wap 站点地址</div>
|
||||||
|
<div class="store-qr-title">H5 店铺首页</div>
|
||||||
|
<el-button v-if="h5Url" size="small" @click="copyText(h5Url)">复制链接</el-button>
|
||||||
|
</div>
|
||||||
|
</el-popover>
|
||||||
|
|
||||||
|
<el-popover v-if="showMp" trigger="hover" placement="bottom" :width="220">
|
||||||
|
<template #reference>
|
||||||
|
<div class="store-qr-thumb">
|
||||||
|
<img v-if="mpQrSrc" :src="mpQrSrc" width="40" height="40" alt="小程序码" />
|
||||||
|
<el-icon v-else class="store-qr-empty"><Picture /></el-icon>
|
||||||
|
<span>小程序</span>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
<div class="store-qr-panel">
|
||||||
|
<img v-if="mpQrSrc" :src="mpQrSrc" width="160" height="160" alt="小程序码" />
|
||||||
|
<div v-else class="store-qr-tip">{{ mpError || "小程序码生成中..." }}</div>
|
||||||
|
<div class="store-qr-title">小程序店铺首页</div>
|
||||||
|
<el-button v-if="mpQrSrc" size="small" @click="downloadMp">下载二维码</el-button>
|
||||||
|
</div>
|
||||||
|
</el-popover>
|
||||||
|
</div>
|
||||||
|
</template>
|
||||||
|
|
||||||
|
<script>
|
||||||
|
import Cookies from "js-cookie";
|
||||||
|
import vueQr from "vue-qr";
|
||||||
|
import { Picture } from "@element-plus/icons-vue";
|
||||||
|
import { getStoreMpQrcode } from "@/api/index";
|
||||||
|
import { getBaseSite } from "@/api/common.js";
|
||||||
|
|
||||||
|
export default {
|
||||||
|
name: "store-qrcode",
|
||||||
|
components: { "vue-qr": vueQr, Picture },
|
||||||
|
data() {
|
||||||
|
return {
|
||||||
|
storeId: "",
|
||||||
|
wapUrl: "",
|
||||||
|
showH5: false,
|
||||||
|
showMp: false,
|
||||||
|
mpQrcode: "",
|
||||||
|
mpError: "",
|
||||||
|
};
|
||||||
|
},
|
||||||
|
computed: {
|
||||||
|
h5Url() {
|
||||||
|
if (!this.storeId || !this.wapUrl) return "";
|
||||||
|
return `${String(this.wapUrl).replace(/\/$/, "")}/pages/product/shopPage?id=${this.storeId}`;
|
||||||
|
},
|
||||||
|
mpQrSrc() {
|
||||||
|
return this.mpQrcode ? `data:image/png;base64,${this.mpQrcode}` : "";
|
||||||
|
},
|
||||||
|
},
|
||||||
|
mounted() {
|
||||||
|
this.initStore();
|
||||||
|
this.loadSiteSetting();
|
||||||
|
},
|
||||||
|
methods: {
|
||||||
|
initStore() {
|
||||||
|
try {
|
||||||
|
const userInfo = JSON.parse(Cookies.get("userInfoSeller") || "{}") || {};
|
||||||
|
this.storeId = userInfo.id || userInfo.storeId || "";
|
||||||
|
} catch (e) {
|
||||||
|
this.storeId = "";
|
||||||
|
}
|
||||||
|
},
|
||||||
|
parseSettingValue(raw) {
|
||||||
|
if (!raw) return {};
|
||||||
|
if (typeof raw === "object") return raw;
|
||||||
|
try {
|
||||||
|
return JSON.parse(raw);
|
||||||
|
} catch (e) {
|
||||||
|
return {};
|
||||||
|
}
|
||||||
|
},
|
||||||
|
loadSiteSetting() {
|
||||||
|
getBaseSite()
|
||||||
|
.then((res) => {
|
||||||
|
if (!res || !res.success || !res.result) return;
|
||||||
|
const data = this.parseSettingValue(res.result.settingValue || res.result);
|
||||||
|
this.showH5 = data.showStoreH5Address === true;
|
||||||
|
this.showMp = data.showStoreMpAddress === true;
|
||||||
|
this.wapUrl =
|
||||||
|
data.staticPageWapAddress ||
|
||||||
|
(typeof window !== "undefined" && window.BASE && window.BASE.WAP_URL) ||
|
||||||
|
"";
|
||||||
|
if (this.showMp) {
|
||||||
|
this.loadMpQrcode();
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.catch(() => {
|
||||||
|
this.showH5 = false;
|
||||||
|
this.showMp = false;
|
||||||
|
});
|
||||||
|
},
|
||||||
|
loadMpQrcode() {
|
||||||
|
if (!this.storeId) return;
|
||||||
|
getStoreMpQrcode()
|
||||||
|
.then((res) => {
|
||||||
|
if (res && res.success && res.result) {
|
||||||
|
if (String(res.result).startsWith("eyJ")) {
|
||||||
|
this.mpError = "请先配置微信小程序";
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
this.mpQrcode = res.result;
|
||||||
|
this.mpError = "";
|
||||||
|
} else {
|
||||||
|
this.mpError = (res && res.message) || "小程序码生成失败";
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.catch(() => {
|
||||||
|
this.mpError = "请先配置微信小程序";
|
||||||
|
});
|
||||||
|
},
|
||||||
|
copyText(text) {
|
||||||
|
if (!text) return;
|
||||||
|
const textArea = document.createElement("textarea");
|
||||||
|
textArea.value = text;
|
||||||
|
document.body.appendChild(textArea);
|
||||||
|
textArea.focus();
|
||||||
|
textArea.select();
|
||||||
|
try {
|
||||||
|
document.execCommand("copy");
|
||||||
|
this.$Message.success("复制成功");
|
||||||
|
} catch (e) {
|
||||||
|
this.$Message.error("复制失败");
|
||||||
|
}
|
||||||
|
document.body.removeChild(textArea);
|
||||||
|
},
|
||||||
|
downloadMp() {
|
||||||
|
if (!this.mpQrSrc) return;
|
||||||
|
const link = document.createElement("a");
|
||||||
|
link.href = this.mpQrSrc;
|
||||||
|
link.download = "店铺小程序码.png";
|
||||||
|
document.body.appendChild(link);
|
||||||
|
link.click();
|
||||||
|
document.body.removeChild(link);
|
||||||
|
},
|
||||||
|
},
|
||||||
|
};
|
||||||
|
</script>
|
||||||
|
|
||||||
|
<style scoped lang="scss">
|
||||||
|
.store-qr-group {
|
||||||
|
display: inline-flex;
|
||||||
|
align-items: center;
|
||||||
|
gap: 12px;
|
||||||
|
margin-right: 16px;
|
||||||
|
}
|
||||||
|
.store-qr-thumb {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
cursor: pointer;
|
||||||
|
line-height: 1.2;
|
||||||
|
span {
|
||||||
|
margin-top: 2px;
|
||||||
|
font-size: 12px;
|
||||||
|
color: #666;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
.store-qr-empty {
|
||||||
|
width: 40px;
|
||||||
|
height: 40px;
|
||||||
|
font-size: 22px;
|
||||||
|
color: #ccc;
|
||||||
|
}
|
||||||
|
.store-qr-panel {
|
||||||
|
display: flex;
|
||||||
|
flex-direction: column;
|
||||||
|
align-items: center;
|
||||||
|
gap: 8px;
|
||||||
|
padding: 4px 0;
|
||||||
|
}
|
||||||
|
.store-qr-title {
|
||||||
|
font-size: 13px;
|
||||||
|
color: #333;
|
||||||
|
}
|
||||||
|
.store-qr-tip {
|
||||||
|
width: 160px;
|
||||||
|
min-height: 80px;
|
||||||
|
display: flex;
|
||||||
|
align-items: center;
|
||||||
|
justify-content: center;
|
||||||
|
text-align: center;
|
||||||
|
font-size: 12px;
|
||||||
|
color: #999;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
Reference in New Issue
Block a user