Unexpected delay when presenting UITableViewController - ios

I have a custom UITableViewCell in a UITableViewController, but when the Controller tries to dequeue the custom cell, it will take a long time (like 2000ms).
This line of code causes the problem
KidsListTableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:#"kidsReuseIdentifier" forIndexPath:indexPath];
The KidsListTableViewCell is a custom cell, which includes couple of UIButtons, some UILabels to show the information. And two delegate methods. It shouldn't be that slow to render that view. By the way, all of the information in the custom cell is basically static.
The is the full code of the UITableViewController. I put the custom view and regular view in different sections and I don't think this causes the problem.
#import "KidDetailTableViewController.h"
#import "KidDetailHeaderTableViewCell.h"
#import <AssetsLibrary/AssetsLibrary.h>
#import "Helper.h"
#interface KidDetailTableViewController () <KidDetailHeaderCellDelegate>
#end
#implementation KidDetailTableViewController
{
KidDetailHeaderTableViewCell *headerCell;
}
- (void)viewDidLoad {
[super viewDidLoad];
[self.tableView registerNib:[UINib nibWithNibName:#"KidDetailHeader" bundle:nil] forCellReuseIdentifier:#"kidDetail"];
[self.tableView registerClass:[UITableViewCell class] forCellReuseIdentifier:#"detailCell"];
self.tableView.showsVerticalScrollIndicator = NO;
}
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
#pragma mark - Table view data source
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
// Return the number of sections.
return 2;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
switch (section) {
case 0:
return 1;
break;
default:
return 10;
break;
}
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
if (indexPath.section == 0) {
if (!headerCell) {
headerCell = [tableView dequeueReusableCellWithIdentifier:#"kidDetail"];
headerCell.delegate = self;
// Keep the background color for the cell when select.
headerCell.selectionStyle = UITableViewCellSelectionStyleNone;
headerCell.nicknameLabel.text = _kidNeedsToShow.nickname;
NSString *kidFullName = [NSString stringWithFormat:#"%# %# %#", _kidNeedsToShow.firstName, _kidNeedsToShow.midName, _kidNeedsToShow.lastName];
kidFullName ? (headerCell.fullNameLabel.text = #"") : (headerCell.fullNameLabel.text = kidFullName);
// Set thumb image or use default
// if there isn't image, use default.
ALAssetsLibrary *library = [ALAssetsLibrary new];
[library assetForURL:_kidNeedsToShow.photoURL resultBlock:^(ALAsset *asset) {
[headerCell.avatarImage setImage:[UIImage imageWithCGImage:[[asset defaultRepresentation] fullResolutionImage]]];
} failureBlock:nil];
return headerCell;
}
else return headerCell;
}
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:#"detailCell" forIndexPath:indexPath];
return cell;
}
- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath {
if (indexPath.section == 0) {
return 290;
}
else return 60;
}
- (CGFloat)tableView:(UITableView *)tableView estimatedHeightForRowAtIndexPath:(NSIndexPath *)indexPath {
if (indexPath.section == 0) {
return 290;
}
else return 60;
}
- (void)didClickLeftButton:(UIButton *)leftButton {
[self dismissViewControllerAnimated:YES completion:nil];
}
#end
I tried to put dequeueReusableCellWithIdentifier into a different thread, apparently it wouldn't work.
UPDATE: KidDetailHeaderTableViewCell.m
- (void)awakeFromNib {
// Initialization code
[_avatarImage.layer setCornerRadius:_avatarImage.frame.size.width / 2];
[_avatarImage.layer setBorderColor:[UIColor whiteColor].CGColor];
[_avatarImage.layer setBorderWidth:1.0];
[_avatarImage setClipsToBounds:YES];
}
- (IBAction)leftButtonClicked:(UIButton *)sender {
if (self.delegate && [self.delegate respondsToSelector:#selector(didClickLeftButton:)]) {
[self.delegate didClickLeftButton:sender];
}
}
- (IBAction)rightButtonClicked:(UIButton *)sender {
if (self.delegate && [self.delegate respondsToSelector:#selector(didClickRightButton:)]) {
[self.delegate didClickRightButton:sender];
}
}
KidDetailHeaderTableViewCell.h
#protocol KidDetailHeaderCellDelegate <NSObject>
#optional
- (void)didClickLeftButton:(UIButton *)leftButton;
- (void)didClickRightButton:(UIButton *)rightButton;
#end
#interface KidDetailHeaderTableViewCell : UITableViewCell
#property (weak) id<KidDetailHeaderCellDelegate> delegate;
#property (weak, nonatomic) IBOutlet UILabel *fullNameLabel;
#property (weak, nonatomic) IBOutlet UIImageView *avatarImage;
#property (weak, nonatomic) IBOutlet UILabel *nicknameLabel;
#property (weak, nonatomic) IBOutlet UILabel *ageText;
#property (weak, nonatomic) IBOutlet UILabel *ageLabel;
#property (weak, nonatomic) IBOutlet UILabel *momentsStatistics;
#property (weak, nonatomic) IBOutlet UILabel *momentsLabel;
#property (weak, nonatomic) IBOutlet UIButton *rightButton;
#property (weak, nonatomic) IBOutlet UIButton *leftButton;
#end
UPDATE 2:
screenshot of instrument
The code for set the height of the cell. I have two sections, the first section actually is only used for header, the height is 290.
- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath {
if (indexPath.section == 0) {
return 290;
}
else return 60;
}

One of my friend pointed out that problem was caused by the custom font (Yes! I used custom font in the custom view). I still not sure about why this causes the problem (the font named 'hero'), but hope this will help someone else.

Related

Why my tableView stretch out?

I create a LMLUpspringChoosePeriodView and on it there is a tableView and a backgroundView,
I can use the LMLUpspringChoosePeriodView as the popup View, in my project.
This is the directory of it:
the LMLUpspringChoosePeriodView have ChoosePeriodTableViewHeader and LMLUpspringPeriodCell, all of them I create a XIB:
And In the LMLUpspringPeriodCell, I add the constraints to the name label, so it must be on the centre of the LMLUpspringPeriodCell:
But however, when I show the LMLUpspringChoosePeriodView as popup view, there comes an issue:
The tableView seems strech out of the screen.
My tableView's constraints is like this:
My code is below:
LMLUpspringChoosePeriodView.h:
typedef void(^LMLUpspringBlock)();
#import <UIKit/UIKit.h>
#interface LMLUpspringChoosePeriodView : UIView
#property (weak, nonatomic) IBOutlet UIView *upspringBackView;
#property (weak, nonatomic) IBOutlet UITableView *tableView;
#property (weak, nonatomic) IBOutlet NSLayoutConstraint *bottom_tableView;
#property (nonatomic, copy) LMLUpspringBlock block;
- (void)showSelf;
- (void)hideSelf;
#end
LMLUpspringChoosePeriodView.m:
#import "LMLUpspringChoosePeriodView.h"
#import "LMLUpspringPeriodCell.h"
#import "ChoosePeriodTableViewHeader.h"
#interface LMLUpspringChoosePeriodView () <UITableViewDelegate, UITableViewDataSource>
#property (weak, nonatomic) IBOutlet NSLayoutConstraint *width_tableView;
#property (nonatomic, strong) NSArray *title_arr;
#end
#implementation LMLUpspringChoosePeriodView
/*
// Only override drawRect: if you perform custom drawing.
// An empty implementation adversely affects performance during animation.
- (void)drawRect:(CGRect)rect {
// Drawing code
}
*/
- (void)awakeFromNib {
[super awakeFromNib];
//_width_tableView.constant = KWidth;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
return 4;
}
- (UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section {
ChoosePeriodTableViewHeader *header = [[NSBundle mainBundle] loadNibNamed:#"ChoosePeriodTableViewHeader" owner:self options:nil].firstObject;
header.cancel_block = ^() {
[self hideSelf];
};
return header;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
LMLUpspringPeriodCell *cell = [tableView dequeueReusableCellWithIdentifier:#"LMLUpspringPeriodCell"];
if (cell == nil) {
cell = [[NSBundle mainBundle] loadNibNamed:#"LMLUpspringPeriodCell" owner:self options:nil].firstObject;
}
// 配置cell
cell.title_label.text = self.title_arr[indexPath.row];
if (indexPath.row == 3) {
cell.bottom_line.hidden = YES;
}
[self setNeedsLayout];
[self layoutIfNeeded];
return cell;
}
- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath {
return 44;
}
- (CGFloat)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section {
return 48;
}
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
[tableView deselectRowAtIndexPath:indexPath animated:YES];
LMLUpspringPeriodCell *cell = [tableView cellForRowAtIndexPath:indexPath];
NSString *period_str = cell.title_label.text;
self.block(period_str);
[self hideSelf];
}
#pragma mark - action
- (void)showSelf {
self.hidden = NO;
[UIView animateWithDuration:0.5 animations:^{
_bottom_tableView.constant = -49;
_upspringBackView.alpha = 0.3f;
}];
}
- (void)hideSelf {
_bottom_tableView.constant = -_tableView.bounds.size.height - 49;
[UIView animateWithDuration:0.25 animations:^{
_upspringBackView.alpha = 0.f;
[self layoutIfNeeded];
} completion:^(BOOL finished) {
if (finished) {
self.hidden = YES;
}
}];
}
- (IBAction)tapBackView:(id)sender {
[self hideSelf];
}
#pragma mark - setter
-(NSArray *)title_arr {
if (!_title_arr) {
_title_arr = #[#"当天", #"最近一周", #"最近一个月", #"最近三个月"];
}
return _title_arr;
}
#end
The ChoosePeriodTableViewHeader.h:
#import <UIKit/UIKit.h>
typedef void(^CancelChooseUpspringView)();
#interface ChoosePeriodTableViewHeader : UIView
#property (nonatomic, copy) CancelChooseUpspringView cancel_block;
#end
The ChoosePeriodTableViewHeader.m:
#import "ChoosePeriodTableViewHeader.h"
#implementation ChoosePeriodTableViewHeader
/*
// Only override drawRect: if you perform custom drawing.
// An empty implementation adversely affects performance during animation.
- (void)drawRect:(CGRect)rect {
// Drawing code
}
*/
// 取消
- (IBAction)cancel:(UIButton *)sender {
self.cancel_block();
}
The LMLUpspringPeriodCell.h:
#import <UIKit/UIKit.h>
typedef void(^ConfirmChoosePeriod)(NSString *);
#interface LMLUpspringPeriodCell : UITableViewCell
#property (weak, nonatomic) IBOutlet UILabel *title_label;
#property (weak, nonatomic) IBOutlet UIView *bottom_line;
#property (nonatomic, copy) ConfirmChoosePeriod confirm_block;
#end
The LMLUpspringPeriodCell.m:
#import "LMLUpspringPeriodCell.h"
#implementation LMLUpspringPeriodCell
- (void)awakeFromNib {
[super awakeFromNib];
// Initialization code
}
- (void)setSelected:(BOOL)selected animated:(BOOL)animated {
[super setSelected:selected animated:animated];
// Configure the view for the selected state
}
#end
I have tried use the below code in the awakeFromNib method in the LMLUpspringChoosePeriodView.m(you can see the LMLUpspringChoosePeriodView.m code, there is annotation in the awakeFromNib method ):
_width_tableView.constant = KWidth;
Replace of the tableView using trailling to constraint the tableView, it still strech out, but use the below code :
_width_tableView.constant = KWidth / 2;
It is perfect in iPhone7, but have issue in iPhone7 Plus:
So, it is a very strange issue here, how to do with that?
Not enough, there is second issue, the last item can not click, I don't know if is related to the tabbar.
How to solve the two issue? Thanks in advance.
EDIT -1
I add the LMLUpspringChoosePeriodView to the kwyWindow on a VC:
#property (nonatomic, strong) LMLUpspringChoosePeriodView *upspring_v;
....
[[UIApplication sharedApplication].keyWindow addSubview:self.upspring_v];
EDIT -2
This is my PurchaseRecordVC.m, in there I show the LMLUpspringChoosePeriodView:
#import "PurchaseRecordVC.h"
#import "LMLUpspringChoosePeriodView.h"
#interface PurchaseRecordVC ()
#property (nonatomic, strong) LMLUpspringChoosePeriodView *upspring_v;
#end
#implementation PurchaseRecordVC
- (void)viewDidLoad {
[super viewDidLoad];
[self initData];
[self initUI];
}
#pragma mark - init
- (void)initData {
}
- (void)initUI {
// 添加界面
[[UIApplication sharedApplication].keyWindow addSubview:self.upspring_v];
}
#pragma mark - Navigation
// In a storyboard-based application, you will often want to do a little preparation before navigation
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender {
// Get the new view controller using [segue destinationViewController].
// Pass the selected object to the new view controller.
}
- (IBAction)clickTheChoosePeriod:(UIButton *)sender {
[_upspring_v showSelf];
}
#pragma mark - getter
- (LMLUpspringChoosePeriodView *)upspring_v {
if (!_upspring_v) {
_upspring_v = [[NSBundle mainBundle] loadNibNamed:#"LMLUpspringChoosePeriodView" owner:self options:nil].firstObject;
// 初始化
_upspring_v.upspringBackView.alpha = 0;
_upspring_v.bottom_tableView.constant = -_upspring_v.tableView.bounds.size.height - 49;
_upspring_v.hidden = YES;
_upspring_v.block = ^(NSString *period){
};
}
return _upspring_v;
}
#pragma mark - dealloc
- (void)dealloc {
// 移除界面
[self.upspring_v removeFromSuperview];
}
#end
I created a playground satisfying the same conditions, but altered it a bit for you to use as an example
Here you go:
https://wetransfer.com/downloads/7cf7267e51b7d265204a3ceaed48d0fd20170424125153/c92374

Get indexpath If user edit the UITextfield in UITableview

I'm using the UITableview like below image. If i typing Unit price and Qty i need to calculate. But now i dont know how to get indexpath for two text box in UITableView . In UITableView if button clicking goes to didSelectRowAtIndexPath method. Same method not calling when I typing in qty and unitprice textbox.
InvoiceMainViewController.h
#import <UIKit/UIKit.h>
#import <QuartzCore/QuartzCore.h>
#class InvoiceGridViewController;
#protocol InvoiceTableCellProtocoll <NSObject>
-(void) didPressButton:(InvoiceGridViewController *)theCell;
#end
#interface InvoiceGridViewController : UITableViewCell {
id<InvoiceTableCellProtocoll> delegationListener; }
#property (nonatomic,assign) id<InvoiceTableCellProtocoll> delegationListener;
#property (nonatomic,retain) IBOutlet UITextField *invoiceItem;
#property (nonatomic,retain) IBOutlet UITextField *invoiceUnitPrice;
#property (nonatomic,retain) IBOutlet UITextField *invoiceQty;
#property (nonatomic,retain) IBOutlet UITextField *invoiceTaxRate;
#property (nonatomic,retain) IBOutlet UILabel *invoiceItemId;
#property (nonatomic,retain) IBOutlet UILabel *invoiceCurrencyId;
#property (nonatomic,retain) IBOutlet UILabel *invoiceTaxRateId;
#property (nonatomic,retain) IBOutlet UILabel *totalItemTax; #property
#property (nonatomic,retain) IBOutlet UILabel *converstionMessage;
-(IBAction)deleteSel:(id)sender;
-(void)delFileSel;
#end
InvoiceMainViewController.m
#import <UIKit/UIKit.h>
#import "SBPickerSelector.h"
#import <Foundation/Foundation.h>
#import "AFHTTPRequestOperationManager.h"
#import "AFURLResponseSerialization.h"
#import "AFURLRequestSerialization.h"
#import "InvoiceGridViewController.h"
#interface InvoiceMainViewController : UIViewController<UITableViewDataSource, UITableViewDelegate,NSXMLParserDelegate,UITextFieldDelegate,InvoiceTableCellProtocoll>{
you can do this in various methods
Type -1
// get the current visible rows
NSArray *paths = [yourtableName indexPathsForVisibleRows];
NSIndexPath *indexpath = (NSIndexPath*)[paths objectAtIndex:0];
Type-2
you can get which cell you touched
CGPoint touchPoint = [sender convertPoint:CGPointZero toView: yourtableName];
NSIndexPath *clickedButtonIndexPath = [mainTable indexPathForRowAtPoint: yourtableName];
Type-3
add `TapGestuure ` for get the current cell.
Type-4
- (void) textFieldDidEndEditing:(UITextField *)textField {
CGRect location = [self convertRect:textField.frame toView:self.tableView];
NSIndexPath *indexPath = [[self.tableView indexPathsForRowsInRect:location] objectAtIndex:0];
// Save the contents of the text field into your array:
[yourArray replaceObjectAtIndex:indexPath.row withObject:textField.text];
}
example
here if you need additional information see this link
Try this one
#import "ViewController.h"
#interface ViewController ()
#end
#implementation ViewController
- (void)viewDidLoad
{
[super viewDidLoad];
firstTxt.delegate = self;
secondTxt.delegate = self;
// Do any additional setup after loading the view, typically from a nib.
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
- (BOOL)textFieldShouldBeginEditing:(UITextField *)textField{
NSLog(#"textFieldShouldBeginEditing");
textField.backgroundColor = [UIColor colorWithRed:220.0f/255.0f green:220.0f/255.0f blue:220.0f/255.0f alpha:1.0f];
return YES;
}
- (void)textFieldDidBeginEditing:(UITextField *)textField{
NSLog(#"textFieldDidBeginEditing");
}
- (BOOL)textFieldShouldEndEditing:(UITextField *)textField{
NSLog(#"textFieldShouldEndEditing");
textField.backgroundColor = [UIColor whiteColor];
return YES;
}
- (void)textFieldDidEndEditing:(UITextField *)textField{
NSLog(#"textFieldDidEndEditing");
[tableView reloadData];
}
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event{
NSLog(#"touchesBegan:withEvent:");
[self.view endEditing:YES];
[super touchesBegan:touches withEvent:event];
}
#pragma mark -
#pragma mark - UITableView Delegates
- (UITableViewCell *)tableView:(UITableView *)tableView1 cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableViewCell *cell = [tableView1 dequeueReusableCellWithIdentifier:#"FirstTableViewCell"];
if (cell == nil)
{
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:#"FirstTableViewCell"];
// cell = [[UITableViewCell alloc]initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:CellIdentifier];
}
if (![firstTxt.text isEqual: #""] && ![secondTxt.text isEqual: #""])
{
NSString *fir = firstTxt.text;
NSString * sec = secondTxt.text;
cell.textLabel.text= [NSString stringWithFormat:#"%d",[fir intValue]+[sec intValue]];
}
else
{
cell.textLabel.text=#"";
}
//etc.
return cell;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
return 4;
}
-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
// NSLog(#"testing1");
}
- (void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath
{
cell.layer.backgroundColor = [UIColor clearColor].CGColor;
cell.backgroundColor = [UIColor clearColor];
}
#end
.h
//
// ViewController.h
// TestingText
#import <UIKit/UIKit.h>
#interface ViewController : UIViewController<UITableViewDelegate,UITableViewDataSource,UITextFieldDelegate>
{
IBOutlet UITableView *tableView;
IBOutlet UITextField *secondTxt;
IBOutlet UITextField *firstTxt;
}
#end
In textfield delegate method you can get the indexpath of row or you can directly get the textfields text
-(void)textFieldDidEndEditing:(UITextField *)textField
{
CGPoint hitPoint = [txtfield convertPoint:CGPointZero toView:tbl];
hitIndex = [tbl indexPathForRowAtPoint:hitPoint];
int localCount = [txtfield.text intValue];
}
Subclass your UITableViewCells. Create a protocol for each cell, with methods like cellName:(UITableViewCell*)cellName didSelectItem:(Item*) item. You can find more info here.
In the UITableViewCell set your UITextView delegate to self, and implement the protocol. textFieldShouldReturn: method, will indicate when the user is typing, so inside you will call [self.delegate cellName:self didEditText:textField.text].
In your MainViewController tableView: cellForRowAtIndexPath: set the UITabelViewCell's delegates, and implement the protocols.
So you will know in MainViewController when a user has typed in any of your textfields, independently from the table row number.

UITableView section header clickable Delegate not Call

I am new to ios development. I am create app in Storyboard, Initially UItableviewController with one prototype cells, with button and labels. The button has IBAction method in it UItableViewCell Class, the class has Delegate to UItableviewController,the delegate method does not called. But the Images in section view is change. The i post my full code here.
Download whole project from Link
ContactHeaderViewCell.h
#protocol SectionClick;
#protocol SectionClick <NSObject>
#optional
- (void) TickCheckbox : (NSInteger) section;
- (void) UnTickCheckbox : (NSInteger) section;
#end
#interface ContactHeaderViewCell : UITableViewCell
{
id<SectionClick> HeaderDelegate;
}
#property (strong, nonatomic) IBOutlet UILabel *lblName;
#property (strong, nonatomic) IBOutlet UIButton *btnCheckBox;
#property (strong, nonatomic) IBOutlet UIButton *btnArrow;
- (IBAction)btnCheckBox_click:(id)sender;
- (IBAction)btnArrow_Click:(id)sender;
#property (nonatomic, strong) id<SectionClick> HeaderDelegate;
#property (nonatomic) NSInteger section;
- (void) setDelegate:(id)delegate;
#end'
ContactHeaderViewCell.m
#implementation ContactHeaderViewCell
#synthesize HeaderDelegate,section;
- (void) setDelegate:(id)delegate
{
self.HeaderDelegate = delegate;
}
- (void)awakeFromNib {
// Initialization code
}
- (void)setSelected:(BOOL)selected animated:(BOOL)animated {
[super setSelected:selected animated:animated];
// Configure the view for the selected state
}
- (IBAction)btnCheckBox_click:(id)sender {
self.btnCheckBox.selected = !self.btnCheckBox.selected;
if (self.btnCheckBox.selected)
{
if ([self.HeaderDelegate respondsToSelector:#selector(UnTickCheckbox:)])
{
[self.HeaderDelegate UnTickCheckbox:self.section];
}
} else
{
if ([self.HeaderDelegate respondsToSelector:#selector(TickCheckbox:)])
{
[self.HeaderDelegate TickCheckbox:self.section];
}
}
}
ContactTableViewController.m
#import "ContactDetail.h"
#import "ContactHeaderViewCell.h"
#interface ContactTableViewController : UITableViewController<SectionClick>
#property(nonatomic) ContactDetail *contacts;
#property(nonatomic) NSMutableArray *ContactList;
#end
ContactTableViewController.m
#import "ContactTableViewController.h"
#import <AddressBook/AddressBook.h>
#import "ContactHeaderViewCell.h"
#import "UserDetailViewCell.h"
#interface ContactTableViewController ()
#end
#implementation ContactTableViewController
- (id)initWithStyle:(UITableViewStyle)style
{
self = [super initWithStyle:style];
if (self) {
}
return self;
}
- (void)viewDidLoad {
[self ArrayContactFunc];
[super viewDidLoad];
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
}
#pragma mark - Table view data source
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
return [self.ContactList count];
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
self.contacts =(self.ContactList)[section];
return (self.contacts.Isopen) ? [self.contacts.mobileNumbers count] : 0;
}
-(UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section
{
static NSString *HeaderIdentifier = #"HeaderCell";
self.contacts = (self.ContactList)[section];
ContactHeaderViewCell *HeaderView = (ContactHeaderViewCell *)[self.tableView dequeueReusableCellWithIdentifier:HeaderIdentifier];
if (HeaderView == nil){
[NSException raise:#"headerView == nil.." format:#"No cells with matching CellIdentifier loaded from your storyboard"];
}
HeaderView.lblName.text = self.contacts.fullName;
if(self.contacts.IsChecked)
{
[HeaderView.btnCheckBox setImage:[UIImage imageNamed:#"Unchecked.png"] forState:UIControlStateSelected];
}
else
{
[HeaderView.btnCheckBox setImage:[UIImage imageNamed:#"Checked.png"] forState:UIControlStateSelected];
}
return HeaderView;
}
- (UITableViewCell *)cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
self.contacts = (self.ContactList)[indexPath.section];
static NSString *DetailCellIdentifier = #"DetailCell";
UserDetailViewCell *cell = [self.tableView dequeueReusableCellWithIdentifier:DetailCellIdentifier];
if(!cell)
{
[NSException raise:#"headerView == nil.." format:#"No cells with matching CellIdentifier loaded from your storyboard"];
}
cell.lblDetail.text = (self.contacts.mobileNumbers)[indexPath.row];
return cell;
}
- (CGFloat)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section
{
return 60.0;
}
-(void)UnTickCheckbox:(NSInteger)section
{
// self.contacts = (self.ContactList)[section];
// self.contacts.IsChecked = NO;
// [self.tableView reloadData];
}
-(void)TickCheckbox:(NSInteger)section
{
// self.contacts = (self.ContactList)[section];
// self.contacts.IsChecked = YES;
// [self.tableView reloadData];
}
Thank in advance.
You must add this line
[HeaderView setHeaderDelegate:self];
in method:
-(UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section;

Set label for a custom cell

I have a custom table cell and I'm just trying to set the label, image, etc but for some reason it's not working.
Here is my code for my custom cell
BrowserMenuCell.h
#import <UIKit/UIKit.h>
#interface BrowseMenuCell : UITableViewCell
#property (strong, nonatomic) IBOutlet UIButton *wishListBUtton;
#property (strong, nonatomic) IBOutlet UIImageView *itemImage;
#property (strong, nonatomic) IBOutlet UILabel *itemLabel;
#property (strong, nonatomic) IBOutlet UILabel *itemPrice;
#property (strong, nonatomic) IBOutlet UITextField *quantityField;
#property (strong, nonatomic) IBOutlet UILabel *totalLabel;
- (IBAction)plusButton:(id)sender;
- (IBAction)cartButton:(id)sender;
- (IBAction)minusButton:(id)sender;
#end
BrowserMenuCell.m
#import "BrowseMenuCell.h"
#implementation BrowseMenuCell
- (id)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier
{
self = [super initWithStyle:style reuseIdentifier:reuseIdentifier];
if (self) {
// Initialization code
}
return self;
}
- (void)setSelected:(BOOL)selected animated:(BOOL)animated
{
[super setSelected:selected animated:animated];
// Configure the view for the selected state
}
- (IBAction)plusButton:(id)sender {
}
- (IBAction)cartButton:(id)sender {
}
- (IBAction)minusButton:(id)sender {
}
#end
Cell for row at index path
-(UITableViewCell *)tableView:(UITableView *)tableView
cellForRowAtIndexPath:(NSIndexPath *)indexPath {
BrowseMenuCell *cell = [tableView dequeueReusableCellWithIdentifier:#"ItemsCell"];
OfficeSupply *supply = [_items objectAtIndex:indexPath.row];
if(cell == nil)
{
NSArray * views = [[NSBundle mainBundle] loadNibNamed:#"BrowseMenuCell" owner:nil options:nil];
for (id obj in views){
if([obj isKindOfClass:[UITableViewCell class]])
{
BrowseMenuCell * obj = [[BrowseMenuCell alloc]init];
obj.itemLabel.text = supply.itemName;
cell = obj;
break;
}
}
}
return cell;
}
Have you tried using [self.tableView reloadData]?
To start with, don't create a new random instance of the cell after you have already created one from the NIB file. Change the code to this:
for (BrowseMenuCell *obj in views){
if([obj isKindOfClass:[BrowseMenuCell class]])
{
obj.reuseIdentifier = #"ItemsCell";
obj.itemLabel.text = supply.itemName;
cell = obj;
break;
}
}
That won't guarantee it works, but at least the NIB setup of your labels won't be getting thrown away.
If it still doesn't work. Debug. Check the frames of the labels. Check the label references are set (not nil).
This is the wrong way you create cell. Try this one:
-(UITableViewCell *)tableView:(UITableView *)tableView
cellForRowAtIndexPath:(NSIndexPath *)indexPath {
BrowseMenuCell *cell = (BrowseMenuCell*)[tableView dequeueReusableCellWithIdentifier:#"ItemsCell"];
OfficeSupply *supply = [_items objectAtIndex:indexPath.row];
if (_cellObj == nil) {
[[NSBundle mainBundle] loadNibNamed:#"BrowseMenuCell" owner:nil options:nil];
}
cell.itemlabel.text = supply.itemName;
return cell;
}

UIImageView background color but not image displaying

I have a UITableViewCell nib file in which there is a UIImageView and a UILabel. I have outlets for both of these to my controller as well as an outlet for the cell itself. I am setting the label and image programmatically, but the image does not show up.
So I went to test it, and even if I set the image itself in the nib file, it does not show up. If I set the background color, it shows up fine. Any ideas? I'm stuck.
It seems to be unrelated to code, in my mind, since it doesn't even work via nib file. But here it is anyway in case it helps somehow.
MyViewController.h
#interface MyViewController : UITableViewController
#property (strong, nonatomic) MyModel *myModel;
#property (strong, nonatomic) NSArray *tableViewCells;
#property (strong, nonatomic) IBOutlet UITableViewCell *tableViewCell;
#property (weak, nonatomic) IBOutlet UILabel *myLabel;
#property (weak, nonatomic) IBOutlet UIImageView *myImage;
#end
MyViewController.m
#interface MyViewController ()
- (void)bindMyModel:(MyModel*)model toView:(UITableViewCell*)view;
- (UITableViewCell*)copyUITableViewCell:(UITableViewCell*)cell;
#end
#implementation MenuViewController
#synthesize myModel = _myModel;
#synthesize tableViewCells = _tableViewCells;
#synthesize tableViewCell = _tableViewCell;
#synthesize myLabel = _myLabel;
#synthesize myImage = _myImage;
- (void)viewDidLoad
{
[super viewDidLoad];
NSMutableArray *cells = [[NSMutableArray alloc] init];
[MyModel loadAndOnSuccess:^(id data, id context) {
self.myModel = data;
for (MyModel *item in self.myModel.items) {
[[NSBundle mainBundle] loadNibNamed:#"TableCellNib" owner:self options:nil];
[self bindMyModel:item toView:self.tableViewCell];
[cells addObject:[self copyUITableViewCell:self.tableViewCell]];
self.tableViewCell = nil;
}
self.tableViewCells = [[NSArray alloc] initWithArray:cells];
} onFail:^(NSString *error, id context) {
NSLog(#"FAIL with error: %#", error);
}];
}
- (void)viewDidUnload
{
[self setTableViewCell:nil];
[self setMyLabel:nil];
[self setMyImage:nil];
[super viewDidUnload];
}
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
return YES;
}
- (void) bindMyModel:(MyModel*)model toView:(UITableViewCell*)view
{
if (view) {
self.myLabel.text = model.myLabelText;
self.myImage.image = model.myImageResource;
self.myLabel = nil;
self.myImage = nil;
}
}
- (UITableViewCell*)copyUITableViewCell:(UITableViewCell*)cell
{
NSData *archivedData = [NSKeyedArchiver archivedDataWithRootObject: cell];
return [NSKeyedUnarchiver unarchiveObjectWithData: archivedData];
}
#pragma mark - Table view data source
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
return [self.tableViewCells objectAtIndex:indexPath.row];
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
return self.myModel.items.count;
}
#pragma mark - Table view delegate
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
// Irrelevant code here
}
- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
{
return ((UITableViewCell*)[self.tableViewCells objectAtIndex:indexPath.row]).frame.size.height;
}
#end
You are trying to use two IBOutlets on your UITableViewController to populate a multitude of UILabels and UIImageViews that are part of the UITableViewCell. You need to create a custom subclass of UITableViewCell and add the IBOutlets to that subclass.
#interface CustomCell : UITableViewCell
#property (weak, nonatomic) IBOutlet UILabel *myLabel;
#property (weak, nonatomic) IBOutlet UIImageView *myImage;
#end
then in your bindMyModel:toView:
- (void) bindMyModel:(MyModel*)model toView:(CustomCell*)view
{
if (view) {
view.myLabel.text = model.myLabelText;
view.myImage.image = model.myImageResource;
}
}
Now you have independent IBOutlets for each of your Cells. You will also need to change some of your bindings as well. This is a fix, but honestly I would rewrite a lot of the code and just use dequeueReusableCellWithIdentifier in your cellForRowAtIndexPath call, and keep a pool of CustomCells that you will reuse, and just set up the myLabel.text and myImage.image in the cellForRowAtIndexPath call.

Resources