0%

第一步,在UI中添加Round Rect Button,并输入相应的title 第二步,选中该Button,打开Attributes inspector,将type设置成Custom。 第三步,在ViewController.m文件中覆盖(void)viewDidLoad方法(默认模板已经创建):

- (void)viewDidLoad
{
    //该方法在载入图形界面后执行
    [super viewDidLoad];

    UIImage * buttonImageNormal=[UIImage imageNamed:@"blue.png"];
    //从项目中的文件构建一个UIImage对象
    UIImage * stretchableButtonImageNormal=[buttonImageNormal stretchableImageWithLeftCapWidth:19 topCapHeight:10];
    //将该对象转换成可扩展拉伸的对象 LeftCapWidth指该图片左边不变的像素,topCapHeight是顶部不变的像素,即该图片上橫座标在0-19的范围或者纵座标在0-10的范围,不会被拉伸
    [_addButton setBackgroundImage:stretchableButtonImageNormal forState:UIControlStateNormal];
    //为正常状态时(未点击)设置显示的图片
    
    UIImage * buttonImagePressed=[UIImage imageNamed:@"green.png"];
    UIImage * stretchableButtonImagePressed=[buttonImagePressed stretchableImageWithLeftCapWidth:19 topCapHeight:0];
    
    [_addButton setBackgroundImage:stretchableButtonImagePressed forState:UIControlStateHighlighted];
    //为高光时(点中)设置显示的图片
    
}

UIActionSheet和UIAlertView在iOS中,都是弹出一个对话框,用户必须点击上面的按钮后才能执行其他操作。 下图是UIActionSheet,对话框显示在底部: 下图是AlertView,显示在屏幕正中: 当按钮在两个以内时,按钮是水平显示的,当超过两个时,会垂直显示。 相当代码: 首先在viewController h头文件添加UIActionSheetDelegate,UIAlertViewDelegate协议,如下:

#import 
@interface TESTViewController : UIViewController 

以下代码在ViewController.m文件中 打开ActionSheet对话框:

    UIActionSheet *sheet=[[UIActionSheet alloc] initWithTitle:@"你确定?" delegate:self cancelButtonTitle:@"不确定" destructiveButtonTitle:@"非常确定" otherButtonTitles: nil];
    [sheet showInView:self.view];

接收ActionSheet点击事件,以及打开AlertView对话框、接收AlertView点击事件:

-(void)actionSheet:(UIActionSheet *)actionSheet didDismissWithButtonIndex:(NSInteger)buttonIndex
{
    //该方法由UIActionSheetDelegate协议定义,在点击ActionSheet的按钮后自动执行
    NSString *string=[NSString stringWithFormat:@"你点击了 %@",[actionSheet buttonTitleAtIndex:buttonIndex]];
    
    UIAlertView *alert=[[UIAlertView alloc] initWithTitle:@"提示" message:string delegate:self cancelButtonTitle:@"确定" otherButtonTitles:@"取消",nil];
    alert.alertViewStyle=UIAlertViewStyleDefault;
    //UIAlertViewStyleDefault 默认风格,无输入框
  //UIAlertViewStyleSecureTextInput 带一个密码输入框
  //UIAlertViewStylePlainTextInput 带一个文本输入框
  //UIAlertViewLoginAndPasswordInput 带一个文本输入框,一个密码输入框
    [alert show];
    
}
-(void)alertView:(UIAlertView *)alertView didDismissWithButtonIndex:(NSInteger)buttonIndex
{
    //该方法由UIAlertViewDelegate协议定义,在点击AlertView按钮时自动执行,所以如果这里再用alertView来弹出提//示,就会死循环,不停的弹AlertView
    NSString * string=[NSString stringWithFormat:@"你点击了 %@",[alertView buttonTitleAtIndex:buttonIndex]];
    //    UIAlertView *alert=[[UIAlertView alloc] initWithTitle:@"提示" message:string delegate:self cancelButtonTitle:@"确定" otherButtonTitles:nil];
    //    [alert show];
    NSLog(@"%@",string);
  
//NSLog(@"输入 %@",[[alertView textFieldAtIndex:0] text]); 获取第一个文本框输入的文本,如果没有文件框,会异常,索引从0开始
    
}

