# scroll-view

组件类型:UniScrollViewElement

可滚动视图容器

# scroll-view 兼容性

Android iOS web
3.9 4.11 4.0

# 属性

名称 类型 默认值 描述
type string - 渲染模式,可取值 nested
值名称 描述
nested 嵌套模式。用于处理父子 scroll-view 间的嵌套滚动,子节点只能是 nested-scroll-header nested-scroll-body 组件或自定义 refresher
direction string "vertical" 滚动方向,可取值 none、all、horizontal、vertical,默认值vertical
值名称 描述
none 禁止滚动
all 横向竖向都可滚动 app端不支持
horizontal 横向滚动
vertical 竖向滚动
scroll-x boolean false 允许横向滚动,不支持同时设置scroll-y属性为true,同时设置true时scroll-y生效。已废弃,请改用direction
scroll-y boolean true 允许纵向滚动,不支持同时设置scroll-x属性为true,同时设置true时scroll-y生效。已废弃,请改用direction
rebound boolean true 控制是否回弹效果。已废弃,请改用bounces
associative-container string "" 关联的滚动容器
值名称 描述
nested-scroll-view 嵌套滚动
enable-back-to-top boolean false iOS点击顶部状态栏滚动条返回顶部,只支持竖向
bounces boolean true 控制是否回弹效果 优先级高于rebound
upper-threshold number 50 距顶部/左边多远时(单位px),触发 scrolltoupper 事件
lower-threshold number 50 距底部/右边多远时(单位px),触发 scrolltolower 事件
scroll-top number 0 设置竖向滚动条位置
scroll-left number 0 设置横向滚动条位置
scroll-into-view string(string.IDString) - 值应为某子元素id(id不能以数字开头)。设置哪个方向可滚动,则在哪个方向滚动到该元素起始位置
scroll-with-animation boolean false 是否在设置滚动条位置时使用滚动动画,设置false没有滚动动画
refresher-enabled boolean false 开启下拉刷新,暂时不支持scroll-x = true横向刷新
refresher-threshold number 45 设置下拉刷新阈值
refresher-max-drag-distance number - 设置下拉最大拖拽距离(单位px),默认是下拉刷新控件高度的2.5倍
refresher-default-style string "black" 设置下拉刷新默认样式,支持设置 black | white | none, none 表示不使用默认样式
值名称 描述
black 深颜色雪花样式
white 浅白色雪花样式
none 不使用默认样式
refresher-background string(string.ColorString) "transparent" 设置下拉刷新区域背景颜色,默认透明
refresher-triggered boolean false 设置当前下拉刷新状态,true 表示下拉刷新已经被触发,false 表示下拉刷新未被触发
show-scrollbar boolean true 控制是否出现滚动条
custom-nested-scroll boolean false 子元素是否开启嵌套滚动 将滚动事件与父元素协商处理
nested-scroll-child string(string.IDString) "" 嵌套滚动子元素的id属性,不支持ref,scroll-view惯性滚动时会让对应id元素视图进行滚动,子元素滚动时会触发scroll-view的nestedprescroll事件,嵌套子元素需要设置custom-nested-scroll = true
@refresherpulling (event: UniRefresherEvent) => void - 下拉刷新控件被下拉
@refresherrefresh (event: UniRefresherEvent) => void - 下拉刷新被触发
@refresherrestore (event: UniRefresherEvent) => void - 下拉刷新被复位
@refresherabort (event: UniRefresherEvent) => void - 下拉刷新被中止
@scrolltoupper (event: UniScrollToUpperEvent) => void - 滚动到顶部/左边,会触发 scrolltoupper 事件
@scrolltolower (event: UniScrollToLowerEvent) => void - 滚动到底部/右边,会触发 scrolltolower 事件
@scroll (event: UniScrollEvent) => void - 滚动时触发,event.detail = {scrollLeft, scrollTop, scrollHeight, scrollWidth, deltaX, deltaY}
@scrollend (event: UniScrollEvent) => void - 滚动结束时触发,event.detail = {scrollLeft, scrollTop, scrollHeight, scrollWidth, deltaX, deltaY}
@startnestedscroll (event: UniStartNestedScrollEvent) => Boolean - 子元素开始滚动时触发, return ture表示与子元素开启滚动协商 默认return false! event = {node}
@nestedprescroll (event: UniNestedPreScrollEvent) => void - 子元素滚动时触发,可执行event.consumed(x,y)告知子元素deltaX、deltaY各消耗多少。子元素将执行差值后的deltaX、deltaY滚动距离。不执行consumed(x,y)则表示父元素不消耗deltaX、deltaY。event = {deltaX, deltaY}
@stopnestedscroll (event: UniStopNestedScrollEvent) => void - 子元素滚动结束或意外终止时触发

