Become a MacRumors Supporter for $50/year with no ads, ability to filter front page stories, and private forums.

KimGysen

macrumors newbie
Original poster
Oct 1, 2012
9
0
Brussel, Belgium
I have been looking until 6 o'clock this morning, but I can't figure out why the didSelectRowAtIndexPath method is not being called. I am getting quite desparate on this one.

The tableview is shown properly, but I cannot succeed to enable the selection of a cell.

In the header file , I added:

Code:
@interface AlertsTable : UIViewController<UITableViewDelegate, UITableViewDataSource, CMPopTipViewDelegate>{     UITableView *TableView; }  
@property (nonatomic, retain)   UITableView *TableView;

In the implementation file:

Code:
@synthesize TableView;
- (void)viewDidLoad {     
    [super viewDidLoad];      
    CGFloat sideMargin = 10;
    CGFloat topBottomMargin = 44;
    CGFloat originX = sideMargin;
    CGFloat sizeWidth = (self.view.bounds.size.width - (sideMargin * 2));
    CGFloat originY = topBottomMargin;
    CGFloat sizeHeight = (self.view.bounds.size.height - (topBottomMargin * 2));
     self.TableView = [[UITableView alloc] initWithFrame:CGRectMake(originX, originY, sizeWidth, sizeHeight) style:UITableViewStylePlain];

       //Initialize the array.
     AlertsItems = [[NSMutableArray alloc] initWithObjects: @"Alert 1", @"Alert 2", @"Alert 3" , @"Alert 4", @"Alert 5", @"Alert 6", nil];
    [self.TableView setDelegate:self];
    [self.TableView setDataSource:self];
    [self.view addSubview:TableView];
    TableView.userInteractionEnabled = YES;
    TableView.allowsSelection = YES;
    TableView.allowsSelectionDuringEditing = YES; NSLog(@"delegate:%@ dataSource:%@", self.TableView.delegate, self.TableView.dataSource);
    }

The delegate and datasource are both not nil on the check.
Note that the "Alertstable" inherits from a UIViewController, not a UITableViewController.
This is necessary due to the implementation I chose: the tableview is shown on a popupwindow shown on the screen (using another class that I took from the internet).

This is the didSelectRowAtIndexPath method:

Code:
#pragma mark - Table view delegate  
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
    NSString *alertString = [NSString stringWithFormat:@"Clicked on row #%d", [indexPath row]];
    UIAlertView *alert = [[UIAlertView alloc] initWithTitle:alertString message:@"" delegate:self cancelButtonTitle:@"Done" otherButtonTitles:nil];
    [alert show];
    }

The methods:

Code:
[super touchesBegan:...];
[super touchesEnded:...];
[super touchesMoved:...];

are not implemented.

I added the AlertTable from another ViewController

Code:
AlertsTable *AlertTable = [[AlertsTable alloc] WithButton:sender withArray:self.PopTipViews];
[self.view addSubview:AlertTable.view];

I also implemented:

Code:
- (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];
    }
      // Set up the cell...
     [[cell textLabel] setText:[AlertsItems objectAtIndex:indexPath.row]];     NSLog (@"%@",[AlertsItems objectAtIndex:indexPath.row]);
     return cell;  }

Do you have any idea what the problem could be?
I'm really stuck.

The link to the project is https://www.bilbu.be/BarConnect_v2.zip
The LoginViewController.xib is not properly linked so you may need to do that (I noticed too late).
ViewController VC class calls the AlertsTable VC class.
There is more in the project that I suppose you can ignore...
Note that the purpose of this project is only to serve as interface prototype.
 
The LoginViewController.xib is not properly linked so you may need to do that (I noticed too late).

The .zip you uploaded doesn't appear to include the file at all. I can't run the app at all because it crashes when it tries to load the main view, which evidently has that. I'm still looking at the code to see if I notice anything wrong.

