|
|
@@ -0,0 +1,575 @@
|
|
|
+<template>
|
|
|
+ <div class="login-wrapper">
|
|
|
+ <div
|
|
|
+ class="back_extend"
|
|
|
+ v-if="appStore?.$wxConfig?.auditModeEnabled"
|
|
|
+ @click="backHome"
|
|
|
+ >
|
|
|
+ {{ "<" }} 回到首页
|
|
|
+ </div>
|
|
|
+ <div class="shading">
|
|
|
+ <image :src="logoUrl" />
|
|
|
+ <!-- <image src="/static/images/logo2.png" v-if="!logoUrl" /> -->
|
|
|
+ </div>
|
|
|
+ <div class="whiteBg" v-if="formItem === 1">
|
|
|
+ <div class="list" v-if="current !== 1">
|
|
|
+ <form @submit.prevent="submit">
|
|
|
+ <div class="item">
|
|
|
+ <div class="acea-row row-middle">
|
|
|
+ <image
|
|
|
+ src="https://sb-admin.oss-cn-shenzhen.aliyuncs.com/crmebimage/public/maintain/2025/08/28/phone_1.png"
|
|
|
+ style="width: 24rpx; height: 34rpx"
|
|
|
+ ></image>
|
|
|
+ <input
|
|
|
+ type="text"
|
|
|
+ class="texts"
|
|
|
+ placeholder="输入手机号码"
|
|
|
+ v-model="account"
|
|
|
+ required
|
|
|
+ />
|
|
|
+ </div>
|
|
|
+ </div>
|
|
|
+ <div class="item">
|
|
|
+ <div class="acea-row row-middle">
|
|
|
+ <image
|
|
|
+ src="https://sb-admin.oss-cn-shenzhen.aliyuncs.com/crmebimage/public/maintain/2025/08/28/1cfaad5f37a64884b3eef985d254606eqzlswf1m9g.png"
|
|
|
+ style="width: 28rpx; height: 32rpx"
|
|
|
+ ></image>
|
|
|
+ <input
|
|
|
+ type="password"
|
|
|
+ class="texts"
|
|
|
+ placeholder="填写登录密码"
|
|
|
+ v-model="password"
|
|
|
+ required
|
|
|
+ />
|
|
|
+ </div>
|
|
|
+ </div>
|
|
|
+ </form>
|
|
|
+ </div>
|
|
|
+ <div
|
|
|
+ class="list"
|
|
|
+ v-if="current !== 0 || appLoginStatus || appleLoginStatus"
|
|
|
+ >
|
|
|
+ <div class="item">
|
|
|
+ <div class="acea-row row-middle">
|
|
|
+ <image
|
|
|
+ src="https://sb-admin.oss-cn-shenzhen.aliyuncs.com/crmebimage/public/maintain/2025/08/28/phone_1.png"
|
|
|
+ style="width: 24rpx; height: 34rpx"
|
|
|
+ ></image>
|
|
|
+ <input
|
|
|
+ type="text"
|
|
|
+ class="texts"
|
|
|
+ placeholder="输入手机号码"
|
|
|
+ v-model="account"
|
|
|
+ />
|
|
|
+ </div>
|
|
|
+ </div>
|
|
|
+ <div class="item">
|
|
|
+ <div class="acea-row row-middle">
|
|
|
+ <image
|
|
|
+ src="https://sb-admin.oss-cn-shenzhen.aliyuncs.com/crmebimage/public/maintain/2025/08/28/1cfaad5f37a64884b3eef985d254606eqzlswf1m9g.png"
|
|
|
+ style="width: 28rpx; height: 32rpx"
|
|
|
+ ></image>
|
|
|
+ <input
|
|
|
+ type="text"
|
|
|
+ placeholder="填写验证码"
|
|
|
+ class="codeIput"
|
|
|
+ v-model="captcha"
|
|
|
+ />
|
|
|
+ <div
|
|
|
+ class="code"
|
|
|
+ :disabled="disabled"
|
|
|
+ :class="disabled === true ? 'on' : ''"
|
|
|
+ @click="getCode"
|
|
|
+ >
|
|
|
+ {{ text }}
|
|
|
+ </div>
|
|
|
+ </div>
|
|
|
+ </div>
|
|
|
+ <div class="item">
|
|
|
+ <div class="text-row row-middle">
|
|
|
+ 新用户可使用验证码登录,将自动注册账号
|
|
|
+ </div>
|
|
|
+ <div class="text-row row-middle" v-if="invite_code">
|
|
|
+ 邀请码:{{ invite_code }}
|
|
|
+ </div>
|
|
|
+ </div>
|
|
|
+ <div class="item" v-if="isShowCode">
|
|
|
+ <div class="acea-row row-middle">
|
|
|
+ <image
|
|
|
+ src="https://sb-admin.oss-cn-shenzhen.aliyuncs.com/crmebimage/public/maintain/2025/08/28/1cfaad5f37a64884b3eef985d254606eqzlswf1m9g.png"
|
|
|
+ style="width: 28rpx; height: 32rpx"
|
|
|
+ ></image>
|
|
|
+ <input
|
|
|
+ type="text"
|
|
|
+ placeholder="填写验证码"
|
|
|
+ class="codeIput"
|
|
|
+ v-model="codeVal"
|
|
|
+ />
|
|
|
+ <div class="code" @click="again"><img :src="codeUrl" /></div>
|
|
|
+ </div>
|
|
|
+ </div>
|
|
|
+ </div>
|
|
|
+ <div class="tips">
|
|
|
+ <div v-if="current == 0" @click="current = 1">快速登录</div>
|
|
|
+ <div v-if="current == 1" @click="current = 0">账号登录</div>
|
|
|
+ <div @click="change_password">忘记密码</div>
|
|
|
+ </div>
|
|
|
+ <div class="logon" @click="loginMobile" v-if="current !== 0">登录</div>
|
|
|
+ <div class="logon" @click="submit" v-if="current === 0">登录</div>
|
|
|
+ </div>
|
|
|
+ <div class="bottom"></div>
|
|
|
+ </div>
|
|
|
+</template>
|
|
|
+
|
|
|
+<script setup>
|
|
|
+import { ref, watch, onMounted } from "vue";
|
|
|
+import { onLoad, onBackPress as uniOnBackPress } from "@dcloudio/uni-app";
|
|
|
+import { useAppStore } from "@/stores/app";
|
|
|
+import {
|
|
|
+ loginH5,
|
|
|
+ loginMobile as loginMobileApi,
|
|
|
+ registerVerify,
|
|
|
+ register,
|
|
|
+ getUserInfo,
|
|
|
+ getUserOpenId,
|
|
|
+} from "@/api/user";
|
|
|
+import { getLogo, appAuth, appleLogin } from "@/api/public";
|
|
|
+import { VUE_APP_API_URL } from "@/utils";
|
|
|
+import { useSendCode } from "@/hooks/useSendCode";
|
|
|
+import Cache from "@/utils/cache";
|
|
|
+import { EXPIRES_TIME } from "@/config/cache";
|
|
|
+import { useToast } from "@/hooks/useToast.js";
|
|
|
+
|
|
|
+const appStore = useAppStore();
|
|
|
+const { Toast } = useToast();
|
|
|
+
|
|
|
+const BACK_URL = "login_back_url";
|
|
|
+
|
|
|
+// Reactive state
|
|
|
+const navList = ref(["快速登录", "账号登录"]);
|
|
|
+const current = ref(1);
|
|
|
+const account = ref("");
|
|
|
+const password = ref("");
|
|
|
+const captcha = ref("");
|
|
|
+const formItem = ref(1);
|
|
|
+const type = ref("login");
|
|
|
+const logoUrl = ref("");
|
|
|
+const keyCode = ref("");
|
|
|
+const codeUrl = ref("");
|
|
|
+const codeVal = ref("");
|
|
|
+const isShowCode = ref(false);
|
|
|
+const platform = ref("");
|
|
|
+const appLoginStatus = ref(false);
|
|
|
+const appUserInfo = ref(null);
|
|
|
+const appleLoginStatus = ref(false);
|
|
|
+const appleUserInfo = ref(null);
|
|
|
+const appleShow = ref(false);
|
|
|
+const invite_code = ref("");
|
|
|
+
|
|
|
+// Watch formItem to update type
|
|
|
+watch(formItem, (newVal) => {
|
|
|
+ type.value = newVal === 1 ? "login" : "register";
|
|
|
+});
|
|
|
+
|
|
|
+const { disabled, text, sendCode } = useSendCode();
|
|
|
+
|
|
|
+// Refresh captcha image
|
|
|
+const again = () => {
|
|
|
+ codeUrl.value = `${VUE_APP_API_URL}/sms_captcha?key=${
|
|
|
+ keyCode.value
|
|
|
+ }${Date.parse(new Date())}`;
|
|
|
+};
|
|
|
+
|
|
|
+// Get logo image
|
|
|
+const getLogoImage = async () => {
|
|
|
+ try {
|
|
|
+ const res = await getLogo();
|
|
|
+ console.log('=========')
|
|
|
+ logoUrl.value = res.data.logoUrl || "/static/images/logo2.png";
|
|
|
+ } catch (err) {
|
|
|
+ console.error(err);
|
|
|
+ }
|
|
|
+};
|
|
|
+
|
|
|
+const getWechatOpenid = async () => {
|
|
|
+ try {
|
|
|
+ const { code, errMsg } = await uni.login();
|
|
|
+ if (!errMsg) return uni.showToast({ title: errMsg, icon: "none" }); // debug
|
|
|
+ // if (!code) return uni.showToast({ title: "无code", icon: "none" }); // debug
|
|
|
+ console.log(code)
|
|
|
+ const res = await getUserOpenId({ code });
|
|
|
+ if (res.data?.code === 200 && res.data?.data?.openid) {
|
|
|
+ const openid = res.data.data.openid;
|
|
|
+
|
|
|
+ Cache.set("wxOpenid", openid);
|
|
|
+ appStore.SET_WX_OPENID(openid);
|
|
|
+ }
|
|
|
+ } catch (err) {
|
|
|
+ console.error("获取openid过程出错:", err);
|
|
|
+ }
|
|
|
+};
|
|
|
+
|
|
|
+// Mobile login
|
|
|
+const loginMobile = async () => {
|
|
|
+ if (!account.value)
|
|
|
+ return uni.showToast({ title: "请填写手机号码", icon: "none" });
|
|
|
+ if (!/^1(3|4|5|7|8|9|6)\d{9}$/i.test(account.value))
|
|
|
+ return uni.showToast({ title: "请输入正确的手机号码", icon: "none" });
|
|
|
+ if (!captcha.value)
|
|
|
+ return uni.showToast({ title: "请填写验证码", icon: "none" });
|
|
|
+ if (!/^[\w\d]+$/i.test(captcha.value))
|
|
|
+ return uni.showToast({ title: "请输入正确的验证码", icon: "none" });
|
|
|
+
|
|
|
+ try {
|
|
|
+ const res = await loginMobileApi({
|
|
|
+ phone: account.value,
|
|
|
+ captcha: captcha.value,
|
|
|
+ spread_spid: Cache.get("spread"),
|
|
|
+ invite_code: invite_code.value,
|
|
|
+ });
|
|
|
+ // 使用 LOGIN action 保存 token 到缓存
|
|
|
+ appStore.LOGIN({ token: res.data.token });
|
|
|
+ // 保存过期时间(7天后过期)
|
|
|
+ const expiresTime = Math.round(new Date() / 1000) + 7 * 24 * 60 * 60;
|
|
|
+ Cache.set(EXPIRES_TIME, expiresTime, 0);
|
|
|
+ await getUserInfoFn(res.data);
|
|
|
+ } catch (res) {
|
|
|
+ uni.showToast({ title: res.message, icon: "none" });
|
|
|
+ }
|
|
|
+};
|
|
|
+
|
|
|
+// Register
|
|
|
+const registerFn = async () => {
|
|
|
+ if (!account.value)
|
|
|
+ return uni.showToast({ title: "请填写手机号码", icon: "none" });
|
|
|
+ if (!/^1(3|4|5|7|8|9|6)\d{9}$/i.test(account.value))
|
|
|
+ return uni.showToast({ title: "请输入正确的手机号码", icon: "none" });
|
|
|
+ if (!captcha.value)
|
|
|
+ return uni.showToast({ title: "请填写验证码", icon: "none" });
|
|
|
+ if (!/^[\w\d]+$/i.test(captcha.value))
|
|
|
+ return uni.showToast({ title: "请输入正确的验证码", icon: "none" });
|
|
|
+ if (!password.value)
|
|
|
+ return uni.showToast({ title: "请填写密码", icon: "none" });
|
|
|
+ if (!/^(?![0-9]+$)(?![a-zA-Z]+$)[0-9A-Za-z]{6,16}$/i.test(password.value))
|
|
|
+ return uni.showToast({ title: "您输入的密码过于简单", icon: "none" });
|
|
|
+
|
|
|
+ try {
|
|
|
+ const res = await register({
|
|
|
+ account: account.value,
|
|
|
+ captcha: captcha.value,
|
|
|
+ password: password.value,
|
|
|
+ spread: Cache.get("spread"),
|
|
|
+ });
|
|
|
+ uni.showToast({ title: res.message, icon: "none" });
|
|
|
+ formItem.value = 1;
|
|
|
+ } catch (res) {
|
|
|
+ uni.showToast({ title: res.message, icon: "none" });
|
|
|
+ }
|
|
|
+};
|
|
|
+
|
|
|
+// Send verification code
|
|
|
+const getCode = async () => {
|
|
|
+ if (!account.value)
|
|
|
+ return uni.showToast({ title: "请填写手机号码", icon: "none" });
|
|
|
+ if (!/^1(3|4|5|7|8|9|6)\d{9}$/i.test(account.value))
|
|
|
+ return uni.showToast({ title: "请输入正确的手机号码", icon: "none" });
|
|
|
+
|
|
|
+ if (formItem.value === 2) type.value = "register";
|
|
|
+ try {
|
|
|
+ const res = await registerVerify(account.value);
|
|
|
+ uni.showToast({ title: res.message, icon: "none" });
|
|
|
+ sendCode();
|
|
|
+ } catch (err) {
|
|
|
+ uni.showToast({ title: err.message, icon: "none" });
|
|
|
+ }
|
|
|
+};
|
|
|
+
|
|
|
+// Navigation tab switch
|
|
|
+const navTap = (index) => {
|
|
|
+ current.value = index;
|
|
|
+};
|
|
|
+
|
|
|
+// h5 login
|
|
|
+const submit = async () => {
|
|
|
+ if (!account.value) return Toast({ title: "请填写账号", icon: "none" });
|
|
|
+ if (!/^[\w\d]{5,16}$/i.test(account.value))
|
|
|
+ return Toast({ title: "请输入正确的账号", icon: "none" });
|
|
|
+ if (!password.value) return Toast({ title: "请填写密码", icon: "none" });
|
|
|
+
|
|
|
+ try {
|
|
|
+ const { data } = await loginH5({
|
|
|
+ account: account.value,
|
|
|
+ password: password.value,
|
|
|
+ spread: Cache.get("spread"),
|
|
|
+ });
|
|
|
+ appStore.LOGIN({ token: data.token });
|
|
|
+ // 保存过期时间(7天后过期)
|
|
|
+ const expiresTime = Math.round(new Date() / 1000) + 7 * 24 * 60 * 60;
|
|
|
+ Cache.set(EXPIRES_TIME, expiresTime, 0);
|
|
|
+
|
|
|
+ await getUserInfoFn(data);
|
|
|
+ } catch (err) {
|
|
|
+ console.log("submit error", err);
|
|
|
+ Toast({ title: err, icon: "none" });
|
|
|
+ }
|
|
|
+};
|
|
|
+
|
|
|
+const getUserInfoFn = async (data) => {
|
|
|
+ try {
|
|
|
+ appStore.SETUID(data.uid);
|
|
|
+ await getWechatOpenid();
|
|
|
+ const res = await getUserInfo();
|
|
|
+ appStore.UPDATE_USERINFO(res.data);
|
|
|
+ Toast({ title: "登录成功" });
|
|
|
+ backHome();
|
|
|
+ } catch (err) {
|
|
|
+ console.error(err);
|
|
|
+ uni.showToast({ title: err.msg, icon: "none" });
|
|
|
+ }
|
|
|
+};
|
|
|
+
|
|
|
+onLoad((options) => {
|
|
|
+ if (options?.invite_code) {
|
|
|
+ invite_code.value = options.invite_code;
|
|
|
+ uni.setStorageSync("inviteCode", options.invite_code);
|
|
|
+ } else {
|
|
|
+ invite_code.value = uni.getStorageSync("inviteCode") || "";
|
|
|
+ }
|
|
|
+ getLogoImage();
|
|
|
+});
|
|
|
+
|
|
|
+onMounted(() => {
|
|
|
+ uni.getDeviceInfo({
|
|
|
+ success(res) {
|
|
|
+ // 获取平台(如 "ios"、"android")
|
|
|
+ platform.value = res.platform.toLowerCase();
|
|
|
+ // 解析系统版本(以 iOS 为例,res.system 格式如 "iOS 16.5")
|
|
|
+ if (platform.value === "ios") {
|
|
|
+ const systemParts = res.system.split(" ");
|
|
|
+ if (systemParts.length > 1) {
|
|
|
+ const iosVersion = parseFloat(systemParts[1]);
|
|
|
+ // iOS 版本 >= 13 时显示 Apple 登录相关内容
|
|
|
+ if (iosVersion >= 13) {
|
|
|
+ appleShow.value = true;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ },
|
|
|
+ fail(err) {
|
|
|
+ console.error("获取设备信息失败:", err);
|
|
|
+ },
|
|
|
+ });
|
|
|
+});
|
|
|
+
|
|
|
+const backHome = () => {
|
|
|
+ uni.switchTab({
|
|
|
+ url: "/pages/index/index",
|
|
|
+ });
|
|
|
+};
|
|
|
+const change_password = () => {
|
|
|
+ uni.navigateTo({
|
|
|
+ url: "/pages/change_password/change_password",
|
|
|
+ });
|
|
|
+};
|
|
|
+</script>
|
|
|
+
|
|
|
+<style lang="scss" scoped>
|
|
|
+page {
|
|
|
+ background: #fff;
|
|
|
+}
|
|
|
+.appLogin {
|
|
|
+ margin-top: 60rpx;
|
|
|
+
|
|
|
+ .hds {
|
|
|
+ display: flex;
|
|
|
+ justify-content: center;
|
|
|
+ align-items: center;
|
|
|
+ font-size: 24rpx;
|
|
|
+ color: #b4b4b4;
|
|
|
+
|
|
|
+ .line {
|
|
|
+ width: 68rpx;
|
|
|
+ height: 1rpx;
|
|
|
+ background: #cccccc;
|
|
|
+ }
|
|
|
+
|
|
|
+ p {
|
|
|
+ margin: 0 20rpx;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ .btn-wrapper {
|
|
|
+ display: flex;
|
|
|
+ align-items: center;
|
|
|
+ justify-content: center;
|
|
|
+ margin-top: 30rpx;
|
|
|
+
|
|
|
+ .btn {
|
|
|
+ display: flex;
|
|
|
+ align-items: center;
|
|
|
+ justify-content: center;
|
|
|
+ width: 68rpx;
|
|
|
+ height: 68rpx;
|
|
|
+ border-radius: 50%;
|
|
|
+ }
|
|
|
+
|
|
|
+ .apple-btn {
|
|
|
+ display: flex;
|
|
|
+ align-items: center;
|
|
|
+ justify-content: center;
|
|
|
+ margin-left: 30rpx;
|
|
|
+ background: #000;
|
|
|
+ border-radius: 34rpx;
|
|
|
+ font-size: 40rpx;
|
|
|
+
|
|
|
+ .icon-s-pingguo {
|
|
|
+ color: #fff;
|
|
|
+ font-size: 40rpx;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ .iconfont {
|
|
|
+ font-size: 40rpx;
|
|
|
+ color: #fff;
|
|
|
+ }
|
|
|
+
|
|
|
+ .wx {
|
|
|
+ margin-right: 30rpx;
|
|
|
+ background-color: #61c64f;
|
|
|
+ }
|
|
|
+
|
|
|
+ .mima {
|
|
|
+ background-color: #28b3e9;
|
|
|
+ }
|
|
|
+
|
|
|
+ .yanzheng {
|
|
|
+ background-color: #f89c23;
|
|
|
+ }
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
+.code img {
|
|
|
+ width: 100%;
|
|
|
+ height: 100%;
|
|
|
+}
|
|
|
+
|
|
|
+.acea-row.row-middle {
|
|
|
+ input {
|
|
|
+ margin-left: 20rpx;
|
|
|
+ display: block;
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
+.text-row {
|
|
|
+ font-size: 22rpx;
|
|
|
+ color: #999;
|
|
|
+}
|
|
|
+
|
|
|
+.login-wrapper {
|
|
|
+ padding: 0 30rpx;
|
|
|
+ height: 100vh;
|
|
|
+
|
|
|
+ .back_extend {
|
|
|
+ position: fixed;
|
|
|
+ top: 50px;
|
|
|
+ left: 10px;
|
|
|
+ font-size: 26rpx;
|
|
|
+ color: #999;
|
|
|
+ }
|
|
|
+
|
|
|
+ .shading {
|
|
|
+ display: flex;
|
|
|
+ align-items: center;
|
|
|
+ justify-content: center;
|
|
|
+ width: 100%;
|
|
|
+
|
|
|
+ /* #ifdef APP-VUE */
|
|
|
+ margin-top: 50rpx;
|
|
|
+ /* #endif */
|
|
|
+ /* #ifndef APP-VUE */
|
|
|
+
|
|
|
+ margin-top: 200rpx;
|
|
|
+ /* #endif */
|
|
|
+
|
|
|
+ image {
|
|
|
+ width: 180rpx;
|
|
|
+ height: 180rpx;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ .whiteBg {
|
|
|
+ margin-top: 100rpx;
|
|
|
+
|
|
|
+ .list {
|
|
|
+ border-radius: 16rpx;
|
|
|
+ overflow: hidden;
|
|
|
+
|
|
|
+ .item {
|
|
|
+ border-bottom: 1px solid #f0f0f0;
|
|
|
+ background: #fff;
|
|
|
+
|
|
|
+ .row-middle {
|
|
|
+ position: relative;
|
|
|
+ padding: 16rpx 45rpx;
|
|
|
+
|
|
|
+ .texts {
|
|
|
+ flex: 1;
|
|
|
+ font-size: 28rpx;
|
|
|
+ height: 80rpx;
|
|
|
+ line-height: 80rpx;
|
|
|
+ display: flex;
|
|
|
+ justify-content: center;
|
|
|
+ align-items: center;
|
|
|
+ }
|
|
|
+
|
|
|
+ input {
|
|
|
+ flex: 1;
|
|
|
+ font-size: 28rpx;
|
|
|
+ height: 80rpx;
|
|
|
+ line-height: 80rpx;
|
|
|
+ display: flex;
|
|
|
+ justify-content: center;
|
|
|
+ align-items: center;
|
|
|
+ }
|
|
|
+
|
|
|
+ .code {
|
|
|
+ position: absolute;
|
|
|
+ right: 30rpx;
|
|
|
+ top: 50%;
|
|
|
+ color: #cd9933;
|
|
|
+ font-size: 26rpx;
|
|
|
+ z-index: 999;
|
|
|
+ transform: translateY(-50%);
|
|
|
+ border: 1px solid;
|
|
|
+ border-radius: 14rpx;
|
|
|
+ padding: 8rpx 10rpx;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ .logon {
|
|
|
+ display: flex;
|
|
|
+ align-items: center;
|
|
|
+ justify-content: center;
|
|
|
+ width: 100%;
|
|
|
+ height: 86rpx;
|
|
|
+ margin-top: 80rpx;
|
|
|
+ background-color: $theme-color;
|
|
|
+ border-radius: 120rpx;
|
|
|
+ color: #ffffff;
|
|
|
+ font-size: 30rpx;
|
|
|
+ }
|
|
|
+
|
|
|
+ .tips {
|
|
|
+ margin: 0.9375rem;
|
|
|
+ text-align: center;
|
|
|
+ color: #999;
|
|
|
+ display: flex;
|
|
|
+ justify-content: space-between;
|
|
|
+ align-items: center;
|
|
|
+ }
|
|
|
+ }
|
|
|
+}
|
|
|
+</style>
|