如何“取消”UIStoryBoardSegue
有谁知道如何有条件地“停止”继续转换:
我的表格视图单元格表示可以在深入的“细节”视图中查看的产品…或者不能! (这取决于几件事情)
现在我的应用程序认为所有产品“解锁”:
- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender { NSIndexPath *selectedRowIndex = [self.tableView indexPathForSelectedRow]; ListaProdottiController *prodottiViewController = [segue destinationViewController]; prodottiViewController.blocco = [self.fetchedResultsController objectAtIndexPath:selectedRowIndex]; }
我怎样才能取消行select=>向下钻取,在这一点上?
如果你的目标是iOS 6或更高版本,那么我最清楚的做法是:
-(BOOL)shouldPerformSegueWithIdentifier:(NSString *)identifier sender:(id)sender { if([identifier isEqualToString:@"show"]) { NSIndexPath *selectedRowIndex = [self.tableView indexPathForSelectedRow]; Blocco *blocco = [self.fetchedResultsController objectAtIndexPath:selectedRowIndex]; return [blocco meetRequiredConditions]; } return YES; }
哪里有方法
-(BOOL) meetsRequiredConditions;
在Blocco类中定义的返回值为YES,如果允许深入分析的“事情”是有效的。
我不知道这是否正确,但我发现了一个解决方法。
从故事板中,我从视图控制器中的状态栏中关联(控制+单击)一个segue。 给Segue一个ID(例如:switchSegue)。
现在,从你的代码中的一个动作(在我的代码中我使用一个button),我打电话给:
[self performSegueWithIdentifier:@"switchSegue" sender:sender];
这样,你可以控制你的赛格是否执行。 尝试从这里和这里帮助我的教程
希望这可以帮助。
我正在使用一个更简单和整洁的方法。
故事板
- 用不同的标识符创build两个相同的单元 例如:“cellWithSegue”和“cellWithoutSegue”。
- 将第一个单元格(“cellWithSegue”)与要显示的segue连接起来。
- 不要连接任何赛格的第二个单元格。
表视图
- 在cellForRowAtIndexPath上,实现一个逻辑来确定单元格是否应该链接一个segue或不。
- 对于应该与segue连接的单元格,使用“cellWithSegue”标识符,其余为“cellWithoutSegue”。
这种方式看起来更容易实现,也不会改变赛道应该工作的方式。
我可能在这里是错误的,但在与我一起挣扎后,我只是禁用单元格的用户交互,我不希望seque触发的单元格(在cellForRowAtIndexPath :)。 似乎完美的工作,这只是一行代码!
cell.userInteractionEnabled = NO;
最简单的解决scheme是在故事板中创build手动search并使用它,如下所示。
[self performSegueWithIdentifier:@"loginSuccessSegue" sender:self];
要么
@Fabio:我试图得到同样的用例的解决scheme,我几乎find了解决scheme。
用例1.有条件地停止继续转换2.有条件地更改目标视图控制器
解:
使用“自定义”继续。 按照以下步骤创build自定义segue 1.创buildUIStoryboardSegue的一个子类“MyCustomSegue.h”
@interface MyCustomSegue : UIStoryboardSegue @end
“MyCustomSegue.m”
覆盖用于实现用例1和2的initWithIdentifier如果返回nil,则将取消segue /不会执行任何操作您将实例化ViewController并将其设置为目标。 你可以设置目的地作为你的旧xib文件..该代码被评论,但我保证,将工作。
@implementation MyCustomSegue - (id)initWithIdentifier:(NSString *)identifier source:(UIViewController *)source destination:(UIViewController *)destination{ UIStoryboard *storyBoard= [UIStoryboard storyboardWithName:@"MainStoryboard_iPhone" bundle:nil]; UIViewController *viewController = [storyBoard instantiateViewControllerWithIdentifier:@"testIdentifier"]; // MyViewController* viewController= [[MyViewController alloc]initWithNibName:@"MyViewController" bundle:nil]; return [super initWithIdentifier:identifier source:source destination:viewController]; }
- 你必须重写“执行”。
你也可以在这里实现用例1 ..
- (void)perform { // if either source or destination is nil, stop if (nil == self.sourceViewController || nil == self.destinationViewController) return; // return; //No Action. Segue will be cancelled UINavigationController *ctrl = [self.sourceViewController navigationController]; [ctrl pushViewController:self.destinationViewController animated:YES]; }
希望这可以帮助。 如果你不清楚,请写信。
这样做的好方法是在UITableViewDelegate方法tableView:willSelectRowAtIndexPath:
– 适用的地方。 因人而异。
以下是我如何做(iOS 5,ARC)。 我在我的视图控制器中使用BOOL实例variables,最初在viewDidLoad
设置为False。 表格单元格被设置为在Interface Builder中继续使用的目标视图控制器依赖于已从服务器加载的一些数据,所以我不希望继续发生,直到我有数据。
简化,这是它的样子:
@implementation SomeViewController { BOOL okayToSegue; } ... - (void)viewDidLoad { [super viewDidLoad]; okayToSegue = NO; // The success block for the data retrieval void(^successBlock)(void) = ^{ // Other code... okayToSegue = YES; } [[ServerClient sharedClient] getDataFromServerSuccess:successBlock]; } ... - (NSIndexPath *)tableView:(UITableView *)tableView willSelectRowAtIndexPath:(NSIndexPath *)indexPath { if (!okayToSegue) { return nil; } return indexPath; }
忽略像那个sharedClient位那样的细节,这就是我如何用成功块调用我的AFHTTPClient子类,在现实生活中我会有一个失败块和其他的东西。
在tableView:willSelectRowAtIndexPath:
返回nil
tableView:willSelectRowAtIndexPath:
导致在表单元格上点击不做任何事情。 只有在从AFHTTPClient实例(通过successBlock)获得了segued-to view controller需要的数据准备就绪并等待的信息之后,我才更改了实例variables,未来的tap会正常工作。 在真实的代码中,您将需要一些用户可见的通知或视觉上明显的迹象表明,继续执行操作仍不可行。
因此,无论您需要确定是否从表格单元格继续是好的逻辑,在许多情况下都可以用这种方式来完成。
苹果公司的模板为iPadpopup的方式是使用手动search,而不是自动search触发,手动search需要使用performSegueWithIdentifier来触发:
要创build一个手动的继续,而不是从元素中按住ctrl拖动,请从视图的控制器图标上按住Ctrl键拖动,设置继续的标识符,然后在IB中完成。
这里我find了另一个解决scheme。
在你的Mainstoryboard TableView中,当你使用从你的单元格(标识符=单元格)到目的地视图的自动search时,你也可以添加另一个单元格(标识符= CellWithoutSegue)。 所以当在cellForRowAtIndexPath中创build新的单元格时,只需要重用你想要的单元标识符(有或没有segue)。
希望能帮助到你!
(告诉我,如果你想要一些代码源示例)。
问候,
在你的- (void)prepareForSegue:(UIStoryboardSegue*)segue sender:(id)sender;
方法,你可以添加一些代码,如:
if ([[segue identifier] isEqualToString:@"DemoSegue"] && !self.canOpenDemo) { id *nc = [segue destinationViewController]; // UIViewController, UINavigationController, etc. (keeping "id" will return warning) [nc dismissModalViewControllerAnimated:NO]; }
这将停止从开放的观点,但是我没有检查,但它似乎已经调用你的目标视图控制器初始化函数(同样,我没有检查Xcode,所以我不完全确定)。