学习斯担福大学2011年秋季iOS 5.0开发视频教程第二课写的,目前没中文字幕,大学英语四级没过的人伤不起,英文字幕加Google翻译。 最终效果图: 与视频教程中的代码稍有不同,那个每输入一个数字,要按enter确认,没看完视频教程的时候,我一直搞不明白为什么要那么写,看完了才知道。 新建Single View Application项目Calculator,类前缀Calculator CalculatorAppDelegat两个文件均为自动生成未修改。 新建一个Objective-C Class,名为CalculatorBrain,这个就是MVC模式中的Model,所有的数据处理都在这里,CalculatorViewController取到数据后,作简单的转换以符合Model的要求,再传给Model,由Model处理完返回处理结果给Controller,再由Controller更新View. CalculatorBrain.h

//
//  CalculatorBrain.h
//  Calculator
//
//  Created by fhp on 12-2-17.
//  Copyright (c) 2012年 __MyCompanyName__. All rights reserved.
//

#import 

@interface CalculatorBrain : NSObject
-(void)operate:(double) num1:(NSString *) operaString;
//接收第一个数字和操作符
-(double)calculate:(double) num2;
//接收第二个数字,并计算,返回计算结果

@end

CalculatorBrain.m

//
//  CalculatorBrain.m
//  Calculator
//
//  Created by fhp on 12-2-17.
//  Copyright (c) 2012年 __MyCompanyName__. All rights reserved.
//

#import "CalculatorBrain.h"

@interface CalculatorBrain()
//定义私有属性
@property (nonatomic) double result;
//储存执行结果
@property (copy,nonatomic) NSString * tempOperaString;
//存储操作符
@end

@implementation CalculatorBrain
@synthesize result=_result,tempOperaString=_tempOperaString;
-(void)operate:(double) num1:(NSString *) operaString
{
    _result=num1;
    _tempOperaString=operaString;
    
}
-(double)calculate:(double) num2
{
    //根据操作符执行相应的计算
    if([_tempOperaString isEqualToString:@"+"])
    {
        _result+=num2;
    }else if([_tempOperaString isEqualToString:@"-"])
    {
        _result-=num2;
    }else if([_tempOperaString isEqualToString:@"*"])
    {
        _result*=num2;
    }else if([_tempOperaString isEqualToString:@"/"])
    {
        if (num2==0) {
            _result=0;
        }else{
        _result/=num2;
        }
    }
    return _result;
    //返回结果
    
}
@end

CalculatorViewController.h

//
//  CalculatorViewController.h
//  Calculator
//
//  Created by fhp on 12-2-17.
//  Copyright (c) 2012年 __MyCompanyName__. All rights reserved.
//

#import 

@interface CalculatorViewController : UIViewController
- (IBAction)digiPressed:(id)sender;
//数字键按下操作
- (IBAction)operatePressed:(id)sender;
//操作符按下操作
- (IBAction)enterPressed:(id)sender;
//等于号按下操作
@property (weak, nonatomic) IBOutlet UILabel *display;
//显示输入和结果的属性

@end

CalculatorViewController.m

//
//  CalculatorViewController.m
//  Calculator
//
//  Created by fhp on 12-2-17.
//  Copyright (c) 2012年 __MyCompanyName__. All rights reserved.
//

#import "CalculatorViewController.h"
#import "CalculatorBrain.h"

@interface CalculatorViewController()
//把私有的方法和属性定义在这
@property  (nonatomic) BOOL isEntering;
//数字输入的状态,指明之前是否正在输入数字
@property (strong,nonatomic) CalculatorBrain * brain;
//Model,CalculatorViewController是一个Controller,
//为了符合MVC模式,需要把数据传送给Model,即这里的CalculatorBrain类处理,CalculatorBrain
//返回计算结果给CalculatorViewController
@end

@implementation CalculatorViewController
@synthesize display = _display;
@synthesize isEntering=_isEntering;
@synthesize brain=_brain;


