Frequently when I pull up on my UITableView to refresh the content drawn from my server it will crash with the following message:
Terminating app due to uncaught exception 'NSRangeException', reason:
'-[__NSCFArray objectAtIndex:]: index (4) beyond bounds (4)'
Now the issue is, my data on my end is set into an NSDictionary with the same data every time, so I know my server is not returning anything that is out of place.
Here how everything is working, I have an integer called i. i will always = 0 at repopulation of cells based on:
-(void) tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath
{
if([indexPath row] == ((NSIndexPath*)[[tableView indexPathsForVisibleRows] lastObject]).row){
//end of loading
//for example [activityIndicator stopAnimating];
i = 0;//<!-- reset the i so that when page reloads cells it does not fail
}
}
I am also adding on 2 extra slots for my NSDictionary because slot 0 and 1 are crucial pieces. There associated with user information that populates the first 2 cells:
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
return [[self.dataGrabed_dictionary objectForKey:#"scheduled_times"] count] + 2;//<!-- by default we want to make sure 2 is being added no matter what. 1 = clients address and name, 2 = upcoming lawn care
}
So back to i the first 2 calls to cellForRowAtIndexPath I use if statements to assign the collected data for the first 2 cells. Than I increment i as I populate the other cells with data (if any)
Here is exactly what is going on within cellForRowAtIndexPath:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
NSLog(#"%d",i);
self.tableView.separatorColor = [UIColor clearColor];// Get rid of speration border color
static NSString *CellIdentifier = #"homecell";
HomePageTimelineCell *cell = (HomePageTimelineCell *)[tableView dequeueReusableCellWithIdentifier:CellIdentifier];
cell = [[HomePageTimelineCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
[cell setSelectionStyle:UITableViewCellSelectionStyleNone];
[cell initTimelineCell];
cell.backgroundColor = [UIColor clearColor];// Set the background color to the cell
// lets check if there is any data
if([self.dataGrabed_dictionary objectForKey:#"scheduled_times"] == nil && [self.dataGrabed_dictionary objectForKey:#"upcoming"] == nil)
{
//<!-- if the indexRow row = 0, this is the clients username and address
if(indexPath.row == 0)
{
NSArray *get = [[SSKeychain allAccounts] init];
NSString *username = [get[0] objectForKey:#"acct"];
//<!-- Get keyname of the address and than point to that keyname and get data
//NSString *KeyName = [[self.dataGrabed_dictionary allKeys] objectAtIndex: indexPath.row];
//<!-- create uppercase strings
NSString *upperCaseAddress = [[self.dataGrabed_dictionary objectForKey:#"client_address"] uppercaseString];
NSString *upperCaseUsername = [username uppercaseString];
//<!-- Set associated strings
cell.addressLabel.text = upperCaseAddress;
cell.usernameLabel.text = upperCaseUsername;
}
else if(indexPath.row == 1)
{
cell.contentView.backgroundColor = [self colorWithHexString:#"666666"];
cell.button.backgroundColor = [self colorWithHexString:#"7ddcb8"];
cell.button.tag = indexPath.row;
[cell.button setTitle:#"schedule" forState:UIControlStateNormal];
[cell.button setTitleColor:[self colorWithHexString:#"666666"] forState:UIControlStateNormal];
/* Setup button action */
//[cell.button addTarget:self action:#selector(onCustomAccessoryTapped:) forControlEvents:UIControlEventTouchUpInside];
cell.dateLabel.tag = indexPath.row + 100; //<!-- 100 = date
cell.dateLabel.text = #"Nothing Scheduled";//<!-- Set the Date
[cell.contentView addSubview:cell.button];
[cell.contentView addSubview:cell.nextLabel];
[cell.contentView addSubview:cell.dayLabel];
[cell.contentView addSubview:cell.dateLabel];
}
}
else
{
//<!-- Set background color
if (indexPath.row % 2) {
cell.contentView.backgroundColor = [self colorWithHexString:#"77d1af"];
//<!-- Set background and text color for even cells
[cell.button setTitleColor:[self colorWithHexString:#"7ddcb8"] forState:UIControlStateNormal];
cell.button.backgroundColor = [self colorWithHexString:#"666666"];
} else {
cell.contentView.backgroundColor = [self colorWithHexString:#"7ddcb8"];
//<!-- Set background and text color for even cells
[cell.button setTitleColor:[self colorWithHexString:#"7ddcb8"] forState:UIControlStateNormal];
cell.button.backgroundColor = [self colorWithHexString:#"ffffff"];
}
//<!-- if the indexRow row = 0, this is the clients username and address
if(indexPath.row == 0)
{
NSArray *get = [[SSKeychain allAccounts] init];
NSString *username = [get[0] objectForKey:#"acct"];
//<!-- Get keyname of the address and than point to that keyname and get data
//NSString *KeyName = [[self.dataGrabed_dictionary allKeys] objectAtIndex: indexPath.row + 4];
//<!-- create uppercase strings
NSString *upperCaseAddress = [[self.dataGrabed_dictionary objectForKey:#"client_address"] uppercaseString];
NSString *upperCaseUsername = [username uppercaseString];
//<!-- Set associated strings
cell.addressLabel.text = upperCaseAddress;
cell.usernameLabel.text = upperCaseUsername;
}
//<!-- if the indexRow row = 1, this is the 2 cell and will show the most upcoming lawn schedule
else if(indexPath.row == 1)
{
//<!-- Lets check if user even has an upcoming mowing date -->
if([self.dataGrabed_dictionary objectForKey:#"upcoming"] == nil)
{
cell.contentView.backgroundColor = [self colorWithHexString:#"666666"];
cell.button.backgroundColor = [self colorWithHexString:#"7ddcb8"];
cell.button.tag = indexPath.row;
[cell.button setTitle:#"schedule" forState:UIControlStateNormal];
[cell.button setTitleColor:[self colorWithHexString:#"666666"] forState:UIControlStateNormal];
/* Setup button action */
//[cell.button addTarget:self action:#selector(onCustomAccessoryTapped:) forControlEvents:UIControlEventTouchUpInside];
cell.dateLabel.tag = indexPath.row + 100; //<!-- 100 = date
cell.dateLabel.text = #"Nothing Scheduled";//<!-- Set the Date
[cell.contentView addSubview:cell.button];
[cell.contentView addSubview:cell.nextLabel];
[cell.contentView addSubview:cell.dayLabel];
[cell.contentView addSubview:cell.dateLabel];
}
else
{
//<!-- create uppercase strings
NSString *upperCaseDay = [[self.dataGrabed_dictionary objectForKey:#"upcoming_day"] uppercaseString];
//<!-- create uppercase strings
NSString *upperCaseDate = [[self.dataGrabed_dictionary objectForKey:#"upcoming_date"] uppercaseString];
cell.contentView.backgroundColor = [self colorWithHexString:#"666666"];
cell.button.backgroundColor = [self colorWithHexString:#"7ddcb8"];
cell.button.tag = indexPath.row;
[cell.button setTitle:#"change" forState:UIControlStateNormal];
[cell.button setTitleColor:[self colorWithHexString:#"666666"] forState:UIControlStateNormal];
/* Setup button action */
//[cell.button addTarget:self action:#selector(onCustomAccessoryTapped:) forControlEvents:UIControlEventTouchUpInside];
cell.dayLabel.text = upperCaseDay;//<!-- Set the day
cell.dateLabel.tag = indexPath.row + 100; //<!-- 100 = date
cell.dateLabel.text = upperCaseDate;//<!-- Set the Date
[cell.contentView addSubview:cell.button];
[cell.contentView addSubview:cell.nextLabel];
[cell.contentView addSubview:cell.dayLabel];
[cell.contentView addSubview:cell.dateLabel];
}
}
else //<!-- Normal cell population
{
//<!-- Re edit labels positioning
cell.dayLabel.frame = CGRectMake(9, 10, 200, 45);
cell.dateLabel.frame = CGRectMake(9, 35, 300, 45);
//<!-- Setup data called from server
NSDictionary *innerClientData =[self.dataGrabed_dictionary objectForKey:#"scheduled_times"][i];
NSString *innerClientDay =[self.dataGrabed_dictionary objectForKey:#"scheduled_times_day"][i];
NSString *innerClientDate =[self.dataGrabed_dictionary objectForKey:#"scheduled_times_date"][i];
//<!-- create uppercase strings
NSString *upperCaseDay = [innerClientDay uppercaseString];
//<!-- create uppercase strings
NSString *upperCaseDate = [ innerClientDate uppercaseString];
//<!-- Check to see if client paid
if([[innerClientData objectForKey:#"client_paid"] isEqual: #"0"])
{
NSString *amount = [innerClientData objectForKey:#"client_price"];
NSString *pay = #"pay $";
NSString * combined = [pay stringByAppendingString:amount];
[cell.button setTitle:combined forState:UIControlStateNormal];
}
else if([[innerClientData objectForKey:#"client_paid"] isEqual: #"1"])
{
[cell.button setTitle:#"PAID" forState:UIControlStateNormal];
}
//[cell.button setTitleColor:[self colorWithHexString:#"666666"] forState:UIControlStateNormal];
cell.button.tag = indexPath.row;
/* Setup button action */
//[cell.button addTarget:self action:#selector(onCustomAccessoryTapped:) forControlEvents:UIControlEventTouchUpInside];
cell.dayLabel.text = upperCaseDay;//<!-- Set the day
cell.dateLabel.tag = indexPath.row + 100; //<!-- 100 = date
cell.dateLabel.text = upperCaseDate;//<!-- Set the Date
[cell.contentView addSubview:cell.button];
[cell.contentView addSubview:cell.dayLabel];
[cell.contentView addSubview:cell.dateLabel];
i++;
}
}
return cell;
}
My assigning of the NSDictionary looks like:
NSString *responseString = [[NSString alloc] initWithData:returnData encoding:NSUTF8StringEncoding];
NSLog(#"responseString: %#",responseString);
// GRAB STATUS OBJECT
NSDictionary* json = [NSJSONSerialization
JSONObjectWithData:returnData //1
options:kNilOptions
error:&error];
self.dataGrabed_dictionary = [json objectForKey:#"retrieved_data"];
Suggestions as in why it crashes with out of bounds?
The most likely issue is the way you get the data for the cells. You are using the instance variable i on the following lines:
NSDictionary *innerClientData =[self.dataGrabed_dictionary objectForKey:#"scheduled_times"][i];
NSString *innerClientDay =[self.dataGrabed_dictionary objectForKey:#"scheduled_times_day"][i];
NSString *innerClientDate =[self.dataGrabed_dictionary objectForKey:#"scheduled_times_date"][i];
That will never work. Replace i with indexPath.row - 2.
Cells can be accessed multiple times and in various orders.
Related
I want to expand and collapse cell when I clicked on the cell at particular index.
I am using auto resize and the data in the cell is dynamic i.e cell size increase based on label content I am using autoresize not autolayouts.
When I click on the cell the cell size will increase and the size to be increase is also dynamic what depends on the label content.
Please find my below code
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
NSInteger numOfSections = 0;
if (tableView==_commentstbl_view) {
return commentsarray.count;
}
else
if (isclassifiedarray.count > 0)
{
_myadstabelview.separatorStyle = UITableViewCellSeparatorStyleSingleLine;
_myadstabelview.backgroundView = nil;
numOfSections = isclassifiedarray.count;
}
else
{
// UILabel *noDataLabel = [[UILabel alloc] initWithFrame:CGRectMake(0, 10, _notificationTblView.bounds.size.width, _notificationTblView.bounds.size.height)];
// noDataLabel.text = #"No Results Found!";
// noDataLabel.textColor = [UIColor blackColor];
// noDataLabel.numberOfLines = 4;
// noDataLabel.textAlignment = NSTextAlignmentCenter;
// _notificationTblView.backgroundView = noDataLabel;
_myadstabelview.separatorStyle = UITableViewCellSeparatorStyleNone;
}
return numOfSections;
return isclassifiedarray.count;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section{
return 1;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
commentscell = (commentsTableViewCell*)[_commentstbl_view dequeueReusableCellWithIdentifier:#"commentsTableViewCell" forIndexPath:indexPath];
commentscell.selectionStyle = UITableViewCellSelectionStyleNone;
[commentscell.layer setCornerRadius:4.0f];
[commentscell.layer setMasksToBounds:YES];
commentscell.profileimg.layer.cornerRadius=4.0f;
commentscell.profileimg.layer.masksToBounds = YES;
NSString *mobilenumber=[NSString stringWithFormat:#"%#",[[commentsarray objectAtIndex:indexPath.section]valueForKey:#"clubber_mobile"]];
NSString *comment=[[commentsarray objectAtIndex:indexPath.section]valueForKey:#"comment"];
UIFont *font=[UIFont fontWithName:#"Montserrat" size:14.0];
CGFloat size1 = [self getLabelHeightForStringforcomment:commentscell.commentlbl.text font:font];
commentscell.commentlbl.frame=CGRectMake(commentscell.commentlbl.frame.origin.x, commentlbYposition, commentscell.commentlbl.frame.size.width, size1);
commentscell.commentdatelbl.frame=CGRectMake(commentscell.commentdatelbl.frame.origin.x, commentlbYposition+size1, commentscell.commentdatelbl.frame.size.width, commentscell.commentdatelbl.frame.size.height);
commentscell.providerdetailsbtnoutlet.frame=CGRectMake(commentscell.providerdetailsbtnoutlet.frame.origin.x, commentlbYposition+size1+commentscell.commentdatelbl.frame.size.height, commentscell.providerdetailsbtnoutlet.frame.size.width, commentscell.providerdetailsbtnoutlet.frame.size.height);
if (selectedIndex==-1) {
commentscell.providerdetails_view.hidden=YES;
}else{
commentscell.providerdetails_view.hidden=NO;
commentscell.providerdetails_view.frame=CGRectMake(commentscell.providerdetailsbtnoutlet.frame.origin.x, commentlbYposition+size1+commentscell.commentdatelbl.frame.size.height+commentscell.providerdetailsbtnoutlet.frame.size.height, commentscell.providerdetails_view.frame.size.width, Providerdrtailviewhight);
commentscell.providerdetails_view.backgroundColor=[UIColor whiteColor];
}
NSString *commentclubbername=[[commentsarray objectAtIndex:indexPath.section]valueForKey:#"clubber_name"];
NSString *commentclubberid=[NSString stringWithFormat:#"%#",[[commentsarray objectAtIndex:indexPath.section]valueForKey:#"clubberId"]];
NSString *commentposteddate=[NSString stringWithFormat:#"%#",[[commentsarray objectAtIndex:indexPath.section]valueForKey:#"posted_date"]];
NSString *imgUrl = [NSString stringWithFormat:#"%s/presignin/clubber/getImage?clubberId=%#",urlPath,commentclubberid];
NSURL *imageURL=[NSURL URLWithString:imgUrl];
commentscell.profileimg.imageURL=imageURL;
commentscell.usernamelbl.text=commentclubbername;
commentscell.commentlbl.text=comment;
commentscell.commentdatelbl.text=[Util formatDateAndTime1:commentposteddate];
commentscell.callbtn.tag = indexPath.section;
commentscell.msgbtn.tag = indexPath.section;
commentscell.providerdetailsbtnoutlet.tag=indexPath.section;
[commentscell.callbtn addTarget:self action:#selector(callbtnClicked:) forControlEvents:UIControlEventTouchUpInside];
[commentscell.msgbtn addTarget:self action:#selector(messagebtnClicked:) forControlEvents:UIControlEventTouchUpInside];
// [commentscell.providerdetailsbtnoutlet addTarget:self action:#selector(providerdetailsbtnclick:) forControlEvents:UIControlEventTouchUpInside];
commentscell.providerdetailsbtnoutlet.userInteractionEnabled=NO;
NSString *experience=[NSString stringWithFormat:#"%#",[[commentsarray objectAtIndex:indexPath.section]valueForKey:#"experience"]];
NSArray* foo = [experience componentsSeparatedByString: #"."];
if (foo.count==1) {
NSString* year = [foo objectAtIndex: 0];
// NSString* month = [foo objectAtIndex: 1];
expersstr=[NSString stringWithFormat:#"%# Years, 00 Months",year];
commentscell.explbl.text=expersstr;
}else{
NSString* year = [foo objectAtIndex: 0];
NSString* month = [foo objectAtIndex: 1];
expersstr=[NSString stringWithFormat:#"%# Years, %# Months",year,month];
commentscell.explbl.text=expersstr;
}
providerdescr=[NSString stringWithFormat:#"%#",[[commentsarray objectAtIndex:indexPath.section]valueForKey:#"description"]];
commentscell.desclbl.text=providerdescr;
return commentscell;
}
- (CGFloat)tableView:(UITableView* )tableView heightForRowAtIndexPath:(NSIndexPath* )indexPath;
{
UIFont *font=[UIFont fontWithName:#"Montserrat" size:14.0];
// NSString *str1 = [[isclassifiedarray objectAtIndex:indexPath.section]valueForKey:#"description"];
if (tableView==_commentstbl_view) {
if (selectedIndex == indexPath.section)
{
CGFloat size1 = [self getLabelHeightForStringforcomment:[[commentsarray objectAtIndex:indexPath.section]valueForKey:#"comment"] font:font];
// commentscell.providerdetails_view.hidden=NO;
return 104+size1-20+45;
}
else{
CGFloat size1 = [self getLabelHeightForStringforcomment:[[commentsarray objectAtIndex:indexPath.section]valueForKey:#"comment"] font:font];
// commentscell.providerdetails_view.hidden=YES;
return 104+size1-20;
}
}
}
please find the img which is clear idea.
Thanks for quick responce
Here in this tableView cell i have created a button i want to hide that button after getting response "1". I am doing it in following way but not working still the cell is showing the button.How would i do that.
- (void)configureCell:(UITableViewCell *)cell atIndexPath:(NSIndexPath *)indexPath {
MyVideos *myvidoeclips = [park objectAtIndex:indexPath.row];
UILabel *lbl2=(UILabel*)[cell viewWithTag:777];
NSString *stateus = [myvidoeclips valueForKey:#"state"];
if([stateus isEqual: #"0"]){
[lbl2 setText:#"Under Moderation"];
}
if([stateus isEqual: #"1"]){
[lbl2 setText:#"Published"];
}
if([stateus isEqual: #"4"]){
[lbl2 setText:#"Rejected"];
}
lbl2.textColor=[UIColor whiteColor];
// Here is my button which i want to hide
UIButton *button=[[UIButton alloc]initWithFrame:CGRectMake(216, 130, 64, 30)];
NSString *strFlagValue = [[NSString alloc]init];
strFlagValue = [myvidoeclips valueForKey:#"state"];
if ([strFlagValue isEqualToString:#"1"])
{
flag = true;
}
else
{
flag = false;
}
if (flag)
{
button.hidden = true;
}
else
{
button.hidden = false;
}
[button addTarget:self action:#selector(yourEditButtonClicked:) forControlEvents:UIControlEventTouchUpInside]; button.tag = indexPath.row;
[button setImage:[UIImage imageNamed:#"btn-details.png"] forState:UIControlStateNormal];
[cell.contentView addSubview:button];
NSLog(#"sender.tag cell is%ld ",(long)button.tag);
}
In cellForRowAtIndex check flag.
Flag will be true or false depending upon your JSON response ( Array / Dictionary )
BOOL flag;
NSString *strFlagValue = [[NSString alloc]init];
strFlagValue = [[array objectAtIndex:indexPath.row] valueForKey:#"Key_From_You_Get_1_Or_0"];
if ([strFlagValue isEqualToString:#"1"])
{
flag = true;
}
else
{
flag = false;
}
if (flag)
{
cell.button.hidden = true;
}
else
{
cell.button.hidden = false;
}
Also check your cell in cellForRowAtIndex must be reusable with identifier.
If you are sure to get "1" or "0" every time from JSON(Array). then below sort code is enough.
BOOL flag = [[[array objectAtIndex:indexPath.row] valueForKey:#"Key_From_You_Get_1_Or_0"] boolValue];
cell.button.hidden = flag;
Whole cellForRowAtIndexPath ( Logic you are writing in your question at wrong method )
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *CellIdentifier = #"ID_CustomCell";
CustomCell *cell = (CustomCell *)[tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if(cell == nil){
cell = (CustomCell *)[[[NSBundle mainBundle] loadNibNamed:#"CustomCell" owner:self options:nil] objectAtIndex:0];
cell.selectionStyle = UITableViewCellSelectionStyleNone;
}
BOOL flag = [[[array objectAtIndex:indexPath.row] valueForKey:#"Key_From_You_Get_1_Or_0"] boolValue];
cell.btn1.hidden = flag;
NSString *strFlagValue = [[NSString alloc]init];
strFlagValue = [[array objectAtIndex:indexPath.row] valueForKey:#"Key_From_You_Get_1_Or_0"];
if ([strFlagValue isEqualToString:#"1"])
{
flag = true;
}
else
{
flag = false;
}
if (flag)
{
cell.btn1.hidden = 1;
}
else
{
cell.btn1.hidden = 0;
}
return cell;
}
For static table cells, create an IBOutlet of UIButton and hide while checking condition using json data.
For dynamic table cells, need to identify the row number for which button needs to be hidden.
Example :- There is an array contains multiple dictionary.
NSDictionary* dict = [array objectAtIndex:indexPath.row];
BOOL isButtonHidden = [dict objectForKey:#"KeyName"];
cell.button.hidden = isButtonHidden
Hope this solution help you..Thanks
I am developing an IOS App. A row consists of an TextField and some textviews. When the value of TextField is changed for any row the number in the TextField should be multiplied with the number in a Label og the same row and displayed in another Label in the same row. What actually happens is that the values are multiplied with the labels of another cell which is apparently random.. The image shows what is actually happening. This problem has me sorely puzzled for days and I am at my wits end.
I Tried Fetching Row From Tableview using didSelectRowAtIndex and
indexPath.row.The Result Are are confusing as row index of first Two rows is being Showns as 0.
IndexPath correct in cellForRowAtIndexPath but is wrong in Textfield Method [ - (void) changedvalue: (UITextField *)textfield ]. What Could Be Worng ?
Any help or advice is greatly appreciated. Thanks in advance.
//Code
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
return _fetchedobj.count;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *MyIdentifier = #"MyReuseIdentifier";
UITableViewCell *cell = [myTable dequeueReusableCellWithIdentifier:MyIdentifier];
if (cell == nil) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:MyIdentifier];
}
data = [_fetchedobj objectAtIndex:indexPath.row];
_quantity = [[UITextField alloc] initWithFrame:CGRectMake(5.0f,28.0f,50.0f , 30.0f)];
[_quantity setTag:indexPath.row];
[_quantity setFont:[UIFont systemFontOfSize:14.0f]];
[_quantity setTextAlignment:NSTextAlignmentCenter];
_quantity.backgroundColor = [UIColor whiteColor];
[_quantity setAdjustsFontSizeToFitWidth:YES];
[_quantity addTarget:self action:#selector(changedvalue:) forControlEvents:UIControlEventAllEditingEvents];
NSString *q_value = [data valueForKey:#"quantity"];
NSInteger q_value1 = [q_value integerValue];
[_quantity setText:[NSString stringWithFormat:#"%li",(long)q_value1]];
[cell addSubview:_quantity];
_total1 = [[UILabel alloc ]initWithFrame:CGRectMake(50.0f, 58.0f, 80.0f, 25.0f)];
[_total1 setFont:[UIFont systemFontOfSize:14.0f]];
[_total1 setTag:1];
[_total1 setTextAlignment:NSTextAlignmentCenter];
[_total1 setAdjustsFontSizeToFitWidth:YES];
_total1.backgroundColor = [UIColor whiteColor];
NSString *totalAmount = [data valueForKey:#"amount"];
NSInteger total_Amount = [totalAmount integerValue];
[_total1 setText:[NSString stringWithFormat:#"%li",(long)total_Amount]];
[cell addSubview:_total1];
- (void) changedvalue: (UITextField *)textfield
{
NSLog(#"%ld",(long)[textfield tag]);
NSString *text = [textfield text];
NSInteger text1 = [text integerValue];
NSString *changevalue = [dict objectForKey:#"_max_purchases_per_user"];
NSInteger valueChange = [changevalue integerValue];
NSString *userPurchase = [dict objectForKey:#"_max_purchases"];
NSInteger itemPurchase = [userPurchase integerValue];
NSString *amount = [data valueForKey:#"amount"];
NSInteger amount1 = [amount integerValue];
NSInteger minValue=MIN(valueChange, itemPurchase);
if (text1 > minValue) {
NSIndexPath *indexPath = [NSIndexPath indexPathForRow:[textfield tag] inSection:0];
UITableViewCell *cell = (UITableViewCell *) [myTable cellForRowAtIndexPath:indexPath];
// UITextField * field=cell.subviews[1];
// field.text = [NSString stringWithFormat:#"%li",minValue * amount1];
NSLog(#"%#",cell);
cell.textLabel.text = [NSString stringWithFormat:#"%li",minValue * amount1];
//[_quantity setText:[NSString stringWithFormat:#"%li",(long)minValue]];
//[ _total1 setText:[NSString stringWithFormat:#"%li",minValue * amount1]];
}else{
[_total1 setText:[NSString stringWithFormat:#"%li",text1 * amount1]];
}
// NSString *Amount =[data valueForKey:#"amount"];
// NSNumber *aNum = [NSNumber numberWithInteger:[Amount integerValue]];
//
// [_total1 setText:[NSString stringWithFormat:#"%ld",([i integerValue] * [aNum integerValue])]];
}
You urgently need to take into account that cells are reused. That's what the "dequeueWithReuseIdentifier" does. So if you have 100 rows, and there are up to 10 visible at a time, you will have 10 rows using the same cell.
You must absolutely NOT create new textfields when dequeueWithReuseIdentifier doesn't return nil. It returns a cell that has already all the textfields created for it, from the previous time that the cell was used for a different or the same row.
And using indexPath.row as the index is a recipe for disaster if the user can add or remove rows. Say you are displaying row 10, then I delete row 8. Your cell now is in row 9, but has a tag that says row 10.
When my UITableView loads for the first time, everything in the code below functions correctly. However, if it reloads for whatever reason (refresh, etc.), it starts assigning a cell.bestMatchLabel.text value of #"Best Match" to random cells, rather than only the first one as I specified in the code. Why is calling reload on my table causing the below code to not run correctly?
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
//load top 3 data
NSDictionary *currentSectionDictionary = _matchCenterArray[indexPath.section];
NSArray *top3ArrayForSection = currentSectionDictionary[#"Top 3"];
// if no results for that item
if (top3ArrayForSection.count-1 < 1) {
// Initialize cell
static NSString *CellIdentifier = #"MatchCenterCell";
EmptyTableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (!cell) {
// if no cell could be dequeued create a new one
cell = [[EmptyTableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:CellIdentifier];
}
// title of the item
cell.textLabel.text = #"No items found, but we'll keep a lookout for you!";
cell.textLabel.font = [UIFont systemFontOfSize:12];
cell.detailTextLabel.text = [NSString stringWithFormat:#""];
[cell.imageView setImage:[UIImage imageNamed:#""]];
return cell;
}
// if results for that item found
else {
// Initialize cell
static NSString *CellIdentifier = #"MatchCenterCell";
MatchCenterCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (!cell) {
// if no cell could be dequeued create a new one
cell = [[MatchCenterCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:CellIdentifier];
}
tableView.separatorColor = [UIColor clearColor];
if (indexPath.row == 0) {
cell.bestMatchLabel.text = #"Best Match";
cell.bestMatchLabel.font = [UIFont systemFontOfSize:12];
cell.bestMatchLabel.textColor = [UIColor colorWithRed:0.18 green:0.541 blue:0.902 alpha:1];
[cell.contentView addSubview:cell.bestMatchLabel];
}
// title of the item
cell.textLabel.text = _matchCenterArray[indexPath.section][#"Top 3"][indexPath.row+1][#"Title"];
cell.textLabel.font = [UIFont systemFontOfSize:14];
// price + condition of the item
NSString *price = [NSString stringWithFormat:#"$%#", _matchCenterArray[indexPath.section][#"Top 3"][indexPath.row+1][#"Price"]];
NSString *condition = [NSString stringWithFormat:#"%#", _matchCenterArray[indexPath.section][#"Top 3"][indexPath.row+1][#"Item Condition"]];
cell.detailTextLabel.text = [NSString stringWithFormat:#"%# - %#", price, condition];
cell.detailTextLabel.textColor = [UIColor colorWithRed:0.384 green:0.722 blue:0.384 alpha:1];
// Load images using background thread to avoid the laggy tableView
[cell.imageView setImage:[UIImage imageNamed:#"Placeholder.png"]];
dispatch_async(dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0), ^{
// Download or get images here
NSData *imageData = [NSData dataWithContentsOfURL:[NSURL URLWithString:_matchCenterArray[indexPath.section][#"Top 3"][indexPath.row+1][#"Image URL"]]];
// Use main thread to update the view. View changes are always handled through main thread
dispatch_async(dispatch_get_main_queue(), ^{
// Refresh image view here
[cell.imageView setImage:[UIImage imageWithData:imageData]];
cell.imageView.layer.masksToBounds = YES;
cell.imageView.layer.cornerRadius = 2.5;
[cell setNeedsLayout];
});
});
return cell;
}
}
That is because table dequeue same cell for multiple indexes as you scroll down, so you need to add else statement in the following code
if (indexPath.row == 0) {
cell.bestMatchLabel.text = #"Best Match";
cell.bestMatchLabel.font = [UIFont systemFontOfSize:12];
cell.bestMatchLabel.textColor = [UIColor colorWithRed:0.18 green:0.541 blue:0.902 alpha:1];
[cell.contentView addSubview:cell.bestMatchLabel];
[cell.bestMatchLabel setHidden:NO];
} else {
[cell.bestMatchLabel setHidden:YES];
}
but a better approach for this case is to use different cell identifier for that row and only add the bestMatchLabel once when first creating the cell
in my tableview I have a button in the custom cell
I used the delegates to take an action to the button
The button image changes only on the selected cell
My problem is this:
When I press the button happens:
the selected cell is working properly and the button changes correctly (correct)
the second immediately after the selected cell does not change the button (corrected)
the third cell repeats the action of the selected cell (wrong)
This is repeated endlessly do not understand why
The button should change only the selected cell and not on other non-selected
Can you help me please?
-(void)ButtonPressedGoPoint:(FFCustomCellWithImage *)custom button:(UIButton *)gopointpressed {
NSNumberFormatter *numberFormatter = [[NSNumberFormatter alloc] init];
[numberFormatter setLocale:[[NSLocale alloc] initWithLocaleIdentifier:#"it_IT"]];
NSNumber *likeCount = [numberFormatter numberFromString:custom.CountGoPoint.text];
if (!custom.AddGoPoint.selected) {
NSLog(#"TastoSelezionato");
likeCount = [NSNumber numberWithInt:[likeCount intValue] + 1];
custom.CountGoPoint.text = [NSString stringWithFormat:#"%#", likeCount];
[custom.AddGoPoint setBackgroundImage:[UIImage imageNamed:#"FFIMG_Medal_Blu"] forState:UIControlStateNormal];
}
else {
if ([likeCount intValue] > 0) {
likeCount = [NSNumber numberWithInt:[likeCount intValue] - 1];
custom.CountGoPoint.text = [NSString stringWithFormat:#"%#", likeCount];
}
NSLog(#"TastoDeselezionato");
[custom.AddGoPoint setBackgroundImage:[UIImage imageNamed:#"FFIMG_MedalADD"] forState:UIControlStateNormal];
}
custom.AddGoPoint.selected = !custom.AddGoPoint.selected;
}
This is my implementation of the tableview
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
self.PostDetails = [ArrayforPost objectAtIndex:indexPath.row];
static NSString *IdentificazioneCellaIMG = #"CellaIMG";
FFCustomCellWithImage * CellaIMG = (FFCustomCellWithImage * )[self.FFTableView dequeueReusableCellWithIdentifier:IdentificazioneCellaIMG];
if (CellaIMG == nil) {
CellaIMG = [[FFCustomCellWithImage alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:IdentificazioneCellaIMG ];
}
CellaIMG.delegate = self;
CellaIMG.tag = indexPath.row;
[CellaIMG.AddGoPoint setTag:indexPath.row];
if ([self AssignedGoPointToPost:self.PostDetails]) {
CellaIMG.AddGoPoint.selected =YES;
[CellaIMG.AddGoPoint setImage:[UIImage imageNamed:#"FFIMG_Medal_Blu"] forState:UIControlStateNormal];
} else {
CellaIMG.AddGoPoint.selected =NO;
[CellaIMG.AddGoPoint setImage:[UIImage imageNamed:#"FFIMG_MedalADD"] forState:UIControlStateNormal];
}
NSString *FotoPostSocial = [self.PostDetails objectForKey:FF_POST_IMMAGINE];
CellaIMG.FotoPost.file = (PFFile *)FotoPostSocial;
[CellaIMG.FotoPost loadInBackground];
CellaIMG.FotoPost.layer.masksToBounds = YES;
CellaIMG.FotoPost.layer.cornerRadius = 2.0f;
CellaIMG.FotoPost.contentMode = UIViewContentModeScaleAspectFill;
CellaIMG.backgroundCell.layer.masksToBounds = YES;
CellaIMG.backgroundCell.layer.cornerRadius = 2.0f;
CellaIMG.backgroundCell.layer.borderColor = [UIColor colorWithRed:(219/255.0) green:(219/255.0) blue:(219/255.0) alpha:(1)].CGColor;
CellaIMG.backgroundCell.layer.borderWidth = 1.0f;
CellaIMG.backgroundCell.autoresizingMask = UIViewAutoresizingFlexibleHeight;
CellaIMG.LeggiCommentoButton.layer.cornerRadius = 2.0f;
CellaIMG.FotoProfilo.layer.masksToBounds = YES;
CellaIMG.FotoProfilo.layer.cornerRadius = 25.0f;
CellaIMG.FotoProfilo.contentMode = UIViewContentModeScaleAspectFill;
CellaIMG.TestoPost.font = [UIFont fontWithName:#"Helvetica" size:14.0f];
NSString *text = [self.PostDetails objectForKey:FF_POST_TEXT];
CellaIMG.TestoPost.text = text;
[CellaIMG.TestoPost setLineBreakMode:NSLineBreakByTruncatingTail];
NSString *NomeUser = [[self.PostDetails objectForKey:FF_POST_UTENTE] objectForKey:FF_USER_NOMECOGNOME];
CellaIMG.NomeUtente.text = NomeUser;
NSString *ImmagineUtente = [[self.PostDetails objectForKey:FF_POST_UTENTE] objectForKey:FF_USER_FOTOPROFILO];
CellaIMG.FotoProfilo.file = (PFFile *)ImmagineUtente;
[CellaIMG.FotoProfilo loadInBackground];
if (CellaSelezionata == indexPath.row) {
CGFloat AltezzaLabel = [self valoreAltezzaCella: indexPath.row];
CellaIMG.TestoPost.frame = CGRectMake(CellaIMG.TestoPost.frame.origin.x, CellaIMG.TestoPost.frame.origin.y, CellaIMG.TestoPost.frame.size.width, AltezzaLabel); }
else {
CellaIMG.TestoPost.frame = CGRectMake(CellaIMG.TestoPost.frame.origin.x, CellaIMG.TestoPost.frame.origin.y, CellaIMG.TestoPost.frame.size.width, 65);
}
return CellaIMG;
}
}