Edit: Just wondering, why not use a storyboard? I'm realizing right now, not only are they a lot easier to make, they're a lot easier to read...

Alright, I was able to edit your project so I could at least run it by modifying the first few lines of application:didFinishLaunchingWithOptions: to simply launch the main view instead of a login screen... and I can confirm that, not only do your alerts not respond when I click them, neither do any of your other tables...

2X Edit: more than just when they're clicked, these tables never respond to any touches whatsoever. I can't drag them.

3X Edit: Well, I spent over a half hour looking... I can't see why it wouldn't work, but a lot of the set up looks very odd to me... why not use

#1 - Storyboards?
#2 - UIPopovers?
 
Last edited:
The .zip you uploaded doesn't appear to include the file at all. I can't run the app at all because it crashes when it tries to load the main view, which evidently has that. I'm still looking at the code to see if I notice anything wrong.

Edit: Just wondering, why not use a storyboard? I'm realizing right now, not only are they a lot easier to make, they're a lot easier to read...

It seems indeed that the xib is missing :-/ :-/ The problem is that I cannot re-upload the file myself as my friend took care of that and is not around at the moment. Perhaps I can ask him in the evening to re-upload.
Well the only thing the xib does is show a button and load the MainViewController. The xib of LoginViewController is loaded from the AppDelegate.

I didn't use the storyboard as I'm not familiar with it and I don't know until where it may limit my possibilities (my interface will need to do quite a lot of things). I also prefer to implement as much as possible programmatically, as I don't know until where the Interface Builder may be a limitation.

I am not very experienced in Xcode / Objective C programming; my only purpose is to create a prototype interface, to visually present to the persons who will take care of the actual development.

Edit Reaction: Indeed. I am sure that I'm doing something wrong. However, I can't see what it is after taking into account the advise given to the people who had the same problem before.
 
Last edited:
I have been looking until 6 o'clock this morning, but I can't figure out why the didSelectRowAtIndexPath method is not being called. I am getting quite desparate on this one.

The tableview is shown properly, but I cannot succeed to enable the selection of a cell.

In the header file , I added:

Code:
@interface AlertsTable : UIViewController<UITableViewDelegate, UITableViewDataSource, CMPopTipViewDelegate>{     UITableView *TableView; }  
@property (nonatomic, retain)   UITableView *TableView;

In the implementation file:

Code:
@synthesize TableView;
- (void)viewDidLoad {     
    [super viewDidLoad];      
    CGFloat sideMargin = 10;
    CGFloat topBottomMargin = 44;
    CGFloat originX = sideMargin;
    CGFloat sizeWidth = (self.view.bounds.size.width - (sideMargin * 2));
    CGFloat originY = topBottomMargin;
    CGFloat sizeHeight = (self.view.bounds.size.height - (topBottomMargin * 2));
     self.TableView = [[UITableView alloc] initWithFrame:CGRectMake(originX, originY, sizeWidth, sizeHeight) style:UITableViewStylePlain];

       //Initialize the array.
     AlertsItems = [[NSMutableArray alloc] initWithObjects: @"Alert 1", @"Alert 2", @"Alert 3" , @"Alert 4", @"Alert 5", @"Alert 6", nil];
    [self.TableView setDelegate:self];
    [self.TableView setDataSource:self];
    [self.view addSubview:TableView];
    TableView.userInteractionEnabled = YES;
    TableView.allowsSelection = YES;
    TableView.allowsSelectionDuringEditing = YES; NSLog(@"delegate:%@ dataSource:%@", self.TableView.delegate, self.TableView.dataSource);
    }

The delegate and datasource are both not nil on the check.
Note that the "Alertstable" inherits from a UIViewController, not a UITableViewController.
This is necessary due to the implementation I chose: the tableview is shown on a popupwindow shown on the screen (using another class that I took from the internet).

This is the didSelectRowAtIndexPath method:

