setObjectForKey: exception: object cannot be nil - ios

I am building an app using Parse and Xcode. When using the Parse PFTableView I am getting the error:
Terminating app due to uncaught exception
'NSInvalidArgumentException', reason: '*** setObjectForKey: object
cannot be nil (key: classname)'
I understand that I am not setting the key somewhere in my code, but I do not know where and how to fix it.
#import "TableViewController.h"
#import <Parse/Parse.h>
#interface TableViewController ()
#end
#implementation TableViewController
- (id)initWithStyle:(UITableViewStyle)style
{
self = [super initWithStyle:style];
if (self) {
// This table displays items in the Todo class
self.parseClassName = #"Todo";
self.pullToRefreshEnabled = YES;
self.paginationEnabled = YES;
self.objectsPerPage = 25;
}
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;
self.parentViewController.view.backgroundColor = [UIColor colorWithPatternImage:[UIImage imageNamed:#"red_bokeh.png"]];
self.tableView.backgroundColor = [UIColor clearColor];
}
- (void)viewDidUnload
{
[super viewDidUnload];
// Release any retained subviews of the main view.
// e.g. self.myOutlet = nil;
}
- (void)viewWillAppear:(BOOL)animated
{
[super viewWillAppear:animated];
}
- (void)viewDidAppear:(BOOL)animated
{
[super viewDidAppear:animated];
}
- (void)viewWillDisappear:(BOOL)animated
{
[super viewWillDisappear:animated];
}
- (void)viewDidDisappear:(BOOL)animated
{
[super viewDidDisappear:animated];
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
#pragma mark - Table view data source
#pragma mark - Parse
- (void)objectsDidLoad:(NSError *)error {
[super objectsDidLoad:error];
// This method is called every time objects are loaded from Parse via the PFQuery
}
- (void)objectsWillLoad {
[super objectsWillLoad];
// This method is called before a PFQuery is fired to get more objects
}
- (PFQuery *)queryForTable {
PFQuery *query = [PFQuery queryWithClassName:self.parseClassName];
// If no objects are loaded in memory, we look to the cache first to fill the table
// and then subsequently do a query against the network.
if (self.objects.count == 0) {
query.cachePolicy = kPFCachePolicyCacheThenNetwork;
}
[query orderByDescending:#"createdAt"];
return query;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath object:(PFObject *)object
{
static NSString *CellIdentifier = #"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:CellIdentifier];
}
// Configure the cell
cell.textLabel.text = object[#"text"];
cell.detailTextLabel.text = [NSString stringWithFormat:#"Priority: %#",
object[#"priority"]];
return cell;
}
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
[super tableView:tableView didSelectRowAtIndexPath:indexPath];
}
#end
Here is the TableViewController.h:
#import <UIKit/UIKit.h>
#interface TableViewController : PFQueryTableViewController
#end

I solved this issue by following this Parse.com/help
I just change the method from initWithStyle to initWithCoder.
- (id)initWithCoder:(NSCoder *)aDecoder
{
self = [super initWithCoder:aDecoder];
if (self) {
// The className to query on
self.parseClassName = kPAPPhotoClassKey;
// Whether the built-in pull-to-refresh is enabled
self.pullToRefreshEnabled = YES;
// Whether the built-in pagination is enabled
self.paginationEnabled = YES;
// The number of objects to show per page
self.objectsPerPage = 10;
}
return self;
}

The variable self.parseclassname is never being set. If I had to guess, you are probably calling -init on the tableView instead of -initWithStyle
To fix it, in a super-temporary, dirty way, you should change this function in the following way:
- (PFQuery *)queryForTable {
if (!self.parseClassName) {
self.parseClassName = #"Todo";
}
PFQuery *query = [PFQuery queryWithClassName:self.parseClassName];
// If no objects are loaded in memory, we look to the cache first to fill the table
// and then subsequently do a query against the network.
if (self.objects.count == 0) {
query.cachePolicy = kPFCachePolicyCacheThenNetwork;
}
[query orderByDescending:#"createdAt"];
return query;
}

Related

cellForRowAtIndexPath not called when compiled with xcode 6.1

In my app I have a popup with a [table view][1] .
When compiled with Xcode 5.1 everything works fine, but the same code compiled with Xcode 6.1 failed to call the [cellForRowAtIndexPath][3] [delegate][4] method.
The other delegate meths are called.
One intersting point is self.tableView.rowHeight; returns -1
I have tried explicitly setting the delegate and data source to self but that makes not difference
The class is called by the following code;
`-(IBAction)selectLanguage:(id)sender
{
ATLMLanguagePopoverTableViewController *pvc = [[ATLMLanguagePopoverTableViewController alloc] initWithNibName:nil bundle:nil];
pvc.target = self;
pvc.action = #selector(popoverDidSelectItem:);
pvc.items = [[[ATLMLibraryManager getManager]libraryDefaults]getAvailableLanguageNames];
_myPopoverController.contentViewController = pvc;
[_myPopoverController setPopoverContentSize:[pvc popoverContentSize]];
[_myPopoverController presentPopoverFromBarButtonItem:(UIBarButtonItem *)sender permittedArrowDirections:UIPopoverArrowDirectionUp animated:YES];
}
`
Hear is the definition of the class
/
/ LanguagePopoverTableViewController.m
// SalesAid
//
// Created by phuang on 1/16/13.
// Copyright (c) 2013 Align Technology. All rights reserved.
//
#import "ATLMLanguagePopoverTableViewController.h"
#import "ATLMLocalizationManager.h"
#import "ATLMUtils.h"
#interface ATLMLanguagePopoverTableViewController ()
#end
#implementation ATLMLanguagePopoverTableViewController
#synthesize items, selectedItem, target, action;
- (id)initWithStyle:(UITableViewStyle)style
{
self = [super initWithStyle:style];
if (self) {
selectedItem = -1;
target = nil;
action = NULL;
}
return self;
}
-(void) resetLocalization {
[self.tableView reloadData];
}
- (void)didReceiveMemoryWarning
{
// Releases the view if it doesn't have a superview.
[super didReceiveMemoryWarning];
// Release any cached data, images, etc that aren't in use.
}
- (void)setItems:(NSArray *)newItems {
items = [newItems copy];
dispatch_async(dispatch_get_main_queue(), ^{
[self.tableView reloadData];
});
}
#pragma mark - View lifecycle
- (void)viewDidLoad
{
[super viewDidLoad];
}
- (void)viewDidUnload
{
[super viewDidUnload];
}
- (void)viewWillAppear:(BOOL)animated
{
[super viewWillAppear:animated];
selectedItem=0;
NSString *curLang = (NSString *) [[ATLMLocalizationManager getManager]getCurrentLanguage] ;
for(int i = 0; i < items.count ; i++ ){
if([curLang isEqualToString:(NSString *)[items objectAtIndex:i]]){
selectedItem = i;
break;
}
}
NSIndexPath *i = [NSIndexPath indexPathForRow:selectedItem inSection:0];
[self.tableView selectRowAtIndexPath:i animated:NO scrollPosition:UITableViewScrollPositionNone];
}
- (void)viewDidAppear:(BOOL)animated
{
[super viewDidAppear:animated];
}
- (void)viewWillDisappear:(BOOL)animated
{
[super viewWillDisappear:animated];
}
- (void)viewDidDisappear:(BOOL)animated
{
[super viewDidDisappear:animated];
}
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
return YES;
}
- (CGSize)popoverContentSize {
NSInteger rowHeight = self.tableView.rowHeight;
UITableView *tv = self.tableView;
rowHeight = 50;
return CGSizeMake(100, [items count] * rowHeight);
}
#pragma mark - Table view data source
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
return 1;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
return [items 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.font = [UIFont systemFontOfSize:14];
UIView *myBackView = [[UIView alloc] initWithFrame:cell.frame];
myBackView.backgroundColor = [ATLMUtils getAlignBlue];
cell.selectedBackgroundView = myBackView;
[cell setSelectedBackgroundView: myBackView ];
NSString *textLabelKey = [items objectAtIndex:[indexPath indexAtPosition:1]];
cell.textLabel.text = ATLMLocalizedString(textLabelKey, nil);
cell.textLabel.textAlignment = NSTextAlignmentCenter;
return cell;
}
#pragma mark - Table view delegate
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
selectedItem = indexPath.row;
if (target != nil && action != NULL) {
[target performSelector:action withObject:self];
}
}
#end
`
OK to answer my own question;
Basically the code adds the model to the view controller after the init method is called. However is seem the thread model has changed a bit and the view is created before the model is added so the row count in the model is zero
The solution is to pass the model as part of the init method.
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil items:(NSArray *)itemArray
{
self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
if (self) {
// Custom initialization
items = [itemArray copy];
selectedItem = -1;
target = nil;
action = nil;
}
return self;
}

Text in my array is not ending up in my table view cell

I cannot seem to find my error can anyone help me? When I attempt to run test the application it works but when I click on the Calendar segue it shows me a blank uitableview list. I want it to show me the "event" in the text
My NSLOG details about the array:
2014-08-08 17:38:28.391 nths[2899:607] array contents: (
" {\n Date = \"9/14/14\";\n Information = \"Mrs. Ford's Room\";\n event = Meeting;\n}",
" {\n Date = \"9/14/19\";\n Information = \"ford room\";\n event = \"lunch at bravos\";\n}"
)
Here are is all of the code that I think would affect this.
CalendarViewController.h
#import <UIKit/UIKit.h>
#import <Parse/Parse.h>
#import "DataCellViewController.h"
#interface CalendarViewController : UIViewController <UITableViewDelegate> {
NSArray *eventArray;
}
#property (weak, nonatomic)IBOutlet UITableView *Datatable;
#end
CalendarViewController.m
#import "CalendarViewController.h"
#interface CalendarViewController ( )
#end
#implementation CalendarViewController
#synthesize Datatable;
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
[self performSelector:#selector(retrieveFromParse)];
}
- (void) retrieveFromParse {
PFQuery *retrieveDate = [PFQuery queryWithClassName:#"Calendar"];
[retrieveDate findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) {
NSLog(#"%#",objects);
if (!error) {
eventArray = [[NSArray alloc] initWithArray:objects];
}
[Datatable reloadData];
}];
}
//Setup table of folder names
//get number of sections in tableview
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
// Return the number of sections.
return 1;
}
//get number of rows by counting number of folders
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
return eventArray.count;
}
//setup cells in tableView
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
//setup cell
static NSString *CellIdentifier = #"CalenderCell";
DataCellViewController *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
cell = [[DataCellViewController alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
}
// Configure the cell...
NSDictionary *tempDict = [eventArray objectAtIndex:indexPath.row];
cell.eventTitle.text = [tempDict objectForKey:#"event"];
NSLog(#"array contents: %#", eventArray);
return cell;
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
#end
DataCellViewController.h
#import <UIKit/UIKit.h>
#interface DataCellViewController : UITableViewCell
#property (nonatomic, strong)IBOutlet UILabel *eventTitle;
#end
DataCellViewController.m
#import "DataCellViewController.h"
#interface DataCellViewController ( )
#end
#implementation DataCellViewController
#synthesize eventTitle;
- (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
}
#end

Delegate set after View Controller is initialized creating issues with the Parse method QueryForTableView

I am using PFQueryTableViewController that requires a certain PFUser to be passed to it before the QueryForTableView is called. To solve this, I created a protocol in the PFQueryTableViewController that has a required method called userForProfileTableView.
#protocol profileTableViewDataSource <NSObject>
#required
-(PFUser *)userForProfileTableView;
#end
The previous view controller uses this method to set the PFUser. However, the previous view controller only sets itself as the dataSource in prepareForSegue:sender:completion. When this method is called, the queryForTableView and initWithCoder methods have already been called meaning there is no PFObject for the PFQueryTableViewClass to work with.
How can I get a reference to the PFQueryTableViewController directly after it is initialized or is there another way I can pass the PFUser before queryForTableView is called? Any help/ideas would be extremely appreciated.
Thanks in advance!
code:
Both are subclasses of PFQueryTableViewController
First view controller which is the Data Source:
.h (not important)
.m
#import "FeedQueryTableViewController.h"
#import "FeedTableViewCell.h"
#interface FeedQueryTableViewController ()
#end
#implementation FeedQueryTableViewController{
PFUser * userToPass;
}
- (void)viewDidLoad {
[super viewDidLoad];
// Do any additional setup after loading the view.
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
- (instancetype)initWithCoder:(NSCoder *)coder
{
self = [super initWithCoder:coder];
if (self) {
self.parseClassName = #"Question";
}
return self;
}
-(PFQuery *)queryForTable{
//First query for followed users
PFQuery * query = [PFQuery queryWithClassName:#"Activity"];
[query whereKey:#"fromUser" equalTo:[PFUser currentUser]];
[query whereKey:#"type" equalTo:#"follow"];
[query includeKey:#"toUser"];
[query includeKey:#"fromUser"];
//Second query for questions
PFQuery * questionQuery = [PFQuery queryWithClassName:#"Question"];
[questionQuery whereKey:#"User" matchesKey:#"toUser" inQuery:query];
[questionQuery includeKey:#"User"];
return questionQuery;
}
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath object:(PFObject *)object{
FeedTableViewCell * cell = [tableView dequeueReusableCellWithIdentifier:#"cell"];
if (cell == nil) {
cell = [[FeedTableViewCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:#"cell"];
}
//Set values of cell
[cell.usernameButton setTitle:[[object objectForKey:#"User"]username] forState:UIControlStateNormal];
[cell.usernameButton addTarget:self action:#selector(userButtonPressed:) forControlEvents:UIControlEventTouchUpInside];
cell.usernameButton.tag = indexPath.row;
cell.questionTextView.text = [object objectForKey:#"Question"];
return cell;
}
-(PFUser *)userForProfileTableView{
//This happens before the other class
if (userToPass != nil){
NSLog(#"%#", userToPass.username);
return userToPass;}
else{
return userToPass;
}
}
-(void)userButtonPressed:(UIButton *)sender {
//Type checking is sketchy here and could lead to potential crashes
PFObject * object = [[[self queryForTable]findObjects] objectAtIndex:sender.tag];
userToPass = [object objectForKey:#"User"];
[self performSegueWithIdentifier:#"userProfile" sender:self];
}
-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender{
ProfileTableViewController * ptvc = segue.destinationViewController;
ptvc.dataSource = self;
}
#end
View Controller which contains the protocol and is retrieving the PFUser to base Tableview data on
.h
//
// ProfileTableViewController.h
// qSocialNetwork
//
// Created by Sam Kirkiles on 7/29/14.
// Copyright (c) 2014 Sam Kirkiles. All rights reserved.
//
#import <Parse/Parse.h>
#protocol profileTableViewDataSource <NSObject>
#required
-(PFUser *)userForProfileTableView;
#end
#interface ProfileTableViewController : PFQueryTableViewController
#property (weak, nonatomic) IBOutlet UILabel *profileNameLabel;
#property (strong, nonatomic) PFUser * userToDisplay;
#property (weak) id <profileTableViewDataSource> dataSource;
#end
.m
//
// ProfileTableViewController.m
// qSocialNetwork
//
// Created by Sam Kirkiles on 7/29/14.
// Copyright (c) 2014 Sam Kirkiles. All rights reserved.
//
#import "ProfileTableViewController.h"
#interface ProfileTableViewController ()
#end
#implementation ProfileTableViewController
- (void)viewDidLoad {
[super viewDidLoad];
// Do any additional setup after loading the view.
[self.dataSource userForProfileTableView];
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
- (id)initWithCoder:(NSCoder *)aCoder
{
self = [super initWithCoder:aCoder];
if (self) {
self.parseClassName = #"Activity";
}
return self;
}
-(void)objectsWillLoad{
[super objectsWillLoad];
self.userToDisplay = [self.dataSource userForProfileTableView];
if (self.userToDisplay != nil) {
NSLog(#"sdfsfd");
[self queryForTable];
//A user has been passed to this view controller
}else{
//User the current user as a backup
//This feature will be added later
}
}
-(PFQuery *)queryForTable{
if (self.userToDisplay != nil){
PFQuery * query = [PFQuery queryWithClassName:#"Question"];
[query whereKey:#"User" equalTo:self.userToDisplay];
return query;
}
PFQuery *noUserQuery = [PFQuery queryWithClassName:#"Question"];
return noUserQuery;
}
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath object:(PFObject *)object{
UITableViewCell * cell = [tableView dequeueReusableCellWithIdentifier:#"cell"];
if (cell == nil){
cell = [[UITableViewCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:#"cell"];
}
cell.textLabel.text = [object objectForKey:#"Question"];
return cell;
}
/*
#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
I had a similar problem when attempting to set an object for queryForTable method on the previous view controller. The solution I came up with was to create a custom initializer that sets the object and then calls the super initializer.
e.g.
- (id)initWithParent:(PFObject *)parent
{
self.parent = parent;
self = [self initWithStyle:UITableViewStylePlain];
if (self) {
...
}
return self;
}
I know it's a less than elegant solution, but it was the only way I could get the queryForTable methd to use my object to query without having to rerun the query in viewDidAppear.

UITableViewController not showing data [duplicate]

This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
UITableViewController not loading data
I have created a UITableViewController in the following way
#import "KLActionsViewController.h"
#interface KLActionsViewController ()
#end
#implementation KLActionsViewController
#synthesize actionList,delegate;
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
if (self) {
// Custom initialization
}
return self;
}
- (void)loadView
{
}
- (void)viewDidLoad {
[super viewDidLoad];
NSMutableArray* list = [[NSMutableArray alloc] init];
self.tableView = [[UITableView alloc] init];
self.tableView.delegate = self;
self.tableView.dataSource = self;
self.actionList = list;
self.clearsSelectionOnViewWillAppear = NO;
self.contentSizeForViewInPopover = CGSizeMake(320.0, 400.0);
[self.actionList addObject:#"Obj1"];
[self.actionList addObject:#"Obj2"];
[self.actionList addObject:#"Obj3"];
[self.actionList addObject:#"Obj4"];
}
- (int)numberOfSectionsInTableView:(UITableView *)tableView
{
NSLog(#"in number of section");
return 1;
}
- (UITableViewCell *)cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = #"Cell";
UITableViewCell *cell = [self.tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
}
NSString* lab = [self.actionList objectAtIndex:indexPath.row];
// NSLog(lab);
NSLog(#"here in there");
cell.textLabel.text = lab;
return cell;
}
- (NSInteger)numberOfRowsInSection:(NSInteger)section
{
NSLog(#"Total entries : %i ",[self.actionList count]);
return [self.actionList count];
}
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
if (self.delegate != nil) {
[self.delegate actionSelected:indexPath.row];
}
}
- (void)viewDidUnload
{
[super viewDidUnload];
self.actionList = nil;
self.delegate = nil ;
// Release any retained subviews of the main view.
}
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
return (interfaceOrientation == UIInterfaceOrientationPortrait);
}
#end
But when I try to create it's instance and show it in a UIPopoverController all I can see is an empty table and no data in it. Also, numberOfRowsInSection and cellForRowAtIndexPath never get called.
Any help ?
You are creating a new table view inside viewDidLoad: but not making it a subview of this controller's view. Since you say you see an empty table, this leads me to believe that you're loading one table from your .xib file, but setting the dataSource only of this new one.
If that's how it's structured, use a connection in the .xib from the table view to the self.tableView property and don't create a new object...just configure the one you have.

Editing UITableViewController's UITableView in stroryboard

I've followed this Parse Tutorial to create a custom UITableViewController. I'd like to be able to edit the UITableView in storyboard. I thought somewhere in this tutorial I'd be linking the ViewController to a TableView, but I didn't have too. How can I access this TableView in stroyboard that is linked to this ViewController for UI editing?
Here is the ViewController code on GitHub.
Edit: This really has nothing to do with the Parse API. The tableview is not in the storyboard - this is the issue I'm trying to solve. The tutorial instructed me to add this to AppDelegate.m:
MyTableViewController *controller = [[MyTableViewController alloc] init];
self.window.rootViewController = controller;
And this to MyTableViewController.m:
- (id)initWithStyle:(UITableViewStyle)style
{
self = [super initWithStyle:style];
if (self) {
// Custom the table
// The className to query on
self.className = #"Artists";
// The key of the PFObject to display in the label of the default cell style
self.keyToDisplay = #"artistName";
// Whether the built-in pull-to-refresh is enabled
self.pullToRefreshEnabled = YES;
// Whether the built-in pagination is enabled
self.paginationEnabled = YES;
// The number of objects to show per page
self.objectsPerPage = 50;
}
return self;
}
The app is running fine, but all I have in storyboard is a blank View. Do I need to create a TableView and link it to MyTableViewController? I'm guessing I would have to remove that self.window... code from AppDelegate.
Edit: Updated Code:
#import "MyTableViewController.h"
#implementation MyTableViewController
#synthesize tableView = _tableView;
#pragma mark - View lifecycle
- (void)viewDidLoad
{
[super viewDidLoad];
// Custom the table
// The className to query on
self.className = #"Artists";
// The key of the PFObject to display in the label of the default cell style
self.keyToDisplay = #"artistName";
// Whether the built-in pull-to-refresh is enabled
self.pullToRefreshEnabled = YES;
// Whether the built-in pagination is enabled
self.paginationEnabled = YES;
// The number of objects to show per page
self.objectsPerPage = 50;
// 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)viewDidUnload
{
[self setTableView:nil];
[super viewDidUnload];
// Release any retained subviews of the main view.
// e.g. self.myOutlet = nil;
}
- (void)viewWillAppear:(BOOL)animated
{
[super viewWillAppear:animated];
}
- (void)viewDidAppear:(BOOL)animated
{
[super viewDidAppear:animated];
}
- (void)viewWillDisappear:(BOOL)animated
{
[super viewWillDisappear:animated];
}
- (void)viewDidDisappear:(BOOL)animated
{
[super viewDidDisappear:animated];
}
- (BOOL)shouldAutorotateToInterfaceOrientation: (UIInterfaceOrientation)interfaceOrientation
{
// Return YES for supported orientations
return (interfaceOrientation == UIInterfaceOrientationPortrait);
}
- (void)didReceiveMemoryWarning
{
// Releases the view if it doesn't have a superview.
[super didReceiveMemoryWarning];
// Release any cached data, images, etc that aren't in use.
}
#pragma mark - Parse
- (void)objectsDidLoad:(NSError *)error {
[super objectsDidLoad:error];
// This method is called every time objects are loaded from Parse via the PFQuery
}
- (void)objectsWillLoad {
[super objectsWillLoad];
// This method is called before a PFQuery is fired to get more objects
}
// Override to customize what kind of query to perform on the class. The default is to query for
// all objects ordered by createdAt descending.
- (PFQuery *)queryForTable {
PFQuery *query = [PFQuery queryWithClassName:self.className];
// If no objects are loaded in memory, we look to the cache first to fill the table
// and then subsequently do a query against the network.
if ([self.objects count] == 0) {
// ** There are other caching options in Parse iOS guide
query.cachePolicy = kPFCachePolicyNetworkElseCache;
}
[query orderByDescending:#"tweetInfluence"];
return query;
}
// Override to customize the look of a cell representing an object. The default is to display
// a UITableViewCellStyleDefault style cell with the label being the first key in the object.
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath object:(PFObject *)object {
static NSString *CellIdentifier = #"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:CellIdentifier];
}
// Configure the cell
cell.textLabel.text = [object objectForKey:#"artistName"];
cell.detailTextLabel.text = [NSString stringWithFormat:#"Tweet Influence: %#", [object objectForKey:#"tweetInfluence"]];
return cell;
}
#pragma mark - Table view delegate
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
[super tableView:tableView didSelectRowAtIndexPath:indexPath];
}
#end
If you are using storyboards, then you should remove
MyTableViewController *controller = [[MyTableViewController alloc] init];
self.window.rootViewController = controller;
From the AppDelegate. With storyboards, the entry point of the app is controlled on the storyboard itself, represented by the right-facing arrow.
Also, as the code stands now, your app is calling the init function on your view controller, not the initWithStyle function. You should put the code that is currently in initWithStyle in your view controller's viewDidLoad function to ensure it will be called.

Resources