# type 兼容性

Android iOS web
nested 4.11 4.11 x

# direction 兼容性

Android iOS web
none 4.0 4.11 4.0
all x x 4.0
horizontal 4.0 4.11 4.0
vertical 4.0 4.11 4.0

# associative-container 兼容性

Android iOS web
nested-scroll-view 4.11 4.11 x

# refresher-default-style 兼容性

Android iOS web
black 3.9 4.11 -
white 3.9 4.11 -
none 3.9 4.11 -

# 事件

# UniRefresherEvent

# UniRefresherEvent 的属性值
名称 类型 必填 默认值 描述
detail UniRefresherEventDetail - -
名称 类型 必备 默认值 描述
dy number - -
bubbles boolean - 是否冒泡
cancelable boolean - 是否可以取消
type string - 事件类型
target UniElement | null - UVUE DOM 元素对象,描述了 UVUE DOM 元素所普通具有的属性和方法。
currentTarget UniElement | null - UVUE DOM 元素对象,描述了 UVUE DOM 元素所普通具有的属性和方法。
timeStamp number - 事件发生时的时间戳
# UniRefresherEvent 的方法
名称 类型 必填 默认值 描述
stopPropagation () => void - 阻止当前事件的进一步传播
preventDefault () => void - 阻止当前事件的默认行为

# UniScrollToUpperEvent

# UniScrollToUpperEvent 的属性值
名称 类型 必填 默认值 描述
detail UniScrollToUpperEventDetail -
名称 类型 必备 默认值 描述
direction string - 滚动方向 top 或 left
bubbles boolean - 是否冒泡
cancelable boolean - 是否可以取消
type string - 事件类型
target UniElement | null - UVUE DOM 元素对象,描述了 UVUE DOM 元素所普通具有的属性和方法。
currentTarget UniElement | null - UVUE DOM 元素对象,描述了 UVUE DOM 元素所普通具有的属性和方法。
timeStamp number - 事件发生时的时间戳
# UniScrollToUpperEvent 的方法
名称 类型 必填 默认值 描述
stopPropagation () => void - 阻止当前事件的进一步传播
preventDefault () => void - 阻止当前事件的默认行为

# UniScrollToLowerEvent

# UniScrollToLowerEvent 的属性值
名称 类型 必填 默认值 描述
detail UniScrollToLowerEventDetail -
名称 类型 必备 默认值 描述
direction string - 滚动方向 bottom 或 right
bubbles boolean - 是否冒泡
cancelable boolean - 是否可以取消
type string - 事件类型
target UniElement | null - UVUE DOM 元素对象,描述了 UVUE DOM 元素所普通具有的属性和方法。
currentTarget UniElement | null - UVUE DOM 元素对象,描述了 UVUE DOM 元素所普通具有的属性和方法。
timeStamp number - 事件发生时的时间戳
# UniScrollToLowerEvent 的方法
名称 类型 必填 默认值 描述
stopPropagation () => void - 阻止当前事件的进一步传播
preventDefault () => void - 阻止当前事件的默认行为

# UniScrollEvent