Code:
#pragma mark - Table view delegate  
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
    NSString *alertString = [NSString stringWithFormat:@"Clicked on row #%d", [indexPath row]];
    UIAlertView *alert = [[UIAlertView alloc] initWithTitle:alertString message:@"" delegate:self cancelButtonTitle:@"Done" otherButtonTitles:nil];
    [alert show];
    }

The methods:

Code:
[super touchesBegan:...];
[super touchesEnded:...];
[super touchesMoved:...];

are not implemented.

I added the AlertTable from another ViewController

Code:
AlertsTable *AlertTable = [[AlertsTable alloc] WithButton:sender withArray:self.PopTipViews];
[self.view addSubview:AlertTable.view];

I also implemented:

Code:
- (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];
    }
      // Set up the cell...
     [[cell textLabel] setText:[AlertsItems objectAtIndex:indexPath.row]];     NSLog (@"%@",[AlertsItems objectAtIndex:indexPath.row]);
     return cell;  }

Do you have any idea what the problem could be?
I'm really stuck.

The link to the project is https://www.bilbu.be/BarConnect_v2.zip
The LoginViewController.xib is not properly linked so you may need to do that (I noticed too late).
ViewController VC class calls the AlertsTable VC class.
There is more in the project that I suppose you can ignore...
Note that the purpose of this project is only to serve as interface prototype.

More than likely you forgot to hook up the dataSource and/or delegate links in your table view to point to your view controller. The tableView:cellForRowAtIndexPath method is a UITableViewDataSource method, so the most likely problem is that you forgot to hook up the table view's dataSource property.

EDIT: I just reread your post, and discovered that you're problem method is didSelectRowAtIndexPath, not cellForRowAtIndexPath. The didSelectRowAtIndexPath method is a delegate method, not a table view method. You might have your data source set up but not your delegate.

Is the cell highlighting when you tap on it? If I recall cells default to being selectable, so you shouldn't need to do anything special, but that's from memory and it's been a while since I created a new table view.
 
Last edited:
More than likely you forgot to hook up the dataSource and/or delegate links in your table view to point to your view controller. The tableView:cellForRowAtIndexPath method is a UITableViewDataSource method, so the most likely problem is that you forgot to hook up the table view's dataSource property.

I don't think it's that. The UITableView doesn't respond to any touches whatsoever. Should it not allow for me to drag down and have it perform the overscroll spring animation?
 
More than likely you forgot to hook up the dataSource and/or delegate links in your table view to point to your view controller. The tableView:cellForRowAtIndexPath method is a UITableViewDataSource method, so the most likely problem is that you forgot to hook up the table view's dataSource property.

Thanks Duncan for your reply.
I have added the three methods:

Code:
numberOfSectionsInTableView
numberOfRowsInSection
cellForRowAtIndexPath

The tables are populated, but they won't respond to touch.
I also didn't receive any bug, what makes it hard for me to identify what the problem is exactly.

----------

The .zip you uploaded doesn't appear to include the file at all. I can't run the app at all because it crashes when it tries to load the main view, which evidently has that. I'm still looking at the code to see if I notice anything wrong.

Edit: Just wondering, why not use a storyboard? I'm realizing right now, not only are they a lot easier to make, they're a lot easier to read...

Alright, I was able to edit your project so I could at least run it by modifying the first few lines of application:didFinishLaunchingWithOptions: to simply launch the main view instead of a login screen... and I can confirm that, not only do your alerts not respond when I click them, neither do any of your other tables...

2X Edit: more than just when they're clicked, these tables never respond to any touches whatsoever. I can't drag them.

3X Edit: Well, I spent over a half hour looking... I can't see why it wouldn't work, but a lot of the set up looks very odd to me... why not use

#1 - Storyboards?
#2 - UIPopovers?

I don't know if it is possible with a storyboard, but I have a deadline in a month and I don't know if I have time enough to learn how it works and start again from scratch. So I'm kinda dissappointed it doesn't work, hope I won't get stuck here, because then I have no other alternative starting again with a new approach.
I implemented the Poptipviews class: I can instantiate this class and it will dynamically adapt to the location of the sender in the screen. As I may use it again, it could save me some time if I need it again later in the app...

