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

Already on GitHub? Sign in to your account

Adding drag-to-reorder rows support to TUITableView, fixes to section header support #36

wants to merge 29 commits into


None yet
2 participants

bww commented Aug 4, 2011

Drag-to-reorder rows support is added to TUITableView in a manner similar to UITableView. To use this functionality, a table's data source should implement the new methods:

- (BOOL)tableView:(TUITableView *)tableView canMoveRowAtIndexPath:(TUIFastIndexPath *)indexPath;
- (void)tableView:(TUITableView *)tableView moveRowAtIndexPath:(TUIFastIndexPath *)fromIndexPath toIndexPath:(TUIFastIndexPath *)toIndexPath;

...and optionally, to constrain where rows may be moved, the table's delegate can implement:

- (TUIFastIndexPath *)tableView:(TUITableView *)tableView targetIndexPathForMoveFromRowAtIndexPath:(TUIFastIndexPath *)fromPath toProposedIndexPath:(TUIFastIndexPath *)proposedPath;

I've added a new category to TUITableView (Cell) which exposes some "internal" methods of the table view that cells need to have access to due to the close relationship between these classes. Specifically, cells can use these methods to forward mouse events to the table so that the table can do something with them (in this case, handle dragging).

In order to allow a table to automatically scroll content into view when a cell is dragged to the top or bottom of the viewport, I've made some small changes to TUIScrollView as well. Specifically, the following methods are added which provide this kind of scrolling:

- (void)beginContinuousScrollForDragAtPoint:(CGPoint)dragLocation animated:(BOOL)animated;
- (void)endContinuousScrollAnimated:(BOOL)animated;

...via the addition of the new animation mode AnimationModeScrollContinuous. Due to the highly specific nature of this kind of scrolling, maybe these methods should be private, but I didn't want to reorganize TUIScrollView too much.

The example project has also been updated to demonstrate drag-to-reorder, however, since there isn't a "real" model and cells are just assigned a label corresponding to their index, when the moved cell is dropped, the table will revert immediately back to its original state. This is because visible cells are laid out again immediately after the operation completes and get re-assigned their index-based label.

Other miscellaneous updates:

  • Adding table will/did reload delegate methods
  • Fixes incorrect geometry in TUITableView -indexesOfSectionsInRect:
  • Adding -rectForSection: method in TUITableView
  • Adding index path enumeration methods to TUITableView

Brian William Wolter added some commits Jul 26, 2011

- More drag-to-reorder updates
- Fixing an issue with table header views which could cause views to get out of sync with section info
- Adding index path enumeration methods to TUITableView
- Updating drag-to-reorder support to use the above
Merge remote-tracking branch 'upstream/master'
- Adding "continuous scrolling" support to TUIScrollView, which is us…
…ed to scroll new content into view during a table drag-to-reorder operation when the cell is dragged near the top or bottom of the viewport

- Updating cell reuse to work correctly with drag-to-reorder while scrolling
- Cleaning up the TUITableView+Cell category a bit

atebits commented Aug 5, 2011

Wow, awesome! Will play for a bit.


bww commented Aug 5, 2011

One thing you might want to take a look at. Originally, I had the table fully reload after the drop completed to make sure the view and model were consistent. This worked fine in the project I'm working on, but caused problems in the example project: after the first drop the view would clear and scroll back to the bottom for some reason; subsequent reorders would work fine, though.

I changed the full reload to essentially a relayout, but I'm not sure about the correctness of this. I think a full reload is perhaps better—in part because the new table will/did reload delegate methods can handle selection changes after the row order changes and this can be done easily since it's invoked after the drop animation completes.

I'm sure you'll have a better sense of what needs to happen there to make sure everything's in a consistent state, though.

Here's the relevant bit:


atebits commented Aug 5, 2011

I full reload would be cleaner. I recently merged in #31 -- it's off by default, perhaps that (if we change it to be the default behavior) would fix the problem?


bww commented Aug 9, 2011

I tried merging that in and setting maintainContentOffsetAfterReload, but it didn't seem to make a difference.


atebits commented Aug 12, 2011

This is fucking awesome btw. Conflicts a bit with the new sticky section headers, but I'd rather merge and fix as we go.


atebits commented Aug 12, 2011

Squash merged in (there were a lot of commits).

@atebits atebits closed this Aug 12, 2011

adib pushed a commit to adib/twui that referenced this pull request Aug 7, 2012

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment