Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add public methods for animation #641

Merged
merged 4 commits into from
Apr 6, 2017
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
29 changes: 29 additions & 0 deletions source/Grid/Grid.jest.js
Original file line number Diff line number Diff line change
Expand Up @@ -366,6 +366,35 @@ describe('Grid', () => {
expect(grid.state.scrollTop).toEqual(900)
})

it('should support scrollToPosition() public method', () => {
const grid = render(getMarkup())
expect(grid.state.scrollLeft).toEqual(0)
expect(grid.state.scrollTop).toEqual(0)

grid.scrollToPosition({
scrollLeft: 50,
scrollTop: 50
})
expect(grid.state.scrollLeft).toEqual(50)
expect(grid.state.scrollTop).toEqual(50)
})

it('should support getOffsetForCell() public method', () => {
const grid = render(getMarkup())
const { scrollLeft, scrollTop } = grid.getOffsetForCell({
columnIndex: 24,
rowIndex: 49
})
// 100 columns * 50 item width = 5,000 total item width
// 4 columns can be visible at a time and :scrollLeft is initially 0,
// So the minimum amount of scrolling leaves the 25th item at the right (just scrolled into view).
expect(scrollLeft).toEqual(1050)
// 100 rows * 20 item height = 2,000 total item height
// 5 rows can be visible at a time and :scrollTop is initially 0,
// So the minimum amount of scrolling leaves the 50th item at the bottom (just scrolled into view).
expect(scrollTop).toEqual(900)
})

// See issue #565
it('should update scroll position to account for changed cell sizes within a function prop wrapper', () => {
let rowHeight = 20
Expand Down
74 changes: 58 additions & 16 deletions source/Grid/Grid.js
Original file line number Diff line number Diff line change
Expand Up @@ -264,8 +264,6 @@ export default class Grid extends PureComponent {
this._invokeOnGridRenderedHelper = this._invokeOnGridRenderedHelper.bind(this)
this._onScroll = this._onScroll.bind(this)
this._setScrollingContainerRef = this._setScrollingContainerRef.bind(this)
this._updateScrollLeftForScrollToColumn = this._updateScrollLeftForScrollToColumn.bind(this)
this._updateScrollTopForScrollToRow = this._updateScrollTopForScrollToRow.bind(this)

this._columnWidthGetter = this._wrapSizeGetter(props.columnWidth)
this._rowHeightGetter = this._wrapSizeGetter(props.rowHeight)
Expand Down Expand Up @@ -381,6 +379,40 @@ export default class Grid extends PureComponent {
})
}

/**
* Ensure offset position is visible
* Useful for animating position changes
*/
scrollToPosition ({
scrollLeft,
scrollTop
} = {}) {
this._setScrollPosition({ scrollLeft, scrollTop })
}

/**
* Gets offsets for a given cell and alignment
*/
getOffsetForCell ({
columnIndex,
rowIndex,
scrollToAlignment = this.props.scrollToAlignment
} = {}) {
const scrollToColumn = columnIndex >= 0 ? columnIndex : this.props.scrollToColumn
const scrollToRow = rowIndex >= 0 ? rowIndex : this.props.scrollToRow
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Tiny nit: You could set the default columnIndex and rowIndex values in the same way as you do the scrollToAlignment for consistency.

const offsetProps = {
...this.props,
scrollToColumn,
scrollToRow,
scrollToAlignment
}

return {
scrollLeft: this._getCalculatedScrollLeft(offsetProps),
scrollTop: this._getCalculatedScrollTop(offsetProps)
}
}

componentDidMount () {
const { getScrollbarSize, scrollLeft, scrollToColumn, scrollTop, scrollToRow } = this.props

Expand Down Expand Up @@ -999,7 +1031,7 @@ export default class Grid extends PureComponent {
return this._wrapPropertyGetter(size)
}

_updateScrollLeftForScrollToColumn (props = this.props, state = this.state) {
_getCalculatedScrollLeft (props = this.props, state = this.state) {
const { columnCount, height, scrollToAlignment, scrollToColumn, width } = props
const { scrollLeft } = state

Expand All @@ -1008,22 +1040,27 @@ export default class Grid extends PureComponent {
const totalRowsHeight = this._rowSizeAndPositionManager.getTotalSize()
const scrollBarSize = totalRowsHeight > height ? this._scrollbarSize : 0

const calculatedScrollLeft = this._columnSizeAndPositionManager.getUpdatedOffsetForIndex({
return this._columnSizeAndPositionManager.getUpdatedOffsetForIndex({
align: scrollToAlignment,
containerSize: width - scrollBarSize,
currentOffset: scrollLeft,
targetIndex
})
}
}

if (scrollLeft !== calculatedScrollLeft) {
this._setScrollPosition({
scrollLeft: calculatedScrollLeft
})
}
_updateScrollLeftForScrollToColumn (props = this.props, state = this.state) {
const { scrollLeft } = state
const calculatedScrollLeft = this._getCalculatedScrollLeft(props, state)

if (calculatedScrollLeft >= 0 && scrollLeft !== calculatedScrollLeft) {
this._setScrollPosition({
scrollLeft: calculatedScrollLeft
})
}
}

_updateScrollTopForScrollToRow (props = this.props, state = this.state) {
_getCalculatedScrollTop (props = this.props, state = this.state) {
const { height, rowCount, scrollToAlignment, scrollToRow, width } = props
const { scrollTop } = state

Expand All @@ -1032,18 +1069,23 @@ export default class Grid extends PureComponent {
const totalColumnsWidth = this._columnSizeAndPositionManager.getTotalSize()
const scrollBarSize = totalColumnsWidth > width ? this._scrollbarSize : 0

const calculatedScrollTop = this._rowSizeAndPositionManager.getUpdatedOffsetForIndex({
return this._rowSizeAndPositionManager.getUpdatedOffsetForIndex({
align: scrollToAlignment,
containerSize: height - scrollBarSize,
currentOffset: scrollTop,
targetIndex
})
}
}

if (scrollTop !== calculatedScrollTop) {
this._setScrollPosition({
scrollTop: calculatedScrollTop
})
}
_updateScrollTopForScrollToRow (props = this.props, state = this.state) {
const { scrollTop } = state
const calculatedScrollTop = this._getCalculatedScrollTop(props, state)

if (calculatedScrollTop >= 0 && scrollTop !== calculatedScrollTop) {
this._setScrollPosition({
scrollTop: calculatedScrollTop
})
}
}

Expand Down
18 changes: 18 additions & 0 deletions source/List/List.js
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,19 @@ export default class List extends PureComponent {
})
}

/** See Grid#getOffsetForCell */
getOffsetForRow ({
rowIndex,
scrollToAlignment
}) {
const { scrollTop } = this.Grid.getOffsetForCell({
columnIndex: 0,
rowIndex,
scrollToAlignment
})
return scrollTop
}

/** See Grid#scrollToCell */
scrollToRow (index = 0) {
this.Grid.scrollToCell({
Expand All @@ -130,6 +143,11 @@ export default class List extends PureComponent {
})
}

/** See Grid#scrollToPosition */
scrollToPosition (scrollTop = 0) {
this.Grid.scrollToPosition({ scrollTop })
}

render () {
const {
className,
Expand Down