开发者

iOS view "redirect"

I'm a web developer tasked with building a basic iOS app for internal use. A number of functions in the app require authentication, and I've successfully built the login view/controller which calls a webservice, authenticates the user etc etc.

I can currently load the "LoginView" with a button click and after authenticating the user, dismiss the view from the view stack returning to the original view, now with established credentials. None of that is my issue.

Now I'm looking for the equivalent of doing a 'redirect' as I would in developing for the web. I need to load the LoginView from any function in my application where authentication is required, and on success, load some other view which would be "passed in" (on the web I would provide a redirect Url) to the LoginView. I feel like this is a simple thing, and must be done all the time, but can not find a good example or explanation of this. I'm certain my obvious newbiness is preventing me from even searching for the right terms.

Hopefully someone can decipher my poor, yet best attempt at explaining what 开发者_如何转开发I am looking for. Thank you in advance.


One pattern I have used is to pass a success handler block to the authentication view controller.

This has an advantage over the delegate system in that you can set it to perform any action, including moving to any view controller, without modifying each and every view controller to match the delegate protocol.

For instance, one thing I might want to do after successfully authenticating is to pop the view controller stack back to the main menu, or to continue to process a web service request that was already underway. The delegate system doesn't really allow for this, while blocks are more flexible as you can pass in any code you want.


This is the perfect job for delegates. In your login view controller interface (please note I'm writing this off the top of my head so there might be a few typos/missing semi-colons etc:

@protocol LoginControlDelegate <NSObject>
- (void)loginDidSucceed:(BOOL)success
@end

@interface ...
{
    ...
}

@property (nonatomic, assign) id<LoginControlDelegate> delegate;

@end

And then in your implementation file, once you have established that the webservice has responded to the login request, you can call:

if (self.delegate != nil)
     {self.delegate loginDidSucceed:<YES/NO depending on the webservice response>]

So every time you create an instance of your login view controller, you can assign the "parent" view controller as the delegate and then conform to the <LoginControlDelegate> by implementing the method loginDidSucceed:

LoginViewController *vc = [[LoginViewController alloc] init....];
vc.delegate = self;
[self presentModalViewController:vc animated:YES];
[vc release];

And the loginDidSucceed method:

- (void)loginDidSucceed:(BOOL)success
{
     if (success)
     // Logged in successfully, push the appropriate view
     } else {
     // Login failed...
}


Developing for mobile is not the same as developing for the web. In general, apps will have a user login once and then never gain (or at least only when the app is opened, like Mint). If possible, consider changing the design of the app to accommodate mobile design conventions rather than borrowing from the web world. It's a different ball game and your users will appreciate it.

That said, I might attack this by building a custom UIView based off of apple's design for the UIAlertView. Give it a delegate protocol and when it returns with an authenticated user, the controller from which you called it can make the appropriate changes to itself using the delegate method.


What @Rog posted will all work fine as stated. I would only suggest that if you already have something akin to a WebRequestManager which dispatches the calls to your web service (creates the connection, manages errors, returns the data) to not worry about delegation of the login, but instead manage that login view in the manager, isolating all of your views from needing this sort of delegate (which becomes a maintenance headache).

This way your views just initiate the request thru the manager and just expect the data to be returned, regardless if a login is required. Notably, the app doesn't even need to (or may not) know what requests require a login, only discovering that as a response from the server. At which point you can launch the login view, get the credentials, and then restart the request with the valid credentials.

And at that point I would keep the credentials, at least for the current run session, so any future requests do not require another login.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