iOS changing switching views - objective-c

when click Audio button in view1.xib
i want to load view2.xib file (this is not in uiwebview)
I want in my application just like this link.
But in this link the rootviewcontroller is in uiview but in my application the root view controller in UIWebView how to change the view if the rootview is in uiwebview?

in the uiwebview html content for navigating to another view, you do have a link
for example
Go To Second View
In the viewcontroller that contains the UIWebView, set the delegate of webView to be the the viewcontroller
- (void) viewDidLoad
{
webView.delegate = self;
}
in the view controller Implement following
- (BOOL)webView:(UIWebView *)webView shouldStartLoadWithRequest:(NSURLRequest *)request navigationType:(UIWebViewNavigationType)navigationType
{
if (navigationType == UIWebViewNavigationTypeLinkClicked) {
NSString *urlAbsolute = [request.URL absoluteString];
if ([urlAbsolute isEqualToString:#"TEST://GOTOVIEW"])
{
//Go to the second view by calling the switchPage function
return NO;
}
}
return YES;
}

Related

Tab bar item third touch for a table view not scrolling to the top

I have a tab bar item which is connected navigation controller with a UIViewController as the root view controller. The first touch on the tab bar item switches to that view. The second touch pops to the root view controller. The third touch does not scroll to the top.
I've seen this scroll-to-top behavior in other apps, but after searching the webs, I cannot find out anything about it.
Is this default behavior for scroll views or table views attached to tab bar items, or is it something I need to implement myself?
I realize this is an older question, but I'm also looking to create this behavior, and I think I have a simpler solution.
First, set your AppDelegate to be the delegate for your UITabBarController. Then add this method to AppDelegate.m:
- (BOOL)tabBarController:(UITabBarController *)tabBarController shouldSelectViewController:(UIViewController *)viewController {
if ([tabBarController.viewControllers objectAtIndex:tabBarController.selectedIndex]==viewController)
{
if ([viewController isKindOfClass:[UITableViewController class]])
{
[[(UITableViewController *)viewController tableView] setContentOffset:CGPointZero animated:YES];
}
else if ([viewController isKindOfClass:[UINavigationController class]])
{
UINavigationController *nav = (UINavigationController *)viewController;
if ([nav.visibleViewController isKindOfClass:[UITableViewController class]])
[[(UITableViewController *)nav.visibleViewController tableView] setContentOffset:CGPointZero animated:YES];
}
}
return YES;
}
This works if your tab points at a UITableViewController or at a UINavigationController with a UITableViewController as the root view, and you don't have to worry about distinguishing between which UITableViewController is affected, sending notifications, etc.
Here is the solution to scroll to top of the table view when tab bar is clicked
In AppDelegate set tabbar delegate
- (BOOL)tabBarController:(UITabBarController *)tabBarController shouldSelectViewController:(UIViewController *)viewController {
if (tabBarController.selectedIndex == 0) {
UINavigationController *selectedNav = [self.tabBarController.viewControllers objectAtIndex:self.tabBarController.selectedIndex];
UIViewController *currentVC = selectedNav.visibleViewController;
if([currentVC isMemberOfClass:NSClassFromString(#"HomeViewController")])
{
[[NSNotificationCenter defaultCenter] postNotificationName:#"refreshView" object:nil];
}
}
return YES;
}
In HomeViewController.m view did load listen for the notification
[[NSNotificationCenter defaultCenter] addObserver:self
selector:#selector(refreshView:)
name:#"refreshView"
object:nil];
Refresh method
-(void)refreshView:(NSNotification *) notification{
if (self == self.navigationController.topViewController)
[self.tableView scrollRectToVisible:CGRectMake(0, 0, 1, 1) animated:YES];
}
No, this isn't default behaviour, you have to implement it yourself.
I'd do it by making the application delegate the delegate of the tab bar controller, and implement -tabBarController:didSelectViewController: to post a notification. Listen for that notification in your table view controller and do something like:
if (self == self.navigationController.topViewController)
[self.tableView scrollToTop];
Since your tab controller can only have one delegate, you may want to look at the answer to this question, which describes how to listen for the tap using KVO.

Reload ViewController by clicking on TabBarItem

I'm kinda desperate right now :/
I have a Tab Bar Controller with 4 Items. In the 4. Tab I included a webView which shows a list of pdf's. If I open a PDF in the webView there is no way to go back to the main webView with the links. Is there a way by re-clicking the 4. TabBar to reload the View? If I change from the 3. to the 4. tabbar it works (viewWillAppear).
Someone told me, that the following method should work:
- (void)tabBarController:(UITabBarController *)tabBarController didSelectViewController:(UIViewController *)viewController{
if ([viewController isKindOfClass:[UIColor class]]) {
//Try this if you're pushing the webView in another ViewController
[viewController.navigationController popToRootViewControllerAnimated:YES];
//or access to your webView and call goBack();
}
}
but actually I have no idea in which file I should insert that method. (See print Screen)
Thanks a LOT in advance for your help guys!
Subclass UITabBarController
1.1. Cmd+N and create a new instance of NSObject class, and name it TabBarController
1.2. in TabBarController.h replace NSObject so that it reads #interface TabBarController : UITabBarController <UITabBarControllerDelegate>
1.3. in TabBarController.m add this:
- (id) init
{
self = [super init];
if (self)
{
self.delegate = self;
}
return self;
}
1.4. and this
- (void)tabBarController:(UITabBarController *)tabBarController
didSelectViewController:(UIViewController *)viewController
{
// Is this the view controller type you are interested in?
if ([viewController isKindOfClass:[MehrViewController class]])
{
// call appropriate method on the class, e.g. updateView or reloadView
[(MehrViewController *) viewController updateView];
}
}
1.5. In IB, Inspection, change the class of Tab Bar Controller to your TabBarController (instead of UITabBarController)
1.6. You also need to include MehrViewController.h in TabBarController.m
Edit
in MehrViewController.m (as you posted in your question, assuming it has a webView)
// An example of implementing reloadView
- (void)reloadView {
[self.webView reload];
}

How to update DetailView using MasterDetail Application Template

I'm new to using the split view for creating iPad applications. When I first create the project just using the standard MasterDetail Application template (Xcode 4.2), it creates a MasterViewController and a DetailViewController. The template has the following method that is called when a row is selected from the popover table (master detail view controller):
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
if (!self.detailViewController)
{
self.detailViewController = [[DetailViewController alloc] initWithNibName:#"DetailViewController" bundle:nil];
}
[self.navigationController pushViewController:self.detailViewController animated:YES];
Now I understand when you are using a regular navigation controller if you are programing for an iPhone you just do this type of thing to push on another view controller on to the stack. However, with this template, it just pushes the detail view onto the popover rather than updating what is already present. I'm confused as what I need to update to select something from the pop over (master detail view), and then have the detailView update.
Update:
To try and test out the "detailItem" that is already setup for you in the DetailViewController, I commented out the pushViewController and added the following:
//[self.navigationController pushViewController:self.detailViewController animated:YES];
self.detailViewController.detailItem = #"Test";
// setter in detailViewController
- (void)setDetailItem:(id)newDetailItem
{
if (_detailItem != newDetailItem) {
_detailItem = newDetailItem;
// Update the view.
[self configureView];
}
if (self.masterPopoverController != nil) {
[self.masterPopoverController dismissPopoverAnimated:YES];
}
}
- (void)configureView
{
// Update the user interface for the detail item.
// detailDescriptionLabel.text is a IBOutlet to the label on the detailView
if (self.detailItem) {
self.detailDescriptionLabel.text = [self.detailItem description];
}
}
According to this code, the text of the label on the detailViewController should be updated. However, when I do click on the item in the master view controller table, nothing happens.
There are a couple different ways you could do it. First off, like you said, remove the pushViewController call (I don't know why Apple's template does this... maybe just to show you you can?).
Next, let your MasterViewController know about the DetailViewController that is already displayed. I usually set master.detailViewController = detailViewController in the appDelegate.
Remember, the DetailViewController is already being displayed, so you won't always need to realloc it (unless you are replacing it with some other view)
First Option
Use delegate calls to set the information. Declare a protocol to pass information to the detailView and have it display it appropriately. Here is a tutorial describing this in more detail.
Second Option
Pass DetailViewController some data & override the setter to refresh the detailView. Here is a tutorial describing this in more detail.
// in DetailViewController
- (void)setDetailItem:(id)newDetailItem {
if (detailItem != newDetailItem) {
[detailItem release];
detailItem = [newDetailItem retain];
// Update the view.
navigationBar.topItem.title = detailItem;
NSString * imageName = [NSString stringWithFormat:#"%#.png",detailItem];
[self.fruitImageView setImage:[UIImage imageNamed:imageName]];
}
}
Edit: Just looked at the template again, and setDetailItem type code is already in there, but the code is creating a completely new detailView so the detailView that is viewable on the splitViewController is not changed at all.

xcode unable to hide tabbarcontroller

I have a tabbarcontroller as main controller and when a view is pushed I would like to hide it. I use hidesBottomBarWhenPushed but not working. Thanks.
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
if (self) {
self.hidesBottomBarWhenPushed = YES;
}
return self;
}
try to add this line when you push this controller, in it's parent view controller :
YourViewController *controller = [[YourViewController alloc]init....];
controller.hidesBottomBarWhenPushed = YES;
//then push the view controller
Good Luck
This will only work if one of the viewControllers of the tabBarController is a UINavigationController. The hidesBottomBarWhenPushed property is only respected if a view controller is pushed onto the stack of a UINavigationController and will not do much if it is the root view controller.
I've implemented my own custom tabBarController (which extends the original UITabBarController), because I need to toggle bars programmatically under certain circumstances (like device rotation), this is my implementation (comments explain how it works):
- (void)hideBottomBar:(BOOL)hide
{
#try
{
// UITabBarController has 2 subviews:
// - the first (index:0) is that one containing the active view controller's view
// - the second (index:1) is that one containing the UITabBar (self.tabBar)
UIView *topView = [self.view.subviews objectAtIndex:0];
UIView *bottomView = [self.view.subviews objectAtIndex:1];
// hide tabs container if necessary
[bottomView setHidden:hide];
// adjust frame
if (hide)
{
// expand main view to fit available space
[topView setFrame:self.view.bounds];
}
else
{
// restore main view frame
CGRect frame = topView.frame;
frame.size.height -= bottomView.frame.size.height;
[topView setFrame:frame];
}
}
#catch (NSException *exception)
{
[[GTMLogger sharedLogger] logError:#"Error occured adjusting tabs view: %#", exception.description];
}
}

How to cancel a UIWebView?

I'm modally presenting a UIViewController with a UIWebView as its view. How do I dismiss the UIWebView when the user hits a cancel button on it?
One idea I have is to have the cancel button link to http://cancel and then check in
- (void)webViewDidStartLoad:(UIWebView *)webView
If webView.request.URL.host isEqualToString:#"cancel", then dismiss the view controller.
Does the host have to have a dot in it, e.g., "cancel.com"?
You're on the right path, but you're approach is slightly off. You don't need or want this to be an HTTP URL. Make your URL cancel:.
Thing to click
Then implement webView:shouldStartLoadWithRequest:navigationType: in your web view delegate. Something like this (untested):
- (BOOL)webView:(UIWebView *)webView shouldStartLoadWithRequest:(NSURLRequest *)request navigationType:(UIWebViewNavigationType)navigationType {
if ([request.URL.scheme isEqualToString:#"cancel"]) {
[self dismissModalViewControllerAnimated:YES];
return NO;
}
return YES;
}
It's not entirely clear if you want to stop loading in a web view or just dismiss the modal view controller that's containing it.
To stop loading:
[webView stopLoading];
To dismiss the view controller:
[self dismissModalViewControllerAnimated:YES];
Don't forget to set the web view's delegate to nil before you release it.