In my custom Tab Bar Application, the orientation never seems to change, even if I force rotate the status bar. Here is my code in my AppDelegate:
AppDelegate.h:
#import <UIKit/UIKit.h>
#import "MBProgressHUD.h"
#class exampleViewContoller;
#class example1ViewController;
#class example2ViewController;
#class example3ViewController;
#class example4ViewController;
#interface <appname>AppDelegate : NSObject <UIApplicationDelegate, MBProgressHUDDelegate> {
UIWindow *window;
UITabBarController *rootController;
exampleViewContoller *viewController;
example1ViewController *viewController1;
example2ViewController *viewController2;
example3ViewController *viewController3;
example4ViewController *viewController4;
NSMutableData *responseData;
NSMutableArray *tweets;
MBProgressHUD *HUD;
}
#property (nonatomic, retain) IBOutlet UIWindow *window;
#property (nonatomic, retain) IBOutlet UITabBarController *rootController;
#property (nonatomic, retain) IBOutlet exampleViewContoller *viewController;
#property (nonatomic, retain) IBOutlet example1ViewController *viewController1;
#property (nonatomic, retain) IBOutlet example2ViewController *viewController2;
#property (nonatomic, retain) IBOutlet example3ViewController *viewController3;
#property (nonatomic, retain) IBOutlet example4ViewController *viewController4;
#property (nonatomic, retain) NSMutableArray *tweets;
#end
AppDelegate.m:
#import "<appname>AppDelegate.h"
#import "exampleViewContoller.h"
#import "example1ViewController.h"
#import "example2ViewController.h"
#import "example3ViewController.h"
#import "example4ViewController.h"
#import "SBJson.h"
#define TMP NSTemporaryDirectory()
#implementation <appname>AppDelegate
#synthesize window = _window;
#synthesize rootController;
#synthesize viewController;
#synthesize viewController1;
#synthesize viewController2;
#synthesize viewController3;
#synthesize viewController4;
#synthesize tweets;
#pragma mark -
#pragma mark Application lifecycle
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
CGFloat width = self.rootController.view.bounds.size.width;
CGFloat height = self.rootController.view.bounds.size.height;
UIView *v = [[UIView alloc] initWithFrame:CGRectMake(0.0, 0.0, width, height)];
UIImage *imageView = [UIImage imageNamed:#"TabBarBackground.png"];
UIColor *kMainColor = [[UIColor alloc] initWithPatternImage:imageView];
[v setBackgroundColor:kMainColor];
[kMainColor release];
[self.rootController.tabBar insertSubview:v atIndex:0];
[imageView release];
[v release];
responseData = [[NSMutableData data] retain];
tweets = [NSMutableArray array];
NSURLRequest *request = [NSURLRequest requestWithURL:
[NSURL URLWithString:#"http://api.twitter.com/1/statuses/user_timeline.json?screen_name=ENTER_USER_HERE&count=20"]];
[[NSURLConnection alloc] initWithRequest:request delegate:self];
NSAssert(nil != self.rootController, #"tab bar controller not hooked up!");
BOOL iPad = NO;
#ifdef UI_USER_INTERFACE_IDIOM
iPad = (UI_USER_INTERFACE_IDIOM() == UIUserInterfaceIdiomPad);
#endif
if (iPad) {
self.viewController = [[[exampleViewContoller alloc] initWithNibName:#"exampleViewController_iPad" bundle:nil] autorelease];
self.viewController1 = [[example1ViewController alloc] initWithNibName:#"example1ViewController_iPad" bundle:nil] autorelease];
self.viewController2 = [[[example2ViewController alloc] initWithNibName:#"example2ViewController_iPad" bundle:nil] autorelease];
self.viewController3 = [[[example3ViewController alloc] initWithNibName:#"example3ViewController_iPad" bundle:nil] autorelease];
self.viewController4 = [[[example4ViewController alloc] initWithNibName:#"example4ViewController_iPad" bundle:nil] autorelease];
} else {
self.viewController = [[[exampleViewContoller alloc] initWithNibName:#"exampleViewContoller_iPhone" bundle:nil] autorelease];
self.viewController1 = [[[example1ViewController alloc] initWithNibName:#"example1ViewController_iPhone" bundle:nil] autorelease];
self.viewController2 = [[[example2ViewController alloc] initWithNibName:#"example2ViewController2_iPhone" bundle:nil] autorelease];
self.viewController3 = [[[example3ViewController alloc] initWithNibName:#"example3ViewController_iPhone" bundle:nil] autorelease];
self.viewController4 = [[[example4ViewController alloc] initWithNibName:#"example4ViewController_iPhone" bundle:nil] autorelease];
}
self.rootController.viewControllers = [NSArray arrayWithObjects:self.viewController, self.viewController4, self.viewController1, self.viewController3, self.viewController2, nil];
[viewController release];
[viewController1 release];
[viewController2 release];
[viewController3 release];
[viewController4 release];
#if __IPHONE_OS_VERSION_MAX_ALLOWED >= __IPHONE_4_0
self.window.rootViewController = self.rootController;
#else
[self.window addSubview:rootController.view];
#endif
[self.window makeKeyAndVisible];
HUD = [[MBProgressHUD alloc] initWithView:viewController.view];
[viewController.view addSubview:HUD];
[HUD show:NO];
HUD.delegate = self;
HUD.labelText = #"Loading";
return YES;
}
//[---CODE CLIP---]
- (void)application:(UIApplication *)application didChangeStatusBarOrientation:(UIInterfaceOrientation)oldStatusBarOrientation {
CGFloat width = self.rootController.view.bounds.size.width*2;
CGFloat height = self.rootController.view.bounds.size.height;
UIView *v = [[UIView alloc] initWithFrame:CGRectMake(0.0, 0.0, width, height)];
UIImage *imageView = [UIImage imageNamed:#"TabBarBackground.png"];
UIColor *kMainColor = [[UIColor alloc] initWithPatternImage:imageView];
[v setBackgroundColor:kMainColor];
[kMainColor release];
[self.rootController.tabBar insertSubview:v atIndex:0];
[imageView release];
[v release];
}
- (void)hudWasHidden {
[HUD removeFromSuperview];
}
//[---CODE CLIP---]
- (void)dealloc
{
[_window release];
[rootController release];
[HUD release];
[super dealloc];
}
#end
The problem is that when I rotate the device in iOS Simulator, the application won't rotate. Any ideas would be much appreciated!
UPDATE
I have also noticed that the launch image is also not rotating (for iPad that is - iPhone doesn't do landscape launch images).
NOTE FOR JMANS
I overrode UITabBarController:
#implementation UITabBarController (MyApp)
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)toInterfaceOrientation {
if(self.selectedIndex==4)
return (toInterfaceOrientation == UIInterfaceOrientationPortrait);
else
return (toInterfaceOrientation != UIInterfaceOrientationPortraitUpsideDown);
}
#end
I would start by including this in all of your view controllers:
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation {
return YES;
}
Also, make sure that you are supporting multiple orientations in your Info.plist.
Tab Bar Controllers and View Rotation
Tab bar controllers support a portrait orientation by default and do not rotate to a landscape orientation unless all of the contained view controllers support such an orientation. When a device orientation change occurs, the tab bar controller queries its array of view controllers. If any one of them does not support the orientation, the tab bar controller does not change its orientation.
Related
*iam a beginner in iphone development.
i have one problem in uitextview...wat iam trying to do is dragging the the selected string in uitextview from out of the textview...and drag it to the tabbarcontroller is it possible plz any on help me on this....*this is the code ihave return up to now....plz help me
#
import <UIKit/UIKit.h>
#import "TabViewController.h"
#class TabBarViewController;
#interface TabBarAppDelegate : UIResponder <UIApplicationDelegate,UITabBarControllerDelegate>
{
TabBarViewController *txtviewcontroller;
UITabBarController *tabbar;
NSArray *viewcontrollerarray;
}
#property(nonatomic,retain)NSArray *viewcontrollerarray;
#property(nonatomic,strong)UITabBarController *tabbar;
#property(nonatomic,retain)TabBarViewController *txtviewcontroller;
#property (strong, nonatomic) UIWindow *window;
#property (strong, nonatomic) TabBarViewController *viewController;
#end
#import "TabBarAppDelegate.h"
#import "TabViewController.h"
#implementation TabBarAppDelegate
#synthesize txtviewcontroller,tabbar,viewcontrollerarray;
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
self.window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]];
// Override point for customization after application launch.
self.window.backgroundColor=[UIColor whiteColor];
self.tabbar=[[UITabBarController alloc]init];
txtviewcontroller=[[TabBarViewController alloc]init];
tabbar.delegate=self;
viewcontrollerarray=[[NSArray alloc]initWithObjects:txtviewcontroller, nil];
self.tabbar.viewControllers=viewcontrollerarray;
if ([[UIDevice currentDevice] userInterfaceIdiom] == UIUserInterfaceIdiomPhone) {
self.viewController = [[TabBarViewController alloc] initWithNibName:#"TabBarViewController_iPhone" bundle:nil];
} else {
self.viewController = [[TabBarViewController alloc] initWithNibName:#"TabBarViewController_iPad" bundle:nil];
}
self.window.rootViewController = self.tabbar;
[self.window makeKeyAndVisible];
return YES;
}
#import <UIKit/UIKit.h>
#interface TabBarViewController : UIViewController
{
UITextView *textview;
}
#property(nonatomic,retain)UITextView *textview;
#end
#import "TabViewController.h"
#import "TabBarAppDelegate.h"
#include <QuartzCore/CoreAnimation.h>
#interface TabBarViewController ()
#end
#implementation TabBarViewController
#synthesize textview;
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view, typically from a nib.
self.title=#"firstname";
CGRect textViewFrame = CGRectMake(20.0f, 20.0f, 280.0f, 124.0f);
textview = [[UITextView alloc] initWithFrame:textViewFrame];
textview.backgroundColor=[UIColor clearColor];
textview.textColor=[UIColor blackColor];
textview.editable=NO;
NSString *filePath=[[NSBundle mainBundle]pathForResource:#"satyadetails" ofType:#"txt"];
NSString *contentString=[NSString stringWithContentsOfFile:filePath encoding:NSUTF8StringEncoding error:nil];
textview.text=contentString;
textview.layer.borderWidth = 3.0f;
textview.layer.borderColor = [[UIColor grayColor] CGColor];
textview.returnKeyType = UIReturnKeyDone;
[self.view addSubview:textview];
enter code here
}
Step 1. Get event when user touches inside textview (You can get that by UITextView's Delegate (startEditing delegate))
Step 2. Add a UILabel on ur view giving position where user touches in textview and giving text as that of textview and giving clear color as backgroundcolor. (Do this inside delegate of textview)
Step 3. Inside touches move of ur view change the positions of ur label dynamically according to touches.
Step 4. When user moves its touches till dropping textview delegate will be called check there if(textview==droppingtextview) then put draggingtextview.text=label.text. and remove label from superview.
The Tabs in my Tab Bar don't seem to be showing up. Here is my App Delegate code:
(appname)AppDelegate.h:
#import <UIKit/UIKit.h>
#class TwitterViewContoller;
#interface <appname>AppDelegate : NSObject <UIApplicationDelegate> {
UIWindow *window;
UITabBarController *rootController;
TwitterViewContoller *viewController;
NSMutableData *responseData;
NSMutableArray *tweets;
}
#property (nonatomic, retain) IBOutlet UIWindow *window;
#property (nonatomic, retain) IBOutlet UITabBarController *rootController;
#property (nonatomic, retain) IBOutlet TwitterViewContoller *viewController;
#property (nonatomic, retain) NSMutableArray *tweets;
#end
(appname)AppDelegate.m:
#import "<appname>AppDelegate.h"
#import "TwitterViewContoller.h"
#import "SBJson.h"
#implementation <appname>AppDelegate
#synthesize window = _window;
#synthesize rootController;
#synthesize viewController;
#synthesize tweets;
#pragma mark -
#pragma mark Application lifecycle
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
// Override point for customization after application launch.
CGFloat width = self.rootController.view.bounds.size.width;
CGFloat height = self.rootController.view.bounds.size.height;
UIView *v = [[UIView alloc] initWithFrame:CGRectMake(0.0, 0.0, width, height)];
UIImage *imageView = [UIImage imageNamed:#"TabBarBackground.png"];
UIColor *kMainColor = [[UIColor alloc] initWithPatternImage:imageView];
[v setBackgroundColor:kMainColor];
[kMainColor release];
[self.rootController.tabBar insertSubview:v atIndex:0];
[imageView release];
[v release];
responseData = [[NSMutableData data] retain];
tweets = [NSMutableArray array];
NSURLRequest *request = [NSURLRequest requestWithURL:
[NSURL URLWithString:#"http://api.twitter.com/1/statuses/user_timeline.json?screen_name=USER_NAME_ID"]];
[[NSURLConnection alloc] initWithRequest:request delegate:self];
NSAssert(nil != self.rootController, #"tab bar controller not hooked up!");
self.viewController = [[[TwitterViewContoller alloc] initWithNibName:#"TwitterViewContoller_iPhone" bundle:nil] autorelease];
self.rootController.viewControllers = [NSArray arrayWithObject:self.viewController];
// this is now the Right Way to set the root view for your app, in iOS 4.0 and later
self.window.rootViewController = self.rootController;
[self.window makeKeyAndVisible];
return YES;
}
#pragma mark NSURLConnection delegate methods
- (void)connection:(NSURLConnection *)connection didReceiveResponse:(NSURLResponse *)response {
[responseData setLength:0];
}
- (void)connection:(NSURLConnection *)connection didReceiveData:(NSData *)data {
[responseData appendData:data];
}
- (void)connection:(NSURLConnection *)connection didFailWithError:(NSError *)error {
}
- (void)connectionDidFinishLoading:(NSURLConnection *)connection {
[connection release];
NSString *responseString = [[NSString alloc] initWithData:responseData encoding:NSUTF8StringEncoding];
[responseData release];
NSArray *allTweets = [responseString JSONValue];
[viewController setTweets:allTweets];
}
- (void)dealloc {
[_window release];
[rootController release];
[viewController release];
[super dealloc];
}
#end
I believe the problem is in application didFinishLaunchingWithOptions: as the only recent changes I have made to App Delegate have been these lines:
NSAssert(nil != self.rootController, #"tab bar controller not hooked up!");
self.viewController = [[[TwitterViewContoller alloc] initWithNibName:#"TwitterViewContoller_iPhone" bundle:nil] autorelease];
self.rootController.viewControllers = [NSArray arrayWithObject:self.viewController];
// this is now the Right Way to set the root view for your app, in iOS 4.0 and later
self.window.rootViewController = self.rootController;
[self.window makeKeyAndVisible];
(EDIT: removing the 2nd and 3rd line above fixes the problem but I need to have them). Any ideas?
Make a Property of your other ViewControllers and synthesize them in your implementation file (.m). Also import them in your AppDelegate.m file. Here is what your header (.h) file will look like (rootController is your TabBarController):
#import <UIKit/UIKit.h>
#class TwitterViewContoller;
#class OtherViewController;
#interface <appname>AppDelegate : NSObject <UIApplicationDelegate> {
UIWindow *window;
UITabBarController *rootController;
TwitterViewContoller *viewController;
OtherViewController *viewController1;
}
#property (nonatomic, retain) IBOutlet UIWindow *window;
#property (nonatomic, retain) IBOutlet UITabBarController *rootController;
#property (nonatomic, retain) IBOutlet TwitterViewContoller *viewController;
#property (nonatomic, retain) IBOutlet OtherViewController *viewController1;
#end
And the first few lines of your implementation (.m) file:
#import "<appname>AppDelegate.h"
#import "TwitterViewContoller.h"
#import "OtherViewController.h"
#implementation <appname>AppDelegate
#synthesize window = _window;
#synthesize rootController;
#synthesize viewController;
#synthesize viewController1;
Add additional allocs and inits for all your ViewControllers:
self.viewController = [[[TwitterViewContoller alloc] initWithNibName:#"TwitterViewContoller_iPhone" bundle:nil] autorelease];
self.viewController1 = [[[SecondViewController alloc] initWithNibName:#"SecondViewController_iPhone" bundle:nil] autorelease];
Then replace this:
self.rootController.viewControllers = [NSArray arrayWithObject:self.viewController];
with this:
self.rootController.viewControllers = [NSArray arrayWithObjects:self.viewController, self.viewController1, nil];
This is so you can add more than one UIViewController to your TabBar Controller.
Then of course, release:
[viewController release];
[viewController1 release];
And under each class for your ViewControllers, under the -initWithNibName method add this inside the if (self) statement:
UITabBarItem *tabBarItem = [self tabBarItem];
UIImage *tabBarImage = [UIImage imageNamed:#"IMAGE NAME.png"];
[tabBarItem setImage:tabBarImage];
[tabBarItem setTitle:#"TITLE GOES HERE"];
Run your application and it should be working now!
I am trying to get my hands on some iphone development. To try to better understand things, I'm going first without IB.
I managed to build a basic app that displays some text. No big deal, until I ran it through Instruments. It shows me some leaks and I cannot understand them.
Any help on this would be greatly appreciated.
MyAppDelegate.h
#interface MyAppDelegate : NSObject <UIApplicationDelegate> {
UIWindow *window;
MyViewController *viewController;
}
#property (nonatomic, retain) IBOutlet UIWindow *window;
#property (nonatomic, retain) MyViewController *viewController;
#end
MyAppDelegate.m
#implementation MyAppDelegate
#synthesize window;
#synthesize viewController;
- (void)applicationDidFinishLaunching:(UIApplication *)application {
// NEXT LINE LEAKS
[window addSubview:viewController.view];
[window makeKeyAndVisible];
}
- (void)dealloc {
[viewController release];
[window release];
[super dealloc];
}
#end
MyViewController.h
#interface MyViewController : UIViewController {
UILabel *firstMessage;
}
MyViewController.m
-(void)loadView {
// Background
CGRect mainFrame = [[UIScreen mainScreen] applicationFrame];
UIView *contentView = [[UIView alloc] initWithFrame:mainFrame];
contentView.backgroundColor = [UIColor blackColor];
self.view = contentView;
[contentView release];
// Add UILabel
// NEXT LINE LEAKS
firstMessage = [[UILabel alloc] initWithFrame:CGRectMake(0, 0, self.view.bounds.size.width, 30)];
firstMessage.font = [UIFont fontWithName:#"Helvetica" size:16];
firstMessage.textColor = [UIColor whiteColor];
firstMessage.backgroundColor = [UIColor blackColor];
[self.view addSubview:firstMessage];
[firstMessage release];
}
-(void) viewDidLoad {
NSString * msg;
msg=[[NSString alloc] initWithFormat:#"stuff here"];
firstMessage.text=msg;
[msg release];
}
-(void)dealloc {
[firstMessage release];
[super dealloc];
}
Try using #property (nonatomic, retain) UILabel* firstMessage in your header, #synthesize firstMessage in your implementation and then release your firstMessage object in the dealloc method.
Try not to release your firstMessage in loadView. Only release it in your controller's dealloc method.
How can I have a UIView over a view that contains a live view from the camera?
Put a NavigationController in uour MainWindow.xib, with a first Controller pointing to a custom CameraController (class attribute). Don't specify any XIB.
Keep a reference to this navigationController with an IBOutlet into your appDelegate, then call at laucnch :
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
[self.window addSubview:navigationController.view];
[self.window makeKeyAndVisible];
return YES;
}
Create another xib for the overlay, with its controller, let's call it OverlayViewController.
Then into this CameraViewController :
.h
#interface CameraController : UIViewController {
UIImagePickerController* __picker;
OverlayViewController* __overlay;
}
#property (nonatomic, retain) UIImagePickerController* picker;
#property (nonatomic, retain) OverlayViewController* overlay;
.m
- (void) viewDidLoad {
self.picker = [[UIImagePickerController alloc] init];
self.picker.sourceType = UIImagePickerControllerSourceTypeCamera;
self.picker.cameraDevice = UIImagePickerControllerCameraDeviceFront;
self.picker.showsCameraControls = NO;
self.picker.navigationBarHidden = YES;
self.picker.wantsFullScreenLayout = YES;
// Insert the overlay
self.overlay = [[OverlayViewController alloc] initWithNibName:#"Overlay" bundle:nil];
self.overlay.pickerRef = self.picker;
self.picker.cameraOverlayView = self.overlay.view;
[self presentModalViewController:self.picker animated:NO];
}
This is a very important auto rotate issue and easy to reproduce.
My application has a UITabBarController. Each tab is a UINavigationController. Auto rotation is handled with normal calls to shouldAutorotateToInterfaceOrientation and didRotateFromInterfaceOrientation.
The interface rotates normally until I call UIViewController.popViewControllerAnimated and change UITabBarController.selectedIndex.
Steps to reproduce:
Create a demo Tab Bar Application.
Add the following code to the App Delegate .h file:#import <UIKit/UIKit.h>
#interface TestRotationAppDelegate : NSObject {
UIWindow *window;
UITabBarController *tabBarController;
}
#property (nonatomic, retain) IBOutlet UIWindow *window;
#property (nonatomic, retain) IBOutlet UITabBarController *tabBarController;
#end
// Redefine the interface to cach rotation messages
#interface UITabBarController (TestRotation1AppDelegate)
#end
Add the following code to the App Delegate .m file:#import "TestRotationAppDelegate.h"
#implementation TestRotationAppDelegate
#synthesize window;
#synthesize tabBarController;
-(BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
[window addSubview:tabBarController.view];
[window makeKeyAndVisible];
return YES;
}
-(BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation {
return YES;
}
-(void)dealloc {
[tabBarController release];
[window release];
[super dealloc];
}
#end
#implementation UITabBarController (TestRotation1AppDelegate)
-(void)viewDidLoad {
[super viewDidLoad];
// Add a third tab and push a view
UIViewController *view1 = [[[UIViewController alloc] init] autorelease];
view1.title = #"Third";
UINavigationController *nav = [[[UINavigationController alloc] initWithRootViewController:view1] autorelease];
NSMutableArray *array = [[NSMutableArray alloc] init];
[array addObjectsFromArray:self.viewControllers];
[array addObject:nav];
self.viewControllers = array;
// Push view2 inside the third tab
UIViewController *view2 = [[[UIViewController alloc] init] autorelease];
[nav pushViewController:view2 animated:YES];
// Create a button to pop view2
UIButton *button = [UIButton buttonWithType:UIButtonTypeRoundedRect];
button.frame = CGRectMake(50, 50, 220, 38);
[button setTitle:#"Pop this view" forState:UIControlStateNormal];
[button addTarget:self action:#selector(doAction) forControlEvents:UIControlEventTouchUpInside];
[view2.view addSubview:button];
}
-(void) doAction {
// ROTATION PROBLEM BEGINS HERE
// Remove one line of code and the problem doesn't occur.
[self.selectedViewController popViewControllerAnimated:YES];
self.selectedIndex = 0;
}
-(BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation {
return YES;
}
#end
The interface auto rotates normally until you tap the button on tab #3.
Your help will be geatly appreciated!
iPhone SDK 3.2 solves this issue.
With previous SDK use [self.selectedViewController popViewControllerAnimated:NO].