Skip to content

Swift library that allows reordering of UITableView cells via long press gesture.

License

Notifications You must be signed in to change notification settings

sivu22/LongPressReorder

Repository files navigation

LongPressReorder

Swift Version License Platform

LongPressReorder adresses a common use case when working with tables on an iOS device: the posibility to reorder table rows using a long press gesture, similar to drag and drop gesture. Lightweight and easy to use, LongPressReorder works with any view controller that manages an UITableView. Autoscroll and tables with one or multiple sections are supported.

This Swift module is based on the well-known article posted on raywenderlich.com:

Cookbook: Moving Table View Cells with a Long Press Gesture

Example

To run the example project, clone the repo, and run pod install from the Example directory first.

UITableViewController with fixed first cell

LongPressReorder

UITableViewController with multiple sections

LongPressReorderMultiple

Usage

Because of the way Swift handles protocols and extensions, it's extremely hard or next to impossible to add the desired behaviour directly on UIViewController or UITableView. Using the objc_setAssociatedObject hack is not an elegant Swift solution, therefore this module uses a wrapper of UITableView to achieve flexibility and cover all use cases.

Creation

First of all, import LongPressReorder into your view controller and declare a new variable

var reorderTableView: LongPressReorderTableView!

Assuming we are working with a UITableViewController, create the object in onViewDidLoad()

override func viewDidLoad() {
    super.viewDidLoad()
        
    reorderTableView = LongPressReorderTableView(tableView)
}

In the case of a regular UIViewController with an UITableView inside, use the specific table outlet

reorderTableView = LongPressReorderTableView(yourTableViewOutlet)

The only thing left now is to enable it with

reorderTableView.enableLongPressReorder()

That was all. All the cells inside the UITableView can now be reordered using the long press gesture. To disable reordering of cells, simply call

reorderTableView.disableLongPressReorder()

You may want to also disable the table's Selection on the cell for a better visual effect.

Interaction

Use the delegate member to enable interaction with the LongPressReorderTableView. onViewDidLoad() usually looks like this

reorderTableView = LongPressReorderTableView(tableView)
reorderTableView.delegate = self
reorderTableView.enableLongPressReorder()

Reordering of cells is now purely visual. If you want to also change the model behind the table, LongPressReorder offers the following optional functions which can be grouped in a view controller extension

extension SpecificViewController {
    
    override func positionChanged(currentIndex: IndexPath, newIndex: IndexPath) {
        // currentIndex and newIndex rows are swapped, implement accordingly
    }
    
    override func reorderFinished(initialIndex: IndexPath, finalIndex: IndexPath) {
        // Gesture is finished and cell is back inside the table at finalIndex position
    }
}

The module offers additional functions, which can be overridden in order to specify which cells cannot be moved or cannot lose their position inside the table

extension SpecificViewController {
    
    override func startReorderingRow(atIndex indexPath: IndexPath) -> Bool {
        // All table cells except the first one can be reordered
        if indexPath.row > 0 {
            return true
        }
        
        // First cell will not respond to the long press gesture
        return false
    }
    
    override func allowChangingRow(atIndex indexPath: IndexPath) -> Bool {
        // All table cells except the first one can be replaced with the selected cell
        if indexPath.row > 0 {
            return true
        }
        
        // First cell will not lose its position and therefore no other cell can replace it
        return false
    }
}

Customization

When there are more cells in the table that the ones that can be displayed on the device screen at a certain moment, autoscroll can be used when reordering the cells. Autoscroll is turned off by default.

reorderTableView = LongPressReorderTableView(elementsTableView, scrollBehaviour: .early)

After pressing on the desired cell, the cell will pop out of the table and will be ready to be dragged around. This pop out effect can be customized using 4 different scales for the selected cell: none, small, medium and big (default is medium).

reorderTableView = LongPressReorderTableView(elementsTableView, selectedRowScale: SelectedRowScale.small)

Requirements

  • Swift 4.1
  • iOS 9.0 +
  • XCode 9.4+

Installation

CocoaPods

LongPressReorder is available through CocoaPods. To install it, simply add the following line to your Podfile:

pod "LongPressReorder"

or

pod 'LongPressReorder', '~> 1.2.1'

Manually

Simply copy LongPressReorder.swift to your project and you're ready to go.

Author

Cristian Sava, cristianzsava@gmail.com

License

LongPressReorder is available under the MIT license. See the LICENSE file for more info.

About

Swift library that allows reordering of UITableView cells via long press gesture.

Resources

License

Stars

Watchers

Forks

Packages

No packages published