master
王文杰 7 months ago
parent fcbc680462
commit 6486ed399a

@ -56,6 +56,12 @@
"navigationBarTitleText": "服务站详情" "navigationBarTitleText": "服务站详情"
} }
}, },
{
"path": "pages/houseDetail/houseDetail",
"style": {
"navigationBarTitleText": "小区详情"
}
},
{ {
"path": "pages/login/protocal", "path": "pages/login/protocal",
"style": { "style": {
@ -71,7 +77,19 @@
{ {
"path": "pages/orderList/orderList", "path": "pages/orderList/orderList",
"style": { "style": {
"navigationBarTitleText": "订单" "navigationBarTitleText": "预约回收订单"
}
},
{
"path": "pages/orderTimeList/orderTimeList",
"style": {
"navigationBarTitleText": "定时回收订单"
}
},
{
"path": "pages/orderSiteList/orderSiteList",
"style": {
"navigationBarTitleText": "到站回收订单"
} }
} }
], ],

@ -0,0 +1,136 @@
<!--
此文件为开发者工具生成生成时间: 2024/3/16下午5:17:10
使用方法
/Users/wangwenjie/chanko/app-nx-personal/dist/dev/mp-weixin/pages/siteDetail/siteDetail.wxml 引入模板
```
<import src="siteDetail.skeleton.wxml"/>
<template is="skeleton" wx:if="{{loading}}" />
```
/Users/wangwenjie/chanko/app-nx-personal/dist/dev/mp-weixin/pages/siteDetail/siteDetail.wxss 中引入样式
```
@import "./siteDetail.skeleton.wxss";
```
更多详细信息可以参考文档https://developers.weixin.qq.com/miniprogram/dev/devtools/skeleton.html
-->
<template name="skeleton">
<view class="sk-container">
<view class="site-detail site-detail data-v-c07d57ff data-v-c07d57ff">
<view is="components/XtxSwiper" class="data-v-c07d57ff data-v-c07d57ff">
<view class="carousel XtxSwiper--carousel">
<swiper circular="true" interval="3000" current="0" autoplay="false">
<swiper-item style="position: absolute; width: 100%; height: 100%; transform: translate(0%, 0px) translateZ(0px);">
<navigator class="navigator XtxSwiper--navigator" hover-class="none">
<image class="image XtxSwiper--image sk-image" mode="aspectFill"></image>
</navigator>
</swiper-item>
</swiper>
<view class="indicator XtxSwiper--indicator">
<text class="dot XtxSwiper--dot active XtxSwiper--active"></text>
<text class="dot XtxSwiper--dot"></text>
</view>
</view>
</view>
<view class="cont cont data-v-c07d57ff data-v-c07d57ff">
<view class="info info data-v-c07d57ff data-v-c07d57ff">
<view class="hd hd data-v-c07d57ff data-v-c07d57ff">
<view class="name data-v-c07d57ff sk-transparent sk-text-14-2857-463 sk-text">测试JY</view>
<view class="num data-v-c07d57ff sk-transparent sk-text-14-2857-544 sk-text">0</view>
</view>
<view class="md md data-v-c07d57ff data-v-c07d57ff">
<view class="label data-v-c07d57ff sk-transparent sk-text-14-2857-85 sk-text">营业时间</view>
<view class="time data-v-c07d57ff sk-transparent sk-text-14-2857-560 sk-text">10:20 - 13:20</view>
</view>
<view class="fd fd data-v-c07d57ff data-v-c07d57ff">
<view class="label data-v-c07d57ff sk-transparent sk-text-14-2857-893 sk-text">地址上海市松江区园中路1号</view>
</view>
</view>
<view class="module-menu module-menu data-v-c07d57ff data-v-c07d57ff">
<view class="item data-v-c07d57ff sk-transparent sk-text-14-2857-881 sk-text" style="background-position-x: 50%;">旧衣服</view>
<view class="item data-v-c07d57ff sk-transparent sk-text-14-2857-330 sk-text" style="background-position-x: 50%;">家用电器</view>
<view class="item data-v-c07d57ff sk-transparent sk-text-14-2857-341 sk-text" style="background-position-x: 50%;">废纸废书</view>
<view class="item data-v-c07d57ff sk-transparent sk-text-14-2857-650 sk-text" style="background-position-x: 50%;">废金属</view>
<view class="item data-v-c07d57ff sk-transparent sk-text-14-2857-961 sk-text" style="background-position-x: 50%;">废塑料</view>
</view>
<view class="detail-list detail-list data-v-c07d57ff data-v-c07d57ff">
<view class="item arrow flex-row data-v-c07d57ff sk-pseudo sk-pseudo-circle">
<view class="service-title data-v-c07d57ff sk-transparent sk-text-33-3333-159 sk-text">服务</view>
<view class="tag-list tag-list data-v-c07d57ff data-v-c07d57ff">
<view class="tag data-v-c07d57ff sk-transparent sk-text-36-6667-477 sk-text">上门服务</view>
<view class="tag data-v-c07d57ff sk-transparent sk-text-36-6667-758 sk-text">家电维修</view>
<view class="tag data-v-c07d57ff sk-transparent sk-text-36-6667-789 sk-text">品控质检</view>
</view>
</view>
<view class="item item flex-column flex-column rate rate data-v-c07d57ff data-v-c07d57ff">
<view class="service-title data-v-c07d57ff sk-transparent sk-text-33-3333-384 sk-text">评分</view>
<view is="node-modules/@dcloudio/uni-ui/lib/uni-rate/uni-rate" class="data-v-c07d57ff data-v-c07d57ff">
<view>
<view class="uni-rate rate--uni-rate">
<view class="uni-rate__icon rate--uni-rate__icon" style="margin-right:0px">
<view is="node-modules/@dcloudio/uni-ui/lib/uni-icons/uni-icons">
<text class="uni-icons icons--uni-icons uniui-star-filled icons--uniui-star-filled sk-pseudo sk-pseudo-circle" style="color: #ececec; font-size: 24px;"></text>
</view>
<view class="uni-rate__icon-on rate--uni-rate__icon-on" style="width:100%">
<view is="node-modules/@dcloudio/uni-ui/lib/uni-icons/uni-icons">
<text class="uni-icons icons--uni-icons uniui-star-filled icons--uniui-star-filled sk-pseudo sk-pseudo-circle" style="color: #FF7D00; font-size: 24px;"></text>
</view>
</view>
</view>
<view class="uni-rate__icon rate--uni-rate__icon" style="margin-right:0px">
<view is="node-modules/@dcloudio/uni-ui/lib/uni-icons/uni-icons">
<text class="uni-icons icons--uni-icons uniui-star-filled icons--uniui-star-filled sk-pseudo sk-pseudo-circle" style="color: #ececec; font-size: 24px;"></text>
</view>
<view class="uni-rate__icon-on rate--uni-rate__icon-on" style="width:100%">
<view is="node-modules/@dcloudio/uni-ui/lib/uni-icons/uni-icons">
<text class="uni-icons icons--uni-icons uniui-star-filled icons--uniui-star-filled sk-pseudo sk-pseudo-circle" style="color: #FF7D00; font-size: 24px;"></text>
</view>
</view>
</view>
<view class="uni-rate__icon rate--uni-rate__icon" style="margin-right:0px">
<view is="node-modules/@dcloudio/uni-ui/lib/uni-icons/uni-icons">
<text class="uni-icons icons--uni-icons uniui-star-filled icons--uniui-star-filled sk-pseudo sk-pseudo-circle" style="color: #ececec; font-size: 24px;"></text>
</view>
<view class="uni-rate__icon-on rate--uni-rate__icon-on" style="width:100%">
<view is="node-modules/@dcloudio/uni-ui/lib/uni-icons/uni-icons">
<text class="uni-icons icons--uni-icons uniui-star-filled icons--uniui-star-filled sk-pseudo sk-pseudo-circle" style="color: #FF7D00; font-size: 24px;"></text>
</view>
</view>
</view>
<view class="uni-rate__icon rate--uni-rate__icon" style="margin-right:0px">
<view is="node-modules/@dcloudio/uni-ui/lib/uni-icons/uni-icons">
<text class="uni-icons icons--uni-icons uniui-star-filled icons--uniui-star-filled sk-pseudo sk-pseudo-circle" style="color: #ececec; font-size: 24px;"></text>
</view>
<view class="uni-rate__icon-on rate--uni-rate__icon-on" style="width:100%">
<view is="node-modules/@dcloudio/uni-ui/lib/uni-icons/uni-icons">
<text class="uni-icons icons--uni-icons uniui-star-filled icons--uniui-star-filled sk-pseudo sk-pseudo-circle" style="color: #FF7D00; font-size: 24px;"></text>
</view>
</view>
</view>
<view class="uni-rate__icon rate--uni-rate__icon" style="margin-right:0px">
<view is="node-modules/@dcloudio/uni-ui/lib/uni-icons/uni-icons">
<text class="uni-icons icons--uni-icons uniui-star-filled icons--uniui-star-filled sk-pseudo sk-pseudo-circle" style="color: #ececec; font-size: 24px;"></text>
</view>
<view class="uni-rate__icon-on rate--uni-rate__icon-on" style="width:100%">
<view is="node-modules/@dcloudio/uni-ui/lib/uni-icons/uni-icons">
<text class="uni-icons icons--uni-icons uniui-star-filled icons--uniui-star-filled sk-pseudo sk-pseudo-circle" style="color: #FF7D00; font-size: 24px;"></text>
</view>
</view>
</view>
</view>
</view>
</view>
</view>
<view class="item item flex-column flex-column activity activity data-v-c07d57ff data-v-c07d57ff">
<view class="activity-title data-v-c07d57ff sk-transparent sk-text-14-2857-597 sk-text">活动</view>
<view class="activity-list activity-list data-v-c07d57ff data-v-c07d57ff">
<view class="activity-item data-v-c07d57ff sk-transparent sk-text-14-2857-423 sk-text">会员价</view>
<view class="activity-item data-v-c07d57ff sk-transparent sk-text-14-2857-853 sk-text">赠送积分</view>
</view>
</view>
</view>
</view>
</view>
</view>
</template>

@ -0,0 +1,288 @@
<script setup lang="ts">
import { ref, reactive } from 'vue'
import { onLoad, onReady } from '@dcloudio/uni-app'
import { getHouseInfoAPI } from '@/services/home'
import { postBookingHouseAPI } from '@/services/booking'
import { serviceDomain, bannerList } from '@/services/constants'
import PageSkeleton from './components/PageSkeleton.vue'
//
const location = uni.getStorageSync('location')
const Info = ref({})
const isLoading = ref(false)
const housingEstateId = ref('')
const getDataList = async (id) => {
// 退
//
isLoading.value = true
//
housingEstateId.value = id
const queryParams = {
housingEstateId: id,
...location,
}
const res = await getHouseInfoAPI(queryParams)
const obj = res.data
const arr = obj.images && JSON.parse(obj.images) || []
const imgUrl = serviceDomain + arr[0]?.url
obj.imgUrl = imgUrl
Info.value = obj
//
isLoading.value = false
}
//
onLoad((options) => {
getDataList(options.id)
})
const isLoadingBook = ref(false)
const handleBook = async () => {
if (isLoadingBook.value) {
return
}
isLoadingBook.value = true
const params = {
housingEstateId: housingEstateId.value,
remark: '请尽快上门',
}
const res = await postBookingHouseAPI(params)
isLoadingBook.value = false
}
</script>
<template>
<view class="site-detail">
<template v-if="!isLoading">
<XtxSwiper :list="bannerList" />
<view class="cont">
<view class="info">
<view class="hd">
<view class="name">{{ Info?.name }}</view>
<view class="num">{{ Info.distance || 0.0 }}千米</view>
</view>
<view class="md">
<view class="label">回收时间</view>
<view class="time">{{ Info.appointmentTimeStart }} - {{ Info.appointmentTimeEnd }}</view>
</view>
<view class="fd">
<view class="label">地址{{ Info.address }}</view>
<image class="img" :src="Info.imgUrl" />
</view>
</view>
<!-- <view class="module-menu">
<view class="module-title">附近回收站</view>
<view class="order-details" v-if="Info.stationProducts">
<view class="detail-item" v-for="item2 in Info.stationProducts" :key="item2.id">
<view class="product-name">
<image class="img-url" :src="item2.imgUrl"></image>
<view class="name">{{ item2.name }}</view>
</view>
<view class="product-price">回收价格{{ item2.recoveryPrice }} </view>
</view>
</view>
</view> -->
<view class="action">
<view :class="[isLoadingBook ? 'disabled' : '','button']" @click="handleBook"></view>
</view>
</view>
</template>
<template v-else>
<PageSkeleton />
</template>
</view>
</template>
<style lang="scss" scoped>
.site-detail {
background: #f2f2fa;
.cont {
background-color: #fff;
margin: 20rpx;
padding: 16rpx;
min-height: 80vh;
overflow: auto;
positon: relative;
.info {
padding: 10rpx 20rpx;
box-shadow: 0px 0px 8px 0px rgba(161, 161, 177, 0.12);
.hd {
display: flex;
justify-content: space-between;
.name {
font-size: 30rpx;
font-weight: 500;
color: #0d0d26;
}
.num {
font-size: 28rpx;
color: #95969d;
}
}
.md {
margin: 10rpx 0;
font-size: 24rpx;
color: #95969d;
display: flex;
}
.fd {
display: flex;
justify-content: space-between;
align-items: center;
.label {
font-size: 24rpx;
}
.img {
width: 72rpx;
height: 72rpx;
border-radius: 50%;
background-color: #3a82fb;
}
}
}
.module-menu {
// display: flex;
padding: 36rpx 20rpx;
box-shadow: 0px 0px 8px 0px rgba(161, 161, 177, 0.12);
.item {
flex: 1;
color: #95969d;
padding: 10rpx 0;
border-radius: 10rpx;
text-align: center;
&.active {
background: #fff7e8;
}
}
.order-details {
.detail-item {
margin: 20rpx;
display: flex;
flex-direction: column;
justify-content: space-around;
.product-name {
display: flex;
align-items: center;
font-size: 28rpx;
.img-url {
width: 40rpx;
height: 40rpx;
margin-right: 20rpx;
}
.name {
font-size: 28rpx;
color: #95969d;
}
}
.product-price {
font-size: 28rpx;
margin: 20rpx;
color: #95969d;
}
}
}
}
.detail-list {
padding: 0 20rpx;
background-color: #fff;
margin-bottom: 20rpx;
border-radius: 10rpx;
.item {
// line-height: 90rpx;
padding-left: 10rpx;
font-size: 30rpx;
color: #333;
border-bottom: 1rpx solid #ddd;
position: relative;
text-align: left;
border-radius: 0;
background-color: #fff;
display: flex;
&::after {
width: auto;
height: auto;
left: auto;
border: none;
}
// &:first-child {
// border: none;
// }
&::after {
right: 5rpx;
}
&.flex-column {
flex-direction: column;
&:first-child {
}
}
&.rate {
line-height: 90rpx;
padding-bottom: 20rpx;
}
&.flex-row {
line-height: 90rpx;
flex-direction: row;
}
.tag-list {
display: flex;
margin-left: 20rpx;
.tag {
color: #95969d;
font-size: 24rpx;
}
}
&.activity {
margin: 20rpx 0;
.activity-list {
display: flex;
.activity-item {
margin: 20rpx 10rpx;
&:first-child {
background: #484540;
padding: 4rpx 6rpx;
border-radius: 10rpx;
color: #ffe6b5;
font-size: 24rpx;
}
&:last-child {
padding: 4rpx 6rpx;
border-radius: 10rpx;
color: #ffb739;
border: 2rpx solid #ffb739;
font-size: 24rpx;
}
}
}
}
}
.arrow::after {
content: '\e6c2';
position: absolute;
top: 50%;
color: #ccc;
font-family: 'erabbit' !important;
font-size: 32rpx;
transform: translateY(-50%);
}
}
.action {
position: absolute;
bottom: 100rpx;
width: 400rpx;
transform: translateX(50%);
text-align: center;
.button {
padding: 30rpx 40rpx;
font-size: 32rpx;
color: #fff;
font-weight: 500;
border-radius: 32rpx;
background: linear-gradient(158deg, #51B6FF 10%, #3775F6 97%);
&.disabled {
background: #95969d;
}
}
}
}
}
</style>

@ -0,0 +1,113 @@
<!--
* @Author: 王文杰
* @Date: 2024-03-15 21:26:32
* @LastEditors: 王文杰
* @LastEditTime: 2024-03-26 15:50:11
* @FilePath: /app-nx-personal/src/pages/index/components/NeighborhoodSite.vue
* @Description: 这是默认设置,请设置`customMade`, 打开koroFileHeader查看配置 进行设置: https://github.com/OBKoro1/koro1FileHeader/wiki/%E9%85%8D%E7%BD%AE
-->
<script setup lang="ts">
defineProps<{
list: []
}>()
const handleToto = (id) => {
const url = `/pages/houseDetail/houseDetail?id=${id}`
uni.navigateTo({ url })
}
</script>
<template>
<view class="neighborhood">
<view class="module-title">定时回收</view>
<view class="module-desc"> 定时上门快捷高效</view>
<view class="item" v-for="item in list" :key="item.id" @tap="handleToto(item.id)">
<view class="module-cont">
<image class="left" :src="item.imgUrl" />
<view class="md">
<view class="name">{{ item.name }}</view>
<view class="time"
>回收时间{{ item.appointmentTimeStart }} - {{ item.appointmentTimeEnd }}</view
>
<view class="loction">{{ item.address }}</view>
</view>
<view class="right">
<view class="num">{{ item.distance }}千米</view>
</view>
</view>
</view>
</view>
</template>
<style lang="scss" scoped>
.neighborhood {
padding: 32rpx 20rpx;
margin: 16rpx;
padding-bottom: 120rpx;
background-color: #fff;
border-radius: 4rpx;
.module-title {
font-size: 30rpx;
color: #0D0D26;
margin: 10rpx 0;
}
.module-desc {
font-size: 24rpx;
color: #95969D;
padding-bottom: 20rpx;
}
.module-cont {
border-top: 2rpx solid #F2F2F2;
padding: 20rpx 0;
display: flex;
flex-direction: row;
.left {
width: 140rpx;
height: 140rpx;
border-radius: 12rpx;
}
.md {
flex: 1;
margin: 0 10rpx;
font-size: 24rpx;
color: #0D0D26;
.name {
font-size: 30rpx;
.zuijin {
font-size: 24rpx;
color: #FF7D00;
background: #FFF7E8;
padding: 4rpx 4rpx;
margin-right: 6rpx;
border-radius: 4rpx;
}
}
.time {
color: #95969D;
margin: 8rpx 0;
}
.loction {
color: #0D0D26;
}
}
.right {
.num {
font-size: 28rpx;
color: #95969D
}
.img {
width: 72rpx;
height: 72rpx;
margin-top: 20rpx;
border-radius: 10rpx;
}
}
}
.foot-desc {
.item {
font-size: 24rpx;
color: #95969D;
margin: 10rpx 0;
}
}
}
</style>

@ -1,47 +0,0 @@
<!--
* @Author: 王文杰
* @Date: 2024-03-15 21:26:32
* @LastEditors: 王文杰
* @LastEditTime: 2024-03-25 16:09:11
* @FilePath: /app-nx-personal/src/pages/index/components/NeighborhoodSite.vue
* @Description: 这是默认设置,请设置`customMade`, 打开koroFileHeader查看配置 进行设置: https://github.com/OBKoro1/koro1FileHeader/wiki/%E9%85%8D%E7%BD%AE
-->
<script setup lang="ts">
defineProps<{
list: []
}>()
const handleToto = (id) => {
const url = `/pages/siteDetail/siteDetail?siteId=${id}`
uni.navigateTo({ url })
}
</script>
<template>
<view class="neighborhood-site">
<view class="module-title">定时回收</view>
<view class="item" v-for="item in list" :key="item.id" @tap="handleToto(item.id)">
<view class="module-cont">
<image class="left" :src="item.imgUrl" />
<view class="md">
<view class="name"><span class="zuijin"> 最近 </span>{{ item.stationName }}</view>
<view class="time"
>营业时间{{ item.appointmentTimeStart }} - {{ item.appointmentTimeEnd }}</view
>
<view class="loction">{{ item.address }}</view>
</view>
<view class="right">
<view class="num">{{ item.distance }}千米</view>
</view>
</view>
<view class="md-tag" v-if="item.categoryStr"
><span class="tag-before">回收品类</span>{{ item.categoryStr }}</view
>
<view class="foot-desc">
<view class="item">特色服务再生资源回收</view>
</view>
</view>
</view>
</template>
<style lang="scss" scoped>
@import '../styles/neighborhoodSite.scss';
</style>

@ -73,16 +73,13 @@ const getHouseNearBy = async () => {
...location, ...location,
} }
const res = await getHouseNearbyAPI(params) const res = await getHouseNearbyAPI(params)
if (res.data) { if (res?.data) {
HouseList = res.data HouseList = res.data
const obj = res.data || {} HouseList.forEach((e) => {
const arr = JSON.parse(obj.stationImg) const arr = e.images && JSON.parse(e.images) || []
const obj2 = arr[0] const imgUrl = serviceDomain + arr[0]?.url
// const imgUrl = serviceDomain + obj2?.url e.imgUrl = imgUrl
// obj.imgUrl = imgUrl })
// const categoryArr = obj.stationProducts?.map((q) => q.name) || []
// obj.categoryStr = categoryArr.join('.')
// siteList = [obj]
} else { } else {
uni.showToast({ icon: 'none', title: '当前位置小区未关联回收站点...' }) uni.showToast({ icon: 'none', title: '当前位置小区未关联回收站点...' })
} }

@ -80,6 +80,20 @@ const getMemberProfileData = async () => {
nickName.value = obj.nickName nickName.value = obj.nickName
banlance.value = obj.banlance banlance.value = obj.banlance
} }
//
const handleJump = (type) => {
if (type == 'book') {
uni.switchTab({ url: '/pages/orderList/orderList' })
return
}
if (type == 'time') {
uni.navigateTo({ url: '/pages/orderTimeList/orderTimeList' })
return
}
if (type == 'site') {
uni.navigateTo({ url: '/pages/orderSiteList/orderSiteList' })
}
}
</script> </script>
<template> <template>
@ -150,27 +164,23 @@ const getMemberProfileData = async () => {
</view> </view>
</view> </view>
</view> --> </view> -->
<!-- <view class="module"> <view class="module">
<view class="module-title">我的服务</view> <view class="module-title">订单中心</view>
<view class="module-list"> <view class="module-list">
<view class="item"> <view class="item" @click="handleJump('book')">
<text class="label">签到</text> <uni-icons type="cart" color="#3775F6" size="32"></uni-icons>
<view class="num">我的评价</view> <view class="label">预约回收</view>
</view> </view>
<view class="item"> <view class="item" @click="handleJump('time')">
<text class="label">签到</text> <uni-icons type="calendar" color="#3775F6" size="32"></uni-icons>
<view class="num">积分兑换</view> <view class="label">定时回收</view>
</view> </view>
<view class="item"> <view class="item" @click="handleJump('site')">
<text class="label">签到</text> <uni-icons type="shop" color="#3775F6" size="32"></uni-icons>
<view class="num">我的评价</view> <view class="label">到站回收</view>
</view> </view>
<view class="item">
<text class="label">签到</text>
<view class="num">积分兑换</view>
</view> </view>
</view> </view>
</view> -->
<view class="list"> <view class="list">
<!-- <navigator class="loation item arrow" url="/pages/orderList/orderList" hover-class="none"> <!-- <navigator class="loation item arrow" url="/pages/orderList/orderList" hover-class="none">
@ -428,9 +438,13 @@ page {
} }
.module { .module {
margin: 40rpx 0; margin: 40rpx 20rpx;
background-color: #fff;
padding: 20rpx;
border-radius: 10rpx;
.module-title { .module-title {
font-size: 30rpx; font-size: 32rpx;
font-weight: 500;
margin: 20rpx; margin: 20rpx;
} }
.module-list { .module-list {
@ -442,13 +456,16 @@ page {
width: 160rpx; width: 160rpx;
height: 160rpx; height: 160rpx;
margin: 0 10rpx; margin: 0 10rpx;
background: #F2F2FA; color: #999a9f;
display: flex; display: flex;
flex-direction: column; flex-direction: column;
justify-content: center; justify-content: center;
align-items: center; align-items: center;
.label {
font-size: 28rpx;
margin-top: 10rpx;
}
} }
} }
} }
</style> </style>
, onShow

@ -65,7 +65,8 @@ const handleCancleOrder = () => {
<template v-if="!isLoading"> <template v-if="!isLoading">
<view class="order-detail"> <view class="order-detail">
<view class="status"> <view class="status">
<view class="title">{{ order.orderStatus?.desc }}</view> <view class="title">订单类型{{ order.orderType?.desc }}</view>
<view class="title">订单状态{{ order.orderStatus?.desc }}</view>
<template v-if="order.orderStatus?.code == '520192817293693253'"> <template v-if="order.orderStatus?.code == '520192817293693253'">
<view class="desc">预约时间{{ order.appointmentTime }}</view> <view class="desc">预约时间{{ order.appointmentTime }}</view>
<view class="action"> <view class="action">

@ -24,6 +24,7 @@ const queryParams: Required<OrderListParams> = {
pageSize: 10, pageSize: 10,
status: props.orderState, status: props.orderState,
location: location, location: location,
orderType: 'SH_ORDER'
} }
// //
@ -75,57 +76,7 @@ const getMemberOrderData = async () => {
onMounted(() => { onMounted(() => {
getMemberOrderData() getMemberOrderData()
}) })
//
//
const onOrderPay = async (id: string) => {
if (import.meta.env.DEV) {
//
await getPayMockAPI({ orderId: id })
} else {
// #ifdef MP-WEIXIN
// 1.2.API
// const res = await getPayWxPayMiniPayAPI({ orderId: id })
// await wx.requestPayment(res.result)
// 线 0.01
await getPayMockAPI({ orderId: id })
// #endif
}
//
uni.showToast({ title: '模拟支付成功' })
//
setTimeout(() => {
wx.showModal({
title: '温馨提示',
content: '此交易是模拟支付,您并未付款,不会导致实际购买商品或服务',
confirmText: '知道了',
showCancel: false,
})
}, 2000)
//
const order = orderList.value.find((v) => v.id === id)
order!.orderState = OrderState.DaiFaHuo
}
//
const onOrderConfirm = (id: string) => {
uni.showModal({
content: '为保障您的权益,请收到货并确认无误后,再确认收货',
confirmColor: '#3775F6',
success: async (res) => {
if (res.confirm) {
await putMemberOrderReceiptByIdAPI(id)
uni.showToast({ icon: 'success', title: '确认收货成功' })
//
const order = orderList.value.find((v) => v.id === id)
order!.orderState = OrderState.DaiPingJia
}
},
})
}
//
const handleCancle = (id: string) => { const handleCancle = (id: string) => {
uni.showModal({ uni.showModal({
content: '你确定要取消该订单?', content: '你确定要取消该订单?',

@ -0,0 +1,348 @@
<script setup lang="ts">
import { serviceDomain } from '@/services/constants'
import { putMemberOrderReceiptByIdAPI } from '@/services/order'
import { getMemberOrderAPI, cancleOrderAPI } from '@/services/order'
import { getPayMockAPI, getPayWxPayMiniPayAPI } from '@/services/pay'
import type { OrderItem } from '@/types/order'
import type { OrderListParams } from '@/types/order'
import { onMounted, ref } from 'vue'
//
const { safeAreaInsets } = uni.getSystemInfoSync()
//
const location = uni.getStorageSync('location')
//
const queryParams: Required<OrderListParams> = {
pageNo: 1,
pageSize: 10,
status: 'FINISHED',
location: location,
orderType: 'DZ_RECOVERY',
}
//
const orderList = ref<OrderItem[]>([])
//
const isLoading = ref(false)
//
const isFinish = ref(false)
const getData = async () => {
// 退
if (isLoading.value) return
// 退
if (isFinish.value === true) {
return uni.showToast({ icon: 'none', title: '没有更多数据~' })
}
//
isLoading.value = true
//
const res = await getMemberOrderAPI(queryParams)
//
isLoading.value = false
res.data.list.forEach((e) => {
const str = e.appointmentTimeStart.slice(0, 10)
const start = e.appointmentTimeStart.slice(11, 16)
const end = e.appointmentTimeEnd.slice(11, 16)
e.appointmentTime = str + ' ' + start + '-' + end
if (e.orderDetails) {
e.orderDetails.forEach((q) => {
const arr = JSON.parse(q.product.photo)
const imgUrl = serviceDomain + arr[0].url
q.imgUrl = imgUrl
})
} else {
e.orderDetails = []
}
})
//
orderList.value.push(...res.data.list)
//
if (queryParams.pageNo < res.data.pages) {
//
queryParams.pageNo++
} else {
//
isFinish.value = true
}
}
onMounted(() => {
getData()
})
const handleDetail = (id) => {
uni.navigateTo({ url: `/pages/orderDetail/orderDetail?orderId=${id}` })
}
//
const isTriggered = ref(false)
//
const onRefresherrefresh = async () => {
//
isTriggered.value = true
//
queryParams.pageNo = 1
orderList.value = []
isFinish.value = false
//
await getData()
//
isTriggered.value = false
}
</script>
<template>
<scroll-view
enable-back-to-top
scroll-y
class="orders"
refresher-enabled
:refresher-triggered="isTriggered"
@refresherrefresh="onRefresherrefresh"
@scrolltolower="getData"
>
<view class="item" v-for="item in orderList" :key="item.id">
<view class="hd" @click="handleDetail(item.id)">
<view class="num">订单编号{{ item.orderNumber }}</view>
<view class="statusLabel">{{ item.orderStatus?.desc }}</view>
</view>
<view class="md" @click="handleDetail(item.id)">
<view class="order-details">
<view class="detail-item" v-for="item2 in item.orderDetails" :key="item2.id">
<image class="img-url" :src="item2.imgUrl"></image>
<view class="product-name">{{ item2.product?.name }}</view>
</view>
</view>
<view class="predict-weight">预估重量{{ item.predictWeight?.desc }}</view>
</view>
<view class="foot">
<view class="appointment-time"> 预约时间 {{ item.appointmentTime }}</view>
<view class="complete-time"> 完成时间 {{ item.completeTime }}</view>
</view>
</view>
<!-- 底部提示文字 -->
<view class="loading-text" :style="{ paddingBottom: safeAreaInsets?.bottom + 'px' }">
{{ isFinish ? '没有更多数据~' : '正在加载...' }}
</view>
</scroll-view>
</template>
<style lang="scss">
//
.orders {
.item {
padding: 20rpx 0;
margin: 20rpx 20rpx;
border-radius: 10rpx;
background-color: #fff;
.hd {
padding: 10rpx;
font-size: 28rpx;
display: flex;
justify-content: space-between;
.statusLabel {
font-size: 24rpx;
color: #FF7D00;
}
}
.md {
padding: 10rpx;
min-height: 100rpx;
font-size: 28rpx;
border-top: 2rpx solid #F2F2F2;
border-bottom: 2rpx solid #F2F2F2;
.order-details {
.detail-item {
margin: 20rpx 0;
display: flex;
align-items: center;
.img-url {
width: 40rpx;
height: 40rpx;
margin-right: 20rpx;
}
.product-name {
//
}
}
}
.predict-weight {
margin: 40rpx 0 20rpx;
}
}
.foot {
margin-top: 16rpx;
padding: 10rpx;
position: relative;
font-size: 24rpx;
.appointment-time {
margin: 10rpx 0;
}
.cancle {
position: absolute;
right: 0;
top: 10rpx;
width: 200rpx;
text-align: center;
border: 2rpx solid #E30000;
padding: 10rpx 30rpx;
color: #E30000;
border-radius: 40rpx;
}
}
&:last-child {
padding-bottom: 40rpx;
}
}
.status {
display: flex;
align-items: center;
justify-content: space-between;
font-size: 28rpx;
color: #999;
margin-bottom: 15rpx;
.date {
color: #666;
flex: 1;
}
.primary {
color: #ff9240;
}
.icon-delete {
line-height: 1;
margin-left: 10rpx;
padding-left: 10rpx;
border-left: 1rpx solid #e3e3e3;
}
}
.goods {
display: flex;
margin-bottom: 20rpx;
.cover {
width: 170rpx;
height: 170rpx;
margin-right: 20rpx;
border-radius: 10rpx;
overflow: hidden;
position: relative;
.image {
width: 170rpx;
height: 170rpx;
}
}
.quantity {
position: absolute;
bottom: 0;
right: 0;
line-height: 1;
padding: 6rpx 4rpx 6rpx 8rpx;
font-size: 24rpx;
color: #fff;
border-radius: 10rpx 0 0 0;
background-color: rgba(0, 0, 0, 0.6);
}
.meta {
flex: 1;
display: flex;
flex-direction: column;
justify-content: center;
}
.name {
height: 80rpx;
font-size: 26rpx;
color: #444;
}
.type {
line-height: 1.8;
padding: 0 15rpx;
margin-top: 10rpx;
font-size: 24rpx;
align-self: flex-start;
border-radius: 4rpx;
color: #888;
background-color: #f7f7f8;
}
.more {
flex: 1;
display: flex;
align-items: center;
justify-content: center;
font-size: 22rpx;
color: #333;
}
}
.payment {
display: flex;
justify-content: flex-end;
align-items: center;
line-height: 1;
padding: 20rpx 0;
text-align: right;
color: #999;
font-size: 28rpx;
border-bottom: 1rpx solid #eee;
.quantity {
font-size: 24rpx;
margin-right: 16rpx;
}
.amount {
color: #444;
margin-left: 6rpx;
}
.symbol {
font-size: 20rpx;
}
}
.action {
display: flex;
justify-content: flex-end;
align-items: center;
padding-top: 20rpx;
.button {
width: 180rpx;
height: 60rpx;
display: flex;
justify-content: center;
align-items: center;
margin-left: 20rpx;
border-radius: 60rpx;
border: 1rpx solid #ccc;
font-size: 26rpx;
color: #444;
}
.secondary {
color: #3775F6;
border-color: #3775F6;
}
.primary {
color: #fff;
background-color: #3775F6;
border-color: #3775F6;
}
}
.loading-text {
text-align: center;
font-size: 28rpx;
color: #666;
padding: 20rpx 0;
}
}
</style>

@ -0,0 +1,40 @@
<!--
* @Author: 王文杰
* @Date: 2024-03-26 16:57:42
* @LastEditors: 王文杰
* @LastEditTime: 2024-03-26 17:13:03
* @FilePath: /app-nx-personal/src/pages/orderSiteList/orderSiteList.vue
* @Description: 这是默认设置,请设置`customMade`, 打开koroFileHeader查看配置 进行设置: https://github.com/OBKoro1/koro1FileHeader/wiki/%E9%85%8D%E7%BD%AE
-->
<script setup lang="ts">
import { ref } from 'vue'
import OrderList from './components/OrderList.vue'
</script>
<template>
<view class="viewport">
<!-- 滑动容器 -->
<swiper class="swiper">
<!-- 滑动项 -->
<OrderList />
</swiper>
</view>
</template>
<style lang="scss">
page {
height: 100%;
overflow: hidden;
}
.viewport {
height: 100%;
display: flex;
flex-direction: column;
background-color: #fff;
}
// swiper
.swiper {
background-color: #f7f7f8;
}
</style>

@ -0,0 +1,373 @@
<script setup lang="ts">
import { OrderState } from '@/services/constants'
import { serviceDomain } from '@/services/constants'
import { putMemberOrderReceiptByIdAPI } from '@/services/order'
import { getMemberOrderAPI, cancleOrderAPI } from '@/services/order'
import { getPayMockAPI, getPayWxPayMiniPayAPI } from '@/services/pay'
import type { OrderItem } from '@/types/order'
import type { OrderListParams } from '@/types/order'
import { onMounted, ref } from 'vue'
import { useMemberStore } from '@/stores'
//
const { safeAreaInsets } = uni.getSystemInfoSync()
const memberStore = useMemberStore()
// porps
const props = defineProps<{
orderState: string
}>()
//
const location = uni.getStorageSync('location')
//
const queryParams: Required<OrderListParams> = {
pageNo: 1,
pageSize: 10,
status: props.orderState,
location: location,
orderType: 'TM_RECOVERY',
}
//
const orderList = ref<OrderItem[]>([])
//
const isLoading = ref(false)
//
const isFinish = ref(false)
const getMemberOrderData = async () => {
// 退
if (isLoading.value) return
// 退
if (isFinish.value === true) {
return uni.showToast({ icon: 'none', title: '没有更多数据~' })
}
//
isLoading.value = true
//
const res = await getMemberOrderAPI(queryParams)
//
isLoading.value = false
// res.data.list.forEach((e) => {
// const str = e.appointmentTimeStart.slice(0, 10)
// const start = e.appointmentTimeStart.slice(11, 16)
// const end = e.appointmentTimeEnd.slice(11, 16)
// e.appointmentTime = str + ' ' + start + '-' + end
// if (e.orderDetails) {
// e.orderDetails.forEach((q) => {
// const arr = JSON.parse(q.product.photo)
// const imgUrl = serviceDomain + arr[0].url
// q.imgUrl = imgUrl
// })
// } else {
// e.orderDetails = []
// }
// })
//
orderList.value.push(...res.data.list)
//
if (queryParams.pageNo < res.data.pages) {
//
queryParams.pageNo++
} else {
//
isFinish.value = true
}
}
onMounted(() => {
getMemberOrderData()
})
//
const handleCancle = (id: string) => {
uni.showModal({
content: '你确定要取消该订单?',
confirmColor: '#3775F6',
success: async (res) => {
if (res.confirm) {
await cancleOrderAPI({ id })
//
const index = orderList.value.findIndex((v) => v.id === id)
orderList.value.splice(index, 1)
}
},
})
}
const handleDetail = (id) => {
uni.navigateTo({ url: `/pages/orderDetail/orderDetail?orderId=${id}` })
}
//
const isTriggered = ref(false)
//
const onRefresherrefresh = async () => {
//
isTriggered.value = true
//
queryParams.pageNo = 1
orderList.value = []
isFinish.value = false
//
await getMemberOrderData()
//
isTriggered.value = false
}
</script>
<template>
<scroll-view
enable-back-to-top
scroll-y
class="orders"
refresher-enabled
:refresher-triggered="isTriggered"
@refresherrefresh="onRefresherrefresh"
@scrolltolower="getMemberOrderData"
>
<view class="item" v-for="item in orderList" :key="item.id">
<view class="hd" @click="handleDetail(item.id)">
<view class="num">订单编号{{ item.orderNumber }}</view>
<view class="statusLabel">{{ item.orderStatus?.desc }}</view>
</view>
<view class="md" @click="handleDetail(item.id)">
<view class="order-details">
<!-- <view class="detail-item" v-for="item2 in item.orderDetails" :key="item2.id">
<image class="img-url" :src="item2.imgUrl"></image>
<view class="product-name">{{ item2.product?.name }}</view>
</view> -->
</view>
<!-- <view class="predict-weight">预估重量{{ item.predictWeight?.desc }}</view> -->
</view>
<view class="foot">
<view class="appointment-time"> 下单时间 {{ item.creatorTime }}</view>
<view class="complete-time" v-if="props.orderState == 'FINISHED'">
完成时间 {{ item.completeTime }}</view
>
<view class="cancle" v-if="props.orderState == 'UNPROCESSED'" @click="handleCancle(item.id)"> </view>
</view>
</view>
<!-- 底部提示文字 -->
<view class="loading-text" :style="{ paddingBottom: safeAreaInsets?.bottom + 'px' }">
{{ isFinish ? '没有更多数据~' : '正在加载...' }}
</view>
</scroll-view>
</template>
<style lang="scss">
//
.orders {
.item {
padding: 20rpx 0;
margin: 20rpx 20rpx;
border-radius: 10rpx;
background-color: #fff;
.hd {
padding: 10rpx;
font-size: 28rpx;
display: flex;
justify-content: space-between;
.statusLabel {
font-size: 24rpx;
color: #FF7D00;
}
}
.md {
padding: 10rpx;
min-height: 100rpx;
font-size: 28rpx;
border-top: 2rpx solid #F2F2F2;
border-bottom: 2rpx solid #F2F2F2;
.order-details {
.detail-item {
margin: 20rpx 0;
display: flex;
align-items: center;
.img-url {
width: 40rpx;
height: 40rpx;
margin-right: 20rpx;
}
.product-name {
//
}
}
}
.predict-weight {
margin: 40rpx 0 20rpx;
}
}
.foot {
margin-top: 16rpx;
padding: 10rpx;
position: relative;
font-size: 24rpx;
.appointment-time {
margin: 10rpx 0;
}
.cancle {
position: absolute;
right: 0;
top: 10rpx;
width: 200rpx;
text-align: center;
border: 2rpx solid #E30000;
padding: 10rpx 30rpx;
color: #E30000;
border-radius: 40rpx;
}
}
&:last-child {
padding-bottom: 40rpx;
}
}
.status {
display: flex;
align-items: center;
justify-content: space-between;
font-size: 28rpx;
color: #999;
margin-bottom: 15rpx;
.date {
color: #666;
flex: 1;
}
.primary {
color: #ff9240;
}
.icon-delete {
line-height: 1;
margin-left: 10rpx;
padding-left: 10rpx;
border-left: 1rpx solid #e3e3e3;
}
}
.goods {
display: flex;
margin-bottom: 20rpx;
.cover {
width: 170rpx;
height: 170rpx;
margin-right: 20rpx;
border-radius: 10rpx;
overflow: hidden;
position: relative;
.image {
width: 170rpx;
height: 170rpx;
}
}
.quantity {
position: absolute;
bottom: 0;
right: 0;
line-height: 1;
padding: 6rpx 4rpx 6rpx 8rpx;
font-size: 24rpx;
color: #fff;
border-radius: 10rpx 0 0 0;
background-color: rgba(0, 0, 0, 0.6);
}
.meta {
flex: 1;
display: flex;
flex-direction: column;
justify-content: center;
}
.name {
height: 80rpx;
font-size: 26rpx;
color: #444;
}
.type {
line-height: 1.8;
padding: 0 15rpx;
margin-top: 10rpx;
font-size: 24rpx;
align-self: flex-start;
border-radius: 4rpx;
color: #888;
background-color: #f7f7f8;
}
.more {
flex: 1;
display: flex;
align-items: center;
justify-content: center;
font-size: 22rpx;
color: #333;
}
}
.payment {
display: flex;
justify-content: flex-end;
align-items: center;
line-height: 1;
padding: 20rpx 0;
text-align: right;
color: #999;
font-size: 28rpx;
border-bottom: 1rpx solid #eee;
.quantity {
font-size: 24rpx;
margin-right: 16rpx;
}
.amount {
color: #444;
margin-left: 6rpx;
}
.symbol {
font-size: 20rpx;
}
}
.action {
display: flex;
justify-content: flex-end;
align-items: center;
padding-top: 20rpx;
.button {
width: 180rpx;
height: 60rpx;
display: flex;
justify-content: center;
align-items: center;
margin-left: 20rpx;
border-radius: 60rpx;
border: 1rpx solid #ccc;
font-size: 26rpx;
color: #444;
}
.secondary {
color: #3775F6;
border-color: #3775F6;
}
.primary {
color: #fff;
background-color: #3775F6;
border-color: #3775F6;
}
}
.loading-text {
text-align: center;
font-size: 28rpx;
color: #666;
padding: 20rpx 0;
}
}
</style>

@ -0,0 +1,113 @@
<script setup lang="ts">
import { ref } from 'vue'
import OrderList from './components/OrderList.vue'
//
const query = defineProps<{
type: string
}>()
// tabs
const orderTabs = ref([
{ orderState: 'UNPROCESSED', title: '待服务', isRender: false },
{ orderState: 'FINISHED', title: '已完成', isRender: false },
{ orderState: 'CANCELED', title: '已取消', isRender: false },
])
//
const activeIndex = ref(orderTabs.value.findIndex((v) => v.orderState === 'UNPROCESSED'))
//
orderTabs.value[activeIndex.value].isRender = true
const handleIndexChange = (index: any) => {
orderTabs.value.forEach((e) => {
e.isRender = false
})
activeIndex.value = index
orderTabs.value[index].isRender = true
}
</script>
<template>
<view class="viewport">
<!-- tabs -->
<view class="tabs">
<text
class="item"
v-for="(item, index) in orderTabs"
:key="item.title"
@tap="handleIndexChange(index)"
>
{{ item.title }}
</text>
<!-- 游标 -->
<view class="cursor" :style="{ left: activeIndex * 33 + '%' }"></view>
</view>
<!-- 滑动容器 -->
<swiper
class="swiper"
:current="activeIndex"
@change="handleIndexChange($event.detail.current)"
>
<!-- 滑动项 -->
<swiper-item v-for="item in orderTabs" :key="item.title">
<!-- 订单列表 -->
<OrderList v-if="item.isRender" :order-state="item.orderState" />
</swiper-item>
</swiper>
</view>
</template>
<style lang="scss">
page {
height: 100%;
overflow: hidden;
}
.viewport {
height: 100%;
display: flex;
flex-direction: column;
background-color: #fff;
}
// tabs
.tabs {
display: flex;
justify-content: space-around;
line-height: 60rpx;
margin: 0 10rpx;
background-color: #fff;
box-shadow: 0 4rpx 6rpx rgba(240, 240, 240, 0.6);
position: relative;
z-index: 9;
.item {
flex: 1;
text-align: center;
padding: 20rpx;
font-size: 28rpx;
color: #262626;
}
.cursor {
position: absolute;
left: 33%;
bottom: 0;
width: 17%;
height: 6rpx;
padding: 0 50rpx;
background-color: #3775F6;
transition: all 0.4s;
text-align: center;
margin: 0;
transform: translateX(50%);
/* 过渡效果 */
transition: all 0.4s;
}
}
// swiper
.swiper {
background-color: #f7f7f8;
}
</style>

@ -19,6 +19,17 @@ export const postBookingAPI = (data: any) => {
data, data,
}) })
} }
/**
*
* @param data
*/
export const postBookingHouseAPI = (data: any) => {
return http<any>({
method: 'POST',
url: `/recycle-order/create-by-housing`,
data,
})
}
// /** // /**
// * 回收站废品价格类目 // * 回收站废品价格类目
// * // *

@ -2,7 +2,7 @@
* @Author: * @Author:
* @Date: 2024-01-04 12:54:56 * @Date: 2024-01-04 12:54:56
* @LastEditors: * @LastEditors:
* @LastEditTime: 2024-03-25 15:39:18 * @LastEditTime: 2024-03-26 15:29:30
* @FilePath: /app-nx-personal/src/services/constants.ts * @FilePath: /app-nx-personal/src/services/constants.ts
* @Description: ,`customMade`, koroFileHeader : https://github.com/OBKoro1/koro1FileHeader/wiki/%E9%85%8D%E7%BD%AE * @Description: ,`customMade`, koroFileHeader : https://github.com/OBKoro1/koro1FileHeader/wiki/%E9%85%8D%E7%BD%AE
*/ */
@ -119,8 +119,8 @@ export const categoryListDefault = [
}, },
] ]
// 文件路径 // 文件路径
// export const serviceDomainPro = 'https://nxhs.cjyx.cc' // export const serviceDomain = 'https://nxhs.cjyx.cc'
export const serviceDomainDev = 'http://222.71.165.188:8808' export const serviceDomain = 'http://222.71.165.188:8808'
export const storage_userInfo = { export const storage_userInfo = {
userType: { userType: {

@ -2,7 +2,7 @@
* @Author: * @Author:
* @Date: 2024-01-04 12:54:56 * @Date: 2024-01-04 12:54:56
* @LastEditors: * @LastEditors:
* @LastEditTime: 2024-03-25 16:03:06 * @LastEditTime: 2024-03-26 15:49:22
* @FilePath: /app-nx-personal/src/services/home.ts * @FilePath: /app-nx-personal/src/services/home.ts
* @Description: ,`customMade`, koroFileHeader : https://github.com/OBKoro1/koro1FileHeader/wiki/%E9%85%8D%E7%BD%AE * @Description: ,`customMade`, koroFileHeader : https://github.com/OBKoro1/koro1FileHeader/wiki/%E9%85%8D%E7%BD%AE
*/ */
@ -41,6 +41,14 @@ export const getHouseNearbyAPI = (data: any) => {
data, data,
}) })
} }
// 小区详情
export const getHouseInfoAPI = (data: any) => {
return http<any[]>({
method: 'GET',
url: '/housing-estate/info',
data,
})
}
/** /**
* -- * --

Loading…
Cancel
Save