【问题标题】:Error when moving objects between NSMutableArray在 NSMutableArray 之间移动对象时出错
【发布时间】:2016-10-30 03:58:27
【问题描述】:

在我的 iOS 应用程序中,我有一个表格视图,它有 2 个部分/2 个数组。我正在尝试将对象从一个数组/部分移动到另一个数组/部分。现在第 0 节称为 followArray,第 1 节称为 dataArray,dataArray 存储构成每个单元格的所有数据。因此,当用户单击我设置的名为 Follow 的按钮时,它应该将该单元格从 dataArray/Section 1 中删除并将其插入到 followArray/Section 0 中。但是当我尝试这样做时,我得到一个错误这么说的。

错误信息

*** -[UITableView _endCellAnimationsWithContext:] 中的断言失败,/BuildRoot/Library/Caches/com.apple.xbs/Sources/UIKit/UIKit-3599.6/UITableView.m:1396

*** 由于未捕获的异常“NSInternalInconsistencyException”而终止应用程序,原因:“尝试将第 0 行插入第 0 节,但更新后第 0 节中只有 0 行”

代码:

表格视图

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
    
    static NSString *CellIdentifier = @"Cell";
    CustomCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
    if (!cell) {
        cell = [[CustomCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
    }
    
    // Configuring the cell
    Data * dataObject;
    if (!isFiltered) {
        
        if (indexPath.section == 0) {
            dataObject = [followedArray objectAtIndex:indexPath.row];
        }
        else if (indexPath.section == 1) {
            dataObject = [dataArray objectAtIndex:indexPath.row];
        }
    }
    else {
        dataObject = [filteredArray objectAtIndex:indexPath.row];
    }
    
    // Loading Button
    cell.followButton.tag = indexPath.row;
    [cell.followButton addTarget:self action:@selector(followButtonClick:) forControlEvents:UIControlEventTouchUpInside];
    cell.followButton.hidden = NO;
    
    return cell;
}

部分标题

-(NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section {
    if (section == 0) {
        return @"Followed Data";
    }
    else {
        return @"All Data";
    }
}

行数

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
    
    if (!isFiltered) {
        
        if (section == 0) {
            return [followedArray count];
        }
        else if (section == 1) {
            return [dataArray count];
        }
    }
    return [filteredArray count];
}

------------------------------------------ ---------

-- 这是动作发生的地方--

------------------------------------------ ---------

关注按钮

-(void)followButtonClick:(UIButton *)sender {
    
    // Adding row to tag
    CGPoint buttonPosition = [sender convertPoint:CGPointZero toView:self.myTableView];
    NSIndexPath *indexPath = [self.myTableView indexPathForRowAtPoint:buttonPosition];
    
    // Creating an action per tag
    if (indexPath != nil)
    {
        NSLog(@"Current Row = %@", indexPath);
        
        
        // ----- ERROR HERE -----
    [self.myTableView beginUpdates];
    
    // ----- Inserting Cell to Section 0 ----- *NOT WORKING*
    [followedArray insertObject:[dataArray objectAtIndex:indexPath.row] atIndex:indexPath.row];
    NSInteger rowToAdd = indexPath.row;
    [self.myTableView insertRowsAtIndexPaths:[NSMutableArray arrayWithObjects:[NSIndexPath indexPathForRow:rowToAdd inSection:0], nil] withRowAnimation:YES];
    
    // ----- Removing Cell from Section 1 ----- *WORKING*
    [dataArray removeObjectAtIndex:indexPath.row];
    NSInteger rowToRemove = indexPath.row;
    [self.myTableView deleteRowsAtIndexPaths:[NSMutableArray arrayWithObjects:[NSIndexPath indexPathForRow:rowToRemove inSection:1], nil] withRowAnimation:YES];
    
    [self.myTableView endUpdates];
        
    }
}

【问题讨论】:

  • 删除 beginUpdates 和 endUpdates。立即尝试!
  • @Manigandasaravanan 同样的错误
  • // 添加行到标签 CGPoint buttonPosition = [sender convertPoint:CGPointZero toView:self.myTableView]; NSIndexPath *indexPath = [self.myTableView indexPathForRowAtPoint:buttonPosition];为什么要为 IndexPath 这样做??
  • @Dhanesh 这就是我在每个单元格中的按钮给我一个不同的标签,为什么,它会导致冲突吗?
  • NSLog(@"当前行 = %@", indexPath);你在这里得到什么?

标签: ios objective-c uitableview nsmutablearray


【解决方案1】:

修改关注按钮代码如下:

关注按钮

-(void)followButtonClick:(UIButton*)sender {
    //Use this IndexPath
    NSInteger buttonTag = [sender tag];
    NSIndexPath *indexPath = [NSIndexPath indexPathForRow:buttonTag inSection:<YourSection>];

    // Creating an action per tag
    if (indexPath != nil)
    {
        NSLog(@"Current Row = %@", indexPath);


        // ----- ERROR HERE -----

        [self.myTableView beginUpdates];

        // ----- Inserting Cell to Section 0 -----
        [followedArray insertObject:[dataArray objectAtIndex:indexPath.row] atIndex:indexPath.row];
        NSInteger rowToAdd = indexPath.row;
        [self.myTableView insertRowsAtIndexPaths:[NSMutableArray arrayWithObjects:[NSIndexPath indexPathForRow:rowToAdd inSection:0], nil] withRowAnimation:YES];

        // ----- Removing Cell from Section 1 -----
        [dataArray removeObjectAtIndex:indexPath.row];
        NSInteger rowToRemove = indexPath.row;
        [self.myTableView deleteRowsAtIndexPaths:[NSMutableArray arrayWithObjects:[NSIndexPath indexPathForRow:rowToRemove inSection:1], nil] withRowAnimation:YES];

        [self.myTableView endUpdates];

    }

}

【讨论】:

  • 对不起,我是 iOS 新手,但是对于 [sender tag] 我应该放什么,我尝试了“sender”,这是我的按钮用于发件人标签的内容,但它显示“Expected identifier”跨度>
  • 您没有做任何事情,只是将您的发件人类型从 :(id)sender 更改为 :(UIButton*)sender 就是这样。
  • 对不起,我不明白,我把 [sender tag] 改成了 [sender]
  • 仍然说“预期标识符”
  • 对不起亲爱的我的错误有多余的括号所以它给出的错误请尝试更新代码。
【解决方案2】:

这可能是因为您使用 convertPoint 来获取单击单元格的 indexPath。尝试在您的 CustomCell 中创建一个协议,并在您的 CustomCell 中实现您的 followButtonClick,并使用委托在您的控制器中使用您的 CustomCell 对象获取回调,并使用该对象获取 indexPath。请参考以下代码。

您的 CustomCell.h #导入

@protocol CustomCellDelegate;

@interface CustomCell : UITableViewCell

@property(nonatomic,weak) id<CustomCellDelegate> delegate;

@end

@protocol CustomCellDelegate <NSObject>

-(void)followButtonClickedWithCell:(CustomCell *) cell;

@end

你的 CustomCell.m

#import "CustomCell.h"

@implementation CustomCell
...
-(void)followButtonClicked:(UIButton *) sender{
    if(self.delegate != nil){
        [self.delegate followButtonClickedWithCell:self];
    }
}

...
@end

确认您的视图控制器实现 CustomCellDelegate 并在委托方法中参考以下代码以获取点击的 indexPath

-(void)followButtonClickedWithCell:(CustomCell *) cell{
    NSIndexPath *clickedIndexPath = [self.tableView indexPathForCell:cell];
    if (clickedIndexPath != nil){
        //Implement your logic here
    }
}

【讨论】:

  • 我试过这个,但不幸的是错误并没有在这里结束。删除对象是可行的,但现在将对象插入到 followArray 会导致崩溃。更新了代码。
  • 您可以发布您在尝试此代码后遇到的错误吗?
【解决方案3】:

这就是帮助我修复错误的原因,感谢 @AliOmari、@Rachel 和 @CodeChanger

    [self.myTableView beginUpdates];

    [followedArray insertObject:[dataArray objectAtIndex:indexPath.row] atIndex:0];
    [myTableView insertRowsAtIndexPaths:@[[NSIndexPath indexPathForRow:0 inSection:0]] withRowAnimation:UITableViewRowAnimationFade];

    [dataArray removeObjectAtIndex:indexPath.row];
    NSInteger rowToRemove = indexPath.row;
    [self.myTableView deleteRowsAtIndexPaths:[NSMutableArray arrayWithObjects:[NSIndexPath indexPathForRow:rowToRemove inSection:1], nil] withRowAnimation:YES];

    [self.myTableView endUpdates];

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2015-02-18
    • 1970-01-01
    • 2014-08-30
    • 2018-03-24
    • 1970-01-01
    • 1970-01-01
    • 2014-07-11
    • 1970-01-01
    相关资源
    最近更新 更多