初始化代码

This commit is contained in:
2025-12-22 17:13:05 +08:00
parent ed0de08e3a
commit 1f7e9d401b
2947 changed files with 526137 additions and 0 deletions

View File

@@ -0,0 +1,606 @@
<template>
<view class="pages-home" v-if="isLoad">
<uni-nav-bar :fixed="true" :shadow="false" :statusBar="true" :onlyLeft="true" color="#fff"
:backgroundColor="scrollTop < 20 ?``:primaryColor">
<view @tap.stop="toChooseLocation" class="flex-y-center" slot="left">
<i class="iconfont icon-dingwei mr-sm"></i>
<view class=" max-400 ellipsis">
{{location.address ?location.address : isLoad ? '定位失败' : '定位中...'}}
</view>
</view>
</uni-nav-bar>
<view :style="{height:`${configInfo.navBarHeight}px`}"></view>
<view mode="aspectFill" lazy-load class="home-index-bg abs"></view>
<view @tap.stop="$util.toCheckLogin({url:`/home/pages/search`})" class="pt-md pl-md pr-md">
<search :padding="0" :radius="10" backgroundColor="rgba(240,240,240,0.2)"
searchColor="rgba(240,240,240,0.2)" frontColor="#fff" textAlign="center" placeholder="请输入商品名称"></search>
</view>
<view class="mt-lg ml-md mr-md" v-if="detail.banner.rotation.length > 0">
<banner @change="goBanner" :list="detail.banner.rotation" :margin="0" :autoplay="true" :borderRadius="25"
:height="286" :indicatorActiveColor="primaryColor"></banner>
</view>
<view @tap="$util.toCheckLogin({url:`/home/pages/welfare?type=2`})"
class="notice-info flex-center mt-md pd-md fill-base">
<image mode="aspectFill" lazy-load class="notice-img" src="/static/image/home/notice.png">
</image>
<view class="ml-sm infomation-left"></view>
<view class="flex-1 ml-md">
<swiper :autoplay="true" :circular='true' :vertical="true" class="roller-box" :interval="2000">
<swiper-item v-for="(item,index) in detail.system_list" :key="index">
<view class="roller-item flex-between f-caption c-desc">
<view class="ellipsis">{{item.title}}</view>
</view>
</swiper-item>
</swiper>
</view>
</view>
<view @tap.stop="goAbout"
class="weather-info flex-warp rel pr-md pl-md pb-md f-icontext c-desc"
v-if="detail.weather.observe.update_time">
<view class="flex-y-baseline">
<view class="flex-center mr-lg">
<view class="number">{{detail.weather.observe.degree}}°</view>
</view>
<view class="weather">{{today}} {{detail.weather.observe.weather}}</view>
</view>
<view class="flex-warp">
<view class="mr-lg">
温度变化{{`${detail.weather.forecast_24h.min_degree}°~${detail.weather.forecast_24h.max_degree}°`}}
</view>
<view class="mr-lg">风力{{detail.weather.observe.wind_power}}</view>
<view class="mr-lg">湿度{{detail.weather.observe.humidity}}%</view>
<view>气压{{detail.weather.observe.pressure}}hPa</view>
</view>
<view class="about-info flex-center abs" :style="{background:primaryColor}">
<image mode="aspectFill" lazy-load class="weather-img ml-sm mr-md"
:src="`${weather_img}${time_key}/${detail.weather.observe.weather_code}.png`">
</image>
</view>
</view>
<view class="flex-warp fill-base pb-md">
<view @tap.stop="toMenu(index)" class="menu-item flex-center flex-column pb-lg"
v-for="(item,index) in menuList" :key="index">
<image mode="aspectFill" lazy-load class="menu-img radius"
:src="`/static/image/home/${item.img_name}.png`">
</image>
<view class="f-caption c-title mt-sm">{{item.title}}</view>
</view>
</view>
<view @tap="$util.toCheckLogin({url:`/shop/pages/coupon`})"
class="advertisement-info fill-base pr-md pl-md pb-md" v-if="detail.coupon_total">
<image mode="aspectFill" lazy-load class="coupon-img"
src="/static/image/home/xrhb.png">
</image>
</view>
<view class="advertisement-info fill-base pr-md pl-md pb-md"
v-if="detail.banner.poster.length > 0">
<banner @change="goBanner" :list="detail.banner.poster" :margin="0" :autoplay="true" :borderRadius="25"
:height="285" :indicatorActiveColor="primaryColor"></banner>
</view>
<view class="mt-md pd-lg fill-base">
<view @tap="$util.toCheckLogin({url:`/shop/pages/hot-goods`})" class="flex-center">
<view class="flex-1 f-paragraph text-bold">热门商品</view>
<view class="flex-y-center c-caption f-caption">查看更多<i class="iconfont icon-right"></i></view>
</view>
<block v-for="(item,index) in detail.hot_goods" :key="index">
<view @tap.stop="goDetail(1,'hot_goods',index)" class="goods-item flex-center mt-lg">
<image mode="aspectFill" lazy-load class="cover radius-16" :src="item.cover"></image>
<view class="flex-1 ml-lg">
<view class="flex-center">
<view class="flex-1">
<view class="f-paragraph c-title mt-sm mb-sm max-400 ellipsis">{{item.goods_name}}
</view>
<view class="flex-y-baseline f-caption c-warning">¥<view class="f-title">
{{item.show_price}}
</view>
</view>
<view class="f-caption c-caption text-delete">¥{{item.show_init_price}}</view>
</view>
<image lazy-load class="add-car-img" src="/static/image/shop/add-car.png">
</image>
</view>
</view>
</view>
</block>
</view>
<view class="mt-md pt-lg pb-lg fill-base">
<view @tap="$util.toCheckLogin({url:`/shop/pages/choose-store`})" class="pl-lg pr-lg flex-center">
<view class="flex-1 f-paragraph text-bold">热门店铺</view>
<view class="flex-y-center c-caption f-caption">查看更多<i class="iconfont icon-right"></i></view>
</view>
<scroll-view scroll-x class="hot-shop-list pt-lg pl-lg" :scroll-with-animation="true"
v-if="detail.store_list.length > 0">
<block v-for="(item,index) in detail.store_list" :key="index">
<view @tap.stop="goDetail(2,'store_list',index)" class="hot-shop-item mr-lg radius-16">
<image mode="aspectFill" lazy-load class="cover box-shadow" :src="item.cover"></image>
<view class="pd-md">
<view class="flex-between f-caption c-desc">
<view class="business-tag flex-center radius-4" :style="{color:primaryColor}">营业中</view>
<view class="pl-sm ellipsis">{{item.distance}}</view>
</view>
<view class="f-paragraph c-title mt-md ellipsis-2">{{item.title}}</view>
</view>
</view>
</block>
</scroll-view>
</view>
<view class="mt-md pd-lg fill-base">
<view @tap="$util.toCheckLogin({url:`/home/pages/welfare`})" class="flex-center">
<view class="flex-1 f-paragraph text-bold">公益栏目</view>
<view class="flex-y-center c-caption f-caption">查看更多<i class="iconfont icon-right"></i></view>
</view>
<block v-for="(item,index) in detail.welfare_list" :key="index">
<view @tap.stop="goDetail(3,'welfare_list',index)" class="welfare-item flex-center mt-lg">
<image mode="aspectFill" lazy-load class="cover radius-16" :src="item.cover"></image>
<view class="flex-1 ml-lg">
<view class="f-title c-title mb-md ellipsis">{{item.title}}</view>
<view class="f-caption c-caption">{{item.create_time_text}}</view>
</view>
</view>
</block>
</view>
<view class="space-footer"></view>
</view>
</template>
<script>
import {
mapState,
mapActions,
mapMutations
} from "vuex"
import uniSegmentedControl from "@/components/uni-segmented-control.vue"
export default {
components: {
uniSegmentedControl
},
data() {
return {
scrollTop: 0,
options: {},
weather_img: `https://mat1.gtimg.com/pingjs/ext2020/weather/pc/icon/currentweather/`,
menuList: [{
id: 1,
title: '土地租赁',
img_name: 'land',
url: '/pages/land'
}, {
id: 2,
title: '农业认养',
img_name: 'claim',
url: '/pages/claim'
}, {
id: 3,
title: '视频监控',
img_name: 'monitor',
url: '/home/pages/monitor/list'
}, {
id: 4,
title: '农场商城',
img_name: 'shop',
url: '/pages/shop'
}, {
id: 5,
title: '会员充值',
img_name: 'stored',
url: '/mine/pages/balance/list'
}, {
id: 6,
title: '众筹认养',
img_name: 'collage',
url: '/claim/pages/collage/list'
}, {
id: 7,
title: '限时秒杀',
img_name: 'seckill',
url: '/shop/pages/seckill'
}, {
id: 8,
title: '积分商城',
img_name: 'integral',
url: '/shop/pages/integral/list'
}, {
id: 9,
title: '农场签到',
img_name: 'sign',
url: '/shop/pages/sign'
}, {
id: 10,
title: '积分抽奖',
img_name: 'luck',
url: '/shop/pages/luck'
}],
isLoad: false,
loading: false,
detail: {},
about_us: 0,
weather: {},
store_list: [],
today: '',
cur_time: '',
time_key: 'day'
}
},
computed: mapState({
primaryColor: state => state.config.configInfo.primaryColor,
subColor: state => state.config.configInfo.subColor,
configInfo: state => state.config.configInfo,
userInfo: state => state.user.userInfo,
location: state => state.user.location,
loginType: state => state.user.loginType,
}),
async onLoad() {
console.log("====onload")
if (this.isLoad) return
this.initIndex()
},
async onShow() {
let cur_time = this.$util.DateToUnix(this.$util.formatTime(new Date(), 'YY-M-D h:m:s'))
let time = this.$util.DateToUnix(this.$util.formatTime(new Date(), 'YY-M-D'))
let min = time + 8 * 3600 - 1
let max = time + 19 * 3600 + 1
this.time_key = cur_time > min && cur_time < max ? 'day' : 'night'
if (!this.isLoad || this.location.lat) return
let [err, result] = await uni.getSetting()
if (err || !result.authSetting[`scope.userLocation`]) return
this.initIndex()
},
onPageScroll(e) {
this.scrollTop = e.scrollTop
},
onPullDownRefresh() {
// #ifndef APP-PLUS
uni.showNavigationBarLoading()
// #endif
this.initRefresh()
uni.stopPullDownRefresh()
},
onShareAppMessage(e) {
let {
id: pid
} = this.userInfo
let path = `/pages/home?pid=${pid}`
this.$util.log(path)
return {
title: '',
imageUrl: '',
path,
}
},
methods: {
...mapActions(['getConfigInfo']),
...mapMutations(['updateUserItem']),
async initIndex(refresh = false) {
this.cur_time = this.$util.formatTime(new Date(), 'YY-M-D')
this.today = this.$util.formatTime(new Date(), 'YY年M月D日')
if (!this.configInfo.id || refresh) {
await this.getConfigInfo()
if (this.loginType == 'apple') {
this.updateUserItem({
key: 'isShowLogin',
val: false
})
}
}
await this.getLocation()
if (!refresh) {
this.$util.showLoading()
}
let {
lat = 0,
lng = 0
} = this.location
let [detail, coupon] = await Promise.all([this.$api.home.index({
lat,
lng
}), this.$api.shop.couponList()])
detail.coupon_total = coupon.total
let {
status = 0,
data
} = detail.weather
if (status == 200) {
let {
forecast_24h
} = data
let cur_day = forecast_24h.filter(item => {
return item.time == this.cur_time
})
data.forecast_24h = cur_day.length > 0 ? cur_day[0] : []
detail.weather = data
}
this.detail = detail
this.isLoad = true
this.loading = false
this.$util.hideAll()
},
initRefresh() {
this.initIndex(true)
},
async getLocation() {
let {
location
} = this
if (!location.lat) {
try {
// #ifdef H5
// H5环境下先检查缓存的位置信息
let cachedLocation = uni.getStorageSync('cached_location');
let cacheTime = uni.getStorageSync('location_cache_time');
let now = new Date().getTime();
// 如果有缓存且缓存时间不超过30分钟直接使用缓存的位置
if (cachedLocation && cacheTime && (now - cacheTime) < 30 * 60 * 1000) {
location = cachedLocation;
} else {
// 没有缓存或缓存过期,才获取新位置
location = await this.$util.getBmapLocation();
}
// #endif
// #ifndef H5
// 非H5环境直接获取位置
location = await this.$util.getBmapLocation();
// #endif
this.updateUserItem({
key: 'location',
val: location
})
} catch (error) {
console.log('获取位置失败:', error);
// 获取位置失败时不更新location使用默认值
this.$util.showToast({
title: '获取位置失败,使用默认位置'
});
}
}
},
// 选择地区
async toChooseLocation(e) {
await this.$util.checkAuth({
type: 'userLocation'
})
let [, {
address = '',
longitude: lng = 0,
latitude: lat = 0
} = {}] = await uni.chooseLocation();
if (!lng) return
let location = {
lng,
lat,
address
}
this.updateUserItem({
key: 'location',
val: location
})
this.initRefresh()
},
toMenu(index) {
let {
title,
url,
} = this.menuList[index]
let arr = ['土地租赁', '农业认养']
let openType = arr.includes(title) ? 'switchTab' : title == '农场商城' ?
'reLaunch' : 'navigateTo'
this.$util.toCheckLogin({
url,
openType
})
},
// 轮播图/广告图跳转
goBanner(e) {
// connect_type 1店铺2文章3图片4店铺
let {
connect_type,
text_id: id = 0,
img: current
} = e.item
switch (connect_type) {
case 1:
case 2:
case 4:
let page = {
1: `/home/pages/farm/detail?id=${id}`,
2: `/home/pages/article?id=${id}&type=1`,
4: `/shop/pages/store?id=${id}`
}
let url = page[connect_type]
this.$util.toCheckLogin({
url
})
break;
case 3:
this.$util.previewImage({
current,
urls: [current]
})
break;
}
},
goAbout() {
if (!this.detail.about_us) return
this.$util.toCheckLogin({
url: `/home/pages/about`
})
},
// 商品/店铺/公益栏目详情
async goDetail(type, key, index) {
let {
id
} = this.detail[key][index]
let url = ''
switch (type) {
case 1:
url = `/shop/pages/detail?id=${id}`
break
case 2:
url = `/shop/pages/store?id=${id}`
break
case 3:
url = `/home/pages/article?id=${id}&type=2`
break
}
this.$util.toCheckLogin({
url
})
}
}
}
</script>
<style lang="scss">
.pages-home {
.icon-right {
font-size: 24rpx;
}
.menu-item {
width: 20%;
.menu-img {
width: 96rpx;
height: 96rpx;
}
}
.notice-info {
height: 110rpx;
.notice-img {
width: 128rpx;
height: 48rpx;
}
.infomation-left {
height: 48rpx;
border-right: 0.03125rem solid #e1e6ec;
}
.roller-box {
height: 40rpx;
.roller-item {
height: 40rpx;
line-height: 1;
}
}
}
.weather-info {
height: 168rpx;
background: #ffffff;
.number {
font-size: 48rpx;
color: #FEB23A;
}
.weather {
color: #FEB23A;
}
.weather-img {
width: 50rpx;
height: 50rpx;
}
.about-info {
right: 0rpx;
width: 84rpx;
height: 84rpx;
border-radius: 5000rpx;
margin-right: 30rpx;
.about-img {
width: 102rpx;
height: 25rpx;
margin: 0 8rpx;
}
.about-right-img {
width: 34rpx;
height: 25rpx;
}
}
}
.advertisement-info {
.coupon-img {
width: 100%;
height: 180rpx;
}
}
.goods-item {
.cover {
width: 180rpx;
height: 170rpx;
}
.add-car-img {
width: 70rpx;
height: 70rpx;
}
}
.hot-shop-list {
white-space: nowrap;
width: calc(100% - 30rpx);
.hot-shop-item {
width: 281rpx;
height: 353rpx;
background: #F9FAF9;
display: inline-block;
.cover {
width: 281rpx;
height: 175rpx;
border-radius: 15rpx 15rpx 0 0;
}
.business-tag {
width: 86rpx;
height: 34rpx;
background: rgba(52, 162, 99, 0.1);
}
}
}
.home-index-bg {
background: rgb(57, 181, 74);
height: 15.625rem;
width: 100%;
top: 0;
border-radius: 0 0 5% 5%;
z-index: -1;
}
.welfare-item {
.cover {
width: 180rpx;
height: 160rpx;
}
.ellipsis {
max-width: 480rpx;
}
}
}
</style>