-(CalculatorBrain *) brain
{
    //重写brain属性的getter方法,在该方法中初始化CalculatorBrain实例
    if(!_brain)_brain=[[CalculatorBrain alloc] init];
    return _brain;
}
- (void)viewDidUnload
{
    [self setDisplay:nil];
    [super viewDidUnload];
    // Release any retained subviews of the main view.
    // e.g. self.myOutlet = nil;
}


- (IBAction)digiPressed:(UIButton *)sender {
    //按到数字键时执行
    if(self.isEntering==YES)
    {
        //如果之前已经是在输入的状态
        if([_display.text length]<12)
        {
            //如果之前输入的数字少于12位
            self.display.text = [self.display.text stringByAppendingString:[sender currentTitle]];
            //把按到的数字转成字符串加到原来显示的字符串的未尾,并更新显示
        }else{
            //如果输入的数字大于等于12位,不操作,直接返回
            return;
        }
        
    }else{
        //如果之前不是输入状态,即现在输入的是数字的第一位(最高位)
        self.display.text=[sender currentTitle];
        //显示输入的数字
        self.isEntering=YES;
        //把输入状态改为YES
    }
    
}

- (IBAction)operatePressed:(UIButton *)sender {
    //操作符被按下时执行
    self.isEntering=NO;
//    把输入状态改为NO
    double num=[self.display.text doubleValue];
    //取到显示的数字,转换为double
    [self.brain operate:num :[sender currentTitle]];
    //把数字和操作符发送给CalculatorBrain的opera接收器
    
}

- (IBAction)enterPressed:(id)sender {
    //等号键被按下
    self.isEntering=NO;
    //把输入状态改为NO
    double num=[self.display.text doubleValue];
    //取到显示的数字,转换为double
    double result=[_brain calculate:num];
    //把数字发送给CalculatorBrain的calculate接收器,并接收返回的结果
    self.display.text=[NSString stringWithFormat:@"%g",result];
    //把结果显示在屏幕上
    
}
@end

在IOS中,使用UITextField输入信息后,即便在手指在其他地方点了,也不会自动失去焦点,关闭软键盘,需要手动执行以下代码:

[UITextField resignFirstResponder];

如果需要在软键盘右下角显示Done,并在按下后隐藏软键盘,可以把UITextField的Return Key属性设为Done,在Connections inspector里,把Send Events下的Did End On Exist右边的小圆,拖到ViewController.h文件中,创建一个Action,在,action中执行

[sender resignFirstResponder];

如果需要在点击背景时,自动隐藏软键盘,点击背景,打开Identity inspector,把Class改为UIControl,再打开Connections inspector,拖运Touch Down后面的小圆到ViewController.h中,创建一个Action,在,action中,让所有的UITextFiled控件执行resignFirstResponder

归档即把变量或对象存储到硬盘文件里,需要的时候再读取,也可以通过归档实现对象的深复制。 main.m:

#import 
#import "ClassA.h"

