ios - Reloading row contains UITextField with a rightView causes infinite loop and memory overflow -


i'm facing strange bug reloading uitableviewcell contains uitextfield custom rightview.

i created simple example demonstrate bug:

my custom cell 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 text field";         [self.contentview addsubview:_textfield];     }      return self; }  @end 

my view controller uitableview:

@interface viewcontroller () <uitableviewdatasource>  @property (weak, nonatomic) iboutlet uitableview *tableview; @property (nonatomic) uiview *rightview;  @end  @implementation viewcontroller  - (void)viewdidload {     [super viewdidload];     // additional setup after loading view, typically nib.      // press reload row rightview     self.navigationitem.rightbarbuttonitem = [[uibarbuttonitem alloc] initwithbarbuttonsystemitem:uibarbuttonsystemitemrefresh target:self action:@selector(reloadrow)];      // create rightview , store 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 

app screenshot

that's it. press reload button. infinite loop starts, application hangs. after seconds, app crashes because uses memory:

terminated due memory error.

but, if don't store rightview in property, , create new view each time tableview dequeue cell, there no problem.

- (uitableviewcell *)tableview:(uitableview *)tableview cellforrowatindexpath:(nsindexpath *)indexpath {     tableviewcell *cell = [tableview dequeuereusablecellwithidentifier:@"cell" forindexpath:indexpath];      cell.textfield.rightview = [[uiview alloc] initwithframe:cgrectmake(0, 0, 24, 24)];     cell.textfield.rightview.backgroundcolor = [uicolor greencolor];     cell.textfield.rightviewmode = uitextfieldviewmodealways;      return cell; } 

but rightview (in real app) not simple view don't want re-create everytime row shows up.

anyone knows why happened? why didn't happen if don't store rightview? reading.

you try add 1 view multiple superview. can't that. @property (nonatomic) uiview *rightview can have 1 superview. try delete subviews cell.textfield.subviews

- (uitableviewcell *)tableview:(uitableview *)tableview cellforrowatindexpath:(nsindexpath *)indexpath {     tableviewcell *cell = [tableview dequeuereusablecellwithidentifier:@"cell" forindexpath:indexpath];     (uiview *subview in cell.textfield.subviews) {         if ([subview isequal:_rightview]) {            [subview removefromsuperview];         }     }     cell.textfield.rightview = _rightview;     cell.textfield.rightviewmode = uitextfieldviewmodealways;      return cell; } 

or make fabric method return instance of rightview


Comments

Popular posts from this blog

Spring Boot + JPA + Hibernate: Unable to locate persister -

go - Golang: panic: runtime error: invalid memory address or nil pointer dereference using bufio.Scanner -

c - double free or corruption (fasttop) -