How to detect a click event in a UIWebView - ios

I have a UITableView that loads content into a UIWebView like this:
//MainViewController.m
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
CGRect bounds = [ [ UIScreen mainScreen ] applicationFrame ];
UIScrollView *scrollView = [[UIScrollView alloc] initWithFrame:bounds];
UIWebView *htmlView = [ [ UIWebView alloc ] initWithFrame:[scrollView bounds]];
htmlView.frame = CGRectMake(10,10,280,360);
NSURLRequest *requestObj = [NSURLRequest requestWithURL:url];
//Load the request in the UIWebView.
[htmlView loadRequest:requestObj];
scrollView.contentSize = [htmlView bounds].size;
[scrollView addSubview:htmlView];
[detailsViewController.view addSubview:htmlView];
[htmlView release];
htmlView = nil;
[scrollView release];
scrollView = nil;
[[self navigationController] pushViewController:detailsViewController animated:YES];
[detailsViewController release];
}
All of the remote content that gets fed to the UIWebView comes from a web service that I wrote. The first screenshot is what is presented when a word is selected from the list view titled "Glossary"
This all is great until you follow a link, in this case clicking on the "frame" link in the UIWebView content. The new content gets loaded but I need to tell the nav bar that the UIWebView has changed so I can at least change the white title text to match the new content. What UIWebView methods should I implement and where should they go?

Set your view controller to be the UIWebView's delegate, then implement
-(BOOL)webView:(UIWebView*)webView shouldStartLoadWithRequest:(NSURLRequest*)request navigationType:(UIWebViewNavigationType)navigationType

Related

How to hide the top layout guide in a UIWebView in landscape mode?