----------

EDIT: I just reread your post, and discovered that you're problem method is didSelectRowAtIndexPath, not cellForRowAtIndexPath. The didSelectRowAtIndexPath method is a delegate method, not a table view method. You might have your data source set up but not your delegate.

Is the cell highlighting when you tap on it? If I recall cells default to being selectable, so you shouldn't need to do anything special, but that's from memory and it's been a while since I created a new table view.[/QUOTE]


I've set the delegate to self, I thought that would do it:

Code:
[self.TableView setDelegate:self];

The cell is not even highlighting. Basically, it isn't reacting at all.
I made the UITableView inherit from a UIViewController.
 
Thanks Duncan for your reply.
I have added the three methods:

Code:
numberOfSectionsInTableView
numberOfRowsInSection
cellForRowAtIndexPath

The tables are populated, but they won't respond to touch.
I also didn't receive any bug, what makes it hard for me to identify what the problem is exactly.

----------



I don't know if it is possible with a storyboard, but I have a deadline in a month and I don't know if I have time enough to learn how it works and start again from scratch. So I'm kinda dissappointed it doesn't work, hope I won't get stuck here, because then I have no other alternative starting again with a new approach.
I implemented the Poptipviews class: I can instantiate this class and it will dynamically adapt to the location of the sender in the screen. As I may use it again, it could save me some time if I need it again later in the app...

----------

EDIT: I just reread your post, and discovered that you're problem method is didSelectRowAtIndexPath, not cellForRowAtIndexPath. The didSelectRowAtIndexPath method is a delegate method, not a table view method. You might have your data source set up but not your delegate.

Is the cell highlighting when you tap on it? If I recall cells default to being selectable, so you shouldn't need to do anything special, but that's from memory and it's been a while since I created a new table view.


I've set the delegate to self, I thought that would do it:

Code:
[self.TableView setDelegate:self];

The cell is not even highlighting. Basically, it isn't reacting at all.
I made the UITableView inherit from a UIViewController.[/QUOTE]

A table view can't inherit from UIViewController. A UITableViewController can inherit from UIViewController, but UITableView can't. Did you mean that you made your view controller inherit from UITableViewController?
 
The link to the project is https://www.bilbu.be/BarConnect_v2.zip
The LoginViewController.xib is not properly linked so you may need to do that (I noticed too late).

It is not usual to attach the entire project to your query (code snippets are the norm), but if you do, it is a courtesy to those you seek help from to make sure the project compiles with no errors before attaching it. Thanks.

Anyways, on to your issue. Take a look at this code:
Code:
    }else if (sender  == btnAlerts){
        AlertsTable *AlertTable = [[AlertsTable alloc] WithButton:sender withArray:self.PopTipViews];
        [self.view addSubview:AlertTable.view];
        self.PopTipViews = [[NSMutableArray alloc] init];
        [self.PopTipViews addObjectsFromArray:AlertTable.visiblePopTipViews];
        
        if ([PopTipViews count] > 0) {
            NSLog( @"%@" , @"Not empty");
        }
    }

What do you think happens to AlertTable after this if-block is done? Do you think it is still retained in memory?

P.S. You might also want to review some Objective-C coding style recommendations. Usually, when we see something in camel-case that starts with an upper-case, we interpret it as a class-name and not as a variable name. That is, AlertTable looks like the name of a class, not a variable. alertTable would be better.
 
I've set the delegate to self, I thought that would do it:

Code:
[self.TableView setDelegate:self];

The cell is not even highlighting. Basically, it isn't reacting at all.
I made the UITableView inherit from a UIViewController.

A table view can't inherit from UIViewController. A UITableViewController can inherit from UIViewController, but UITableView can't. Did you mean that you made your view controller inherit from UITableViewController?[/QUOTE]

