diff --git a/packages/react-bootstrap-table2-example/examples/column-filter/select-filter-preserve-option-order.js b/packages/react-bootstrap-table2-example/examples/column-filter/select-filter-preserve-option-order.js new file mode 100644 index 0000000..f7a0fca --- /dev/null +++ b/packages/react-bootstrap-table2-example/examples/column-filter/select-filter-preserve-option-order.js @@ -0,0 +1,70 @@ +/* eslint max-len: 0 */ +import React from 'react'; +import BootstrapTable from 'react-bootstrap-table-next'; +import filterFactory, { selectFilter } from 'react-bootstrap-table2-filter'; +import Code from 'components/common/code-block'; +import { productsQualityGenerator } from 'utils/common'; + +const products = productsQualityGenerator(6); + +const selectOptions = [ + { label: 0, value: 'good' }, + { label: 1, value: 'Bad' }, + { label: 2, value: 'unknown' } +]; + +const columns = [{ + dataField: 'id', + text: 'Product ID' +}, { + dataField: 'name', + text: 'Product Name' +}, { + dataField: 'quality', + text: 'Product Quailty', + formatter: cell => selectOptions.find(opt => opt.label === cell).value, + filter: selectFilter({ + options: selectOptions + }) +}]; + +const sourceCode = `\ +import BootstrapTable from 'react-bootstrap-table-next'; +import filterFactory, { selectFilter } from 'react-bootstrap-table2-filter'; + +const selectOptions = [ + { label: 0, value: 'good' }, + { label: 1, value: 'Bad' }, + { label: 2, value: 'unknown' } +]; + +const columns = [{ + dataField: 'id', + text: 'Product ID' +}, { + dataField: 'name', + text: 'Product Name' +}, { + dataField: 'quality', + text: 'Product Quailty', + formatter: cell => selectOptions.find(opt => opt.label === cell).value, + filter: selectFilter({ + options: selectOptions + }) +}]; + + +`; + +export default () => ( +
+

selectFilter.options accept an Array and we keep that order when rendering the options

+ + { sourceCode } +
+); diff --git a/packages/react-bootstrap-table2-example/stories/index.js b/packages/react-bootstrap-table2-example/stories/index.js index fd04751..2757280 100644 --- a/packages/react-bootstrap-table2-example/stories/index.js +++ b/packages/react-bootstrap-table2-example/stories/index.js @@ -55,6 +55,7 @@ import CustomFilterValue from 'examples/column-filter/custom-filter-value'; import SelectFilter from 'examples/column-filter/select-filter'; import SelectFilterWithDefaultValue from 'examples/column-filter/select-filter-default-value'; import SelectFilterComparator from 'examples/column-filter/select-filter-like-comparator'; +import SelectFilterWithPreservedOptionsOrder from 'examples/column-filter/select-filter-preserve-option-order'; import CustomSelectFilter from 'examples/column-filter/custom-select-filter'; import MultiSelectFilter from 'examples/column-filter/multi-select-filter'; import MultiSelectFilterDefaultValue from 'examples/column-filter/multi-select-filter-default-value'; @@ -263,6 +264,7 @@ storiesOf('Column Filter', module) .add('Programmatically Multi Select Filter', () => ) .add('Custom Filter', () => ) .add('Advance Custom Filter', () => ) + .add('Preserved Option Order on Select Filter', () => ) .add('Clear All Filters', () => ); storiesOf('Work on Rows', module) diff --git a/packages/react-bootstrap-table2-filter/README.md b/packages/react-bootstrap-table2-filter/README.md index 8369efd..f73b962 100644 --- a/packages/react-bootstrap-table2-filter/README.md +++ b/packages/react-bootstrap-table2-filter/README.md @@ -115,6 +115,27 @@ const qualityFilter = selectFilter({ // omit... ``` +> Note, the selectOptions can be an array also: + +```js +const selectOptions = [ + { label: 0, value: 'good' }, + { label: 1, value: 'Bad' }, + { label: 2, value: 'unknown' } +]; +const columns = [ + ..., { + dataField: 'quality', + text: 'Product Quailty', + formatter: cell => selectOptions.find(opt => opt.label === cell).value, + filter: selectFilter({ + options: selectOptions + }) +}]; +``` + +The benifit is `react-bootstrap-table2` will render the select options by the order of array. + ## MultiSelect Filter A quick example: diff --git a/packages/react-bootstrap-table2-filter/src/components/select.js b/packages/react-bootstrap-table2-filter/src/components/select.js index e505138..a30e691 100644 --- a/packages/react-bootstrap-table2-filter/src/components/select.js +++ b/packages/react-bootstrap-table2-filter/src/components/select.js @@ -7,6 +7,14 @@ import { LIKE, EQ } from '../comparison'; import { FILTER_TYPE } from '../const'; function optionsEquals(currOpts, prevOpts) { + if (Array.isArray(currOpts)) { + for (let i = 0; i < currOpts.length; i += 1) { + if (currOpts[i].label !== prevOpts[i].label) { + return false; + } + } + return currOpts.length === prevOpts.length; + } const keys = Object.keys(currOpts); for (let i = 0; i < keys.length; i += 1) { if (currOpts[keys[i]] !== prevOpts[keys[i]]) { @@ -16,11 +24,21 @@ function optionsEquals(currOpts, prevOpts) { return Object.keys(currOpts).length === Object.keys(prevOpts).length; } +function getOptionValue(options, key) { + if (Array.isArray(options)) { + const result = options + .filter(({ label }) => label === key) + .map(({ value }) => value); + return result[0]; + } + return options[key]; +} + class SelectFilter extends Component { constructor(props) { super(props); this.filter = this.filter.bind(this); - const isSelected = props.options[props.defaultValue] !== undefined; + const isSelected = getOptionValue(props.options, props.defaultValue) !== undefined; this.state = { isSelected }; } @@ -66,9 +84,14 @@ class SelectFilter extends Component { )); } - Object.keys(options).forEach(key => - optionTags.push() - ); + if (Array.isArray(options)) { + options.forEach(({ value, label }) => + optionTags.push()); + } else { + Object.keys(options).forEach(key => + optionTags.push() + ); + } return optionTags; } @@ -128,7 +151,7 @@ class SelectFilter extends Component { SelectFilter.propTypes = { onFilter: PropTypes.func.isRequired, column: PropTypes.object.isRequired, - options: PropTypes.object.isRequired, + options: PropTypes.oneOfType([PropTypes.object, PropTypes.array]).isRequired, comparator: PropTypes.oneOf([LIKE, EQ]), placeholder: PropTypes.string, style: PropTypes.object,