Skip to content

Commit af80883

Browse files
author
Malik Kawee
committed
initial commit
0 parents  commit af80883

File tree

5 files changed

+204
-0
lines changed

5 files changed

+204
-0
lines changed

. babelrc

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
{
2+
"presets": ["module:metro-react-native-babel-preset"]
3+
}

.gitignore

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
# Logs
2+
*.log
3+
npm-debug.log
4+
5+
# Runtime data
6+
tmp
7+
build
8+
dist
9+
10+
# Dependency directory
11+
node_modules

.npmignore

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
# Logs
2+
*.log
3+
npm-debug.log
4+
5+
# Dependency directory
6+
node_modules
7+
8+
# Runtime data
9+
tmp

package.json

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
{
2+
"name": "rn-faded-scrollview",
3+
"version": "1.0.0",
4+
"description": "A simple and customizable React Native component that allows you to add fade effect in ScrollView at both ends.",
5+
"main": "src/index.js",
6+
"scripts": {
7+
"test": "echo \"Error: no test specified\" && exit 1"
8+
},
9+
"repository": {
10+
"type": "git",
11+
"url": "git+https://github.com/mak12/rn-faded-scrollview.git"
12+
},
13+
"keywords": [
14+
"react-native",
15+
"scrollview",
16+
"fadedscrollview",
17+
"faded",
18+
"rn-faded-scrollview",
19+
"fade",
20+
"effects"
21+
],
22+
"author": "Malik Abdul Kawee",
23+
"license": "MIT",
24+
"bugs": {
25+
"url": "https://github.com/mak12/rn-faded-scrollview/issues"
26+
},
27+
"homepage": "https://github.com/mak12/rn-faded-scrollview#readme",
28+
"peerDependencies": {
29+
"react": "16.11.0",
30+
"react-native": "0.62.2"
31+
},
32+
"dependencies": {
33+
"react-native-linear-gradient": "^2.5.6"
34+
},
35+
"devDependencies": {
36+
"metro-react-native-babel-preset": "^0.59.0"
37+
}
38+
}

src/index.js

