1. 程式人生 > 其它 >iOS長按手勢列表拖拽功能實現

iOS長按手勢列表拖拽功能實現

專案開發中遇到拖拽功能的需求,具體要求是在編輯狀態下,首頁底部選單項可以拖動位置,便於位置切換。遇到問題後的初步想法是新增拖拽手勢,拖拽到某個位置,判斷拖拽cell的中心點是否在另一個cell內,這樣處理比較複雜,需要自己計算座標。後經一同事推薦,找到了一個更簡單的解決方案,程式碼如下。

//1、給cell新增長按手勢,在編輯狀態下可用,非編輯狀態下不可用

-(UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath{

CCNewMoreMenuCell *cell = [collectionView dequeueReusableCellWithReuseIdentifier:CCNewMoreMenuCellIdentifier forIndexPath:indexPath];

CCHighSeasPoolManager *seas=[CCHighSeasPoolManager sharedManager];

//新增長按手勢

UILongPressGestureRecognizer *longPressGesture = [[UILongPressGestureRecognizer alloc] initWithTarget:self action:@selector(longPressAction:)];

[cell addGestureRecognizer:longPressGesture];

if (seas.isEdit) {

[cell.btnDelete setHidden:NO];

[cell.imageDelete setHidden:NO];

[cell.btnMenu setHidden:YES];

longPressGesture.cancelsTouchesInView=YES;

//編輯狀態開啟手勢

longPressGesture.enabled=YES;

}else{

[cell.btnDelete setHidden:YES];

[cell.imageDelete setHidden:YES];

[cell.btnMenu setHidden:NO];

//非編輯狀態禁用手勢

longPressGesture.enabled=NO;

}

[cell.btnMenu addTarget:self action:@selector(btnMenuAction:) forControlEvents:UIControlEventTouchDown];

cell.btnMenu.btnRow=indexPath.item;

[cell.btnDelete addTarget:self action:@selector(btnDeleteAction:) forControlEvents:UIControlEventTouchDown];

cell.btnDelete.btnRow=indexPath.item;

CCMoreListModel *model = [seas.dataList objectAtIndex:indexPath.item];

cell.headerModel=model;

return cell;

}

//2、新增長按手勢處理方法

- (void)longPressAction:(UILongPressGestureRecognizer *)longPress {

//獲取此次點選的座標,根據座標獲取cell對應的indexPath

CGPoint point = [longPress locationInView:_collectionView];

NSIndexPath *indexPath = [self.collectionView indexPathForItemAtPoint:point];

//根據長按手勢的狀態進行處理。

switch (longPress.state) {

case UIGestureRecognizerStateBegan:

//當沒有點選到cell的時候不進行處理

if (!indexPath) {

break;

}

//開始移動

[self.collectionView beginInteractiveMovementForItemAtIndexPath:indexPath];

break;

case UIGestureRecognizerStateChanged:

//移動過程中更新位置座標

[self.collectionView updateInteractiveMovementTargetPosition:point];

break;

case UIGestureRecognizerStateEnded:

//停止移動呼叫此方法

[self.collectionView endInteractiveMovement];

break;

default:

//取消移動

[self.collectionView cancelInteractiveMovement];

break;

}

}

//3、監測可移動狀態

- (BOOL)collectionView:(UICollectionView *)collectionView canMoveItemAtIndexPath:(NSIndexPath *)indexPath {

//根據indexpath判斷單元格是否可以移動,如果都可以移動,直接就返回YES ,不能移動的返回NO

return YES;

}

//4、通過系統的移動代理,交換拖動選單項

- (void)collectionView:(UICollectionView *)collectionView moveItemAtIndexPath:(NSIndexPath *)sourceIndexPath

toIndexPath:(NSIndexPath *)destinationIndexPath{

CCHighSeasPoolManager *seas=[CCHighSeasPoolManager sharedManager];

[seas.dataList exchangeObjectAtIndex:sourceIndexPath.row withObjectAtIndex:destinationIndexPath.row];

}