Skip to content

Commit

Permalink
Merge pull request #35 from toptal/picas-36-initial-components-pagina…
Browse files Browse the repository at this point in the history
…tion

Add Pagination component
  • Loading branch information
bytasv authored Jan 25, 2019
2 parents c1f0b9d + f48eb18 commit 38c72bf
Show file tree
Hide file tree
Showing 10 changed files with 523 additions and 0 deletions.
2 changes: 2 additions & 0 deletions components/ButtonGroup/styles.js
Original file line number Diff line number Diff line change
@@ -1,5 +1,7 @@
export default {
root: {
display: 'inline-block',

'& Button': {
margin: '0',
'&:first-child': {
Expand Down
67 changes: 67 additions & 0 deletions components/Pagination/Pagination.example.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
/* global alert */

import React from 'react'
import { storiesOf } from '@storybook/react'

import StoryTeller from '../../.storybook/StoryTeller'
import Pagination from './'
import Spacer from '../Spacer'

const stories = storiesOf('Pagination', module)

const teller = new StoryTeller(
'Pagination',
'Component which allows navigating long data lists'
)
const chapter = teller.addChapter()

chapter
.addSection('Pagination', 'variations', () => (
<div>
<Pagination
activePage={1}
onPageChange={page => {
alert('Page change...' + page)
}}
totalPages={10}
/>
<Spacer bottom={2} />
<Pagination
activePage={9}
onPageChange={page => {
alert('Page change...' + page)
}}
totalPages={10}
/>
<Spacer bottom={2} />
<Pagination
activePage={5}
onPageChange={page => {
alert('Page change...' + page)
}}
totalPages={10}
/>
<Spacer bottom={2} />
<Pagination
activePage={10}
onPageChange={page => {
alert('Page change...' + page)
}}
totalPages={10}
/>
</div>
))
.addSection('Pagination', 'disabled', () => (
<div>
<Pagination
activePage={1}
disabled
onPageChange={page => {
alert('Page change...' + page)
}}
totalPages={10}
/>
</div>
))

stories.addWithChapters('Pagination', teller.toStory())
125 changes: 125 additions & 0 deletions components/Pagination/Pagination.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,125 @@
import React from 'react'
import PropTypes from 'prop-types'

import Button from '../Button'
import { getRange, ELLIPSIS, FIRST_PAGE, ONE_PAGE } from './range-utils'

const NAVIGATION = {
FIRST: 'FIRST',
LAST: 'LAST',
PREVIOUS: 'PREVIOUS',
NEXT: 'NEXT'
}
const SIBLING_COUNT = 3

class Pagination extends React.PureComponent {
static propTypes = {
activePage: PropTypes.number.isRequired,
disabled: PropTypes.bool,
onPageChange: PropTypes.func.isRequired,
totalPages: PropTypes.number.isRequired
}

static defaultProps = {
disabled: false
}

handleChange (navigation) {
const { onPageChange, totalPages, activePage } = this.props
let page

switch (navigation) {
case NAVIGATION.FIRST:
page = FIRST_PAGE
break
case NAVIGATION.PREVIOUS:
page = activePage - ONE_PAGE
break
case NAVIGATION.NEXT:
page = activePage + ONE_PAGE
break
case NAVIGATION.LAST:
page = totalPages
break
default:
page = navigation
}

onPageChange(page)
}

isFirstActive = activePage => activePage === 1
isLastActive = (activePage, totalPages) => activePage === totalPages

renderRange () {
const { totalPages, activePage, disabled } = this.props

const range = getRange({
activePage,
totalPages,
siblingCount: SIBLING_COUNT
})

return range.map((pageItemLabel, index) => {
return (
<Button
color={activePage === pageItemLabel ? 'primary' : undefined}
disabled={pageItemLabel === ELLIPSIS || disabled}
key={pageItemLabel + index} // eslint-disable-line react/no-array-index-key
onClick={() => this.handleChange(pageItemLabel)}
variant={activePage === pageItemLabel ? 'contained' : 'outlined'}
>
{pageItemLabel}
</Button>
)
})
}

render () {
const { activePage, totalPages, disabled } = this.props
const isFirstActive = this.isFirstActive(activePage)
const isLastActive = this.isLastActive(activePage, totalPages)

return (
<Button.Group>
<Button
color='default'
disabled={isFirstActive || disabled}
onClick={() => this.handleChange(NAVIGATION.FIRST)}
variant='outlined'
>
«
</Button>
<Button
color='default'
disabled={isFirstActive || disabled}
onClick={() => this.handleChange(NAVIGATION.PREVIOUS)}
variant='outlined'
>
</Button>

{this.renderRange()}

<Button
color='default'
disabled={isLastActive || disabled}
onClick={() => this.handleChange(NAVIGATION.NEXT)}
variant='outlined'
>
</Button>
<Button
color='default'
disabled={isLastActive || disabled}
onClick={() => this.handleChange(NAVIGATION.LAST)}
variant='outlined'
>
»
</Button>
</Button.Group>
)
}
}

export default Pagination
187 changes: 187 additions & 0 deletions components/Pagination/__snapshots__/test.jsx.snap
Original file line number Diff line number Diff line change
@@ -0,0 +1,187 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP

exports[`renders default 1`] = `
<div>
<div
class="ButtonGroup-root"
>
<button
class="MuiButtonBase-root MuiButton-root Button-root MuiButton-outlined Button-outlined"
tabindex="0"
type="button"
>
<span
class="MuiButton-label"
>
<div
class="Button-children"
>
«
</div>
</span>
<span
class="MuiTouchRipple-root"
/>
</button>
<button
class="MuiButtonBase-root MuiButton-root Button-root MuiButton-outlined Button-outlined"
tabindex="0"
type="button"
>
<span
class="MuiButton-label"
>
<div
class="Button-children"
>
</div>
</span>
<span
class="MuiTouchRipple-root"
/>
</button>
<button
class="MuiButtonBase-root MuiButton-root Button-containedPrimary Button-root MuiButton-contained Button-contained MuiButton-containedPrimary Button-containedPrimary MuiButton-raised MuiButton-raisedPrimary"
tabindex="0"
type="button"
>
<span
class="MuiButton-label"
>
<div
class="Button-children"
/>
</span>
<span
class="MuiTouchRipple-root"
/>
</button>
<button
class="MuiButtonBase-root MuiButtonBase-disabled MuiButton-root Button-root MuiButton-outlined Button-outlined MuiButton-disabled"
disabled=""
tabindex="-1"
type="button"
>
<span
class="MuiButton-label"
>
<div
class="Button-children"
>
</div>
</span>
</button>
<button
class="MuiButtonBase-root MuiButtonBase-disabled MuiButton-root Button-root MuiButton-outlined Button-outlined MuiButton-disabled"
disabled=""
tabindex="-1"
type="button"
>
<span
class="MuiButton-label"
>
<div
class="Button-children"
>
»
</div>
</span>
</button>
</div>
</div>
`;

exports[`renders disabled 1`] = `
<div>
<div
class="ButtonGroup-root"
>
<button
class="MuiButtonBase-root MuiButton-root Button-root MuiButton-outlined Button-outlined"
tabindex="0"
type="button"
>
<span
class="MuiButton-label"
>
<div
class="Button-children"
>
«
</div>
</span>
<span
class="MuiTouchRipple-root"
/>
</button>
<button
class="MuiButtonBase-root MuiButton-root Button-root MuiButton-outlined Button-outlined"
tabindex="0"
type="button"
>
<span
class="MuiButton-label"
>
<div
class="Button-children"
>
</div>
</span>
<span
class="MuiTouchRipple-root"
/>
</button>
<button
class="MuiButtonBase-root MuiButton-root Button-containedPrimary Button-root MuiButton-contained Button-contained MuiButton-containedPrimary Button-containedPrimary MuiButton-raised MuiButton-raisedPrimary"
tabindex="0"
type="button"
>
<span
class="MuiButton-label"
>
<div
class="Button-children"
/>
</span>
<span
class="MuiTouchRipple-root"
/>
</button>
<button
class="MuiButtonBase-root MuiButtonBase-disabled MuiButton-root Button-root MuiButton-outlined Button-outlined MuiButton-disabled"
disabled=""
tabindex="-1"
type="button"
>
<span
class="MuiButton-label"
>
<div
class="Button-children"
>
</div>
</span>
</button>
<button
class="MuiButtonBase-root MuiButtonBase-disabled MuiButton-root Button-root MuiButton-outlined Button-outlined MuiButton-disabled"
disabled=""
tabindex="-1"
type="button"
>
<span
class="MuiButton-label"
>
<div
class="Button-children"
>
»
</div>
</span>
</button>
</div>
</div>
`;
1 change: 1 addition & 0 deletions components/Pagination/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export { default } from './Pagination'
1 change: 1 addition & 0 deletions components/Pagination/range-utils/index.js
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export { getRange, ELLIPSIS, FIRST_PAGE, ONE_PAGE } from './range-utils'
Loading

0 comments on commit 38c72bf

Please sign in to comment.