Lines changed: 143 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,143 @@
1+
import React, { Component } from 'react';
2+
import { StyleSheet, ScrollView, View } from 'react-native';
3+
import PropTypes from "prop-types";
4+
import LinearGradient from "react-native-linear-gradient"
5+
const defaultFadeColors = ['rgba(229, 229, 229, 0.18)', 'rgba(206, 201, 201, 0.6)', 'rgba(206, 201, 201, 0.9)'];
6+
export default class RNFadedScrollView extends Component {
7+
8+
constructor(props) {
9+
super(props);
10+
this.state = {
11+
// We don't know the size of the content initially, and the probably won't instantly try to scroll,
12+
// so set the initial content height and width to 0
13+
scrollHeight: 0,
14+
scrollWidth: 0,
15+
availableWidth: 0,
16+
availableHeight: 0,
17+
allowStartFade: false
18+
}
19+
}
20+
21+
22+
onContentSizeChange = (contentWidth, contentHeight) => {
23+
// Save the content height in state
24+
this.setState({ scrollHeight: contentHeight, scrollWidth: contentWidth });
25+
};
26+
_onLayout(event) {
27+
const containerWidth = event.nativeEvent.layout.width;
28+
const containerHeight = event.nativeEvent.layout.width;
29+
30+
this.setState({ availableWidth: containerWidth, availableHeight: containerHeight })
31+
}
32+
33+
isEndFadeAllowed() {
34+
const sizeToCompare = this.props.isHorizontal ? this.state.scrollWidth : this.state.scrollHeight;
35+
const availableSpace = this.props.isHorizontal ? this.state.availableWidth : this.state.availableHeight;
36+
return this.props.allowEndFade ? sizeToCompare > availableSpace : false;
37+
}
38+
39+
ifCloseToStart({ layoutMeasurement, contentOffset, contentSize }) {
40+
return this.props.isHorizontal ? contentOffset.x < 10 : contentOffset.y < 10;
41+
}
42+
isCloseToBottom({ layoutMeasurement, contentOffset, contentSize }) {
43+
return layoutMeasurement.height + contentOffset.y >= contentSize.height - 20;
44+
}
45+
46+
onScrolled = (e) => {
47+
if (this.props.allowStartFade) {
48+
if (this.ifCloseToStart(e.nativeEvent)) {
49+
this.setState({ allowStartFade: false })
50+
51+
}
52+
else {
53+
this.setState({ allowStartFade: true })
54+
}
55+
}
56+
57+
if (this.props.onScroll) {
58+
this.props.onScroll();
59+
}
60+
}
61+
62+
//get start fade view
63+
getStartFaade() {
64+
return (this.props.isHorizontal ?
65+
<LinearGradient
66+
start={{ x: 1, y: 0 }} end={{ x: 0, y: 0 }}
67+
style={{ position: 'absolute', start: 0, width: this.props.fadeSize, height: '100%' }}
68+
colors={this.props.fadeColors}
69+
pointerEvents={'none'}
70+
/> :
71+
<LinearGradient
72+
start={{ x: 0, y: 1 }} end={{ x: 0, y: 0 }}
73+
style={{ position: 'absolute', top: 0, width: '100%', height: this.props.fadeSize }}
74+
colors={this.props.fadeColors}
75+
pointerEvents={'none'}
76+
/>
77+
)
78+
}
79+
80+
getEndFade() {
81+
return (this.props.isHorizontal ?
82+
<LinearGradient
83+
start={{ x: 0, y: 0 }} end={{ x: 1, y: 0 }}
84+
style={{ position: 'absolute', end: 0, width: this.props.fadeSize, height: '100%' }}
85+
colors={this.props.fadeColors}
86+
pointerEvents={'none'}
87+
/>
88+
:
89+
<LinearGradient
90+
start={{ x: 0, y: 0 }} end={{ x: 0, y: 1 }}
91+
style={{ position: 'absolute', bottom: 0, width: '100%', height: 20 }}
92+
colors={this.props.fadeColors}
93+
pointerEvents={'none'}
94+
/>)
95+
}
96+
97+
render() {
98+
const endFadeEnable = this.isEndFadeAllowed();
99+
return (
100+
<View style={[styles.container, { flexDirection: this.props.isHorizontal ? "row" : "column" }]}
101+
onLayout={this._onLayout.bind(this)}>
102+
<ScrollView
103+
{...this.props}
104+
style={[styles.scrollViewStyle, this.props.scrollViewStyle]}
105+
horizontal={this.props.isHorizontal}
106+
onContentSizeChange={this.onContentSizeChange}
107+
scrollEventThrottle={16}
108+
onScroll={this.onScrolled}
109+
>
110+
{this.props.children}
111+
</ScrollView>
112+
{(this.state.allowStartFade) && this.getStartFaade()}
113+
{endFadeEnable && this.getEndFade()}
114+
</View>
115+
)
116+
}
117+
118+
119+
}
120+
121+
const styles = StyleSheet.create({
122+
container: {
123+
flex: 1,
124+
flexDirection: "column"
125+
},
126+
scrollViewStyle: {
127+
flex: 1
128+
}
129+
});
130+
RNFadedScrollView.propTypes = {
131+
isHorizontal: PropTypes.bool,
132+
allowStartFade: PropTypes.bool,
133+
allowEndFade: PropTypes.bool,
134+
fadeSize: PropTypes.number,
135+
fadeColors: PropTypes.array,
136+
}
137+
RNFadedScrollView.defaultProps = {
138+
isHorizontal: false,
139+
allowStartFade: false,
140+
allowEndFade: true,
141+
fadeSize: 20,
142+
fadeColors: defaultFadeColors
143+
}

0 commit comments

Comments
 (0)