# UniScrollEvent 的属性值
名称 类型 必填 默认值 描述
detail UniScrollEventDetail -
名称 类型 必备 默认值 描述
scrollTop number - 竖向滚动的距离
scrollLeft number - 横向滚动的距离
scrollHeight number - 滚动区域的高度
scrollWidth number - 滚动区域的宽度
deltaY number - 当次滚动事件竖向滚动量
deltaX number - 当次滚动事件横向滚动量
bubbles boolean - 是否冒泡
cancelable boolean - 是否可以取消
type string - 事件类型
target UniElement | null - UVUE DOM 元素对象,描述了 UVUE DOM 元素所普通具有的属性和方法。
currentTarget UniElement | null - UVUE DOM 元素对象,描述了 UVUE DOM 元素所普通具有的属性和方法。
timeStamp number - 事件发生时的时间戳
# UniScrollEvent 的方法
名称 类型 必填 默认值 描述
stopPropagation () => void - 阻止当前事件的进一步传播
preventDefault () => void - 阻止当前事件的默认行为

# UniStartNestedScrollEvent

# UniStartNestedScrollEvent 的属性值
名称 类型 必填 默认值 描述
node UniElement - 开始滚动子节点对象
isTouch boolean - 是否由触摸行为发生的Event
bubbles boolean - 是否冒泡
cancelable boolean - 是否可以取消
type string - 事件类型
target UniElement | null - UVUE DOM 元素对象,描述了 UVUE DOM 元素所普通具有的属性和方法。
currentTarget UniElement | null - UVUE DOM 元素对象,描述了 UVUE DOM 元素所普通具有的属性和方法。
timeStamp number - 事件发生时的时间戳
# UniStartNestedScrollEvent 的方法
名称 类型 必填 默认值 描述
stopPropagation () => void - 阻止当前事件的进一步传播
preventDefault () => void - 阻止当前事件的默认行为

# UniNestedPreScrollEvent

# UniNestedPreScrollEvent 的属性值
名称 类型 必填 默认值 描述
deltaX number - x轴滚动距离
deltaY number - y轴滚动距离
isTouch boolean - 是否由触摸行为发生的Event
bubbles boolean - 是否冒泡
cancelable boolean - 是否可以取消
type string - 事件类型
target UniElement | null - UVUE DOM 元素对象,描述了 UVUE DOM 元素所普通具有的属性和方法。
currentTarget UniElement | null - UVUE DOM 元素对象,描述了 UVUE DOM 元素所普通具有的属性和方法。
timeStamp number - 事件发生时的时间戳
# UniNestedPreScrollEvent 的方法
名称 类型 必填 默认值 描述
consumed (consumedX: number, consumedY: number) => void - 通知到子节点x,y轴滚动距离的消耗
stopPropagation () => void - 阻止当前事件的进一步传播
preventDefault () => void - 阻止当前事件的默认行为

# UniStopNestedScrollEvent

# UniStopNestedScrollEvent 的属性值
名称 类型 必填 默认值 描述
isTouch boolean - 是否由触摸行为发生的Event
bubbles boolean - 是否冒泡
cancelable boolean - 是否可以取消
type string - 事件类型
target UniElement | null - UVUE DOM 元素对象,描述了 UVUE DOM 元素所普通具有的属性和方法。
currentTarget UniElement | null - UVUE DOM 元素对象,描述了 UVUE DOM 元素所普通具有的属性和方法。
timeStamp number - 事件发生时的时间戳
# UniStopNestedScrollEvent 的方法
名称 类型 必填 默认值 描述
stopPropagation () => void - 阻止当前事件的进一步传播
preventDefault () => void - 阻止当前事件的默认行为

# 自定义下拉刷新样式

  1. 设置refresher-default-style属性为 none 不使用默认样式
  2. 自定义下拉刷新元素必须要声明为 slot="refresher",需要设置刷新元素宽高信息否则可能无法正常显示!
  3. 通过组件提供的refresherpulling、refresherrefresh、refresherrestore、refresherabort下拉刷新事件调整自定义下拉刷新元素!实现预期效果

