unable to stop device rotation - ios

I have posted a question here . In which one buddy replied and gave solution. Although the solution is working on few view controllers but on view its not working. When I enter a view controller that has TabController + navigation controller on there tab Bar Items, the code doesn't work. and the views are able to rotate.
I used the Following code for iOS 6.1
//For iOS6
- (BOOL)shouldAutorotate {
return NO;
}
- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
return UIInterfaceOrientationPortrait;
}
- (NSUInteger)supportedInterfaceOrientations {
return UIInterfaceOrientationMaskPortrait;
}
I have to implement the same thing in iOS 7 too.
Please Help

shouldAutorotate, supportedInterfaceOrientations, preferredInterfaceOrientationForPresentation
The above methods don't get called of a viewcontroller if they are inside any tabbarcontroller of navigationcontroller. If these methods are declared inside tabbarcontroller or navigation controller then they will get called.
For solving this make a class FixedOrientationTab, it is a subclass of UITabBarController, and a navigation class OrientationEnabledNavigation, it is a subclass of UINavigationController. Then implemented shouldAutorotate, supportedInterfaceOrientations, preferredInterfaceOrientationForPresentation methods inside FixedOrientationTab and OrientationEnabledNavigation.
OrientationEnabledNavigation.h
#import <UIKit/UIKit.h>
#interface OrientationEnabledNavigation : UINavigationController
#end
OrientationEnabledNavigation.m
#import "OrientationEnabledNavigation.h"
#interface OrientationEnabledNavigation ()
#end
#implementation OrientationEnabledNavigation
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
if (self) {
// Custom initialization
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view.
}
- (BOOL)shouldAutorotate
{
return [self.topViewController shouldAutorotate];
// return NO;
}
- (NSUInteger)supportedInterfaceOrientations
{
return [self.topViewController supportedInterfaceOrientations];
}
- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
return [self.topViewController preferredInterfaceOrientationForPresentation];
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
#end
FixedOrientationTab.h
#import <UIKit/UIKit.h>
#interface FixedOrientationTab : UITabBarController
#end
FixedOrientationTab.m
#import "FixedOrientationTab.h"
#interface FixedOrientationTab ()
#end
#implementation FixedOrientationTab
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
if (self) {
// Custom initialization
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view.
}
- (BOOL)shouldAutorotate
{
return [self.selectedViewController shouldAutorotate];
// return NO;
}
- (NSUInteger)supportedInterfaceOrientations
{
return [self.selectedViewController supportedInterfaceOrientations];
}
- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
return [self.selectedViewController preferredInterfaceOrientationForPresentation];
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
#end
Then if you want to use navigation controller in your project then use OrientationEnabledNavigation and for tabbar FixedOrientationTab. After that if you implement shouldAutorotate, supportedInterfaceOrientations, preferredInterfaceOrientationForPresentation these method inside your viewcontroller then they will get called.
Hope this helps.. :)
Edit
As Jeev pointed out another way is that add some code beginning of your app delegate:
For UITabBarController
#implementation UITabBarController (AutoRotationForwarding)
-(BOOL)shouldAutorotate
{
if ([self.selectedViewController respondsToSelector:#selector(shouldAutorotate)]) {
return [self.selectedViewController shouldAutorotate];
}
else {
return YES;
}
}
- (NSUInteger)supportedInterfaceOrientations {
if ([self.selectedViewController respondsToSelector:#selector(supportedInterfaceOrientations)]) {
return [self.selectedViewController supportedInterfaceOrientations];
}
else {
return UIInterfaceOrientationMaskAll;
}
}
#end
For UINavigationController
#implementation UINavigationController (AutoRotationForwarding)
-(BOOL)shouldAutorotate
{
if ([self.topViewController respondsToSelector:#selector(shouldAutorotate)]) {
return [self.topViewController shouldAutorotate];
}
else {
return YES;
}
}
-(NSUInteger) supportedInterfaceOrientations {
if([self.topViewController respondsToSelector:#selector(supportedInterfaceOrientations)])
{
return [self.topViewController supportedInterfaceOrientations];
}
return UIInterfaceOrientationMaskPortrait;
}
#end

I have UINavigationController contains UIViewController.
You should disable rotate in UINavigationController by subclass UINavigationController and implement
- (BOOL)shouldAutorotate
{
return YES;
}
- (NSUInteger)supportedInterfaceOrientations
{
// return some
}
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation
{
// return some thing that you want
}
Hope this helps you.

Since I m using a TabBarController, the only working solution I got was to create a category.
so just make a category
here's the .h class of the category, I named it AutoRotationtab
#import <UIKit/UIKit.h>
#import "AppDelegate.h"
#interface UITabBarController (AutoRotationTab)
#end
here's the .m class of the category
#import "UITabBarController+AutoRotationTab.h"
#implementation UITabBarController (AutoRotationTab)
-(BOOL)shouldAutorotate
{
if(globalvariable_shouldRotate)
{
return YES;
}
else
{
return NO;
}
}
- (NSUInteger)supportedInterfaceOrientations
{
if(globalvariable_shouldRotate)
{
return UIInterfaceOrientationMaskAll;
}
else
{
return UIInterfaceOrientationMaskPortrait;
}
}
just make this category, and see the Magic, It works

Related

Request for member 'subview' in something not a structure or union?

I've created a gradient using Quartz, only one issue. I can't get it to rotate with the screen. I've tried everything listed on this tutorial. Here's the view controller header:
#import <UIKit/UIKit.h>
#interface RadialGradientBackgroundViewController : UIViewController {
}
#end
And here's the view controller:
#import "RadialGradientBackgroundViewController.h"
#import "BackgroundLayer.h"
#implementation RadialGradientBackgroundViewController
/*
// The designated initializer. Override to perform setup that is required before the view is loaded.
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil {
self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
if (self) {
// Custom initialization
}
return self;
}
*/
/*
// Implement loadView to create a view hierarchy programmatically, without using a nib.
- (void)loadView {
}
*/
- (void)viewDidLoad {
[super viewDidLoad];
}
-(void)viewWillAppear:(BOOL)animated {
[super viewWillAppear:animated];
CAGradientLayer *bgLayer = [BackgroundLayer gradient];
bgLayer.frame = self.view.bounds;
[self.view.layer insertSublayer:bgLayer atIndex:0];
}
-(void)willRotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation duration:(NSTimeInterval)duration {
[[[self.subview.layer sublayers] objectAtIndex:0] setFrame:self.view.bounds]; // Error is here!
}
/*
// Override to allow orientations other than the default portrait orientation.
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation {
// Return YES for supported orientations
return (interfaceOrientation == UIInterfaceOrientationPortrait);
}
*/
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
}
- (void)viewDidUnload {
}
- (void)dealloc {
[super dealloc];
}
#end
Your view controller does not have a subview property or method. As rmaddy said, change subview to view.

How to open a view controller in landscape mode?

I have a table view and when the cell is tapped in table, I'm pushing another view controller
as follows:
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
UIStoryboard *storyboard = [UIStoryboard storyboardWithName:#"MainStoryboard_iPhone" bundle:nil];
PriceChart *vc = [storyboard instantiateViewControllerWithIdentifier:#"pricechart"];
[self.navigationController pushViewController:vc animated:YES];
}
Now My question is: the view controller I'm going to show should be in land scape mode but it is in portrait mode.
Another question is how to open different view controllers when different cell is tapped. I tried it using indexpath.row but is there any other way using storyboard?
shouldAutorotate, supportedInterfaceOrientations, preferredInterfaceOrientationForPresentation
The above methods don't get called of a UIViewController if they are inside any UINavigationController. If these methods are declared inside UINavigationController then they will get called.
For solving this make a class lets call it OrientationEnabledNavigation, it is a subclass of UINavigationController. Then implemented shouldAutorotate, supportedInterfaceOrientations, preferredInterfaceOrientationForPresentation methods inside OrientationEnabledNavigation.
OrientationEnabledNavigation.h
#import <UIKit/UIKit.h>
#interface OrientationEnabledNavigation : UINavigationController
#end
OrientationEnabledNavigation.m
#import "OrientationEnabledNavigation.h"
#interface OrientationEnabledNavigation ()
#end
#implementation OrientationEnabledNavigation
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
if (self) {
// Custom initialization
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view.
}
- (BOOL)shouldAutorotate
{
return [self.topViewController shouldAutorotate];
// return NO;
}
- (NSUInteger)supportedInterfaceOrientations
{
return [self.topViewController supportedInterfaceOrientations];
}
- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
return [self.topViewController preferredInterfaceOrientationForPresentation];
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
#end
Then if you want to use navigation controller in your project then use OrientationEnabledNavigation. After that if you implement shouldAutorotate, supportedInterfaceOrientations, preferredInterfaceOrientationForPresentation these method inside your viewcontroller then they will get called.
The in you viewcontroller implement these:
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
return (interfaceOrientation == UIInterfaceOrientationPortrait);
}
-(BOOL)shouldAutorotate
{
return NO;
}
-(NSUInteger)supportedInterfaceOrientations
{
return UIInterfaceOrientationMaskPortrait;
}
Another way is that add some code beginning of your app delegate:
For UITabBarController
#implementation UITabBarController (AutoRotationForwarding)
-(BOOL)shouldAutorotate
{
if ([self.selectedViewController respondsToSelector:#selector(shouldAutorotate)]) {
return [self.selectedViewController shouldAutorotate];
}
else {
return YES;
}
}
- (NSUInteger)supportedInterfaceOrientations {
if ([self.selectedViewController respondsToSelector:#selector(supportedInterfaceOrientations)]) {
return [self.selectedViewController supportedInterfaceOrientations];
}
else {
return UIInterfaceOrientationMaskAll;
}
}
#end
For UINavigationController
#implementation UINavigationController (AutoRotationForwarding)
-(BOOL)shouldAutorotate
{
if ([self.topViewController respondsToSelector:#selector(shouldAutorotate)]) {
return [self.topViewController shouldAutorotate];
}
else {
return YES;
}
}
-(NSUInteger) supportedInterfaceOrientations {
if([self.topViewController respondsToSelector:#selector(supportedInterfaceOrientations)])
{
return [self.topViewController supportedInterfaceOrientations];
}
return UIInterfaceOrientationMaskPortrait;
}
#end
Hope this helps.. :)
This is how you can force to landscape
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
return (interfaceOrientation == UIInterfaceOrientationPortrait);
}
-(BOOL)shouldAutorotate
{
return NO;
}
-(NSUInteger)supportedInterfaceOrientations
{
return UIInterfaceOrientationMaskPortrait;
}
In class which is in landscape mode:
- (NSUInteger)supportedInterfaceOrientations
{
// return orientation that you want
//return UIInterfaceOrientationMaskPortrait|UIInterfaceOrientationMaskPortraitUpsideDown;
}
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation
{
return YES;
//return UIInterfaceOrientationIsPortrait(toInterfaceOrientation);
}
If you use UINavigationController, you should inherit your navigationController from UINavigationController and implement
- (BOOL)shouldAutorotate
{
return YES;
}
- (NSUInteger)supportedInterfaceOrientations
{
return [[self.viewControllers lastObject] supportedInterfaceOrientations];
}
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation
{
return [[self.viewControllers lastObject] shouldAutorotateToInterfaceOrientation:toInterfaceOrientation];
}
Try This..
This demo has solved my problem...
https://github.com/alloy/ForceOrientationTest
You can force an orientation refresh as explained here and the other answers in that question.
As for the second question, just populate a UITableViewController with either static cells or dynamic prototype cells. Then control+drag from the cell to another view controller in your Storyboard. You'll have the same Push/Modal/Custom actions that show up for buttons.

playInputClick not working

Hi I was trying some examples and checking documentation but I can't get this to work.
Here's my code:
#interface AHMSoudView : UIView <UIInputViewAudioFeedback>
- (void) playClick;
#end
#implementation AHMSoudView
- (id)initWithFrame:(CGRect)frame {
self = [super initWithFrame:frame];
if (self) {
// Initialization code
}
return self;
}
- (BOOL) enableInputClicksWhenVisible {
return YES;
}
- (void) playClick {
[[UIDevice currentDevice] playInputClick];
}
#end
In the storyboard I have the view set to my AHMSoundView. In the controller I then have:
- (IBAction)keypadTouchDown:(id)sender {
[((AHMSoudView *)self.view) playClick];
}
But nothing happens. What am I doing wrong?

Autolayout IOS 7 Storyboard Force Landscape or Portrait

I have a single storyboard where a majority of the views should be in portrait mode but one should be in Landscape. I've down a significant amount of searching but keep coming up a little blank.
My current implementation which isn't exactly seeming to work as I hoped consists of the following bits of code I've pieced together from this website:
I've made a RotationalViewController which extends from UINavigationController
#import "RotationControlledViewController.h"
#interface RotationControlledViewController ()
#end
#implementation RotationControlledViewController
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
if (self) {
// Custom initialization
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view.
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
-(BOOL)shouldAutorotate
{
return [[self.viewControllers lastObject] shouldAutorotate];
}
-(NSUInteger)supportedInterfaceOrientations
{
return [[self.viewControllers lastObject] supportedInterfaceOrientations];
}
- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
UIInterfaceOrientation ret = [[self.viewControllers lastObject] preferredInterfaceOrientationForPresentation];
return ret;
}
#end
And then I've made a PortraitViewController
#import "PortraitViewController.h"
#interface PortraitViewController ()
#end
#implementation PortraitViewController
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
if (self) {
// Custom initialization
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view.
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
-(BOOL)shouldAutorotate
{
return YES;
}
- (NSUInteger)supportedInterfaceOrientations
{
return UIInterfaceOrientationMaskPortrait | UIInterfaceOrientationMaskPortraitUpsideDown;
}
- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
return UIInterfaceOrientationPortrait;
}
and a LandscapeViewController
#import "LandscapeViewController.h"
#interface LandscapeViewController ()
#end
#implementation LandscapeViewController
- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
if (self) {
// Custom initialization
}
return self;
}
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view.
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
-(BOOL)shouldAutorotate
{
return YES;
}
-(NSUInteger)supportedInterfaceOrientations
{
return UIInterfaceOrientationLandscapeRight | UIInterfaceOrientationLandscapeLeft;
}
- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
return UIInterfaceOrientationLandscapeRight;
}
#end
I have played around with changing some of the settings but to no avail. My general plan of attack has been to make specific view controllers inherit from either LandscapeViewController or PortraitViewController if I want to lock them to a specific orientation.
Things seem to be working for portrait view ( i can lock controllers into portrait view) but I seem unable to load my 1 landscape view and have it a) auto rotate to landscape upon load, or b) rotate to landscape at all.
Any suggestions would be very appreciated.
Applying the solution presented in:
Force controllers to Change their orientation in Either Portrait or Landscape
I was able to make things work.
In both my PortraiteViewController and LandscapeViewControllers I modified the viewDidLoad method to:
PortraiteViewController:
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view.
[[UIApplication sharedApplication] setStatusBarOrientation:UIInterfaceOrientationPortrait animated:YES];
UIViewController *mVC = [[UIViewController alloc] init];
[self presentModalViewController:mVC animated:NO];
[self dismissModalViewControllerAnimated:NO];
}
LandscapeViewController:
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view.
[[UIApplication sharedApplication] setStatusBarOrientation:UIInterfaceOrientationLandscapeLeft animated:YES];
UIViewController *mVC = [[UIViewController alloc] init];
[self presentModalViewController:mVC animated:NO];
[self dismissModalViewControllerAnimated:NO];
}
This solution MAY stop working after IOS7 because both presentModalViewController and dismissModalViewController are deprecated.

