Detect ScrollView has reached the end

血红的双手。 提交于 2019-11-30 12:33:38

问题


I have a Text with long text inside a ScrollView and I want to detect when the user has scrolled to the end of the text so I can enable a button.

I've been debugging the event object from the onScroll event but there doesn't seem any value I can use.


回答1:


I did it like this:

import React from 'react';
import {ScrollView, Text} from 'react-native';

const isCloseToBottom = ({layoutMeasurement, contentOffset, contentSize}) => {
  const paddingToBottom = 20;
  return layoutMeasurement.height + contentOffset.y >=
    contentSize.height - paddingToBottom;
};

const MyCoolScrollViewComponent = ({enableSomeButton}) => (
  <ScrollView
    onScroll={({nativeEvent}) => {
      if (isCloseToBottom(nativeEvent)) {
        enableSomeButton();
      }
    }}
    scrollEventThrottle={400}
  >
    <Text>Here is very long lorem ipsum or something...</Text>
  </ScrollView>
);

export default MyCoolScrollViewComponent;

I wanted to add paddingToBottom because usually it is not needed that ScrollView is scrolled to the bottom till last pixel. But if you want that set paddingToBottom to zero.




回答2:


<... onScroll={(e) => {
        let paddingToBottom = 10;
        paddingToBottom += e.nativeEvent.layoutMeasurement.height;
        if(e.nativeEvent.contentOffset.y >= e.nativeEvent.contentSize.height - paddingToBottom) {
          // make something...
        }
      }}>...

like this react-native 0.44




回答3:


As people helped here I will add the simple code they write to make reached to top and reached to bottom event and I did a little illustration to make things simpler

<ScrollView
onScroll={({nativeEvent})=>{
if(isCloseToTop(nativeEvent)){
    //do something
}
if(isCloseToBottom(nativeEvent)){
   //do something
}
}}
>
...contents
</ScrollView>



isCloseToBottom({layoutMeasurement, contentOffset, contentSize}){
   return layoutMeasurement.height + contentOffset.y >= contentSize.height - 20;
}



ifCloseToTop({layoutMeasurement, contentOffset, contentSize}){
   return contentOffset.y == 0;
}



回答4:


Another solution could be to use a ListView with a single row (your text) which has onEndReached method. See the documentation here




回答5:


For Horizontal ScrollView (e.g. Carousels) replace isCloseToBottom function with isCloseToRight

isCloseToRight = ({ layoutMeasurement, contentOffset, contentSize }) => {
    const paddingToRight = 20;
    return layoutMeasurement.width + contentOffset.x >= contentSize.width - paddingToRight;
};



回答6:


@Henrik R's right. But you should use Math.ceil() too.

function handleInfinityScroll(event) {
        let mHeight = event.nativeEvent.layoutMeasurement.height;
        let cSize = event.nativeEvent.contentSize.height;
        let Y = event.nativeEvent.contentOffset.y;

        if(Math.ceil(mHeight + Y) >= cSize) return true;
        return false;
}




回答7:


As an addition to the answer of Henrik R:

If you need to know wether the user has reached the end of the content at mount time (if the content may or may not be too long, depending on device size) - here is my solution:

<ScrollView 
        onLayout={this.onLayoutScrollView}
        onScroll={this.onScroll}>
    <View onLayout={this.onLayoutScrollContent}>
        {/*...*/}
    </View>
</ScrollView>

in combination with

onLayout(wrapper, { nativeEvent }) {
    if (wrapper) {
        this.setState({
            wrapperHeight: nativeEvent.layout.height,
        });
    } else {
        this.setState({
            contentHeight: nativeEvent.layout.height,
            isCloseToBottom:
              this.state.wrapperHeight - nativeEvent.layout.height >= 0,
        });
    }
}


来源:https://stackoverflow.com/questions/41056761/detect-scrollview-has-reached-the-end

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!