Hmm, I mean what I did is that I instantiated a UIViewController object (AlertsTable -> Implementing the delegate and datasource) and made its view a subview of the current ViewController.
In this object, I created a property of type UITableView (*TableView).
Then I set the delegate to self.

I didn't make it inherit from UITableViewController.

----------

It is not usual to attach the entire project to your query (code snippets are the norm), but if you do, it is a courtesy to those you seek help from to make sure the project compiles with no errors before attaching it. Thanks.

Anyways, on to your issue. Take a look at this code:
Code:
    }else if (sender  == btnAlerts){
        AlertsTable *AlertTable = [[AlertsTable alloc] WithButton:sender withArray:self.PopTipViews];
        [self.view addSubview:AlertTable.view];
        self.PopTipViews = [[NSMutableArray alloc] init];
        [self.PopTipViews addObjectsFromArray:AlertTable.visiblePopTipViews];
        
        if ([PopTipViews count] > 0) {
            NSLog( @"%@" , @"Not empty");
        }
    }

What do you think happens to AlertTable after this if-block is done? Do you think it is still retained in memory?

P.S. You might also want to review some Objective-C coding style recommendations. Usually, when we see something in camel-case that starts with an upper-case, we interpret it as a class-name and not as a variable name. That is, AlertTable looks like the name of a class, not a variable. alertTable would be better.

You are right, I uploaded the file as supplementary input. I understand about the Xcode file, it's a shame. The problem is I didn't zip and upload the file myself, and something must have gone at my friend's place (who did the upload but doesn't use Xcode himself). I cannot bother him too much with my stuff either, so I was glad that he was willing to help me with the upload. However, I did request him this evening to add the xib file, rezip the file and upload it. I will install the necessary software so I can do this myself in the future. It may be possible that xib needs to be linked (or re-added) manually, but that should be about it then.
I will have a look at the general objective c style rules and respect them more in the future.

About the issue, my current version of Xcode uses ARC standard.
I expected that I did not manually need to retain anymore.
Can you please lend me your expertise and explain ot me what you have in mind?

Many thanks.
 
Last edited:
About the issue, my current version of Xcode uses ARC standard.
I expected that I did not manually need to retain anymore.
Can you please lend me your expertise and explain ot me what you have in mind?

Yes, you don't need to manually retain anymore. But what do you think the automatic retention is doing with your AlertTable at the end of the if-block I've highlighted?

You are presenting a pop-over view but using addSubview: to do it rather than using a UIPopoverController instead. What lead you to make that decision?
 
Last edited:
Yes, you don't need to manually retain anymore. But what do you think the automatic retention is doing with your AlertTable at the end of the if-block I've highlighted?

You are presenting a pop-over view but using addSubview: to do it rather than using a UIPopoverController instead. What lead you to make that decision?

Well, I'll try to explain what led me to my actions (even when it may not make a lot of sense to experienced Objective C like yourself).
I found a class on the internet that implements a dynamic "popover" menu (not created from a UIPopoverController - in the demo, the class is called "CMPopTipView"). The popover that is shown on the screen is dynamic in the sense that its size adapts to the size of the view it takes and it is shown automatically based on the location of the sender. This is for me perfect, because I don't need to create every single popover myself.

This class takes a view as parameter, so in this case I fed it an instance of UITableView.
From the main view (named ViewController in my project), I wanted to dynamically create CMPopTipView instances for multiple TableViews, so I created different classes for each of the tables I wanted to show (depending on the button tapped), inheriting from UIViewController (not UITableViewController, but implementing UITableViewDelegate and UITableViewDataSource -> I read that this was possible).
So the moment I instantiated these UIViewControllers (containing the tableView implementation), I implemented some code in the ViewDidLoad method to instantiate the CMPopTipView class and feed the TableView directly in order to display in the "popover".

Between brackets, I hope that I am clear in my explanations.

