Loading webViews using iCarousel doesnt scroll when swiping on centre View - ios

I am using iCarousel library to load UIWebViews. I am unable to scroll the carousel when i swipe on the center view. When i swipe outside the centre View, I do not have any problem in scrolling. I do not have the similar problem when i use UIImageView. I am facing this problem only for UIWebview. I am using the below code to create the web views in viewForItemAtIndex method.
-(UIView *)carousel:(iCarousel *)carousel1 viewForItemAtIndex:(NSUInteger)index reusingView:(UIView *)view {
UIWebView *webView = [[UIWebView alloc]initWithFrame:CGRectMake(50, 0, 100, 100)];
return webView;
}
Can anyone please help me to fix this issue?

This is probably a gesture recognizer issue preventing the carousel pan gesture from working. It seems you can't set your controller as the delegate of the webView.scrollView.panGestureRecognizer so, you will need to edit the carousel because it doesn't make the panGestureRecognizer it uses publicly available. Edit it to add your controller as the delegate and then you can return YES from gestureRecognizer:shouldRecognizeSimultaneouslyWithGestureRecognizer:. Alternatively, you can hide this inside the carousel by making it the delegate of its own gesture...

Related

Disable scrolling UIPageViewController

I want disable scrolling UIPageViewController until webview is loading in ViewController.
When webview is loaded, then enabled scrolling in PageViewController.
I use:
for (UIScrollView *view in self.pageViewController.view.subviews) {
if ([view isKindOfClass:[UIScrollView class]]) {
view.scrollEnabled = NO;
}}
But that disable scrolling forever.
Help me please!
Simple. Inside of your if block, store away a reference to the scrollview for later use. Then, implement UIWebView's delegate method webViewDidFinishLoad: and webView:didFailLoadWithError: and in both of those re-enable scrolling using the reference you captured earlier.
Docs for reference: https://developer.apple.com/library/ios/documentation/Uikit/reference/UIWebViewDelegate_Protocol/index.html

Determine if button can be seen by user

