Skip to content

Commit 5819729

Browse files
author
Bas Pellis
committed
Added index to start at specified index. Added fromIndex and toIndex to limit page indexes. Bug fixes.
1 parent 808f855 commit 5819729

File tree

4 files changed

+50
-23
lines changed

4 files changed

+50
-23
lines changed

README.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,9 @@ Simple Calendar example included.
2020
- **renderPage** - Required - (Function) - Must return a component representing the page for the provided index.
2121
- **horizontal** - Optional - (Boolean) - Scroll horizontal instead of vertical (default).
2222
- **offScreenPages** - Optional - (Integer) - Number of pages to render before and after the current page. Default is 1 (total 3 pages are rendered).
23+
- **index** - Optional - (Integer) - Start the scrollview with this index. Default is 0 or toIndex whichever is greater.
24+
- **toIndex** - Optional - (Integer) - Don't allow scrolling below this page index
25+
- **fromIndex** - Optional - (Integer) - Don't allow scrolling above this page index
2326

2427
### Questions?
2528
Feel free to contact me via

example/package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,6 @@
88
"dependencies": {
99
"moment": "^2.11.2",
1010
"react-native": "^0.20.0",
11-
"react-native-infinite-scrollview": "^0.1.1"
11+
"react-native-infinite-scrollview": "^0.2.0"
1212
}
1313
}

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "react-native-infinite-scrollview",
3-
"version": "0.1.1",
3+
"version": "0.2.0",
44
"description": "ScrollView with infinte paged scrolling (no looping). The number of pages rendered before and after current page can be customized. Pages are rendered when user scrolled.",
55
"main": "src/index.js",
66
"scripts": {

src/index.js

Lines changed: 45 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -7,31 +7,56 @@ import React, {
77
export default class InfiniteScrollView extends Component {
88
constructor(props) {
99
super(props);
10+
11+
var fromIndex = props.fromIndex || Number.NEGATIVE_INFINITY;
12+
var toIndex = props.toIndex || Number.POSITIVE_INFINITY;
13+
14+
var index = 0;
15+
if(this.props.index) index = Math.min(Math.max(this.props.index, fromIndex), toIndex);
16+
else index = Math.max(0, fromIndex);
17+
1018
this._scrollView = null;
1119
this._offscreenPages = this.props.offScreenPages || 1;
20+
this._renderedRange = {};
1221
this.state = {
13-
index: 0,
22+
index: index,
23+
fromIndex: fromIndex,
24+
toIndex: toIndex,
1425
size: {
1526
width: 0,
1627
height: 0,
1728
}
1829
}
1930
}
31+
shouldComponentUpdate(nextProps, nextState) {
32+
var range = this._pagesRange(nextState);
33+
return (
34+
nextState.size !== this.state.size ||
35+
range.to !== this._renderedRange.to || range.from !== this._renderedRange.from
36+
);
37+
}
38+
componentDidUpdate() {
39+
var scrollTo = {animated: false}
40+
if(this.props.horizontal) scrollTo.x = (this.state.index - this._renderedRange.from) * this.state.size.width;
41+
else scrollTo.y = (this.state.index - this._renderedRange.from) * this.state.size.height;
42+
this._scrollView.scrollTo(scrollTo);
43+
}
2044
render() {
21-
var pages = this._createPages();
22-
var contentOffset = {x:0,y:0};
23-
if(this.props.horizontal) contentOffset.x = this._offscreenPages * this.state.size.width;
24-
else contentOffset.y = this._offscreenPages * this.state.size.height;
25-
return (
45+
var pages = null;
46+
if(this.state.size.width > 0 && this.state.size.width > 0) {
47+
var range = this._pagesRange(this.state);
48+
pages = this._createPages(range);
49+
}
50+
return (
2651
<View style={this.props.style} onLayout={(event) => this._layoutChanged(event)}>
2752
<ScrollView
53+
style={{overflow: 'visible'}}
2854
ref={(scrollView) => { this._scrollView = scrollView; }}
2955
horizontal={this.props.horizontal}
3056
automaticallyAdjustContentInsets={false}
3157
showsHorizontalScrollIndicator={false}
3258
showsVerticalScrollIndicator={false}
3359
pagingEnabled={true}
34-
contentOffset={contentOffset}
3560
onMomentumScrollEnd={(e) => this._scrollEnded(e)}>
3661
{pages}
3762
</ScrollView>
@@ -46,14 +71,21 @@ export default class InfiniteScrollView extends Component {
4671
width: width,
4772
height: height
4873
}
49-
})
74+
});
75+
}
76+
_pagesRange(state) {
77+
var range = {};
78+
range.from = Math.max(state.index - this._offscreenPages, state.fromIndex);
79+
range.to = Math.min(range.from + 2 * this._offscreenPages, state.toIndex);
80+
range.from = Math.min(range.from, range.to - 2 * this._offscreenPages);
81+
return range;
5082
}
51-
_createPages() {
83+
_createPages(range) {
5284
var pages = [];
53-
var numberOfPages = this._offscreenPages * 2 + 1;
54-
for(i = 0; i < numberOfPages; i ++) {
55-
pages.push(this._renderPage(i + this.state.index - this._offscreenPages));
85+
for(i = range.from; i <= range.to; i++) {
86+
pages.push(this._renderPage(i));
5687
}
88+
this._renderedRange = range;
5789
return pages;
5890
}
5991
_renderPage(index) {
@@ -65,15 +97,7 @@ export default class InfiniteScrollView extends Component {
6597
}
6698
_scrollEnded(event) {
6799
var scrollIndex = Math.round(this.props.horizontal ? event.nativeEvent.contentOffset.x / this.state.size.width : event.nativeEvent.contentOffset.y / this.state.size.height);
68-
var index = this.state.index + scrollIndex - this._offscreenPages;
69-
this._positionPages(index);
70-
}
71-
_positionPages(index) {
72-
var scrollTo = {animated: false}
73-
if(this.props.horizontal) scrollTo.x = this._offscreenPages * this.state.size.width;
74-
else scrollTo.y = this._offscreenPages * this.state.size.height;
75-
76-
this._scrollView.scrollTo(scrollTo);
100+
var index = this.state.index + scrollIndex - Math.min(this._offscreenPages, this.state.index - this.state.fromIndex) - Math.max(0, this._offscreenPages + this.state.index - this.state.toIndex);
77101
this.setState({index: index});
78102
}
79103
}

0 commit comments

Comments
 (0)