320 likes | 473 Views
HelloWorld. 朱中華 2009/10/02. Helloworld 流程圖. HelloController.
E N D
HelloWorld 朱中華 2009/10/02
HelloController • #import <UIKit/UIKit.h>@class UIImageView;@interface HelloController : UIViewController{ UIImageView *contentView;}@end@implementation HelloController- (id)init{ if (self = [super init]) { self.title = [[[NSBundle mainBundle] infoDictionary] objectForKey:@"CFBundleName"]; // place any further initialization here } return self;}
LoadView • - (void)loadView{ // Load an application image and set it as the primary view contentView = [[UIImageView alloc] initWithFrame:[[UIScreen mainScreen] applicationFrame]]; [contentView setImage:[UIImage imageNamed:@"helloworld.png"]]; // Provide support for auto-rotation and resizing contentView.autoresizesSubviews = YES; contentView.autoresizingMask = (UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight); // Assign the view to the view controller self.view = contentView; [contentView release]; // reduce retain count by one }// Allow the view to respond to iPhone Orientation changes-(BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation{ return YES;}-(void) dealloc{ // add any further clean-up here [contentView release]; [super dealloc];}@end
SampleAppDelegate • @interface SampleAppDelegate : NSObject <UIApplicationDelegate> {}@end@implementation SampleAppDelegate// On launch, create a basic window- (void)applicationDidFinishLaunching:(UIApplication *)application { UIWindow *window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]]; UINavigationController *nav = [[UINavigationController alloc] initWithRootViewController:[[HelloController alloc] init]]; [window addSubview:nav.view]; [window makeKeyAndVisible];}- (void)applicationWillTerminate:(UIApplication *)application { // handle any final state matters here}- (void)dealloc { [super dealloc];}@end
Main • int main(int argc, char *argv[]){ NSAutoreleasePool * pool = [[NSAutoreleasePool alloc] init]; int retVal = UIApplicationMain(argc, argv, nil, @"SampleAppDelegate"); [pool release]; return retVal;}
Overview • Navigation Bar上有project名HelloWorld (CFBundleName ), Application area上有hello World這張圖 (圖名 helloworld.png檔案,以 setImage : [UIImage imageNamed: @“helloworld.png”];“ load進來)。
Overview(Cont.) • 整個程式由UIApplication進入applicationDidFinishLaunching。 • 在applicationDidFinishLaunching中, 創造出一個Window的UIWindow *window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]]; • 產生一個NavigationViewController:UINavigationController *nav = [[UINavigationController alloc] initWithRootViewController: [[HelloController alloc] init] ]; • 將project名"HelloWorld"放入HelloController的title內:self.title = [[[NSBundle mainBundle] infoDictionary] objectForKey: @"CFBundleName"]; • 將navigation bar及application content圖片的navigation view controller nav放入window成為subview,讓window成為main window • 跳入loadView去load hello World這張圖:[[contentView setImage:[UIImage imageNamed:@"helloworld.png"]];
UIApplication • int retVal = UIApplication(argc, argv, nil, @"SampleAppDelegate”); • 在SDK3.0 Xcode/Help/documentation/iPhone OS3.0 Library/裡的UIApp可找到UIApplication Class, UIApplicationMain會產生一個 UIApplication object。而UIApplicationMain是在 UIKit Function Reference定義的, 參看UIKit Function Reference可了解 UIApplicationMain
UIApplicationMain • int UIApplicationMain( int argc, char *argv[], NSString *principalClassName, NSString *delegateClassName ); • 說明:UIApplicationMain的主要功能即為將control交到application手中。 • 參數:argc, argv即為C的argc, argv。 • principalClassName: UIApplication class(或subclass名),若為nil,則以UIApplication為名。 • delegateClassName:實體化application delegate "delegateClassName",若為nil,則從main nib load delegate object。 其實, 一般 "delegateClassName"均為 nil,
iPhone程式進入點 • 建置一個iPhone應用程式的基本骨架,提到main()、 applicationDidFinishLaunching、 applicationWillTerminate、 LoadView、 ShouldAutorotateToInterfaceOrientation, main()即為iPhone程式的進入點,這和一般的C程式相同, 緊接著進入 applicationDidFinishLaunching ( 這仍是受main()內的程式決定, 一般main()只有幾行,其中一行是進入 applicationDidFinishLaunching), applicationDidFinishLaunching才是真正的主程式,在 applicationDidFinishLaunching中會跳至 LoadView。
UIWindow • UIWindow *window = [[UIWindow alloc] initWithFrame:[[UIScreen mainScreen] bounds]]; • "[UIWindow alloc] initWithFrame:":[UIWindow alloc]產生一UIWindow object,然後呼叫initWithFrame,要注意的是,在 SDK3.0 Xcode/Help/documentation/iPhone OS3.0 Library/中找不到 UIWindow的alloc和initWithFrame,但因為 UIWindow是 UIView的 subclass,所以看 UIView,即可找到。看 UIView的initWithFrame就可知道其需要一個 CGRect的object作為parameter。並 return一個id object。所以要看看 initWithFrame:後的東西了!
UIWindow (Cont.) • [[UIScreen mainScreen] bounds]]: [UIScreen mainScreen]會產生一個 screen object,成為 iPhone的 device's screen。然後呼叫 bounds,bounds是 UIScreen的一個 property(而且read-only),所以是種getter,回傳的是 "bounding rectangle of the screen, measured in points.",也就是說,回傳 CGRect structure。 CGRect是: struct CGRect{ CGPoint origin; CGSize size; };
UIWindow (Cont.) • 由以上說明合起來看,[[UIScreen mainScreen] bounds]]正好回傳[UIWindow alloc] initWithFrame:"需要的parameter----CGRect structure。 • 注意:在SDK3.0 Xcode/Help/documentation/iPhone OS3.0 Library/中,CGRect需找CGGeometry reference。打CGRect找不到。 • [[UIWindow alloc] initWithFrame : [[UIScreen mainScreen] bounds]];表示出 UIWindow必需和 UIScreen(產生frame)合用, 由書中 58頁2-1-2的說明及 60頁的例子也可看到一個 window必需有個frame。 • 在SampleAppDelegate.m的applicationDidFinishLaunching中加入: • printf("x= %f, y = %f, width = %f, height = %f n",[window frame].origin.x, [window frame].origin.y,[window frame].size.width, [window frame].size.height ); 即可印出window的frame。上printf會印出"x = 0, y =0, width = 320, height = 480",也就是說iPhone整個320x480是frame。
UINavigationController • UINavigationController *nav = [[UINavigationController alloc] initWithRootViewController:[[HelloController alloc] init] ]; • SDK3.0 Xcode/Help/documentation/iPhone OS3.0 Library/search for UIKit framework reference,有 class references、 protocol references、 other references, 在 class references下, 找到 UINavigationController.也可以:UINavigationController是UIKIT的external class,type是UIKIT_EXTERN_CLASS,它的定義在UIKIT.framework裡的UINavigationController.h裡。找到後, 可知UINavigationController是UIViewController的subclass,[[UINavigationController alloc] initWithRootViewController:....]完成後, 回傳id,也就是 UINavigationController。initWithRootViewController所需的parameter--UIViewController,這是程式設計師自訂的 HelloController,而 HelloController是 UIViewController的 subclass, 所以是個 UIViewController,看一下[[HelloController alloc] init] ]的init。
Application Title • self.title = [[[NSBundle mainBundle] infoDictionary] objectForKey:@“CFBundleName”]; • 本行是找出HelloWorld program並assign給HelloController。self.title就是未來display在navigation controller上的字,title是個NSString pointer
Application Title (Cont.) • 本例中的self是由[[HelloController alloc] init] 中的[HelloController alloc]而來,所以是個HelloController。因為是 UIViewController的 subclass,所以繼承了其 instance variable及method。找UIViewController,用 SDK3.0 Xcode/Help/documentation/iPhone OS3.0 Library/search for UIKit framework reference,在 class中找到 UIViewController ( UIViewController是 UIResponder的 subclass)。
Application Title (Cont.) • [[[NSBundle mainBundle] infoDictionary] objectForKey:@"CFBundleName"]; • 用SDK3.0 Xcode/Help/documentation/iPhone OS3.0 Library/search for NSBundle可找到NSBundle class, NSBundle object代表 file system上某個地方 ( location),該地方有可執行的 program。 [NSBundle mainBundle]回傳指向 NSBundle的pointer。 [[NSBundle mainBundle] infoDictionary] 回傳指向 NSDictionary的pointer。
Application Title (Cont.) • NSDictionary可用 SDK3.0 Xcode/Help/documentation/iPhone OS3.0 Library/search for NSDictionary找到, objectForKey: @"CFBundleName"傳回 [ NSBundle mainBundle]可執行的 program的 file system上某個地方 (location)。在本例,即為 project名稱: HelloWorld。至此,UINavigationController *nav是個UINavigationController,包含有一個RootViewController、"指向project名稱:HelloWorld"的HelloController。
addSubview • [window addSubview:nav.view]; • 在SDK3.0 Xcode/Help/documentation/iPhone OS3.0 Library/search for UIKit framework reference,有 class references、 protocol references、 other references,在 class references下,找到 UINavigationController,再找到其superclass UIViewController的property--- view,由 view的內容:If you access this property and its value is nil, the view controller automatically calls the loadView。可知,因為從未assign過nav.view,自然是nil,因而call loadView將helloworld.png及Navigation Bar整個視圖界面設定為視窗的子視圖,並將這個視窗呈現到畫面上。
makeKeyAndVisible • SDK3.0 Xcode/Help/documentation/iPhone OS3.0 Library/search for UIWindow, windows makeKeyAndVisible]讓 window成為 main window並 display in front of other windows。
UIImage • UIKit class representing an image • Creating UIImages: • Fetching image in application bundle • Use +[UIImage imageNamed:(NSString *)name] • Include file extension in file name, e.g. @”myImage.jpg” • Read from file on disk • Use -[UIImage initWithContentsOfFile:(NSString *)path] • From data in memory • Use -[UIImage initWithData:(NSData *)data]
Getting Image Data • Given UIImage, want PNG or JPG representation • NSData *UIImagePNGRepresentation (UIImage * image); • NSData *UIImageJPGRepresentation (UIImage * image); • UIImage also has a CGImage property which will give you a CGImageRef to use with CG calls
Debugger • BreakPoint
Homework 1 • Change Navigation Bar with “NTIT and content image with a logo of NTIT • Hand in: due 2009/10/30, 00:00 • chchu777@gmail.com • 以組別學號姓名為檔名來繳報告