I have an interesting requirement. I have a webview that expands in size when the user swipes up. This works well, but now I am trying to detect if the user has scrolled up to the top, so that I can minimize it again.
I am trying to do this by placing an image behind the webview, if the user scrolls past the top of the webview, the bounce effect takes place and the underlying image becomes visible. I was trying to use the "hidden" property thinking that the image is hidden when under the webview, but visible when the webview has been pulled down. This however, doesnt seem to work properly.
Anyone have any ideas on how to detect if a button/image is visible to the user?
Because the UIWebView implements UIScrollViewDelegate, it declares conformity to that protocol, you can use the ScrollViewDidScroll delegate method.
First make sure that your UIWebView is not inside a UIScrollView
Important: You should not embed UIWebView or UITableView objects in
UIScrollView objects. If you do so, unexpected behavior can result
because touch events for the two objects can be mixed up and wrongly
handled.
Instead, you can access the UIScrollView through the UIWebView properties since we now know that UIWebView is based on a UIScrollView. Your view controller can implement the UIScrollViewDelegate.
#interface MyViewController : UIViewController<UIScrollViewDelegate>
#end
Then you have to set the scrollView property inside your webview to the UIScrollViewDelegate like so:
- (void)viewDidLoad
{
[super viewDidLoad];
// Set the scrollView property's delegate protocol to self. This is so that this view controller will receive the delegate methods being fired when we interact with the scrollView.
webView.scrollView.delegate = self;
}
We're only interested in one of the ScrollView's delegate method - scrollViewDidScroll. Then you can detect when the scrollView has been scrolled inside your webview and ultimately have a simple mathematics equation that checks if the scrollView has been scrolled to the top:
- (void)scrollViewDidScroll:(UIScrollView *)scrollView
{
if(scrollView.contentOffset.y <= 0.0){
NSLog(#"TOP REACHED so do the chicken dance");
}
}
Look for contentOffset of scroll view of Web view if it's Y==0 then it means that user has scrolled up to the top.
CGRect visibleRect;
visibleRect.origin = webView.scrollView.contentOffset;
if(visibleRect.origin.y == 0)
{
//t means that user has scrolled up to the top
}

UITableView didSelectRowAtIndexPath Not Selected on UIPageViewController

I have a UIViewController that has UIPageViewController's view added to it. That UIPageViewController has a page with a subview that has a UITableView added as a subview. I am using iOS 6 and the method didSelectRowAtIndexPath is not being called when I click on the cell. There is a weird "bug" though... If I turn the page halfway and then come back to the page I was on (without completing the page turn), I'm then able to select the cell. I assume this has something to do with gesture recognizers, but I can't figure it out. I tried removing the gesture recognizers from the instantiation of the UIPageViewController, but was unable to get that to work.
I remove the tap gesture recognizers from the UIPageViewController like so, but still the buggy behavior exists...
for (UIGestureRecognizer *recognizer in pageViewController.gestureRecognizers) {
if ([recognizer isKindOfClass:[UITapGestureRecognizer class]]) {
recognizer.enabled = NO;
}
}
Any suggestions?
Subclass UIView with UITableView. let say myUIView.
Implement the UITableView delegates in myUIView.
Add myUIView as a subview of UIPageControl.
UITableView delegates in myUIView will trigger.
It turned out to be something very simple. On my UIViewController I had the autoresizingMask set to FlexibleHeight. Changing it to None for some reason fixed my problem.
// self.contentView.autoresizingMask = UIViewAutoresizingFlexibleHeight;
// Changed to :
self.contentView.autoresizingMask = UIViewAutoresizingNone;
If anyone can shed some light onto the reasons why this is the case, I'd appreciate it.

how to override the swipe gesture in UIWebView?

all, I'm a newbie on ios development.
I want to implement a right swipe gesture to UIWebView, which should have the action specified by me. However, the when the web page is too large that causes the UIWebView has a scroll bar, then my custom left swipe gesture doesn't work at all. In this case, when I swipe right, then the scroll bar will move, instead of triggering my specified action. Is there any way to disable the scroll bar moving action when I swipe right?
Hope my question is clear to you ...
Thanks in advance.
Either add a transparent view over the webview, or make a subclass of UIWebView and override the touchmethods.
you can disable the whole scroll in the UIWebView like this
UIScrollView *scroll = [[webView subviews] lastObject];
if([scroll isKindOfClass:[UIScrollView class]])
{
scroll = (UIScrollView*)scroll;
[scroll setScrollEnabled:NO];
}

Stop UIWebView from "bouncing" vertically?

Does anyone know how to stop a UIWebView from bouncing vertically? I mean when a user touches their iphone screen, drags their finger downwards, and the webview shows a blank spot above the web page I had loaded?
I've looked at the following possible solutions, but none of them worked for me:
http://www.iphonedevsdk.com/forum/iphone-sdk-development/996-turn-off-scrolling-bounces-uiwebview.html
http://forums.macrumors.com/showthread.php?t=619534
How do I stop a UIScrollView from bouncing horizontally?
for (id subview in webView.subviews)
if ([[subview class] isSubclassOfClass: [UIScrollView class]])
((UIScrollView *)subview).bounces = NO;
...seems to work fine.
It'll be accepted to App Store as well.
Update: in iOS 5.x+ there's an easier way - UIWebView has scrollView property, so your code can look like this:
webView.scrollView.bounces = NO;
Same goes for WKWebView.
I was looking at a project that makes it easy to create web apps as full fledged installable applications on the iPhone called QuickConnect, and found a solution that works, if you don't want your screen to be scrollable at all, which in my case I didn't.
In the above mentioned project/blog post, they mention a javascript function you can add to turn off the bouncing, which essentially boils down to this:
document.ontouchmove = function(event){
event.preventDefault();
}
If you want to see more about how they implement it, simply download QuickConnect and check it out.... But basically all it does is call that javascript on page load... I tried just putting it in the head of my document, and it seems to work fine.
Well all I did to accomplish this is :
UIView *firstView = [webView.subviews firstObject];
if ([firstView isKindOfClass:[UIScrollView class]]) {
UIScrollView *scroll = (UIScrollView*)firstView;
[scroll setScrollEnabled:NO]; //to stop scrolling completely
[scroll setBounces:NO]; //to stop bouncing
}
Works fine for me...
Also, the ticked answer for this question is one that Apple will reject if you use it in
your iphone app.
In the iOS 5 SDK you can access the scroll view associated with a web view directly rather than iterating through its subviews.
So to disable 'bouncing' in the scroll view you can use:
myWebView.scrollView.bounces = NO;
See the UIWebView Class Reference.
(However if you need to support versions of the SDK before 5.0, you should follow Mirek Rusin's advice.)
Swift 3
webView.scrollView.bounces = false
Warning. I used setAllowsRubberBanding: in my app, and Apple rejected it, stating that non-public API functions are not allowed (cite: 3.3.1)
In Swift to disable bounces
webViewObj.scrollView.bounces = false
Brad's method worked for me. If you use it you might want to make it a little safer.
id scrollView = [yourWebView.subviews objectAtIndex:0];
if( [scrollView respondsToSelector:#selector(setAllowsRubberBanding:)] )
{
[scrollView performSelector:#selector(setAllowsRubberBanding:) withObject:NO];
}
If apple changes something then the bounce will come back - but at least your app won't crash.
On iOS5 only if you plan to let the users zoom the webview contents (e.i.: double tap) the bounce setting isn't enough. You need to set also alwaysBounceHorizontal and alwaysBounceVertical properties to NO, else when they zoom-out (another double tap...) to default it will bounce again.
I traversed the collection of UIWebView's subviews and set their backgrounds to [UIColor blackColor], the same color as the webpage background. The view will still bounce but it will not show that ugly dark grey background.
It looks to me like the UIWebView has a UIScrollView. You can use documented APIs for this, but bouncing is set for both directions, not individually. This is in the API docs.
UIScrollView has a bounce property, so something like this works (don't know if there's more than one scrollview):
NSArray *subviews = myWebView.subviews;
NSObject *obj = nil;
int i = 0;
for (; i < subviews.count ; i++)
{
obj = [subviews objectAtIndex:i];
if([[obj class] isSubclassOfClass:[UIScrollView class]] == YES)
{
((UIScrollView*)obj).bounces = NO;
}
}
I was annoyed to find out that UIWebView is not a scroll view, so I made a custom subclass to get at the web view's scroll view. This suclass contains a scroll view so you can customize the behavior of your web view. The punchlines of this class are:
#class CustomWebView : UIWebview
...
- (id) initWithFrame:(CGRect)frame{
self = [super initWithFrame:frame];
// WebViews are subclass of NSObject and not UIScrollView and therefore don't allow customization.
// However, a UIWebView is a UIScrollViewDelegate, so it must CONTAIN a ScrollView somewhere.
// To use a web view like a scroll view, let's traverse the view hierarchy to find the scroll view inside the web view.
for (UIView* v in self.subviews){
if ([v isKindOfClass:[UIScrollView class]]){
_scrollView = (UIScrollView*)v;
break;
}
}
return self;
}
Then, when you create a custom web view, you can disable bouncing with:
customWebView.scrollView.bounces = NO; //(or customWebView.scrollView.alwaysBounceVertically = NO)
This is a great general purpose way to make a web view with customizable scrolling behavior. There are just a few things to watch out for:
as with any view, you'll also need to override -(id)initWithCoder: if you use it in Interface Builder
when you initially create a web view, its content size is always the same as the size of the view's frame. After you scroll the web, the content size represents the size of the actual web contents inside the view. To get around this, I did something hacky - calling -setContentOffset:CGPointMake(0,1)animated:YES to force an unnoticeable change that will set the proper content size of the web view.
Came across this searching for an answer and I eventually just lucked on an answer of my own by messing about. I did
[[webview scrollView] setBounces:NO];
and it worked.
This worked for me, and beautifully too (I am using phonegap with webView)
[[webView.webView scrollView] setScrollEnabled:NO];
or
[[webView scrollView] setScrollEnabled:NO];
I tried a slightly different approach to prevent UIWebView objects from scrolling and bouncing: adding a gesture recognizer to override other gestures.
It seems, UIWebView or its scroller subview uses its own pan gesture recognizer to detect user scrolling. But according to Apple's documentation there is a legitimate way of overriding one gesture recognizer with another. UIGestureRecognizerDelegate protocol has a method gestureRecognizer:shouldRecognizeSimultaneouslyWithGestureRecognizer: - which allows to control the behavior of any colliding gesture recognizers.
So, what I did was
in the view controller's viewDidLoad method:
// Install a pan gesture recognizer // We ignore all the touches except the first and try to prevent other pan gestures
// by registering this object as the recognizer's delegate
UIPanGestureRecognizer *recognizer;
recognizer = [[UIPanGestureRecognizer alloc] initWithTarget:self action:#selector(handlePanFrom:)];
recognizer.delegate = self;
recognizer.maximumNumberOfTouches = 1;
[self.view addGestureRecognizer:recognizer];
self.panGestureFixer = recognizer;
[recognizer release];
then, the gesture override method:
// Control gestures precedence
- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer
shouldRecognizeSimultaneouslyWithGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer
{
// Prevent all panning gestures (which do nothing but scroll webViews, something we want to disable in
// the most painless way)
if ([otherGestureRecognizer isKindOfClass:[UIPanGestureRecognizer class]])
{
// Just disable every other pan gesture recognizer right away
otherGestureRecognizer.enabled = FALSE;
}
return NO;
}
Of course, this delegate method can me more complex in a real application - we may disable other recognizers selectively, analyzing otherGestureRecognizer.view and making decision based on what view it is.
And, finally, for the sake of completeness, the method we registered as a pan handler:
- (void)handlePanFrom:(UIPanGestureRecognizer *)recognizer
{
// do nothing as of yet
}
it can be empty if all we want is to cancel web views' scrolling and bouncing, or it can contain our own code to implement the kind of pan motions and animations we really want...
So far I'm just experimenting with all this stuff, and it seems to be working more or less as I want it. I haven't tried to submit any apps to iStore yet, though. But I believe I haven't used anything undocumented so far... If anyone finds it otherwise, please inform me.
Here's two newer potential solutions. Apparently, you can use jqtouch or pastrykit to disable scrolling. However, I haven't got these to work. You might be more competent.
turning off vertical scrolling
digging into pastrykit
fixed positioning on mobile safari
This link helped me lot.....Its easy.. There is a demo..
(Xcode 5 iOS 7 SDK example) Here is a Universal App example using the scrollview setBounces function. It is an open source project / example located here: Link to SimpleWebView (Project Zip and Source Code Example)
One of the subviews of UIWebView should be a UIScrollView. Set its scrollEnabled property to NO and the web view will have scrolling disabled entirely.
Note: this is technically using a private API and thus your app could be rejected or crash in future OS releases. Use #try and respondsToSelector
Look into the bounces property of UIScrollView. Quoth the Apple docs:
If the value of the property is YES (the default), the scroll view bounces when it encounters a boundary of the content. Bouncing visually indicates that scrolling has reached an edge of the content. If the value is NO, scrolling stops immediately at the content boundary without bouncing.
Make sure you're using the right UIScrollView. I'm not sure what the hierarchy looks like for a UIWebView, but the scroll view could be a parent, not a child, of the UIWebView.
To disable UIWebView scrolling you could use the following line of code:
[ObjWebview setUserInteractionEnabled:FALSE];
In this example, ObjWebview is of type UIWebView.
webView.scrollView.scrollEnabled=NO;
webView.scrollView.bounces=NO;

Resources