int main (int argc, const char * argv[])
{
    
    @autoreleasepool {
        //如果对象是NSString NSDictionary NSArray NSData NSNumber,可以使用writeToFile:atomically方法将其写入文件
        //atomically参数为是否先写入缓存
        NSDictionary *dic=[NSDictionary dictionaryWithObjectsAndKeys:@"aaa",@"a",@"bbb",@"b",@"ccc",@"c", nil];
        if([dic writeToFile:@"/Users/fhp/Desktop/5.xml" atomically:YES]==NO)
        {
            NSLog(@"写入文件失败");
        }
        //从文件中读回,用这个方法可以也实现深复制
        NSDictionary *dic2=[NSDictionary dictionaryWithContentsOfFile:@"/Users/fhp/Desktop/5.xml"];
        for(NSString *key in dic2)
            NSLog(@"key=%@  object=%@",key,[dic2 valueForKey:key]);
        
        
        //NSKeyedArchiver可以将各种类的对象存储到文件,包括自定义的类,但生成的文件不再是明文的xml文件
        [NSKeyedArchiver archiveRootObject:dic toFile:@"/Users/fhp/Desktop/6"];
        NSDictionary *dic3=[NSKeyedUnarchiver unarchiveObjectWithFile:@"/Users/fhp/Desktop/6"];
        for(NSString *key in dic3)
            NSLog(@"key=%@  object=%@",key,[dic3 valueForKey:key]);
        //如果对象是自定义的类,需要该类遵循协议,实现encodeWithCoder和initWithCoder方法
        ClassA *a =[ClassA new];
        [a setNum:20];
        [a setName:@"nameaaa"];
        [NSKeyedArchiver archiveRootObject:a toFile:@"/Users/fhp/Desktop/7"];
        ClassA *b=[NSKeyedUnarchiver unarchiveObjectWithFile:@"/Users/fhp/Desktop/7"];
        NSLog(@"%@",b);
        
        
        //使用NSMutableDate将dic和a写入同一文件
        NSMutableData *dataArea=[NSMutableData data];
        NSKeyedArchiver * archiver=[[NSKeyedArchiver alloc] initForWritingWithMutableData:dataArea];
        [archiver encodeObject:dic forKey:@"NSDictionary"];
        [archiver encodeObject:a forKey:@"ClassA"];
        [archiver finishEncoding];
        if([dataArea writeToFile:@"/Users/fhp/Desktop/8" atomically:YES]==NO)
        {
            NSLog(@"写入文件失败");
        }
        //读取
        NSData *dataArea2=[NSData dataWithContentsOfFile:@"/Users/fhp/Desktop/8"];
        //读取的时候因为数据是固定的,不需要mutable
        NSKeyedUnarchiver *unarchive=[[NSKeyedUnarchiver alloc] initForReadingWithData:dataArea2];
        NSDictionary *dic4=[unarchive decodeObjectForKey:@"NSDictionary"];
        ClassA *a2=[unarchive decodeObjectForKey:@"ClassA"];
        [unarchive finishDecoding];
        for(NSString *key in dic4)
            NSLog(@"key=%@  object=%@",key,[dic4 valueForKey:key]);
        NSLog(@"%@",a2);
        //可以跳过写入读取文件那两个环节,实现深复制
        
                
    }
    return 0;
    
}

ClassA.h

//
//  ClassA.h
//  hello
//
//  Created by fhp on 12-2-13.
//  Copyright (c) 2012年 __MyCompanyName__. All rights reserved.
//

#import 

@interface ClassA : NSObject//遵循NSCoding协议
{
    int num;
    NSString * name;
}
-(id)copyWithZone:(NSZone *)zone;
@property (atomic) int num;
@property (copy,atomic) NSString * name;
-(void) encodeWithCoder:(NSCoder *)aCoder;
-(id)initWithCoder:(NSCoder *)aDecoder;
//NSCoding协议必须实现encodeWithCoder和initWithCoder方法
@end

ClassA.m

#import "ClassA.h"

@implementation ClassA
@synthesize num,name;
-(NSString *)description
{
    NSString * s1=[NSString stringWithFormat:@"%d   %@",num,name];
    return s1;
}
-(id)copyWithZone:(NSZone *)zone
{
    ClassA * a=[[ClassA allocWithZone:zone] init];
    [a setNum:num];
    [a setName:name];
    return a;
}
-(void)encodeWithCoder:(NSCoder *)aCoder
{
    //归档时调用此方法
    [aCoder encodeInt:num forKey:@"ClassNum"];
    [aCoder encodeObject:name forKey:@"ClassName"];
    
}
-(id)initWithCoder:(NSCoder *)aDecoder
{
    //解码时调用此方法还原
    num=[aDecoder decodeIntForKey:@"ClassNum"];
    name=[aDecoder decodeObjectForKey:@"ClassName"];
    return self;
}

@end

下面的例子使用NSFileHandle读取写入文件。

#import 