I still don't know exactly what is going wrong honestly speaking... Am I missing a big point here? Please enlighten me if so, because I can't see the light at all.

You say indeed that the AlertTable is not retained in memory. I'd like to find a way to understand what I'm missing - is this the reason for the DidSelect method not to be fired? I set the delegate to self from within the instance, and the view seems to be properly displayed, so I don't see the reason for failure...

Perhaps .addsubview is not the way to go as you mention it, but I can't find the alternative. I'm willing to study whatever it takes to make this work, but I need some guidance because I don't know where to start here (no errors are generated).

You mentioned that I shouldn't use .addsubview. I will study the UIPopoverController class tomorrow, but I hoped that I did not need to replace the class that I am currently implementing due to its many benefits that it offers me.
 
I found a class on the internet that implements a dynamic "popover" menu (not created from a UIPopoverController - in the demo, the class is called "CMPopTipView"). The popover that is shown on the screen is dynamic in the sense that its size adapts to the size of the view it takes and it is shown automatically based on the location of the sender. This is for me perfect, because I don't need to create every single popover myself.
You have promised to look at UIPopoverController closer and that is a good idea since the two reasons you have given for choosing CMPopTipView (dynamic sizing and pointing to the instigator) are also available with a UIPopoverController. And, it seems that CMPopTipView was only intended to provide a simple, non-interactive "speech bubble". I suspect you are trying to extend it a bit too far.

You say indeed that the AlertTable is not retained in memory. I'd like to find a way to understand what I'm missing - is this the reason for the DidSelect method not to be fired? I set the delegate to self from within the instance, and the view seems to be properly displayed, so I don't see the reason for failure...

Yes, I believed the reason your didSelectRowAtIndexPath: was not being called was because your viewController had been released and, therefore, the delegate that you set was now nil. (The view was properly displayed, and retained, because it had been made a subview of the view). So, I tried making the viewController a strong property. This didn't help. Still no interaction with the table view.

So, the retention of your viewController is not the problem. I suspect it has something to do with the interaction capabilities (or lack thereof) of the CMPopTipView but I am not willing to tackle debugging it and/or your extended approach to using it. Sorry.

P.S. You seem to be putting in a lot of effort to produce a fully functional prototype interface (which will then be handed off to other developers anyways). I hope it's justified.
 
You have promised to look at UIPopoverController closer and that is a good idea since the two reasons you have given for choosing CMPopTipView (dynamic sizing and pointing to the instigator) are also available with a UIPopoverController. And, it seems that CMPopTipView was only intended to provide a simple, non-interactive "speech bubble". I suspect you are trying to extend it a bit too far.



Yes, I believed the reason your didSelectRowAtIndexPath: was not being called was because your viewController had been released and, therefore, the delegate that you set was now nil. (The view was properly displayed, and retained, because it had been made a subview of the view). So, I tried making the viewController a strong property. This didn't help. Still no interaction with the table view.

So, the retention of your viewController is not the problem. I suspect it has something to do with the interaction capabilities (or lack thereof) of the CMPopTipView but I am not willing to tackle debugging it and/or your extended approach to using it. Sorry.

P.S. You seem to be putting in a lot of effort to produce a fully functional prototype interface (which will then be handed off to other developers anyways). I hope it's justified.

Yes, I looked in the UIPopoverview class, and it looks promising. Indeed, there is much information available and I found a few samples to download and investigate.
If I don't find a solution the next days, I will implement this UIPopoverview as a replacement.

I want to thank you for the time you spend on this post. I certainly appreciate it. I understand that you will not debug further, since this is not the purpose of a forum.

PS: Yes I spend a lot of time in it, because I am the one who started the project and who is leading the project. I'm spending a lot of time on the interfaces, because I want the app to be exactly the way I have it in mind.
The name of the project is BarConnect, in case you hear something about it one day ;-)
 
Register on MacRumors! This sidebar will go away, and you'll see fewer ads.