scroll.vue 6.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242
  1. <template>
  2. <div ref="wrapper" class="better-scroll">
  3. <div class="content">
  4. <div v-if="pulldown" class="pulldown-tip">
  5. <span>{{pulldownTip.text}}</span>
  6. </div>
  7. <div class="list">
  8. <slot></slot>
  9. </div>
  10. <div v-if="pullupShow" class="pullup-tip">
  11. <span>{{pullupTip.text}}</span>
  12. </div>
  13. </div>
  14. </div>
  15. </template>
  16. <script>
  17. import BScroll from 'better-scroll'
  18. export default {
  19. name: "scroll",
  20. props: {
  21. // 滚动的时候会触发scroll事件,会截流
  22. // 滚动的时候实时触发scroll事件,不会截流
  23. // 在swipe的情况下也能使用scroll事件
  24. probeType: {
  25. type: Number,
  26. default: 3
  27. },
  28. //点击列表触发click事件
  29. click: {
  30. type: Boolean,
  31. default: true
  32. },
  33. //开启横向滚动
  34. scrollX: {
  35. type: Boolean,
  36. default: false
  37. },
  38. //滚动事件
  39. listenScroll: {
  40. type: Boolean,
  41. default: false
  42. },
  43. //列表数据
  44. data: {
  45. type: Array,
  46. default: null,
  47. },
  48. //滚动到底部事件,用于上拉加载
  49. pullup: {
  50. type: Boolean,
  51. default: true
  52. },
  53. //顶部下拉事件,用于下拉刷新
  54. pulldown: {
  55. type: Boolean,
  56. default: true
  57. },
  58. //列表滚动事件
  59. beforeScroll: {
  60. type: Boolean,
  61. default: false
  62. },
  63. //刷新scroll延时。
  64. refreshDelay: {
  65. type: Number,
  66. default: 20
  67. },
  68. },
  69. data(){
  70. return{
  71. loadingConnecting: false,
  72. pullupShow:false,
  73. pulldownTip: {
  74. text: '下拉刷新',
  75. },
  76. pullupTip: {
  77. text: '上拉加载',
  78. },
  79. }
  80. },
  81. mounted() {
  82. this.initScroll();
  83. },
  84. watch: {
  85. pullup(v){
  86. console.log(v,'监听pullup事件')
  87. //this.pullup = v;
  88. },
  89. data(v) {
  90. setTimeout(() => {
  91. this.refresh()
  92. }, this.refreshDelay)
  93. }
  94. },
  95. methods: {
  96. initScroll() {
  97. if (!this.$refs.wrapper) {
  98. return;
  99. }
  100. // better-scroll的初始化
  101. this.scroll = new BScroll(this.$refs.wrapper, {
  102. probeType: this.probeType,
  103. click: this.click,
  104. scrollX: this.scrollX
  105. });
  106. // 是否触发滚动事件
  107. if (this.listenScroll || this.pulldown || this.pullup) {
  108. //监听滚动事件
  109. this.scroll.on('scroll', (pos) => {
  110. if (this.listenScroll) {
  111. this.$emit('scroll', pos);
  112. }
  113. // 下拉刷新
  114. if (this.pulldown) {
  115. if (pos.y > 50) {
  116. this.pulldownTip = {
  117. text: '松开立即刷新',
  118. }
  119. } else {
  120. this.pulldownTip = {
  121. text: '下拉刷新',
  122. }
  123. }
  124. }
  125. //上拉加载
  126. if (this.pullup) {
  127. if (pos.y < (this.scroll.maxScrollY + -50)) {
  128. this.pullupTip = {
  129. text: '加载中..',
  130. };
  131. }else {
  132. this.pullupTip = {
  133. text: '上拉加载',
  134. };
  135. }
  136. this.pullupShow = true;
  137. }
  138. })
  139. }
  140. console.log(this.pullup,'pullup')
  141. // 底部上拉事件,上拉加载
  142. if (this.pullup) {
  143. this.scroll.on('touchEnd', (pos) => {
  144. // 下拉动作
  145. if (pos.y < -40) {
  146. // this.pullupTip = {
  147. // text: '111', // 松开立即刷新
  148. // };
  149. console.log('上拉加载,touchEnd')
  150. this.$emit('pullup');
  151. }
  152. });
  153. }
  154. //顶部下拉事件,下拉刷新
  155. if (this.pulldown) {
  156. this.scroll.on('touchEnd', (pos) => {
  157. // 下拉动作
  158. if (pos.y > 50) {
  159. // 重置提示信息
  160. // this.pulldownTip = {
  161. // text: '222', // 松开立即刷新
  162. // };
  163. console.log('下拉刷新,touchEnd')
  164. this.$emit('pulldown');
  165. }
  166. });
  167. }
  168. // 是否派发列表滚动开始的事件
  169. if (this.beforeScroll) {
  170. this.scroll.on('beforeScrollStart', () => {
  171. this.$emit('beforeScroll')
  172. });
  173. }
  174. },
  175. disable() {
  176. // 代理better-scroll的disable方法
  177. this.scroll && this.scroll.disable();
  178. },
  179. enable() {
  180. // 代理better-scroll的enable方法
  181. this.scroll && this.scroll.enable();
  182. },
  183. refresh() {
  184. // 代理better-scroll的refresh方法
  185. this.scroll && this.scroll.refresh();
  186. },
  187. scrollTo() {
  188. // 代理better-scroll的scrollTo方法
  189. this.scroll && this.scroll.scrollTo.apply(this.scroll, arguments);
  190. },
  191. scrollToElement() {
  192. // 代理better-scroll的scrollToElement方法
  193. this.scroll && this.scroll.scrollToElement.apply(this.scroll, arguments);
  194. }
  195. },
  196. }
  197. </script>
  198. <style lang="scss">
  199. .better-scroll{
  200. height: 100%;
  201. position: relative;
  202. overflow: hidden;
  203. .content {
  204. min-height: calc(100% + 1px);
  205. border-top: 1px solid #f2f2f2;
  206. overflow: auto;
  207. }
  208. .list{
  209. overflow: auto;
  210. }
  211. .pulldown-tip {
  212. width: 100%;
  213. display: flex;
  214. justify-content: center;
  215. align-items: center;
  216. position: absolute;
  217. top: -80px;
  218. height: 80px;
  219. line-height: 80px;
  220. color: #bbb;
  221. font-size: 3.5vw;
  222. z-index: 1;
  223. }
  224. .pullup-tip{
  225. box-sizing: border-box;
  226. line-height: 80px;
  227. width: 100%;
  228. color: #bbb;
  229. font-size: 3.5vw;
  230. text-align: center;
  231. margin: 0 auto;
  232. }
  233. }
  234. </style>