int main (int argc, const char * argv[])
{
    
    @autoreleasepool {
        NSString *file1=@"/Users/fhp/Desktop/1.txt";
        NSString *file2=@"/users/fhp/Desktop/2.txt";
        
        NSFileHandle *inFile=[NSFileHandle fileHandleForReadingAtPath:file1];
        //打开1.txt
        if(inFile==nil)
        {
            NSLog(@"打开1.txt错误");
            return 1;
        }
//		[[NSFileManager defaultManager] createFileAtPath:file2 contents:nil attributes:nil];
        //创建文件 2.txt
        NSFileHandle *outFile=[NSFileHandle fileHandleForWritingAtPath:file2];
        [outFile truncateFileAtOffset:0];
        //清空内容,把指针指向开头
//		[outFile seekToEndOfFile];
        //可以把指针移动到文件结尾,这样就是增加文件内容,也可以seekTo到指定的位置
        
        
        
        NSMutableData *buffer=[NSMutableData dataWithCapacity:2048];
        
        while ((buffer=[inFile readDataOfLength:2048])!=nil) {
            [outFile writeData:buffer];
            //循环读取文件并写入
        }
        

        //当文件不大时,也可以用下面的方法,一次读入整个文件
        //最多不超过UINT_MAX个字节,定义在limits.h中,一般为FFFFFFFF,即4GB
//		NSData *buffer=[inFile readDataToEndOfFile];
//		//读取整个文件内容
//		[outFile writeData:buffer];
//		//写入文件
        [inFile closeFile];
        [outFile closeFile];
        //关闭文件
        
        
    }
    return 0;
    
}

#import 

int main (int argc, const char * argv[])
{
    
    @autoreleasepool {
        NSFileManager *fm=[NSFileManager defaultManager];
        NSString *tempdir=NSTemporaryDirectory();
        
        NSLog(@"临时目录:%@",tempdir);
        
        NSString * currentPath=[fm currentDirectoryPath];
        NSLog(@"当前路径:%@",currentPath);
        
        NSString * filePath=[currentPath stringByAppendingPathComponent:@"main.m"];
        NSLog(@"当前文件路径:%@",filePath);
        
        NSString * extension=[filePath pathExtension];
        NSLog(@"当前文件扩展名:%@",extension);
        
        NSString * homeDir=NSHomeDirectory();
        NSLog(@"当前用户主目录:%@",homeDir);
        
        NSArray * components=[homeDir pathComponents];
        //用户主目录路径结构拆分
        for (NSString *path in components) {
            NSLog(@"%@",path);
        }
        
    }
    return 0;
    
}

NSFileManager是Objective-C中管理文件的类。

#import 

int main (int argc, const char * argv[])
{
    
    @autoreleasepool {
        NSFileManager *fm=[NSFileManager defaultManager];
        NSString *file1=@"/Users/fhp/Desktop/1.txt";
        NSString *file2=@"/Users/fhp/Desktop/2.txt";
        

        NSData *data=[fm contentsAtPath:file2];
        //读取文件内容
        if(![fm fileExistsAtPath:file1])
        {
            [fm createFileAtPath:file1 contents:data attributes:nil];
            //如果文件不存在,就以file2的文件内容创建file1
        }
        NSLog(@"%@",[NSString stringWithContentsOfFile:file1 encoding:NSUTF8StringEncoding error:nil]);
        //输出文件内容
        [fm removeItemAtPath:file2 error:nil];
        //删除文件file2
        [fm movePath:file1 toPath:file2 handler:nil];
        //移动file1到file2,因为在同一目录,所以只是简章的改名

        //下面是目录枚举
        NSDirectoryEnumerator *dir=[fm enumeratorAtPath:@"/Users/fhp/"];
        NSString *path=[NSString new];
        while ((path=[dir nextObject])!=nil) {
            NSLog(@"%@",path);
        }
        //上面这种方法会递归
        //下面这种不会
        NSArray *array=[fm directoryContentsAtPath:@"/Users/fhp/"];
        for(NSString *p in array)
            NSLog(@"%@",p);
        
    }
    return 0;
    
}

这两个类类似于Java中的map,可以为Object定义一个key,通过key来查询对应的Object

#import 

int main (int argc, const char * argv[])
{
    
    @autoreleasepool {
        NSDictionary *dic1=[NSDictionary dictionaryWithObjectsAndKeys:@"Object1",@"key1",@"Object2",@"key2",nil];
        for(NSString *key in dic1)
        {
            NSLog(@"key=%@,Object=%@",key,[dic1 objectForKey:key]);
        }
         
        NSMutableDictionary *dic2=[NSMutableDictionary dictionary];
        [dic2 setObject:@"object3" forKey:@"key3"];
        [dic2 setObject:@"object4" forKey:@"key4"];
        //可以自行增加object
        
        for(NSString *key in dic2)
        {
            NSLog(@"key=%@,Object=%@",key,[dic2 objectForKey:key]);
        }
        
        
    }
    return 0;
    
}