supportedInterfaceOrientation not working

I have two viewController, So I want the first viewController can rotate all side and second viewController can rotate left side only. And this is my code in second viewController.
Thank you very much.
-(NSUInteger) supportedInterfaceOrientations
{
return UIInterfaceOrientationMaskLandscapeLeft;
}
If you are using navigationController,
Create a category like this,
#interface UINavigationController (Rotation_IOS6)
#end
#implementation UINavigationController (Rotation_IOS6)
-(BOOL)shouldAutorotate
{
if([self.visibleViewController isMemberOfClass:NSClassFromString(#"SecondViewController")])
{
return UIInterfaceOrientationMaskLandscapeLeft
}
return NO;
}
- (NSUInteger)supportedInterfaceOrientations
{
return [[self topViewController] supportedInterfaceOrientations];
}
- (UIInterfaceOrientation)preferredInterfaceOrientationForPresentation
{
if([self.visibleViewController isMemberOfClass:NSClassFromString(#"SecondViewController")])
{
return UIInterfaceOrientationMaskLandscapeLeft
}
return [[self.viewControllers lastObject] preferredInterfaceOrientationForPresentation];
}
#end
- (BOOL)shouldRotateToOrientation:(UIDeviceOrientation)orientation {
if (orientation == UIDeviceOrientationLandscapeLeft) {
return NO;
}
else if (orientation == UIDeviceOrientationLandscapeRight) {
return NO;
}
else if (orientation == UIDeviceOrientationPortrait) {
return NO;
}
else if (orientation == UIDeviceOrientationPortraitUpsideDown) {
return YES;
}
}
//Use this method to check which orientation going to execute and you can return no if you
//want to stop orientation and if you return yes then orientation execute
First you need to add the category of NavigationController
Declare that bool in AppDelegate to used in all over projcet.
Declare property AppDelegate.h
#property BOOL * islandscape;
AppDelegate.m file
#synthesize islandscape;
.h file
#import <UIKit/UIKit.h>
#import "AppDelegate.h"
#interface UINavigationController (orientation1)
#end
.M File
#import "UINavigationController+orientation1.h"
#implementation UINavigationController (orientation1)
- (BOOL)shouldAutorotate
{
return YES;
}
- (NSUInteger)supportedInterfaceOrientations
{
AppDelegate * delegate=(AppDelegate *)[[UIApplication sharedApplication]delegate];
if (delegate.islandscape)
{
// for iPhone, you could also return UIInterfaceOrientationMaskAllButUpsideDown
return UIInterfaceOrientationMaskLandscape;
}
return UIInterfaceOrientationMaskPortrait;
}
#end
and then used that bool varible in SeconViewController.
delegate.islandscape=Yes;

Resources