注意: 目前自定义下拉刷新元素不支持放在scroll-view的首个子元素位置上。可能无法正常显示

<scroll-view refresher-default-style="none" :refresher-enabled="true" :refresher-triggered="refresherTriggered"
			 @refresherpulling="onRefresherpulling" @refresherrefresh="onRefresherrefresh"
			 @refresherrestore="onRefresherrestore" style="flex:1" >

		<view v-for="i in 20" class="content-item">
			<text class="text">item-{{i}}</text>
		</view>

		<!-- 自定义下拉刷新元素 -->
		<view slot="refresher" class="refresh-box">
			<text class="tip-text">{{text[state]}}</text>
		</view>

</scroll-view>

具体代码请参考:自定义下拉刷新样式示例

# 嵌套模式

当存在两个 scroll-view 相互嵌套的场景时,两者滚动存在冲突不能很丝滑的进行衔接,可将外层 scroll-view 改成嵌套模式,这样可以让两个 scroll-view 的滚动衔接起来。

<scroll-view style="flex:1" type="nested">
	<nested-scroll-header>
		<view style="height: 200px;background-color: #66ccff;align-items: center;justify-content: center;">
			<text>nested-scroll-header</text>
		</view>
	</nested-scroll-header>
	<nested-scroll-body>
		<view style="flex:1">
			<scroll-view style="flex:1" associative-container="nested-scroll-view">
				<view v-for="index in 20" style="background-color: aliceblue; height: 80px;justify-content: center;">
					<text style="color: black;">{{index}}</text>
				</view>
			</scroll-view>
		</view>
	</nested-scroll-body>
</scroll-view>

开启嵌套模式设置如下:

  1. 设置外层 scroll-view 的 type 属性为 "nested" ,将外层 scroll-view 改成嵌套模式
  2. 设置内层 scroll-view 的 associative-container 属性为 "nested-scroll-view",开启内层 scroll-view 支持与外层 scroll-view 嵌套滚动

嵌套滚动策略:

当向下滚动时,先滚动外层 scroll-view 再滚动内层 scroll-view;当向上滚动时,先滚动内层 scroll-view 再滚动外层 scroll-view

注意事项:

  • 4.11版本开始支持嵌套模式
  • 外层 scroll-view 的子节点只支持nested-scroll-headernested-scroll-body和自定义 refresher
  • 外层 scroll-view 的子节点中只能有一个 nested-scroll-body
  • nested-scroll-headernested-scroll-body 只能有一个子节点
  • nested-scroll-header 只能渲染在 nested-scroll-body 上面
  • 与nested-scroll嵌套滚动协商互不兼容,nested-scroll-headernested-scroll-body优先级高于nested-scroll嵌套滚动协商
  • 内层滚动视图支持 scroll-view 和 list-view

具体代码请参考:嵌套模式示例

# nested-scroll嵌套滚动协商

嵌套滚动是原生才有的概念,web没有。

它是指父子2个滚动容器嵌套,在滚动时可以互相协商,控制父容器怎么滚、子容器怎么滚。

  1. 通过在子滚动容器设置custom-nested-scroll = true,开启与父组件实现嵌套滚动协商。仅list-view、scroll-view组件支持与父组件嵌套滚动协商。

下面的示例代码,在一个scroll-view中嵌套了一个list-view。在list-view上设置了custom-nested-scroll="true"。

<scroll-view style="height: 100%;" scroll-y="true" rebound ="false" nested-scroll-child="listview" @startnestedscroll="onStartNestedScroll" @nestedprescroll="onNestedPreScroll"
	@stopnestedscroll="onStopNestedScroll">
		...
		<view style="height: 100px;">停靠视图</view>
		<list-view id="listview"  class="child-scroll" scroll-y="true" custom-nested-scroll="true">
			...
		</list-view>
