iPhone SDK示例代码
iPhone SDK示例代码
http://www.cocoadev.cn/iPhone-iPad/iPhone-sdk-sample-code-20100306.asp
iPhone SDK新手必读 写Log 在Xcode里,点菜单Run > Console 就可以看到NSLog的记录. NSLog(@"log: %@ ", myString); NSLog(@"log: %f ", myFloat); NSLog(@"log: %i ", myInt); 图片显示 不需要UI资源绑定,在屏幕任意处显示图片。 下面的代码可以被用到任意 View 里面。 CGRect myImageRect = CGRectMake(0.0f, 0.0f, 320.0f, 109.0f); UIImageView *myImage = [[UIImageView alloc] initWithFrame:myImageRect]; [myImage setImage:[UIImage imageNamed:@"myImage.png"]]; myImage.opaque = YES; // explicitly opaque for performance [self.view addSubview:myImage]; [myImage release]; 应用程序边框大小 我们应该使用"bounds"来获得应用程序边框。不是用"applicationFrame"。"applicationFrame"还包含了一个20像素的status bar。除非我们需要那额外的20像素的status bar。 Web view UIWebView类的调用. CGRect webFrame = CGRectMake(0.0, 0.0, 320.0, 460.0); UIWebView *webView = [[UIWebView alloc] initWithFrame:webFrame]; [webView setBackgroundColor:[UIColor whiteColor]]; NSString *urlAddress = @"http://www.google.com"; NSURL *url = [NSURL URLWithString:urlAddress]; NSURLRequest *requestObj = [NSURLRequest requestWithURL:url]; [webView loadRequest:requestObj]; [self addSubview:webView]; [webView release]; 显示网络激活状态图标 在iPhone的状态栏的左上方显示的一个icon假如在旋转的话,那就说明现在网络正在被使用。 UIApplication* app = [UIApplication sharedApplication]; app.networkActivityIndicatorVisible = YES; // to stop it, set this to NO Animation: 一组图片 连续的显示一组图片 NSArray *myImages = [NSArray arrayWithObjects: [UIImage imageNamed:@"myImage1.png"], [UIImage imageNamed:@"myImage2.png"], [UIImage imageNamed:@"myImage3.png"], [UIImage imageNamed:@"myImage4.gif"], nil]; UIImageView *myAnimatedView = [UIImageView alloc]; [myAnimatedView initWithFrame:[self bounds]]; myAnimatedView.animationImages = myImages; myAnimatedView.animationDuration = 0.25; // seconds myAnimatedView.animationRepeatCount = 0; // 0 = loops forever [myAnimatedView startAnimating]; [self addSubview:myAnimatedView]; [myAnimatedView release]; Animation: 移动一个对象 让一个对象在屏幕上显示成一个移动轨迹。注意:这个Animation叫"fire and forget"。也就是说编程人员不能够在animation过程中获得任何信息(比如当前的位置)。假如你需要这个信息的话,那么就需要通过animate和定时器在必要的时候去调整x&y坐标。 CABasicAnimation *theAnimation; theAnimation=[CABasicAnimation animationWithKeyPath:@"transform.translation.x"]; theAnimation.duration=1; theAnimation.repeatCount=2; theAnimation.autoreverses=YES; theAnimation.fromValue=[NSNumber numberWithFloat:0]; theAnimation.toValue=[NSNumber numberWithFloat:-60]; [view.layer addAnimation:theAnimation forKey:@"animateLayer"]; NSString和int类型转换 下面的这个例子让一个text label显示的一个整型的值。 currentScoreLabel.text = [NSString stringWithFormat:@"%d", currentScore]; 正泽表达式 (RegEx) 当前的framework还不支持RegEx。开发人员还不能在iPhone上使用包括NSPredicate在类的regex。但是在模拟器上是可以使用NSPredicate的,就是不能在真机上支持。 可以拖动的对象items 下面展示如何简单的创建一个可以拖动的image对象: 1. 创建一个新的类来继承UIImageView。 @interface myDraggableImage : UIImageView { } 2. 在新的类实现的时候添加两个方法: - (void) touchesBegan:(NSSet*)touches withEvent:(UIEvent*)event { // Retrieve the touch point CGPoint pt = [[touches anyObject] locationInView:self]; startLocation = pt; [[self superview] bringSubviewToFront:self]; } - (void) touchesMoved:(NSSet*)touches withEvent:(UIEvent*)event { // Move relative to the original touch point CGPoint pt = [[touches anyObject] locationInView:self]; CGRect frame = [self frame]; frame.origin.x += pt.x - startLocation.x; frame.origin.y += pt.y - startLocation.y; [self setFrame:frame]; } 3. 现在再创建一个新的image加到我们刚创建的UIImageView里面,就可以展示了。 dragger = [[myDraggableImage alloc] initWithFrame:myDragRect]; [dragger setImage:[UIImage imageNamed:@"myImage.png"]]; [dragger setUserInteractionEnabled:YES]; 震动和声音播放 下面介绍的就是如何让手机震动(注意:在simulator里面不支持震动,但是他可以在真机上支持。) AudioServicesPlaySystemSound(kSystemSoundID_Vibrate); Sound will work in the Simulator, however some sound (such as looped) has been reported as not working in Simulator or even altogether depending on the audio format. Note there are specific filetypes that must be used (.wav in this example). SystemSoundID pmph; id sndpath = [[NSBundle mainBundle] pathForResource:@"mySound" ofType:@"wav" inDirectory:@"/"]; CFURLRef baseURL = (CFURLRef) [[NSURL alloc] initFileURLWithPath:sndpath]; AudioServicesCreateSystemSoundID (baseURL, &pmph); AudioServicesPlaySystemSound(pmph); [baseURL release]; 线程 1. 创建一个新的线程: [NSThread detachNewThreadSelector:@selector(myMethod) toTarget:self withObject:nil]; 2. 创建线程所调用的方法: - (void)myMethod { NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init]; *** code that should be run in the new thread goes here *** [pool release]; } 假如我们需要在线程里面调用主线程的方法函数,就可以用performSelectorOnMainThread来实现: [self performSelectorOnMainThread:@selector(myMethod) withObject:nil waitUntilDone:false]; 读取crash的日记文件 假如很不幸,我们的某处代码引起了crash,那么就可以阅读这篇文章应该会有用: navigate here 测试 1. 在模拟器里,点击 Hardware > Simulate Memory Warning to test. 那么我们整个程序每个页面就都能够支持这个功能了。 2. Be sure to test your app in Airplane Mode. Access properties/methods in other classes One way to do this is via the AppDelegate: myAppDelegate *appDelegate = (myAppDelegate *)[[UIApplication sharedApplication] delegate]; [[[appDelegate rootViewController] flipsideViewController] myMethod]; 创建随机数 调用arc4random()来创建随机数. 还可以通过random()来创建, 但是必须要手动的设置seed跟系统时钟绑定。这样才能够确保每次得到的值不一样。所以相比较而言arc4random()更好一点。 定时器 下面的这个定时器会每分钟调用一次调用myMethod。 [NSTimer scheduledTimerWithTimeInterval:1 target:self selector:@selector(myMethod) userInfo:nil repeats:YES]; 当我们需要给定时器的处理函数myMethod传参数的时候怎么办?用"userInfo"属性。 1. 首先创建一个定时器: [NSTimer scheduledTimerWithTimeInterval:1 target:self selector:@selector(myMethod) userInfo:myObject repeats:YES]; 2. 然后传递NSTimer对象到处理函数: -(void)myMethod:(NSTimer*)timer { // Now I can access all the properties and methods of myObject [[timer userInfo] myObjectMethod]; } 用"invalidate"来停止定时器: [myTimer invalidate]; myTimer = nil; // ensures we never invalidate an already invalid Timer 应用分析 当应用程序发布版本的时候,我们可能会需要收集一些数据,比如说程序被使用的频率如何。这个时候大多数的人使用PinchMedia来实现。他们会提供我们可以很方便的加到程序里面的Obj-C代码,然后就可以通过他们的网站来查看统计数据。 Time Calculate the passage of time by using CFAbsoluteTimeGetCurrent(). CFAbsoluteTime myCurrentTime = CFAbsoluteTimeGetCurrent(); // perform calculations here 警告窗口 显示一个简单的带OK按钮的警告窗口。 UIAlertView *alert = [[UIAlertView alloc] initWithTitle:nil message:@"An Alert!" delegate:self cancelButtonTitle:@"OK" otherButtonTitles:nil]; [alert show]; [alert release]; Plist文件 应用程序特定的plist文件可以被保存到app bundle的Resources文件夹。当应用程序运行起来的时候,就会去检查是不是有一个plist文件在用户的Documents文件夹下。假如没有的话,就会从app bundle目录下拷贝过来。 // Look in Documents for an existing plist file NSArray *paths = NSSearchPathForDirectoriesInDomains( NSDocumentDirectory, NSUserDomainMask, YES); NSString *documentsDirectory = [paths objectAtIndex:0]; myPlistPath = [documentsDirectory stringByAppendingPathComponent: [NSString stringWithFormat: @"%@.plist", plistName] ]; [myPlistPath retain]; // If it's not there, copy it from the bundle NSFileManager *fileManger = [NSFileManager defaultManager]; if ( ![fileManger fileExistsAtPath:myPlistPath] ) { NSString *pathToSettingsInBundle = [[NSBundle mainBundle] pathForResource:plistName ofType:@"plist"]; } 现在我们就可以从Documents文件夹去读plist文件了。 NSArray *paths = NSSearchPathForDirectoriesInDomains( NSDocumentDirectory, NSUserDomainMask, YES); NSString *documentsDirectoryPath = [paths objectAtIndex:0]; NSString *path = [documentsDirectoryPath stringByAppendingPathComponent:@"myApp.plist"]; NSMutableDictionary *plist = [NSDictionary dictionaryWithContentsOfFile: path]; Now read and set key/values myKey = (int)[[plist valueForKey:@"myKey"] intValue]; myKey2 = (bool)[[plist valueForKey:@"myKey2"] boolValue]; [plist setValue:myKey forKey:@"myKey"]; [plist writeToFile:path atomically:YES]; Info button 为了更方便End-User去按,我们可以增大Info button上可以触摸的区域。 CGRect newInfoButtonRect = CGRectMake(infoButton.frame.origin.x-25, infoButton.frame.origin.y-25, infoButton.frame.size.width+50, infoButton.frame.size.height+50); [infoButton setFrame:newInfoButtonRect]; 查找Subviews(Detecting Subviews) 我们可以通过循环来查找一个已经存在的View。当我们使用view的tag属性的话,就很方便实现Detect Subviews。 for (UIImageView *anImage in [self.view subviews]) { if (anImage.tag == 1) { // do something } } 手册文档 Official Apple How-To'sLearn Objective-C