NSMutableArray是可变数组,以下的例子是一个通讯录,可增加、删除、搜索联系人。 AddressCard.h:

#import 

@interface AddressCard : NSObject
{
    NSString * nickname;
    //存放昵称
    NSString * email;
    //电邮
    
}
@property (copy,nonatomic) NSString * nickname,* email;
//属性,必须加copy nonatomic参数
-(void)setNickName:(NSString *)n andEmail:(NSString *) e;
//设置昵称和邮件的接收器
-(NSComparisonResult) compareNames:(AddressCard *) card;
//排序用,返回nickname对比的结果
@end

AddressCard.m:

#import "AddressCard.h"

@implementation AddressCard
-(void)setNickName:(NSString *)n andEmail:(NSString *)e
{
    self.nickname=[NSString stringWithString:n];
    self.email=[NSString stringWithString:e];
    
}
- (NSString *)description
{
    return [nickname stringByAppendingFormat:@"     Email: %@",email];
}

-(BOOL) isEqual:(AddressCard *)object
{
    if([nickname isEqualToString:[object nickname]]&&[email isEqualToString:[object email]])
    {
        return YES;
    }
    return NO;
}
-(NSComparisonResult) compareNames:(AddressCard *)card
{
    return [nickname compare:[card nickname]];
}

@synthesize nickname,email;
@end

AddressBook.h:

#import 
#import "AddressCard.h"

@interface AddressBook : NSObject
{
    NSString *bookName;
    NSMutableArray *book;
}
-(id)initWithName:(NSString *) name;
-(void)addCard:(AddressCard *) card;
//添加联系人
-(int)entries;
//返回联系人数量
-(void)list;
//列出所有联系人
-(void)deleteCard:(AddressCard *)card;
//删除联系人
-(void)sort;
//排序

-(AddressCard *) lookup:(NSString *) theName;
//搜索联系人

@end

AddressBook.m:

#import "AddressBook.h"

@implementation AddressBook
-(id)initWithName:(NSString *)name
{
    self=[super init];
    name=[NSString stringWithString:name];
    book=[NSMutableArray new];
    return self;
}
-(void)addCard:(AddressCard *)card
{
    [book addObject:card];
}
-(int)entries
{
    return [book count];
}
-(void)list
{
    for(AddressCard *card in book)
    {
        NSLog(@"%@",card);
    }
}
-(AddressCard *) lookup:(NSString *)theName
{
    for(AddressCard * nextCard in book)
    {
        if([theName caseInsensitiveCompare:[nextCard nickname]]==NSOrderedSame)
        {
            //忽略大小写,查找联系人
            return nextCard;
        }
    }
    return nil;
}
-(void)deleteCard:(AddressCard *)card
{
    [book removeObject:card];
}

-(void)sort
{
    [book sortUsingSelector:@selector(compareNames:)];
    //使用选择器排序,使用AddressCard中的compareNames方法作选择器
}

@end

main.m:

#import 
#import "AddressBook.h"
//AddressBook.h中已经有导入AddressCard.h,所以这里无需再导

int main (int argc, const char * argv[])
{
    
    @autoreleasepool {
        AddressCard *card1=[AddressCard new];
        [card1 setNickName:@"bcd" andEmail:@"adf@adf.com"];
        AddressBook *book=[AddressBook alloc];
        book=[book initWithName:@"MyAddressBook"];
        [book addCard:card1];
        AddressCard *card2=[AddressCard new];
        [card2 setNickName:@"afd" andEmail:@"asdf@dadfsff.com"];
        [book addCard:card2];
        
        [book list];
        //列出排序前所有的AddressCard
        [book sort];
        //排序
        [book list];
        //列出排序后所有的AddressCard


        
        AddressCard *findCard=[book lookup:@"bcd"];
        NSLog(@"%@",[findCard email]);
        //搜索
        [book deleteCard:findCard];
        //删除
        [book list];
        
        
    }
    return 0;
    
}