I'm pretty new to iOS dev so please bear with me.
I created a simple app that had a TabBarController with 2 items. The first item was a TableViewController with some cells and the 2nd item was a simple UIView with a picture and some text. Everything worked just fine in the simulator. This was all done programmatically (did not use storyboard)
I wanted to practice using the storyboard so I decided to try and replicate the original program I made using a storyboard. The problem arises when created a TableViewController. It's asking me to specify a "reuse identifier" , at first I tried naming them all "cell" but it said I couldn't use the same identifier, so then I set the first one to "cell1" and the next to "cell2" and so on.. I didn't have to do this when I wrote the app with just code, so why now?
My coded TableViewController looks like:
#implementation FeedTableViewController
- (id)init //constructor
{
self = [super init];
if (self)
{
self.title = #"Feed";
}
return self;
}
- (void)viewDidLoad {
[super viewDidLoad];
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
}
#pragma mark - Table view data source
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
// Return the number of sections.
return 1;
}
- (NSInteger)tableView:(UITableView *)tableView
numberOfRowsInSection:(NSInteger)section
{
return 10;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:#"Title"];
if (cell == nil)
{
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:#"Title"];
}
cell.textLabel.text = [NSString stringWithFormat:#"%li", indexPath.row];
return cell;
}
in the last method
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
I just named them all "title" and it ran fine.
Thanks in advance for the help
Related
I have made a custom cell in the storyboard having height 300, which include label and imageView, but for some case if I had not received image from the response I want to decrease the cell height and want to remove the imageView from the cell so that it could not be visible to the user .
In that case I just want to show the text in the label.
How could I achieve that? I know its silly question but I am stuck here.
Your help would be appreciated.
Thanks
I have wrote some basic code fro your understanding how table view cell resizing works (irrelevant of custom or basic cells).
#interface MasterViewController ()
#property NSArray *objects;
#end
#implementation MasterViewController
- (void)viewDidLoad {
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
_objects = [NSArray arrayWithContentsOfFile:[[NSBundle mainBundle] pathForResource:#"ImageList" ofType:#"plist"]];
}
- (void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
#pragma mark - Table View
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
return 1;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
return _objects.count;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:#"Cell" forIndexPath:indexPath];
NSDictionary *object = _objects[indexPath.row];
cell.textLabel.text = object[#"text"];
cell.imageView.image = [UIImage imageNamed:object[#"image"]];
return cell;
}
//- (NSString *) tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section {
// return _objects.allKeys[section];
//}
- (BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath {
// Return NO if you do not want the specified item to be editable.
return YES;
}
- (CGFloat) tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath {
return [_objects[indexPath.row][#"image"] length] ? 60.0f : 30.0f;
}
#end
In above code you prime focus should be on method heightForRowAtIndexPath and it's code line return [_objects[indexPath.row][#"image"] length] ? 60.0f : 30.0f;.
Now as if you load image dynamically from server then keep track for image of which cell is been loaded and call [tableView reloadRowsAtIndexPaths:<#(nonnull NSArray<NSIndexPath *> *)#> withRowAnimation:<#(UITableViewRowAnimation)#>] with relevant index path. Also make sure you update image loaded information in your dataSource i.e. _objects in above code.
I have uploaded code here. Check UITableViewTest in workspace.
I am trying to customize my UITableView cells and have done it successfully without problems before but that was using a storyboard. Now i am doing it using a xib file. For some reason I cannot change the cells to be "custom" cells not static. Even simple things like numberofcells methods don't work because I can't make the cells custom. Usually in a storyboard I would "delete" the cells or change them but I can't even select a cell in the nib file!
I can't find any way to do this and using storyboards is not really an option at this point. My code is below, thanks!
#import "YouTubeViewController.h"
#import "YouTubeCell.h"
#interface YouTubeViewController ()
#end
#implementation YouTubeViewController
- (void)viewDidLoad {
[super viewDidLoad];
// Do any additional setup after loading the view from its nib.
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
-(BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath
{
return NO;
}
-(BOOL)tableView:(UITableView *)tableView canMoveRowAtIndexPath:(NSIndexPath *)indexPath
{
return NO;
}
-(UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath
{
return UITableViewCellEditingStyleNone;
}
- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
{
return 88;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
return 1;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
NSString *reuseIdentifier = #"YouTubeCell"; UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:reuseIdentifier];
if (cell == nil)
{
cell = [[[NSBundle mainBundle] loadNibNamed:#"YouTubeCell" owner:nil options:nil] objectAtIndex:0];
}
//set up cell
return cell;
// [[cell authorName] setText:#"Collin Ruffenach"];
// [[cell articleName] setText:#”Test Article 1″];
// [[cell date] setText:#”May 5th, 2009″];
// [[cell imageView] setImage:[UIImage imageNamed:#"1.png"]];
}
/*
#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.
}
*/
#end
It turns out all I needed to do was set up the delegate and datasource by control clicking from the uitableview to the "files owner". Everything worked after that!
I am very new to iOS but I've created a view controller with a table view which i want to put into editing mode. This is my view controller implementation file code:
#import "ViewController.h"
#interface ViewController ()
#end
#implementation ViewController
#synthesize progsTable, programmes;
- (void)viewDidLoad
{
[super viewDidLoad];
programmes = [[NSMutableArray alloc] initWithObjects:#"one",#"two",#"three",nil];
//set the title
self.title = #"Programmes";
//add an edit button
self.navigationItem.leftBarButtonItem = self.editButtonItem;
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
- (void)setEditing:(BOOL)editing animated:(BOOL)animated
{
[super setEditing:editing animated:animated];
[progsTable setEditing:editing animated:animated];
}
#pragma mark - UITableView Datasource
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
return 1;
}
-(NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
return programmes.count;
}
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *cellIdentifier = #"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier];
if(cell==nil) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:cellIdentifier];
}
cell.textLabel.text = [programmes objectAtIndex: indexPath.row];
return cell;
}
- (BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *) indexPath {
return YES;
}
- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath
{
if (editingStyle==UITableViewCellEditingStyleDelete) {
//remove from array
[programmes removeObjectAtIndex:indexPath.row];
//remove from table
[tableView deleteRowsAtIndexPaths:#[indexPath] withRowAnimation:UITableViewRowAnimationFade];
}
}
#pragma mark - UITableView Delegate methods
-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
}
#end
I get the edit button in the top left but when i click it the red delete buttons don't appear - what am I doing wrong?
Running your exact code does work - the delete buttons are displaying when i test it.
I believe the problem is that you haven't assigned your #property called progsTable to your Table View.
To solve it do the following:
Go to your Storyboard
Right click on your View Controller
Click and hold the + next to the outlet called progsTable while you drag the mouse to your Table View, like this:
Try running your app - the delete buttons should now appear.
I think you need to add the code below:
- (UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath {
return UITableViewCellEditingStyleDelete; }
This tells the UITableView which editing style you want.
Use this
- (IBAction)deleteDrug:(id)sender event:(id)event {
selectedButtonIndex = [self indexPathForButton:sender event:event];
[tableView setEditing:YES animated:YES];
}
- (BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath
{
if (indexPath == selectedButtonIndex) {
return YES;
}
return NO;
}
You may need to implement this method for your datasource.
- (UITableViewCellEditingStyle) tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath
{
return UITableViewCellEditingStyleDelete;
}
Check that you also have auto-layout constraints added in interface builder so that the very end of the cell lines up with the width of your device.
Run the code on the ipad in the simulator, if the delete button shows up there but not on the iphone simulator then it probably just that the contents are not aligned properly to the viewport of your device.
My 'delete' button was not showing up but the cell title content were moving over to the left when I swiped, however I had not set constraints on my cell width in my storyboard, as soon as I set the right-edge constraint to '0' or '16', the delete button appeared.
I'm using this tutorial on how to create a pop out menu.
http://www.appcoda.com/ios-programming-sidebar-navigation-menu/
I got it working when going through the tutorial, now i'm trying to implement it into my app.
I'm at the stage where i can press the menu button and the popout menu appears. The problem is, it doesn't populate itself with my table view cells.
I set the identifiers for each table view cell and then in the code reference them to full an array.
I know when woking through the tutorial, if I misspelled one of the identifiers when defining what's in the array, the program would crash. In my app, that's not the case. Hopefully that can help pin down the problem. It doesn't even change the colours which is the first part of the code.
Here's the code.
#import "SidebarViewController.h"
#import "SWRevealViewController.h"
#interface SidebarViewController ()
#property (nonatomic, strong) NSArray *menuItems;
#end
#implementation SidebarViewController
- (id)initWithStyle:(UITableViewStyle)style
{
self = [super initWithStyle:style];
if (self) {
// Custom initialization
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
self.view.backgroundColor = [UIColor colorWithWhite:0.2f alpha:1.0f];
self.tableView.backgroundColor = [UIColor colorWithWhite:0.2f alpha:1.0f];
self.tableView.separatorColor = [UIColor colorWithWhite:0.15f alpha:0.2f];
_menuItems = #[#"markup",#"tax"];
}
- (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 1;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
// Return the number of rows in the section.
return [self.menuItems count];
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
NSString *CellIdentifier = [self.menuItems objectAtIndex:indexPath.row];
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier forIndexPath:indexPath];
return cell;
}
Any help would be great.
Thanks
All you're doing is creating an array with two string literals. You must set the textlabel's text property in the following method to display the strings in table view cells:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
static NSString *CellIdentifier = #"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
cell = [[[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier] autorelease];
}
cell.textLabel.text = [_menuItems objectAtIndexPath:indexPath.row];
return cell;
}
OMG I feel like such a noob. It turns out the ViewControler didn't have a target, hence why it wasn't responding.
I'm so sorry for wasting your time, I really feel bad now.
I just followed a few steps in a tutorial to create a simple TableView with 50 rows but i get "Signal SIGABRT" :/
I connected the TableView in Storyboard with the TableViewController-Class i created.
Here's my simple code:
#import "TableViewController.h"
#interface TableViewController ()
#end
#implementation TableViewController
- (id)initWithStyle:(UITableViewStyle)style
{
self = [super initWithStyle:style];
if (self) {
// Custom initialization
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
// Uncomment the following line to preserve selection between presentations.
// self.clearsSelectionOnViewWillAppear = NO;
// Uncomment the following line to display an Edit button in the navigation bar for this view controller.
// self.navigationItem.rightBarButtonItem = self.editButtonItem;
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
#pragma mark - Table view data source
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
return 1;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
return 50;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = #"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier forIndexPath:indexPath];
// Configure the cell...
cell.textLabel.text = [NSString stringWithFormat:#"Row %i",indexPath.row];
return cell;
}
Welcome to Stack Overflow! The standard methods for setting up UITableViewCells changed slightly a little while ago. This means that the template code Xcode provides for tableViews uses the -tableView: dequeueReusableCellWithIdentifier: forIndexPath: method, while older tutorials and books (most of them) use tableView: dequeueReusableCellWithIdentifier:
If you want to do it the new way ( -tableView: dequeueReusableCellWithIdentifier: forIndexPath) you need to either add
[self.tableView registerClass:[UITableViewCell class] forCellReuseIdentifier:#"Cell"]; in viewDidLoad, (or set the prototype cell reuse id in the storyboard/nib, and set the cell type appropriately - basic should do for a normal cell).
The old way (tableView: dequeueReusableCellWithIdentifier:) is normally followed by an if statement something like:
if(cell == nil)
{
cell = [UITableViewCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
}
(where the \\Configure the cell. . . comment is)
While this is really straightforward stuff, in fairness most tutorials do teach the old way, which I imagine can be confusing for a beginner if you don't notice the small difference between the two -tableView:dequeueReusableCell methods. A tutorial showing the new way is here