Viewcontroller appear twice when I click cell - ios

I have a problem.
I have a ViewController embed in navigationController.
And use the storyBoard to add the tableView in this viewController.
then,I add the segue.
Finally,I click the cell that the next viewController show twice.
I don't know how to fix it.
Thanks!
This is my code:
-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
if(indexPath.row == 2){
[self performSegueWithIdentifier:#"showAdd" sender:self];
}
}
-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender{
if ([segue.identifier isEqualToString:#"showAdd"]) {
AddCommentViewController *AddCommentVC = segue.destinationViewController;
AddCommentVC.CommentString = _DetailString;
}
}

You have to add the segue between both the UIViewController, not with the cell and UIViewController, as you have connected that segue on click of cell and you are calling the segue manually also that's why it is showing twice.
Do one thing, remove the segue and connect it between UIViewControllers then it will called only once.

Related

Creating and using segue to launch storyboard view via didSelectRowAtIndexPath

I have a table view with cells created with:
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *cellIdentifier = #"GalleryCell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:cellIdentifier];
if (cell == nil) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:cellIdentifier];
}
NSMutableArray *gallery = [gallerys objectAtIndex:indexPath.row];
cell.textLabel.text = [gallery objectAtIndex:1];
return cell;
}
What I need to be able to do is within the didSelectRowAtIndexPath, fire a segue to launch another view, this will also send some information across using the prepareForSegue method.
This issue is I am not sure how to go about creating the segue to be used in this instance as within the storyboard I have nothing to attach it to (no buttons etc) and the cells are created within the code, is it possible to also create the segue in the code? Or is there another method to this?
Okay, you can attach it to your table view controller, it is not necessary to attach it to a button. Just go to the storyboard and do the following:
Right click on the VC that you would like to push.
Under Presenting Segues in the menu click and hold 'push' and drag it to your table view controller.
Choose manual when the dialog shows above your table view controller.
Select the segue after it appears and go to its attribute inspector.
Choose a name for the segue.
Call performSegue
simply drag a segue from your table to destination Controller and give a name for that.
And in didSelectRowAtIndexPath call
[self performSegueWithIdentifier:#"MySegue" sender:self];
then following method will get called
-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
// here you can pass any value to new ViewController;
if ([segue.identifier isEqualToString:#"MySegue"]) {
YourNewViewController *VC = segue.destinationViewController;
VC.data = yourData;
}
}
Push your view controller
[self performSegueWithIdentifier:#"yourSegueID" sender:self];
You can send the information as below
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender {
if ([segue.identifier isEqualToString:#"yourSegueID"]) {
YourViewController *yourVC = segue.destinationViewController;
yourVC.information = myInformation;
}
}

Side Menu revealcontroller issue with UITableViewController

I implemented SWRevealController in my application. It has two segues one for slideviewcontroller and viewcontroller.
My slideviewcontroller is UITableViewController, I created a new class MenuTableViewController for use as a custom class of that siderbar(slideview). When I add a MenuTableViewController as a custom class of that view, it isn't shown when i slide a menu. If i leave it blank it's shown.
The problem is that I want when cell clicked to perform segue identifier or a button clicked, but I don't know where to implement them.
You can implement your segue in your tableview's delegate method:
-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
[self performSegueWithIdentifier:#"YourSegueIdentifier" sender:self];
}
You can segue to a proper ViewController depending on indexPath of the selected item inside of that method. Then implement your:
-(void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
if ([segue.identifier isEqualToString:#"YourSegueIdentifier"])
{
DestinatinoVCClass *destinationVC = (DestinatinoVCClass *)segue.destinationViewController;
//here you can set any public properties of the destinationVC
}
}
But in general, as far implementing SWRevealController into your app goes here is a full tutorial.

prepareForSegue called before didSelectRowAtIndexPath only when third segue is added

I have 3 segues to 3 different views. 2 are implemented with no problem, it is when the third is created that the problems occur.
I have the following didSelectRowAtIndexPath method:
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{
NSLog(#" ---------- did select row");
if(indexPath.section == 0){
if(indexPath.row == [self.data count]-1){
//prior to adding this, everything works
[self performSegueWithIdentifier:#"MoreComments" sender:self];
}else{
[self performSegueWithIdentifier:#"FriendView" sender:friend];
}
}else if(indexPath.section == 1){
if(indexPath.row == [self.data2 count]-1){
[self performSegueWithIdentifier:#"MorePosts" sender:self];
}else{
[self performSegueWithIdentifier:#"FriendView" sender:friend];
}
}
}
I have the following prepareForSeque method:
-(void) prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender{
if([segue.identifier isEqualToString:#"MorePosts"]){
MorePostsViewController *mfamvc = segue.destinationViewController;
mfamvc.data = self.data;
}else if([segue.identifier isEqualToString:#"FriendView"]){
FriendViewController *fvc = segue.destinationViewController;
fvc.friend = friend;
}else if([segue.identifier isEqualToString:#"MoreComments"]){
MoreCommentsViewController *mcvc = segue.destinationViewController;
mcvc.data = self.data2;
}
}
Before control dragging from my cell to the last view I can see that my program hits didselectrow and then prepareforseque. This makes all the view navigation work perfect.
As soon as I control drag from my cell to the MoreCommentsViewController I start to see the error:
nested push animation can result in corrupted navigation bar
Finishing up a navigation transition in an unexpected state. Navigation Bar subview tree might get corrupted.
I notice that now also prepareforseque is being called twice, with prepareforseque being called first, then didselectrow, then prepareforsegue again.
What am I doing wrong to conditionally go to these different views?
You should use either didSelectRowAtIndexPath or segues from cell, but not both. If you want your didSelectRowAtIndexPath to invoke segues, those segues should not be from the cell to the next scene, but rather from the view controller icon in the bar above the scene:
You can now select this new segue, go to the "attributes inspector" (option+command+4), and supply a storyboard identifier which you can reference in your code when you call performSegueWithIdentifier.
The reason is you can't drag from a tableview cell to multiple views. As #rdelmar mentioned this is wrong. You should drag from the destination to the source view and then handle manually the way I did above.
Also can be found here: Conditional segue performed on tap on UITableViewCell

storyboard push segue isn't properly animated

I'm new to iOS development and don't get on well with storyboard.
screenshot of storyboard: http://i.stack.imgur.com/s9VTB.png
I have got the push segue working now. But only pushing from the first tableViewController to the second one is animated and pushing back isn't animated.
In the first tableViewController:
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
[self performSegueWithIdentifier:#"xxx" sender:self];
}
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
if ([segue.identifier isEqualToString:#"xxx"]) {
// set some properties of segue.destinationViewController
}
}
the second one is not modified.
Update:
I deleted the storyboard, did all of them programmatically and now everything works well.
Sometimes storyboard is just so confusing...
Whether the segue is animated will depend on how you do it. Try:
[self.navigationController popViewControllerAnimated:YES];

IOS StoryBoard multiple Segue's from a TableCell

Hi I have a storyboard and am able to show a detail view when clicking on a table cell. I want to add extra functionality so that depending on what cell I click I show a different view controller. I tried dragging two segues from the same cell but it doesn't allow it.
My thinking was that I would have two segue's from the cell each pointing to a different view and then invoke the desired segue:
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
NSInteger row = indexPath.row;
NSLog(#"Selected Item :-) %#",[NSString stringWithFormat:#"%#",[myData objectAtIndex:row]]);
if(row %2 ==0){
NSLog(#"Even");
[self performSegueWithIdentifier:#"ShowSecondIndex" sender:self];
}else{
[self performSegueWithIdentifier:#"ShowSelectedMovie" sender:self];
NSLog(#"Odd");
}
}
I would then handle the segue in prepareForSegue
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender
{
NSLog(#"Prepare For Segue ID:%#",[segue identifier]);
if([[segue identifier] isEqualToString:#"ShowSelectedMovie"]){
Tab2_ItemViewController *vc = [segue destinationViewController];
NSInteger selectedIndex = [[self.tableView indexPathForSelectedRow] row];
NSLog(#"Selected Index: %d",selectedIndex);
[vc setSelectedItem: [NSString stringWithFormat:#"%#",[myData objectAtIndex:selectedIndex]]];
NSLog(#"String Value: %#",[NSString stringWithFormat:#"%#",[myData objectAtIndex:selectedIndex]]);
[vc setSelectedIndex:selectedIndex];
}else if([[segue identifier] isEqualToString:#"ShowSecondIndex"]){
NSLog(#"Viewing Second Index");
}
}
However it never shows the second view. Is this because its not possible to have two segues from a single table cell. I also tried dragging both segue's from the controller to each destination rather than one from the cell and one from the controller but sill no luck???
Don't try to hook up the Segues to a tableviewcell in this case. Hook them up to the View Controller itself.
Don't try to create multiple segues from a TableCell to other view controllers, you want to ctrl+drag from the view controller icon below the view controller in the storyboard interface to the viewcontrollers you want to segue to. Then it will allow you to set up multiple segues.
and then to actually make the segues work, you need to add identifiers to the segues themselves, which you can do by clicking on them and then giving it a name in the property inspector:
then, for the example of TableCells, in your UITableViewDelegate, in
-tableView:didSelectRowAtIndexPath:
you can use
- (void)performSegueWithIdentifier:(NSString *)identifier sender:(id)sender
to manually start a segue depending on your own logic of what segue should be chosen.
Here's a sample code from my demo project:
- (void)tableView:(UITableView *)tableView
didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
NSString *segueName = nil;
if (type == kCore) {
segueName = #"segue1";
} else if (type == kStdlib) {
segueName = #"segue2";
}
[self performSegueWithIdentifier: segueName sender: self];
}
type is a property of view controller, which determines which segue should be performed.
As the above answer said, the key is to create segue by linking two view controllers.
In swift 3.1, with a segment control of two states
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
var segue: String!
if selectedSegment == 0 {
segue = "segue1"
} else {
segue = "segue2"
}
self.performSegue(withIdentifier: segue, sender: self)
}

Resources