</scroll-view>
  1. 子组件准备滚动时会触发父组件的startnestedscroll事件。父组件响应startnestedscroll事件return ture则表示与子组件建立嵌套滚动协商。
onStartNestedScroll(event: StartNestedScrollEvent): Boolean {
	//开启与子组件建立嵌套滚动协商
	return true
}
  1. 当建立嵌套滚动协商后,子组件滚动时父组件会持续收到nestedprescroll事件,这个事件的含义是嵌套滚动即将发生。 事件中会返回NestedPreScrollEvent子组件将要滚动的数据。
  2. 父组件执行NestedPreScrollEvent.consumed(x,y)函数,告知子组件本次nestedprescroll事件deltaX、deltaY各消耗多少,即父组件要消费掉多少滚动距离。 子组件将执行差值后的deltaX、deltaY滚动距离,也就是剩余的滚动余量留给子组件。
onNestedPreScroll(event: NestedPreScrollEvent) {
	var deltaY = event.deltaY
	var deltaX = event.deltaX
	...
	if() {
		//告知子组件deltaX、deltaY各消耗多少
		event.consumed(x, y)
	}
}
  1. 父组件配置nested-scroll-child后,父组件惯性滚动时会让nested-scroll-child配置的子元素进行滚动。从而触发nestedprescroll协商处理滚动事件
  2. 滚动行为停止后会触发stopnestedscroll事件

注意:

  • 仅Android平台支持嵌套滚动协商
  • 嵌套滚动协商仅支持竖向滚动,横向滚动不支持
  • nested-scroll-child设置的元素必须配置custom-nested-scroll = true,否则配置无效
  • nested-scroll-headernested-scroll-body不兼容,scroll-view 设置嵌套模式后,嵌套滚动手势协商相关事件将不会触发

具体代码请参考:nested-scroll嵌套滚动示例

# scroll-view 属性兼容性

Android iOS web
type 4.11 4.11 x
direction 4.0 4.11 4.0
scroll-x 3.9 x 4.0
scroll-y 3.9 x 4.0
rebound 3.9 x -
associative-container 4.11 4.11 x
enable-back-to-top x 4.11 x
bounces 4.0 4.11 x
upper-threshold 3.9 4.11 4.0
lower-threshold 3.9 4.11 4.0
scroll-top 3.9 4.11 4.0
scroll-left 3.9 4.11 4.0
scroll-into-view 3.9 4.11 4.0
scroll-with-animation 3.9 4.11 4.0
refresher-enabled 3.9 4.11 x
refresher-threshold 3.9 4.11 x
refresher-max-drag-distance 3.9 4.11 x
refresher-default-style 3.9 4.11 x
refresher-background 3.9 4.11 x
refresher-triggered 3.9 4.11 x
show-scrollbar 3.9 4.11 4.0
custom-nested-scroll 3.9 x x
nested-scroll-child 3.97 x x
@refresherpulling 3.9 4.11 x
@refresherrefresh 3.9 4.11 x
@refresherrestore 3.9 4.11 x
@refresherabort 3.9 4.11 x
@scrolltoupper 3.9 4.11 4.0
@scrolltolower 3.9 4.11 4.0
@scroll 3.9 4.11 4.0
@scrollend 3.9 4.11 4.0
@startnestedscroll 3.9 x x
@nestedprescroll 3.9 x x
@stopnestedscroll 3.9 x x

# App平台

  • App平台scroll-x、scroll-y属性不支持同时设置为true, 同时设置true时仅scroll-y生效,4.0版本开始scroll-x、scroll-y已废弃,请使用direction属性。
  • App平台scroll-view组件不支持动态切换横竖滚动方向
  • App平台scroll-view组件的overflow属性不支持配置visible
  • App平台scroll-view组件默认高度取值:
    • scroll-view组件的子元素高度之和未超过scroll-view组件的父元素高度:
      • scroll-view组件的默认高度取值为子元素高度之和
    • scroll-view组件的子元素高度之和超过scroll-view组件的父元素高度:
      • 3.9版本scroll-view组件默认高度取值为scroll-view组件父元素的高度。子元素高度之和超过scroll-view组件的高度,scroll-view组件可滚动。
      • 4.0版本开始scroll-view组件的默认高度取值为子元素高度之和。高度相同scroll-view组件无法滚动。开发者需要设置css属性定义scroll-view组件高度,让scroll-view组件高度小于子元素高度之和,实现滚动能力。

