Browse Source

优化首页刷新组件

pull/19/head
zyronon 3 years ago
parent
commit
03bda164b6
  1. BIN
      src/assets/img/icon/newicon/eim.webp
  2. BIN
      src/assets/img/icon/newicon/el1.webp
  3. 97
      src/pages/slide/IndicatorHome.vue
  4. 10
      src/pages/slide/Slide.vue
  5. 18
      src/pages/slide/SlideHorizontal.vue
  6. 33
      src/pages/slide/SlideVertical.vue
  7. 4
      src/store/index.js
  8. 16
      src/utils/mixin.js

BIN
src/assets/img/icon/newicon/eim.webp

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.3 KiB

BIN
src/assets/img/icon/newicon/el1.webp

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.7 KiB

97
src/pages/slide/IndicatorHome.vue

@ -3,24 +3,29 @@ @@ -3,24 +3,29 @@
<transition name="fade">
<div class="mask" v-if="open" @click="open = false"></div>
</transition>
<div class="notice"><span>下拉刷新内容</span></div>
<div class="toolbar" ref="toolbar">
<div class="left" @click="$nav('/home/live')">直播</div>
<div class="notice" :style="noticeStyle"><span>下拉刷新内容</span></div>
<div class="toolbar" ref="toolbar" :style="toolbarStyle">
<img src="../../assets/img/icon/scan.png"
class="search"
@click="$nav('/home/live')"
style="margin-top: .5rem;">
<div class="tab-ctn">
<div class="tabs" ref="tabs">
<div class="tab" :class="tabOneClass" @click.stop="change(0)">
<span>同城</span>
<img v-show="index === 0" src="../../assets/img/icon/arrow-up-white.png" alt="">
<img v-show="index === 0" src="../../assets/img/icon/arrow-up-white.png" class="tab1-img">
</div>
<div class="tab" :class="{active:index === 1}" @click.stop="change(1)">
<span>关注</span>
<img src="../../assets/img/icon/live.webp" class="tab2-img">
</div>
<div class="tab" :class="{active:index === 2}" @click.stop="change(2)"><span>推荐</span>
</div>
</div>
<div class="indicator" ref="indicator"></div>
</div>
<img src="../../assets/img/icon/search-gray.png" alt=""
<img v-hide="!loading" src="../../assets/img/icon/search-light.png"
class="search"
@click="$nav('/home/search')"
style="margin-top: .5rem;">
</div>
@ -33,12 +38,13 @@ @@ -33,12 +38,13 @@
<div class="l-button" :class="{active:type === 2}" @click="toggleType(2)">热点</div>
</div>
<Loading class="loading" style="width: 4rem;" :is-full-screen="false"/>
<Loading :style="loadingStyle" class="loading" style="width: 4rem;" :is-full-screen="false"/>
</div>
</template>
<script>
import Loading from "../../components/Loading";
import bus from "../../utils/bus";
import {mapState} from "vuex";
export default {
name: "IndicatorHome",
@ -63,25 +69,72 @@ export default { @@ -63,25 +69,72 @@ export default {
lefts: [],
indicatorSpace: 0,
open: false,
type: 1
loading: false,
type: 1,
moveY: 0
}
},
computed: {
...mapState(['judgeValue', 'homeRefresh']),
tabOneClass() {
return {active: this.index === 0, open: this.open}
},
transform() {
return `translate3d(0, ${this.moveY - this.judgeValue > this.homeRefresh ? this.homeRefresh : this.moveY - this.judgeValue}px, 0)`
},
toolbarStyle() {
if (this.loading) {
return {opacity: 1, 'transition-duration': '300ms', transform: `translate3d(0, 0, 0)`,}
}
if (this.moveY) {
return {
opacity: 1 - (this.moveY - this.judgeValue) / (this.homeRefresh / 2),
transform: this.transform
}
}
return {opacity: 1, 'transition-duration': '300ms', transform: `translate3d(0, 0, 0)`,}
},
noticeStyle() {
if (this.loading) {
return {opacity: 0,}
}
if (this.moveY) {
return {
opacity: (this.moveY - this.judgeValue) / (this.homeRefresh / 2) - .5,
transform: this.transform
}
}
return {opacity: 0,}
},
loadingStyle() {
if (this.loading) {
return {opacity: 1, 'transition-duration': '300ms',}
}
if (this.moveY) {
return {
opacity: (this.moveY - this.judgeValue) / (this.homeRefresh / 2) - .5,
transform: this.transform
}
}
}
},
watch: {
// index(newVal) {
// this.end()
// }
},
created() {
},
mounted() {
this.initTabs()
bus.on(this.name + '-move', this.move)
bus.on(this.name + '-moveX', this.move)
bus.on(this.name + '-moveY', e => {
// console.log('moveY', e)
this.moveY = e
})
bus.on(this.name + '-end', this.end)
bus.on(this.name + '-loading', () => {
console.log('loading')
this.loading = true
setTimeout(() => {
this.loading = false
}, 3000)
})
},
methods: {
toggleType(type) {
@ -118,9 +171,10 @@ export default { @@ -118,9 +171,10 @@ export default {
this.$setCss(this.indicatorRef, 'transition-duration', `0ms`)
this.$setCss(this.indicatorRef, 'left',
this.lefts[this.index] -
e.x.distance / (this.$store.state.bodyWidth / this.indicatorSpace) + 'px')
e / (this.$store.state.bodyWidth / this.indicatorSpace) + 'px')
},
end(index) {
this.moveY = 0
this.$setCss(this.indicatorRef, 'transition-duration', `300ms`)
this.$setCss(this.indicatorRef, 'left', this.lefts[index] + 'px')
setTimeout(() => {
@ -190,7 +244,7 @@ export default { @@ -190,7 +244,7 @@ export default {
color: rgb(156, 158, 165);
position: relative;
img {
.tab1-img {
position: absolute;
@width: 1rem;
width: @width;
@ -200,8 +254,15 @@ export default { @@ -200,8 +254,15 @@ export default {
margin-top: .7rem;
}
.tab2-img {
position: absolute;
height: 1.5rem;
left: 2.4rem;
top: -.5rem;
}
&.open {
img {
.tab1-img {
transform: rotate(180deg);
}
}
@ -223,6 +284,10 @@ export default { @@ -223,6 +284,10 @@ export default {
border-radius: .5rem;
}
}
.search {
width: 2rem;
}
}
.toggle-type {

10
src/pages/slide/Slide.vue

@ -34,9 +34,9 @@ @@ -34,9 +34,9 @@
<span>住宿</span>
</div>
</div>
<SlideVertical>
<div class="item" style="background: tan">
<p style="padding: 1rem;" v-for="i in 50">
<SlideVertical name="main">
<div class="item">
<p style="padding: 1rem;" v-for="i in 5">
r2222222222222222222222222222222222222222222222222222222
</p>
</div>
@ -60,14 +60,14 @@ @@ -60,14 +60,14 @@
</div>
</div>
</div>
<SlideVertical>
<SlideVertical name="main">
<div class="item">r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1</div>
<div class="item">r2222222222222222222222222222222222222222222222222222222</div>
<div class="item">r333333333333333333333333333333333333333333333333333333</div>
</SlideVertical>
</div>
<div class="item">
<SlideVertical>
<SlideVertical name="main">
<div class="item">r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1r1</div>
<div class="item">r2222222222222222222222222222222222222222222222222222222</div>
<div class="item">r333333333333333333333333333333333333333333333333333333</div>

18
src/pages/slide/SlideHorizontal.vue

@ -1,5 +1,6 @@ @@ -1,5 +1,6 @@
<script lang="jsx">
import bus from "../../utils/bus";
import {mapState} from "vuex";
export default {
props: {
@ -25,9 +26,11 @@ export default { @@ -25,9 +26,11 @@ export default {
startY: 0,
needCheck: true,
next: false,
judgeValue: 20
}
},
computed: {
...mapState(['judgeValue'])
},
mounted() {
this.wrapper = this.$refs.wrapper
this.total = this.wrapper.children.length
@ -59,9 +62,7 @@ export default { @@ -59,9 +62,7 @@ export default {
this.checkDirection(e)
if (this.next) {
bus.emit(this.name + '-move', {
x: {distance: this.moveX, isRight},
})
bus.emit(this.name + '-moveX', this.moveX)
this.$stopPropagation(e)
this.$setCss(this.wrapper, 'transform',
`translate3d(${this.getDistance()
@ -74,12 +75,7 @@ export default { @@ -74,12 +75,7 @@ export default {
if (!this.needCheck) return
if (Math.abs(this.moveX) > this.judgeValue || Math.abs(this.moveY) > this.judgeValue) {
let angle = (Math.abs(this.moveX) * 10) / (Math.abs(this.moveY) * 10)
if (angle > 1) {
this.next = true
// console.log('')
} else {
// console.log('')
}
this.next = angle > 1;
// console.log(angle)
return this.needCheck = false
}
@ -104,12 +100,12 @@ export default { @@ -104,12 +100,12 @@ export default {
this.$emit('update:index', this.lIndex)
this.reset()
bus.emit(this.name + '-end', this.lIndex)
},
reset() {
this.moveX = 0
this.next = false
this.needCheck = true
bus.emit(this.name + '-end', this.lIndex)
},
getDistance() {
return -this.lIndex * this.wrapperWidth

33
src/pages/slide/SlideVertical.vue

@ -1,5 +1,14 @@ @@ -1,5 +1,14 @@
<script lang="jsx">
import bus from "../../utils/bus";
import {mapState} from "vuex";
export default {
props: {
name: {
type: String,
default: () => ''
},
},
data() {
return {
wrapper: null,
@ -13,9 +22,11 @@ export default { @@ -13,9 +22,11 @@ export default {
startY: 0,
needCheck: true,
next: false,
judgeValue: 20
}
},
computed: {
...mapState(['judgeValue','homeRefresh'])
},
mounted() {
this.wrapper = this.$refs.wrapper
this.total = this.wrapper.children.length
@ -29,14 +40,18 @@ export default { @@ -29,14 +40,18 @@ export default {
this.startY = e.touches[0].pageY
},
touchMove(e) {
console.log('move',e.touches[0].pageY)
this.moveX = e.touches[0].pageX - this.startX
this.moveY = e.touches[0].pageY - this.startY
let isDown = this.moveY < 0
this.checkDirection(e)
if (this.index === 0 && !isDown && this.next) {
bus.emit(this.name + '-moveY', this.moveY)
}
if ((this.index === 0 && !isDown) || (this.index === this.total - 1 && isDown)) return
this.checkDirection(e)
if (this.next) {
this.$stopPropagation(e)
@ -55,12 +70,7 @@ export default { @@ -55,12 +70,7 @@ export default {
}
if (Math.abs(this.moveX) > this.judgeValue || Math.abs(this.moveY) > this.judgeValue) {
let angle = (Math.abs(this.moveX) * 10) / (Math.abs(this.moveY) * 10)
if (angle > 1) {
// console.log('')
} else {
this.next = true
// console.log('')
}
this.next = angle <= 1;
// console.log(angle)
return this.needCheck = false
}
@ -68,6 +78,9 @@ export default { @@ -68,6 +78,9 @@ export default {
},
touchEnd(e) {
let isDown = this.moveY < 0
if (this.index === 0 && !isDown && this.moveY > (this.homeRefresh + this.judgeValue)) {
bus.emit(this.name + '-loading')
}
let next = true
if ((this.index === 0 && !isDown) || (this.index === this.total - 1 && isDown)) next = false
@ -88,12 +101,12 @@ export default { @@ -88,12 +101,12 @@ export default {
this.moveX = 0
this.next = false
this.needCheck = true
bus.emit(this.name + '-end', this.index)
},
getDistance() {
return -this.index * this.wrapperHeight
},
},
render(createElement, context) {
return (
<div className="slide">

4
src/store/index.js

@ -42,7 +42,9 @@ const store = Vuex.createStore({ @@ -42,7 +42,9 @@ const store = Vuex.createStore({
"is_private": 1
},
friends: resource.users,
excludeRoutes: []
excludeRoutes: [],
judgeValue: 20,
homeRefresh: 60,
},
mutations: {
setUserinfo(store, val) {

16
src/utils/mixin.js

@ -93,6 +93,22 @@ export default { @@ -93,6 +93,22 @@ export default {
el.addEventListener("touchend", cancel);
el.addEventListener("touchcancel", cancel);
}
},
hide: {
beforeMount: function (el, binding, vNode) {
if (binding.value) {
el.style.opacity = 1
} else {
el.style.opacity = 0
}
},
updated: function (el, binding, vNode) {
if (binding.value) {
el.style.opacity = 1
} else {
el.style.opacity = 0
}
}
}
},
}
Loading…
Cancel
Save