百度地图 + vant,移动端样式,根据地图查看当前位置,以及表单提交。
<template>
<div class="create_order">
<nav-bar @clickLeft="showExit = true" :isShowCircle="true"></nav-bar>
<div class="toplayout">
<baidu-map
id="map"
:class="['map', {'map-height': currentHeight <= 50 }]"
:scroll-wheel-zoom="true"
:center="location"
:zoom="zoom"
@click="getLocation"
@ready="handleMap"
/>
</div>
<div class="vertical-drawable" :style="heightStyle">
<div class="title" ref="drawer">
<van-divider class="slider_line" />
</div>
<div class="listview" @scroll.passive="onListScrolled($event)" ref="listView">
<van-form ref="orderForm" name="order">
<div class="pd_x-16">
<p class="second_title">确认位置信息</p>
<van-search
class="location_search"
name="searchContent"
v-model="locationContent"
placeholder="请输入您所在的位置"
@focus="searchAddress"
/>
<van-icon
class="location_icon"
:name="require('@/assets/images/icon/Shapelocation.svg')"
/>
<span class="location_info">当前定位:{{ address }}</span>
</div>
<div class="pd_x-16 mt-24 service_type">
<p class="second_title">选择救援服务</p>
<van-radio-group
name="serviceType"
v-model="serviceType"
@change="vServiceType"
>
<van-cell-group>
<van-cell clickable @click="serviceType = '05'">
<template #title>
<van-icon
class="radio_icon"
:name="require('@/assets/images/icon/oil.svg')"
/>
<span class="radio-title">送油</span>
</template>
<template #right-icon>
<van-radio name="05">
<template #icon="props">
<img
class="img-icon"
:src="props.checked ? activeIcon : inactiveIcon"
/>
</template>
</van-radio>
</template>
</van-cell>
<van-cell clickable @click="serviceType = '04'">
<template #title>
<van-icon
class="radio_icon"
:name="require('@/assets/images/icon/electricity.svg')"
/>
<span class="radio-title">搭电</span>
</template>
<template #right-icon>
<van-radio name="04">
<template #icon="props">
<img
class="img-icon"
:src="props.checked ? activeIcon : inactiveIcon"
/>
</template>
</van-radio>
</template>
</van-cell>
<van-cell clickable @click="serviceType = '03'">
<template #title>
<van-icon
class="radio_icon"
:name="require('@/assets/images/icon/tire.svg')"
/>
<span class="radio-title">换胎</span>
</template>
<template #right-icon>
<van-radio name="03">
<template #icon="props">
<img
class="img-icon"
:src="props.checked ? activeIcon : inactiveIcon"
/>
</template>
</van-radio>
</template>
</van-cell>
<van-cell clickable @click="serviceType = '07'">
<template #title>
<van-icon
class="radio_icon"
:name="require('@/assets/images/icon/trailer.svg')"
/>
<span class="radio-title">拖车</span>
</template>
<template #right-icon>
<van-radio name="07">
<template #icon="props">
<img
class="img-icon"
:src="props.checked ? activeIcon : inactiveIcon"
/>
</template>
</van-radio>
</template>
</van-cell>
<van-cell clickable @click="serviceType = '22'">
<template #title>
<van-icon
class="radio_icon"
:name="require('@/assets/images/icon/warning.svg')"
/>
<span class="radio-title">事故</span>
</template>
<template #right-icon>
<van-radio name="22">
<template #icon="props">
<img
class="img-icon"
:src="props.checked ? activeIcon : inactiveIcon"
/>
</template>
</van-radio>
</template>
</van-cell>
<van-cell clickable @click="serviceType = '27'">
<template #title>
<van-icon
class="radio_icon"
:name="require('@/assets/images/icon/other.svg')"
/>
<span class="radio-title">其他</span>
</template>
<template #right-icon>
<van-radio name="27">
<template #icon="props">
<img
class="img-icon"
:src="props.checked ? activeIcon : inactiveIcon"
/>
</template>
</van-radio>
</template>
</van-cell>
</van-cell-group>
</van-radio-group>
</div>
<div class="order_info pd_x-16 mt-24 mb_108">
<p class="second_title">确认车辆和联系人信息</p>
<van-field
v-model="vehicleType"
name="vehicleType"
label="车型"
disabled
class="bd-bottom-normal"
/>
<van-field
v-model="contactName"
name="contactName"
label="联系人姓名"
placeholder="联系人姓名"
:class="[
contactNameErrorMessage === ''
? 'bd-bottom-normal'
: 'bd-bottom-error',
'require',
]"
@input="vContactName"
/>
<span v-if="contactNameErrorMessage !== ''" class="input_error">{{
contactNameErrorMessage
}}</span>
<van-field
v-model="vehicleLicence"
name="vehicleLicence"
label="车牌信息"
placeholder="车牌信息"
:class="[
vehicleLicenceErrorMessage === ''
? 'bd-bottom-normal'
: 'bd-bottom-error',
'require',
]"
@input="vVehicleLicence"
/>
<span
v-if="vehicleLicenceErrorMessage !== ''"
class="input_error"
>{{ vehicleLicenceErrorMessage }}</span
>
<van-field
type="digit"
v-model="phone"
name="phone"
label="手机号码"
placeholder="手机号码"
:class="[
phoneErrorMessage === ''
? 'bd-bottom-normal'
: 'bd-bottom-error',
'require',
]"
@input="vPhone"
/>
<span v-if="phoneErrorMessage !== ''" class="input_error">{{
phoneErrorMessage
}}</span>
<van-field
type="digit"
class="verification_code"
v-model="verificationCode"
name="verificationCode"
label="验证码"
placeholder="请输入验证码"
:class="[
verificationCodeErrorMessage === ''
? 'bd-bottom-normal'
: 'bd-bottom-error',
'require',
]"
@input="vVerificationCode"
>
<template #button>
<van-count-down
class="send_code_time"
:time="1000 * 60"
format="ss s"
v-if="showTime"
@finish="showTime = false"
/>
<van-button
v-else-if="!showTime && !showAgain"
native-type="button"
class="send_code_button"
size="small"
type="primary"
@click="getVerificationCode"
>获取验证码</van-button
>
<van-button
v-else
native-type="button"
class="send_code_button"
size="small"
type="primary"
@click="getVerificationCode"
>重新获取</van-button
>
</template>
</van-field>
<span
v-if="verificationCodeErrorMessage !== ''"
class="input_error"
>{{ verificationCodeErrorMessage }}</span
>
</div>
</van-form>
</div>
<div class="foot_button">
<van-button
native-type="button"
class="info_button half_button mt-16 mb-24 ml-16"
@click="showCallingForHelp = true"
>联系客服</van-button
>
<van-button
class="primary_button half_button mt-16 mb-24 ml-11"
v-if="
contactNameFlag &&
vehicleLicenceFlag &&
phoneFlag &&
verificationCodeFlag &&
serviceTypeFlag
"
@click="onSubmit"
>确认并提交信息</van-button
>
<van-button
native-type="button"
class="disabled_button half_button mt-16 mb-24 ml-11"
v-if="
!(
contactNameFlag &&
vehicleLicenceFlag &&
phoneFlag &&
verificationCodeFlag &&
serviceTypeFlag
)
"
@click="beforeSubmit"
>确认并提交信息</van-button
>
</div>
</div>
<div class="search_dialog">
<van-action-sheet
v-model="showSearch"
:round="false"
style="height: 100%"
>
<div class="content">
<van-icon @click="showSearch = false" name="arrow-left" />
<van-search
ref="search"
v-model="searchContent"
@input="searchPlace"
@clear="searchResult = []"
@search="searchLocation"
placeholder="请输入搜索关键词"
/>
<span class="search_btn" @click="searchLocation">搜索</span>
<van-cell
v-for="(item, i) in searchResult"
:key="item.address + i"
:title="item.title"
:label="item.address"
@click="chooseAddress(item)"
/>
</div>
</van-action-sheet>
</div>
<order-exit-prompt
:show-order-exit="showExit"
@cancel="showExit = false"
@confirm="exitOrder"
/>
<rsa-toast
:show="verificationCodeError"
context="验证码请求过于频繁,请稍后再试"
></rsa-toast>
<rsa-toast
:show="formError"
:icon-src="require('@/assets/images/icon/alarmInformation.svg')"
context="提交失败,请重试或拨打电话"
></rsa-toast>
<!-- 致电道路救援 -->
<calling-for-help-prompt :showCallingForHelp="showCallingForHelp" @cancel="showCallingForHelp = false"></calling-for-help-prompt>
</div>
</template>
<script>
import NavBar from '@/components/layout/navbar'
import OrderExitPrompt from '@/pages/order/OrderExitPrompt.vue'
import CallingForHelpPrompt from '@/pages/home/CallingForHelpPrompt.vue'
import { Toast } from 'vant'
import { getPasscode, createOrder } from '@/api/order'
import RsaToast from '@/components/toast'
import { mapGetters } from 'vuex'
export default {
name: 'CreateOrder',
components: { OrderExitPrompt, NavBar, RsaToast, CallingForHelpPrompt },
computed: {
...mapGetters([
'userName',
'userPhone',
'localMarketValue',
'licensePlateNo'
]),
heightStyle() {
return {
height: this.currentHeight + '%',
}
}
},
data() {
return {
showCallingForHelp: false,
isToped: true, //判断列表的第一个元素是否位于顶部
defaultHeight: 60, //记录默认高度 %
currentHeight: 60, //记录当前窗体高度%
middleHeight: 60,
endHeight: 86,
startHeight: 32,
startPosY: 0,
endPosY: 0,
searchContent: '',
locationContent: '',
touchStartY: 0,
moveType: 'none',
moveStatus: 'none',
touchFlag: false,
vehicleType: '林肯飞行家',
contactName: '',
contactNameFlag: false,
contactNameErrorMessage: '',
vehicleLicence: '',
vehicleLicenceFlag: false,
vehicleLicenceErrorMessage: '',
phone: '',
phoneFlag: false,
phoneErrorMessage: '',
verificationCode: '',
verificationCodeFlag: false,
errorVerificationCode: '',
verificationCodeErrorMessage: '',
serviceType: '05',
serviceTypeFlag: true,
activeIcon: require('@/assets/images/icon/Radioactive.svg'),
inactiveIcon: require('@/assets/images/icon/Radioinactive.svg'),
rules: {
contactName: [
{
required: true,
message: '请输入联系人姓名',
trigger: 'onBlur',
},
],
vehicleLicence: [
{ required: true, message: '请输入车牌信息', trigger: 'onBlur' },
{
pattern:
/^([京津沪渝冀豫云辽黑湘皖鲁新苏浙赣鄂桂甘晋蒙陕吉闽贵粤青藏川宁琼使领A-Z]{1}[A-Z]{1}(([0-9]{5}[DF])|([DF][A-HJ-NP-Z0-9][0-9]{4})))$|^([京津沪渝冀豫云辽黑湘皖鲁新苏浙赣鄂桂甘晋蒙陕吉闽贵粤青藏川宁琼使领A-Z]{1}[A-Z]{1}[A-HJ-NP-Z0-9]{4}[A-HJ-NP-Z0-9挂学警港澳]{1})$/,
message: '车牌号不正确',
trigger: 'onBlur',
},
],
phone: [
{ required: true, message: '请输入手机号码', trigger: 'onBlur' },
{
pattern: /^1[3-9]\d{9}$/,
message: '手机号不正确',
trigger: 'onBlur',
},
],
verificationCode: [
{ required: true, message: '请输入验证码', trigger: 'onBlur' },
{ pattern: /^\d{6}$/, message: '验证码错误', trigger: 'onBlur' },
],
},
showTime: false,
showAgain: false,
location: {},
address: '',
city: '',
zoom: 15,
map: null,
BMap: null,
showSearch: false,
showExit: false,
searchResult: [],
serviceTypeList: [
{ code: '03', name: '更换轮胎' },
{ code: '04', name: '接电服务' },
{ code: '05', name: '紧急送油' },
{ code: '07', name: '拖车' },
{ code: '22', name: '事故救援' },
{ code: '27', name: '未知' },
],
verificationCodeError: false,
formError: false,
}
},
mounted() {
this.handleTounchListener() // 布局监听
if (this.userPhone) {
this.phone = this.userPhone
this.phoneFlag = true
}
if (this.userName) {
this.contactName = this.userName
this.contactNameFlag = true
}
if (this.licensePlateNo) {
this.vehicleLicence = this.licensePlateNo
this.vehicleLicenceFlag = true
}
this.vehicleType = this.localMarketValue
// 轮询订单接口 状态
this.$on('getStatusCode', (code) => {
this.$router.replace({ name: 'orderInProgress' })
})
window.addEventListener('popGesture', function (e) {
this.showExit = true
})
},
methods: {
onListScrolled(event) {
this.isToped = true
// this.scrollListView()
},
scrollListView(flag) {
let listView = this.$refs.listView
if (listView.scrollTop <= 0) { // 滚动到顶部
listView.scrollTop = 1
} else if ((listView.scrollHeight - listView.clientHeight - listView.scrollTop) <= 0) { // 滚动到底部
listView.scrollTop = listView.scrollHeight - listView.clientHeight - 1
} else {
if (flag === 'touchend') {
listView.scrollTop += 1
}
}
},
handleTounchListener() {
this.$refs.drawer.addEventListener('touchstart', (event) => {
//记录点击坐标
this.startPosY = event.targetTouches[0].pageY
this.defaultHeight = this.currentHeight
})
this.$refs.drawer.addEventListener('touchmove', (event) => {
event.preventDefault()
//计算移动距离
if (event.targetTouches.length > 1) {
return
}
let touch = event.targetTouches[0]
this.endPosY = touch.pageY
let dy = ((this.startPosY - touch.pageY) * 100) / 667
if (dy > 0) {
// 向上
// middleHeight: 60, endHeight: 86, startHeight: 32,
if (this.defaultHeight + dy >= 86) {
this.currentHeight = this.endHeight
} else {
if (this.defaultHeight === 32) {
this.currentHeight = Math.max(this.startHeight, this.defaultHeight + dy)
} else if (this.defaultHeight === 60) {
this.currentHeight = Math.max(this.middleHeight, this.defaultHeight + dy)
}
}
} else {
// 向下
if (this.defaultHeight + dy <= 32) {
this.currentHeight = this.startHeight
} else {
if (this.defaultHeight === 86) {
this.currentHeight = Math.min(this.endHeight, this.defaultHeight + dy)
} else if (this.defaultHeight === 60) {
this.currentHeight = Math.min(this.middleHeight, this.defaultHeight + dy)
}
}
}
})
this.$refs.drawer.addEventListener('touchend', (event) => {
this.scrollListView('touchend')
// 阈值 = 差值的20%
const threshold = Math.abs(this.defaultHeight - this.currentHeight) * 0.2
if (!this.isToped || threshold === 0) {
return
}
const isDirectorTop = this.endPosY - this.startPosY < 0
if (isDirectorTop) {
// 向上
if (this.defaultHeight === 32) {
this.currentHeight = this.middleHeight
} else if (this.defaultHeight === 60) {
this.currentHeight = this.endHeight
}
} else {
// 向下
if (this.defaultHeight === 86) {
this.currentHeight = this.middleHeight
} else if (this.defaultHeight === 60) {
this.currentHeight = this.startHeight
}
}
})
this.$refs.drawer.addEventListener('touchcancel', (event) => {
})
},
// --------------------以上关于布局,表单上下滑动----------------------------
handleMap({ BMap, map }) {
this.$store.dispatch('app/changeLoading', true)
this.map = map
this.BMap = BMap
let geolocation = new BMap.Geolocation()
geolocation.enableSDKLocation()
let that = this
geolocation.getCurrentPosition(function (r) {
if (this.getStatus() == BMAP_STATUS_SUCCESS) {
that.getAddress(r.point)
that.setLocation(r.point)
that.$store.dispatch('app/changeLoading', false)
}
})
},
setLocation(point) {
this.map.clearOverlays()
let icon = new this.BMap.Icon(
require('@/assets/images/icon/location.svg'),
new BMap.Size(48, 48)
)
let mk = new this.BMap.Marker(point, { icon: icon })
this.map.addOverlay(mk)
this.map.panTo(point)
this.location.lng = point.lng
this.location.lat = point.lat
},
getLocation(e) {
this.getAddress(e.point)
this.setLocation(e.point)
},
getAddress(point) {
let geoc = new BMap.Geocoder()
let that = this
geoc.getLocation(point, function (rs) {
that.address = rs.address
that.city = rs ? rs.addressComponents.city : ''
})
},
getPosition(address) {
let geoc = new BMap.Geocoder()
let that = this
geoc.getPoint(
address,
function (point) {
if (point) {
that.setLocation(point)
that.getAddress(point)
that.showSearch = false
} else {
Toast('您选择的地址没有找到!')
}
},
this.city
)
},
searchPlace() {
let localSearch = new this.BMap.LocalSearch(this.map)
localSearch.setSearchCompleteCallback((res) => {
this.searchResult = res ? res.Yr : []
})
localSearch.search(this.searchContent)
},
chooseAddress(address) {
this.setLocation(address.point)
this.getAddress(address.point)
this.locationContent = address.title
this.showSearch = false
},
searchLocation() {
this.getPosition(this.searchContent)
},
searchAddress() {
this.searchContent = ''
this.showSearch = true
this.searchResult = []
this.$nextTick(() => {
this.$refs.search.querySelector('input').focus()
})
},
vServiceType() {
this.serviceTypeFlag = this.serviceType !== ''
},
vContactName() {
if (this.contactName === '') {
this.contactNameFlag = false
this.contactNameErrorMessage = '请输入联系人姓名'
} else {
this.contactNameFlag = true
this.contactNameErrorMessage = ''
}
},
vVehicleLicence() {
if (this.vehicleLicence === '') {
this.vehicleLicenceFlag = false
this.vehicleLicenceErrorMessage = '请输入车牌信息'
} else {
this.vehicleLicenceFlag = true
this.vehicleLicenceErrorMessage = ''
}
},
vPhone() {
let reg = /^1[3-9]\d{9}$/
if (this.phone === '') {
this.phoneFlag = false
this.phoneErrorMessage = '请输入手机号码'
} else if (!reg.test(this.phone)) {
this.phoneFlag = false
this.phoneErrorMessage = '手机号不正确'
} else {
this.phoneFlag = true
this.phoneErrorMessage = ''
}
},
vVerificationCode() {
if (
this.errorVerificationCode !== '' &&
this.verificationCode === this.errorVerificationCode
) {
return
}
let reg = /^\d{6}$/
if (this.verificationCode === '') {
this.verificationCodeFlag = false
this.verificationCodeErrorMessage = '请输入验证码'
} else if (!reg.test(this.verificationCode)) {
this.verificationCodeFlag = false
this.verificationCodeErrorMessage = '验证码错误'
} else {
this.verificationCodeFlag = true
this.verificationCodeErrorMessage = ''
}
},
getVerificationCode() {
this.showTime = true
this.showAgain = true
this.$refs.orderForm.validate('phone').then(() => {
getPasscode({ encryptedPhone: this.phone }).then((res) => {
if (res.data.status === '1' || res.data.status === '2') {
this.verificationCodeError = true
setTimeout(() => {
this.verificationCodeError = false
}, 2000)
return
}
})
})
},
beforeSubmit() {
this.vContactName()
this.vVehicleLicence()
this.vPhone()
this.vVerificationCode()
},
onSubmit(values) {
let type = this.serviceTypeList.find((item) => {
return item.code === this.serviceType
})
if (!type) {
return
}
let param = {
setCode: 'APP',
encryptedPhone: this.phone,
encryptedName: this.contactName,
encryptedRegNo: this.vehicleLicence,
model: this.vehicleType,
coordinateType: '02',
encryptedLongitude: this.location.lng,
encryptedLatitude: this.location.lat,
typeCode: type.code,
typeName: type.name,
encryptedPinCode: this.verificationCode,
}
createOrder(param)
.then((res) => {
if (res.status !== 200) {
if (res.status === 600 && res.errorCode === '222040') {
this.verificationCodeFlag = false
this.errorVerificationCode = this.verificationCode
this.verificationCodeErrorMessage = '验证码错误'
} else {
this.formError = true
this.verificationCodeFlag = false
this.verificationCode = ''
setTimeout(() => {
this.formError = false
}, 3000)
}
return
}
this.$emit('clearPolling')
this.$router.replace({ name: 'orderInProgress' })
})
.catch((err) => {
this.formError = true
setTimeout(() => {
this.formError = false
}, 3000)
})
},
exitOrder() {
this.showExit = false
this.$router.go(-1)
}
},
}
</script>
<style lang="scss" scoped>
.create_order {
width: 100%;
display: flex;
height: 100%;
flex-direction: column;
.toplayout {
width: 100%;
height: 100%;
.map {
width: 100%;
height: calc(100% - 50%);
::v-deep .anchorBL {
display: none;
}
}
.map-height{
height: calc(100% - 30%);
}
}
.vertical-drawable {
position: fixed;
left: 0px;
right: 0px;
bottom: 0px;
overflow-y: hidden;
display: flex;
flex-direction: column;
.title {
line-height: 32px;
text-align: center;
border-radius: 16px 16px 0px 0px;
background: white;
.slider_line {
display: inline-block;
margin: 12px 0 0 0;
width: 32px;
height: 4px;
background: rgba(0, 0, 0, 0.1);
border-radius: 2px;
}
}
.listview {
background: white;
display: flex;
flex: 1;
flex-direction: column;
overflow-y: auto;
.van-form{
padding-bottom: 10px;
-webkit-overflow-scrolling: touch;
}
.location_search {
padding: 8px 0;
border-radius: 4px;
> img {
width: 10px;
height: 14px;
margin-left: 7px;
}
.van-cell {
padding: 8px 16px 8px 0;
}
::v-deep .van-icon {
font-size: 24px;
}
}
.location_info {
font-weight: 400;
font-size: 14px;
line-height: 28px;
color: #f26147;
margin-left: 9px;
}
.service_type {
.van-radio-group {
.van-cell-group {
.van-cell {
padding: 16px 0;
border-top: 0;
border-bottom: 1px solid rgba(0, 0, 0, 0.1);
.radio_icon {
line-height: 24px;
img {
position: absolute;
width: 18.84px;
height: 21px;
top: -17px;
}
}
.radio-title {
font-family: "PingFang SC";
font-style: normal;
font-weight: 400;
font-size: 16px;
line-height: 24px;
color: rgba(0, 0, 0, 0.85);
margin-left: 30px;
}
}
}
.van-hairline--top-bottom {
&:after {
border: 0;
}
}
}
}
.order_info {
.send_code_time {
color: #f26147;
}
.bd-bottom-normal {
border-bottom: 1px solid rgba(0, 0, 0, 0.1);
}
.bd-bottom-error {
border-bottom: 1px solid #db373c;
}
.van-cell {
padding: 16px 0;
::v-deep .van-field__control {
text-align: right;
}
::v-deep .van-field__error-message {
text-align: right;
}
}
.require {
::v-deep .van-cell__title.van-field__label {
span {
position: relative;
&:after {
position: absolute;
right: -8px;
color: #f26147;
font-size: 16px;
content: "*";
}
}
}
}
.input_error {
width: 317px;
height: 20px;
font-family: "PingFang SC";
font-style: normal;
font-weight: 400;
font-size: 12px;
line-height: 20px;
color: #db373c;
}
::v-deep .van-cell--required {
&:before {
content: "";
}
.van-cell__title.van-field__label {
span {
position: relative;
&:after {
position: absolute;
right: -8px;
color: #f26147;
font-size: 16px;
content: "*";
}
}
}
}
.send_code_button {
height: 22px;
font-family: "PingFang SC";
font-style: normal;
font-weight: 500;
font-size: 14px;
line-height: 22px;
text-align: right;
letter-spacing: 0.4px;
color: #f26147;
border: 0;
background-color: #ffffff;
}
}
}
.foot_button{
background: white;
}
}
.search_dialog {
.van-action-sheet {
max-height: 100%;
.content {
padding: 8px 16px;
.van-search {
::v-deep .van-icon {
font-size: 24px;
}
}
}
i {
color: rgba(0, 0, 0, 0.85);
padding: 0 0 0 5px;
font-size: 20px;
}
.van-search {
display: inline-block;
padding: 8px 16px;
width: 275px;
border-radius: 4px;
.van-cell {
padding: 8px 16px 8px 0;
}
}
.search_btn {
font-family: "PingFang SC";
font-style: normal;
font-weight: 500;
font-size: 16px;
line-height: 24px;
color: #f26147;
}
.van-cell {
&:after {
content: none;
}
.van-cell__title {
span {
display: inline-block;
font-family: "PingFang SC";
font-style: normal;
font-weight: 400;
font-size: 16px;
line-height: 24px;
color: rgba(0, 0, 0, 0.85);
}
}
.van-cell__label {
font-family: "PingFang SC";
font-style: normal;
font-weight: 400;
font-size: 14px;
line-height: 22px;
letter-spacing: 0.4px;
color: rgba(0, 0, 0, 0.45);
margin-top: 4px;
}
}
}
}
}
</style>