# 子组件

# 示例

hello uni-app x

Template

Script

<template>
  <!-- #ifdef APP -->
  <scroll-view class="page-scroll-view">
  <!-- #endif -->
    <view>
      <page-head title="scroll-view,区域滚动视图"></page-head>
      <view class="uni-padding-wrap uni-common-mt">
        <view class="uni-title uni-common-mt">
          <text class="uni-title-text">Vertical Scroll</text>
          <text class="uni-subtitle-text">纵向滚动</text>
        </view>
        <view>
          <scroll-view :scroll-top="scrollTop" direction="vertical" class="scroll-Y" scroll-with-animation="true"
            @scrolltoupper="upper" @scrolltolower="lower" @scroll="scroll" :show-scrollbar="showScrollbar">
            <view class="scroll-view-item uni-bg-red"><text class="text">A</text></view>
            <view class="scroll-view-item uni-bg-green"><text class="text">B</text></view>
            <view class="scroll-view-item uni-bg-blue"><text class="text">C</text></view>
          </scroll-view>
        </view>
        <view @tap="goTop" class="uni-center uni-common-mt">
          <text class="uni-link">点击这里返回顶部</text>
        </view>

        <view class="uni-title uni-common-mt">
          <text class="uni-title-text">Horizontal Scroll</text>
          <text class="uni-subtitle-text">横向滚动</text>
        </view>
        <view>
          <scroll-view class="scroll-view_H" direction="horizontal" @scroll="scroll" :scroll-left="120" :show-scrollbar="showScrollbar">
            <view class="scroll-view-item_H uni-bg-red"><text class="text">A</text></view>
            <view class="scroll-view-item_H uni-bg-green"><text class="text">B</text></view>
            <view class="scroll-view-item_H uni-bg-blue"><text class="text">C</text></view>
          </scroll-view>
        </view>

        <navigator url="/pages/component/scroll-view/scroll-view-props" hover-class="none">
          <button type="primary" class="button">
            非下拉刷新的属性示例
          </button>
        </navigator>
        <view class="uni-common-pb"></view>

        <!-- #ifdef APP -->
        <navigator url="/pages/component/scroll-view/scroll-view-refresher-props" hover-class="none">
          <button type="primary" class="button">
            下拉刷新的属性示例
          </button>
        </navigator>
        <view class="uni-common-pb"></view>
        <navigator url="/pages/component/scroll-view/scroll-view-refresher" hover-class="none">
          <button type="primary" class="button"> 默认下拉刷新示例 </button>
        </navigator>
        <view class="uni-common-pb"></view>
        <navigator url="/pages/component/scroll-view/scroll-view-custom-refresher-props" hover-class="none">
          <button type="primary" class="button">
            自定义下拉刷新示例
          </button>
        </navigator>
        <view class="uni-common-pb"></view>
        <!-- #endif -->
      </view>
    </view>
  <!-- #ifdef APP -->
  </scroll-view>
  <!-- #endif -->
</template>


<style>
  .scroll-Y {
    height: 150px;
  }

  .scroll-view_H {
    width: 100%;
    flex-direction: row;
  }

  .scroll-view-item {
    height: 150px;
    justify-content: center;
    align-items: center;
  }

  .scroll-view-item_H {
    width: 100%;
    height: 150px;
    justify-content: center;
    align-items: center;
  }

  .text {
    font-size: 18px;
    color: #ffffff;
  }

  .button {
    margin-top: 15px;
  }
</style>

# 参见