diff --git a/SuperGridSectionList.js b/SuperGridSectionList.js new file mode 100644 index 0000000..09e1188 --- /dev/null +++ b/SuperGridSectionList.js @@ -0,0 +1,151 @@ +/* eslint react/no-array-index-key: 0 */ +import React, { Component } from 'react'; +import PropTypes from 'prop-types'; +import { View, Dimensions, ViewPropTypes, SectionList } from 'react-native'; +import { chunkArray } from './utils'; + +class SuperGridSectionList extends Component { + constructor(props) { + super(props); + this.renderRow = this.renderRow.bind(this); + this.onLayout = this.onLayout.bind(this); + this.getDimensions = this.getDimensions.bind(this); + this.state = this.getDimensions(); + } + + componentWillReceiveProps(nextProps) { + if (nextProps.itemDimension !== this.props.itemDimension) { + this.setState({ + ...this.getDimensions(this.state.totalDimension, nextProps.itemDimension), + }); + } + } + + onLayout(e) { + const { staticDimension } = this.props; + if (!staticDimension) { + const { width, height } = e.nativeEvent.layout || {}; + + this.setState({ + ...this.getDimensions(width), + }); + } + } + + getDimensions(lvDimension, itemDim) { + const { itemWidth, spacing, fixed, staticDimension } = this.props; + let itemDimension = itemDim || this.props.itemDimension; + if (itemWidth) { + itemDimension = itemWidth; + console.warn('React Native Super Grid - property "itemWidth" is depreciated. Use "itemDimension" instead.'); + } + + const dimension = 'width'; + const totalDimension = lvDimension || staticDimension || Dimensions.get('window')[dimension]; + const itemTotalDimension = itemDimension + spacing; + const availableDimension = totalDimension - spacing; // One spacing extra + const itemsPerRow = Math.floor(availableDimension / itemTotalDimension); + const containerDimension = availableDimension / itemsPerRow; + + return { + totalDimension, + itemDimension, + spacing, + itemsPerRow, + containerDimension, + fixed, + }; + } + + renderHorizontalRow(data) { + const { itemDimension, containerDimension, spacing, fixed } = this.state; + const rowStyle = { + flexDirection: 'row', + paddingLeft: spacing, + paddingBottom: spacing, + }; + if (data.isLast) { + rowStyle.marginBottom = spacing; + } + const itemContainerStyle = { + flexDirection: 'column', + justifyContent: 'center', + width: containerDimension, + paddingRight: spacing, + }; + let itemStyle = {}; + if (fixed) { + itemStyle = { + width: itemDimension, + alignSelf: 'center', + }; + } + + return ( + + {(data || []).map((item, i) => ( + + + {this.props.renderItem(item, i)} + + + ))} + + ); + } + + renderRow({ item }) { // item is array of items which go in one row + return this.renderHorizontalRow(item); + } + + render() { + const { items, style, spacing, fixed, itemDimension, renderItem, renderSectionHeader, ...props } = this.props; + const { itemsPerRow } = this.state; + + const chunked = chunkArray(items, itemsPerRow); + const rows = chunked.map((r, i) => { + const keydRow = [...r]; + keydRow.key = `row_${i}`; + keydRow.isLast = (chunked.length - 1 === i); + return keydRow; + }); + + return ( + + ); + } +} + +SuperGrid.propTypes = { + renderItem: PropTypes.func.isRequired, + items: PropTypes.arrayOf(PropTypes.any).isRequired, + itemDimension: PropTypes.number, + itemWidth: PropTypes.number, // for backward compatibility + fixed: PropTypes.bool, + spacing: PropTypes.number, + style: ViewPropTypes.style, + staticDimension: PropTypes.number, + horizontal: PropTypes.bool, +}; + +SuperGrid.defaultProps = { + fixed: false, + itemDimension: 120, + itemWidth: null, + spacing: 10, + style: {}, + staticDimension: undefined, + horizontal: false, +}; + +export default SuperGridSectionList; diff --git a/index.js b/index.js index 48bbbc7..ededc1c 100644 --- a/index.js +++ b/index.js @@ -3,6 +3,7 @@ import React, { Component } from 'react'; import PropTypes from 'prop-types'; import { View, Dimensions, ViewPropTypes, FlatList } from 'react-native'; import { chunkArray } from './utils'; +import SuperGridSectionList from './GridSectionList' class SuperGrid extends Component { constructor(props) { @@ -191,3 +192,4 @@ SuperGrid.defaultProps = { }; export default SuperGrid; +export {SuperGridSectionList}; diff --git a/package.json b/package.json index 0398ea1..4bef274 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "react-native-super-grid", - "version": "2.1.0", + "version": "2.2.0", "description": "Responsive Grid View for React Native", "main": "index.js", "types": "index.d.ts",