Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/ios/113.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Ios 使用rightView重新加载包含UITextField的行会导致无限循环和内存溢出_Ios_Objective C_Uitableview_Uitextfield - Fatal编程技术网

Ios 使用rightView重新加载包含UITextField的行会导致无限循环和内存溢出

Ios 使用rightView重新加载包含UITextField的行会导致无限循环和内存溢出,ios,objective-c,uitableview,uitextfield,Ios,Objective C,Uitableview,Uitextfield,我遇到了一个奇怪的错误,关于用自定义的rightView重新加载UITableViewCell包含UITextField 我创建了一个非常简单的示例来演示这个bug: 我的自定义单元格带有UITextField: @implementation TableViewCell - (instancetype)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier { if (

我遇到了一个奇怪的错误,关于用自定义的
rightView
重新加载
UITableViewCell
包含
UITextField

我创建了一个非常简单的示例来演示这个bug:

我的自定义单元格带有
UITextField

@implementation TableViewCell

- (instancetype)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier {
    if (self = [super initWithStyle:style reuseIdentifier:reuseIdentifier]) {
        _textField = [[UITextField alloc] initWithFrame:CGRectMake(0, 0, 320, 44)];
        _textField.text = @"This is a text field";
        [self.contentView addSubview:_textField];
    }

    return self;
}

@end
带有
UITableView的我的视图控制器

@interface ViewController () <UITableViewDataSource>

@property (weak, nonatomic) IBOutlet UITableView *tableView;
@property (nonatomic) UIView *rightView;

@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];
    // Do any additional setup after loading the view, typically from a nib.

    // Press to reload the row with rightView
    self.navigationItem.rightBarButtonItem = [[UIBarButtonItem alloc] initWithBarButtonSystemItem:UIBarButtonSystemItemRefresh target:self action:@selector(reloadRow)];

    // Create rightView and store to a property
    _rightView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, 24, 24)];
    _rightView.backgroundColor = [UIColor greenColor];

    [_tableView registerClass:[TableViewCell class] forCellReuseIdentifier:@"Cell"];
    _tableView.dataSource = self;
}

- (void)reloadRow {
    [_tableView reloadRowsAtIndexPaths:@[[NSIndexPath indexPathForRow:0
                                                            inSection:0]]
                      withRowAnimation:(UITableViewRowAnimationAutomatic)];
}

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
    return 1;
}

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
    TableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"Cell" forIndexPath:indexPath];

    cell.textField.rightView = _rightView;
    cell.textField.rightViewMode = UITextFieldViewModeAlways;

    return cell;
}

@end
但是我的
rightView
(在real app中)不是一个简单的视图,所以我不想每次显示行时都重新创建它


有人知道为什么会这样吗?如果我不存储
rightView
,为什么不会发生这种情况?感谢阅读。

您尝试将一个视图添加到多个
超级视图中。你不能那样做。您的
@属性(非原子)UIView*rightView
只能有一个
superView
。尝试从子视图
cell.textField.subviews中删除它

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
    TableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"Cell" forIndexPath:indexPath];
    for (UIView *subview in cell.textField.subviews) {
        if ([subview isEqual:_rightView]) {
           [subview removeFromSuperView];
        }
    }
    cell.textField.rightView = _rightView;
    cell.textField.rightViewMode = UITextFieldViewModeAlways;

    return cell;
}

或者创建一个fabric方法,该方法将返回
rightView

的实例。您可以尝试将一个视图添加到多个
superview
。你不能那样做。您的
@属性(非原子)UIView*rightView
只能有一个
superView
。尝试从子视图
cell.textField.subviews中删除它

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
    TableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:@"Cell" forIndexPath:indexPath];
    for (UIView *subview in cell.textField.subviews) {
        if ([subview isEqual:_rightView]) {
           [subview removeFromSuperView];
        }
    }
    cell.textField.rightView = _rightView;
    cell.textField.rightViewMode = UITextFieldViewModeAlways;

    return cell;
}

或者创建一个fabric方法,该方法将返回
rightView

的实例。为什么不在TableViewCell中创建右视图,如textfield?我有一个子类
UITableViewCell
,用于应用程序中的每个位置,我只在一个视图控制器中使用
rightView
,因此我不想将其添加到cell子类中。正确的方法是使用不同的UITableViewCell类,不仅仅是应用程序中的一个:-)为什么不在TableViewCell中创建右视图,如文本字段?我有一个子类
UITableViewCell
,用于应用程序中的每个位置,我只在一个视图控制器中使用
rightView
,所以我不想将它添加到cell子类中。正确的方法是使用不同的UITableViewCell类,而不仅仅是整个应用程序中的一个:-)我尝试了你说的,但问题仍然存在。是的,我提出了一种方法,每当单元格需要时创建一个新的
rightView
,这解决了问题,但正如我所说,我的自定义视图不是一个简单的视图,所以我不想多次重新创建它,因为它会使tableView在滚动时闪烁。我的答案有点改变,尝试以不同方式从子视图中删除我尝试了您所说的,但问题仍然存在。是的,每次单元格需要时,我都会创建一个新的
rightView
,这解决了问题,但正如我所说,我的自定义视图不是一个简单的视图,所以我不想多次重新创建它,因为它会使tableView在滚动时闪烁。我的答案有点改变,请尝试从子视图中以不同的方式删除