This is a problem I am facing in portrait mode. The UIWebView is in fullscreen and the title bar is not starting from the screen size.
I want to hide the little portion which shows battery, and time status. This portion shows after scrolling the web view.
I have used this code:
NSLog(#"loadWebView1");
UIView *contentView = [[UIView alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
contentView.autoresizesSubviews = YES;
self.view = contentView;
//set the web frame size
CGRect webFrame = [[UIScreen mainScreen] bounds];
webFrame.origin.y = 0;
//add the web view
theWebView = [[UIWebView alloc] initWithFrame:webFrame];
theWebView.autoresizingMask = (UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight);
theWebView.scalesPageToFit = YES;
theWebView.delegate = self;
NSURL *url = [NSURL URLWithString:urlString];
NSURLRequest *req = [NSURLRequest requestWithURL:url];
[theWebView loadRequest:req];
[self.view addSubview: theWebView];
if you want to hide it for a single view the you can do it like this
-(BOOL)prefersStatusBarHidden {
return true;
}
if you want to hide it for all the views then you can do from TARGETS
check the Hide status bar checkmark
Set "View controller-based status bar appearance" to "true" in Info.plist.
Then, place the following code in the desired view controller:
- (BOOL)prefersStatusBarHidden {
return true
}

How to add a subView on a WKWebView that can be panning along this webView?

I want to add a subView to this WKWebView with this content (https://www.windytv.com/?-34.816,138.608,5). so that the subView can be panning along with the webview (imagine there's landmark view being panning along), but I could do it.
I tried many ways as follows:
I add a landmarkView to different subViews of the webView, failed.
1.1 For example:
[self.webView addSubView:landmarkView];
1.2 Or:
[self.webView.scroolView addSubView:landmarkView];
1.3 Or:
[self.webView.scroolView.subViews.firstObject addSubView:landmarkView]; // In viewDidAppear
The interesting thing here is the view hierachy of WKWebsite will change in viewDidAppear. It gets more subView like "WKContentView".
Followed by 1., I try to add a gestureView to pass the gesture to move the landmarkView, failed. The action of the gesture did not procceed.
1.1. For example, I add on the super view of webView.
[self.view addSubView: baseView];
[self.baseView addSubView: webView];
self.panGestureRecognizer.cancelsTouchesInView = NO;
[webView addGestureRecognizer: self.panGestureRecognizer];
Or, I add on the subView of webView.
[self.view addSubView: webView];
[self.webView addSubView: gestureView];
gestureView.backgroundColor = [UIColor clearColor];
self.panGestureRecognizer.cancelsTouchesInView = NO;
[gestureView addGestureRecognizer: self.panGestureRecognizer];
Anyone familiar with WKWebView?
Except for UIGesture, Is there other ways to distribute a touch to many views?
If I could override the touchesBegan method in one of the subViews, it should be much easier. And I think hitTest still work only on a view.
The general
- (void)viewDidLoad
{
UIView *landmarkView = [[UIView alloc] initWithFrame:CGRectMake(200, 200, 200, 200)];
landmarkView.backgroundColor = [UIColor redColor];
NSString *path = #"https://www.windytv.com/?-37.331,145.102,7";
NSURL *url = [NSURL URLWithString:path];
NSURLRequest *request = [NSURLRequest requestWithURL:url];
[self.webView loadRequest:request];
[self.view addSubView: self.webView];
[self.webView.scrool addSubView:landmarkView]; // This is one of the failed attempts.
}
It can be solved by adding a panGesture with this delegate method.
The trick is introduced here:
UIPanGestureRecognizer on MKMapView?

Adding header view to WKWebView ScrollView

Has anyone managed to successfully add a header or footer view to a WKWebView ScrollView?
I'm currently trying to do this using the method described here for a UIWebView Adding a header view to a UIWebView similar to Safari and Articles.
When this method is used in a WKWebView the content view origin.y is correctly changed but content is cut off at the bottom.
Using the scroll view content offset is also not possible as it breaks fixed positioned CSS elements in the web view.
In webView Delegate method
- (void)webViewDidFinishLoad:(UIWebView *)webView
add the following codebase,
mainWebViewObj.scrollView.contentInset = UIEdgeInsetsMake(headerView.frame.size.height,0.0,headerView.frame.size.height,0.0);
mainWebViewObj.scrollView.backgroundColor = [UIColor whiteColor];
if(![headerView superview])
{
[webView.scrollView addSubview:headerView];
[webView.scrollView bringSubviewToFront:headerView];
}
[mainWebViewObj.scrollView setContentOffset:
CGPointMake(0, -mainWebViewObj.scrollView.contentInset.top) animated:NO];
this worked perfect for me. Hope it solves your problem.
Here's an example that I think does as you describe. It offsets the web content by setting contentInset on the scrollView, and by offsetting the header view frame by a negative amount:
#implementation ViewController
{
WKWebView* _webView;
UIView* _headerView;
}
- (void)viewDidLoad
{
[super viewDidLoad];
_webView = [[WKWebView alloc] initWithFrame: self.view.bounds];
[self.view addSubview: _webView];
[_webView loadRequest: [NSURLRequest requestWithURL: [NSURL URLWithString: #"http://www.stackoverflow.com"]]];
[_webView.scrollView setContentInset: UIEdgeInsetsMake(100, 0, 0, 0)];
_headerView = [[UIView alloc] initWithFrame: CGRectMake(0, -100, 375, 100)];
_headerView.backgroundColor = [UIColor redColor];
[_webView.scrollView addSubview: _headerView];
}
- (void) viewDidLayoutSubviews
{
[super viewDidLayoutSubviews];
_webView.frame = self.view.bounds;
CGRect f = _headerView.frame;
f.size.width = _webView.bounds.size.width;
_headerView.frame = f;
}

iOS UIWebView not showing keyboard when textfields receive focus

I have a UIWebView embeded as a subview which loads an html form from the web. The problem is that when you select one of the text fields it receives the focus, but the keyboard does not display. this only happens on iOS6 if i run this app on iOS 4.3, 5.1 etc it works as expected. Any one have any advice
- (void)viewDidLoad
{
[super viewDidLoad];
webView = [[UIWebView alloc] init];
[webView setUserInteractionEnabled:YES];
[webView setScalesPageToFit:YES];
[webView setKeyboardDisplayRequiresUserAction:YES];
// load url here
NSURL *url = [NSURL URLWithString:redirectUrl];
//URL Requst Object
NSMutableURLRequest *requestObj = [NSMutableURLRequest requestWithURL:url];
[requestObj setHTTPMethod:#"POST"];
[webView loadRequest:requestObj];
UIScrollView* sv = nil;
for(UIView* v in [webView subviews]){
if([v isKindOfClass:[UIScrollView class] ]){
sv = (UIScrollView*) v;
sv.scrollEnabled = NO;
sv.bounces = NO;
}
}
[webView setOpaque:NO];
[webView setBackgroundColor:[UIColor whiteColor]];
webView.delegate = self;
[self.view addSubview:webView];
}
You can use the answer of this question:
Some UITextfields don't respond in iOs6
You have to resingfirstresponder before presentmodalviewcontroller in the the controller where are you calling the view with the problem.
BUT, you also have to resignfirst responder in all previews controllers, that is.
In my case i go from a searchbar to a detail view, and from detail to share in facebook. The view of share in facebook wasn't showing the keyboard, and it was 'cause i wasn't resiginif first responder of search bar.
Hope it helps.

UIWebView do not display contents in ios

I have been working around one small project which needs a similar GUI as that of SplitViewController. Now what i have done is, I have two UIViewControllers namely MasterViewController and DetailViewController which are added as subview of ViewController
The code is shown below for ViewController.m
- (void)viewDidLoad
{
UIScreen *screen = [UIScreen mainScreen];
CGRect fullScreenRect = screen.bounds; // always implicitly in Portrait orientation.
width = fullScreenRect.size.width;
height = fullScreenRect.size.height;
detailViewController = [[DetailViewController alloc] initWithNibName:#"DetailViewController" bundle:nil];
masterViewController = [[[MasterViewController alloc]initWithNibName:#"MasterViewController" bundle:nil] autorelease];
masterViewController.view.frame = CGRectMake(0, 0, 299, height);
detailViewController.view.frame = CGRectMake(300, 0, width-300, height);
[self.view addSubview:masterViewController.view];
[self.view addSubview:detailViewController.view];
}
Now in the MasterViewController didLoad method i have added as a subview MasterTableViewController...
MasterTableViewController class looks like this...
#interface MasterTableViewController : UITableViewController
{
DetailViewController *detailViewController;
}
All the functions related to UITableViewController are already made... and i have also added the functionality to add URL from user and store it in the MasterTableView.
Now in the following function I am trying to call loadWebView function of DetailViewController with the required string. The call is made perfectly to the function.
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
NSString *urlString = [_objects objectAtIndex:indexPath.row];
detailViewController = [[DetailViewController alloc]init];
[detailViewController loadWebView:urlString];
}
In the loadWebView method of DetailViewController i have the following implementation..
-(void) loadWebView: (NSString *) urlToLoad
{
self.webView = [[[UIWebView alloc]
initWithFrame:CGRectMake(0, 45, self.view.frame.size.width, self.view.frame.size.height)] autorelease];
[self.webView setDelegate:self];
NSLog(#"SELF->WEBVIEW: %#",self.webView);
NSURL *url = [NSURL URLWithString:urlToLoad];
NSLog(#"loading url %# %#", urlToLoad, self.webView);
NSURLRequest *requestObj = [NSURLRequest requestWithURL:url];
[self.webView loadRequest:requestObj];
}
I have also implemented the following function just to make sure that my Webview is working..
- (void)webViewDidStartLoad:(UIWebView *)webView
{
NSLog(#"webViewDidStartLoad");
}
- (void)webViewDidFinishLoad:(UIWebView *)webView
{
NSLog(#"webViewDidFinishLoad");
}
Now when i run my program the log prints all these things...
2012-10-15 20:04:21.621 SyneBlogApp[2320:c07] device width height 768.000000 1024.000000
2012-10-15 20:04:21.630 SyneBlogApp[2320:c07] calling viewDidLoad for detailView
2012-10-15 20:04:21.636 SyneBlogApp[2320:c07] /Users/Library/Application Support/iPhone Simulator/5.1/Applications/B846EDA4-49CF-4DD3-AAB3-FF8BC19C65DA/Documents/Data.plist:
2012-10-15 20:04:22.942 SyneBlogApp[2320:c07] calling viewDidLoad for detailView
2012-10-15 20:04:22.954 SyneBlogApp[2320:c07] SELF>WEBVIEW: <UIWebView: 0x6a94510; frame = (0 45; 768 1004); layer = <CALayer: 0x6a94930>>
2012-10-15 20:04:22.955 SyneBlogApp[2320:c07] loading url http://wordpress.com <UIWebView: 0x6a94510; frame = (0 45; 768 1004); layer = <CALayer: 0x6a94930>>
2012-10-15 20:04:22.994 SyneBlogApp[2320:c07] webViewDidStartLoad
2012-10-15 20:04:26.828 SyneBlogApp[2320:c07] webViewDidFinishLoad
According to log my webview loads the data perfectly, but when i have a look at the emulator i get a white screen. That is the content is not shown up...
Now just to make sure that nothing is wrong with webview i tried in DetailViewController viewDiDloadMethod the following which works and shows up the google page...
- (void)viewDidLoad
{
self.webView = [[[UIWebView alloc]
initWithFrame:CGRectMake(0, 45, self.view.frame.size.width, self.view.frame.size.height)] autorelease];
NSURL *url = [NSURL URLWithString:#"http://www.google.com"];
NSURLRequest *requestObj = [NSURLRequest requestWithURL:url];
[self.webView loadRequest:requestObj];
[self.view addSubview:self.webView];
[super viewDidLoad];
NSLog(#"calling viewDidLoad for detailView");
}
Now I seriously have no idea of what is going wrong. Even after all the things are working up well in log still the webpage content is not shown up.. Guys if you have any clue of what is going wrong please help...
This...
detailViewController = [[DetailViewController alloc]init];
...creates a new DetailViewController instead of using the one you already created and made part of your display in the first code segment you showed. You are therefore loading up your web view for a controller/view that isn't on screen.

Resources