iOS几种常见的页面传值方式
Posted APP技术社区
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了iOS几种常见的页面传值方式相关的知识,希望对你有一定的参考价值。
几种常见的页面传值方式:
属性传值
最简单的传值方式,正向传递。
单例传值
很灵活,可以双向传递。(写入内存读取)
NSUserDefaults传值
可以双向传递。(写入沙盒文件读取)
利用 NSUserDefaults类 将数据存储起来,在第二个页面中读取。
代理传值(最经典)
多用于反向传递
在第二个页面中定义一个协议,并调用。让第一个页面也遵守这个协议,并实现传递数据的方法。
block传值(官方推荐 最流行)
多用于反向传递
在第二个页面中定义一个block,并调用。并且在第一个页面中实现。
通知传值
多用于反向传值。
第一个页面监听 消息中心,第二个页面发送消息给消息中心。
1、属性传值
在第二个页面 中定义一个属性,在第一个页面中赋值。并在第二个页面中取出来使用。
考虑采用UINavigationController方式作为页面跳转机制
指定AppDelegate.h根控制器并显示
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
self.window = [[UIWindow alloc]initWithFrame:[UIScreen mainScreen].bounds];
//创建导航控制器
UINavigationController *nav = [[UINavigationController alloc]initWithRootViewController: [[ViewController alloc]init]];
//设置window的根控制器
self.window.rootViewController = nav;
//设置并显示
[self.window makeKeyAndVisible];
return YES;
}
实现A与B界面传值,需要新建两个UIViewController
A --> AUIViewController
b --> BUIViewController
AUIViewController.h
@interface AUIViewController : UIViewController
@end
BUIViewController.h
为实现A-->B 属性传值,需要在B中添加属性。然后在跳转前给B中的属性赋值,在B中获取自己的属性值就OK了。
@interface BUIViewController : UIViewController
//传递值属性
@property(nonatomic,strong) NSString * bValue;
@end
详细代码如下:
@interface AUIViewController ()
//准备在界面创建两个控件,一个输入文字,一个用来跳转
@property (strong,nonatomic) UIButton *button;
@property (strong,nonatomic) UITextField *textField;
@end
@implementation AUIViewController
- (void)viewDidLoad{
[super viewDidLoad];
self.navigationItem.title = @"A界面";
//将控件添加到View上
[self.view addSubview:self.button];
[self.view addSubview:self.textField];
}
- (UIButton *)button{
if(!_button){
_button = [UIButton alloc]initWithFrame:CGRectMake(100,100,200,100);
[_button setTitle:@"go to B View" forState:UIControlStateNormal];
[_button addTarget:self action:@selector(btnOnClick) forControlEvents:UIControlEventTouchUpInside];
}
}
- (UITextField *)textField{
if(!_textField){
_textField = [UITextField alloc]initWithFrame:CGRectMake(100,200,200,40);
[_textField setFont:[UIFont systemFontSize:18]];
}
}
//点击事件
-(void)btOnClick{
BUIViewController *BVC = [[BUIViewController alloc]init];
//属性传值给B
NSString *textfieldStr = self.textField.text;
//BVC.BValue = @"属性传值:A --> B";
BVC.bValue = textfieldStr;
[self.navigationController pushViewController:BVC animated:YES];
}
@end
@interface BUIViewController ()
//准备在界面创建两个控件,一个输入文字,一个用来跳转
@property (strong,nonatomic) UIButton *button;
@property (strong,nonatomic) UITextField *textField;
@end
@implementation BUIViewController
- (void)viewDidLoad{
[super viewDidLoad];
self.navigationItem.title = @"B界面";
//将控件添加到View上
[self.view addSubview:self.button];
[self.view addSubview:self.textField];
//打印上一个界面传递过来的值
_textField.text = self.bValue;
NSLog(@"%@--%@",[self class],self.bValue);
}
- (UIButton *)button{
if(!_button){
_button = [UIButton alloc]initWithFrame:CGRectMake(100,100,200,100);
[_button setTitle:@"返回" forState:UIControlStateNormal];
[_button addTarget:self action:@selector(backClick) forControlEvents:UIControlEventTouchUpInside];
}
}
- (UITextField *)textField{
if(!_textField){
_textField = [UITextField alloc]initWithFrame:CGRectMake(100,200,200,40);
[_textField setFont:[UIFont systemFontSize:18]];
}
}
//点击事件(返回上一个界面)
-(void)backClick{
[self.navigationController popViewControllerAnimated:YES];
}
@end
2、单例传值
需要定义一个静态单例,第一个页面赋值给静态对象,第二个页面从其中取值。
MyInstance.h
NS_ASSUME_NONNULL_BEGIN
@interface MyInstance : NSObject
@property(nonatomic, strong) NSString *str;
+(instancetype) sharedInstance;
@end
NS_ASSUME_NONNULL_END
MyInstance.m
@implementation MyInstance
//单例对象
+ (instancetype) sharedInstance {
static DefaultInstance *sharedVC = nil;
if(sharedVC == nil) {
sharedVC = [[MyInstance alloc] init];
}
return sharedVC;
}
@end
第一个页面给单例赋值
SecondviewController *secondViewController = [[SecondviewController alloc] init];
//属性传值
//secondViewController.str = @"属性传递的值"; //传递
[MyInstance sharedInstance].str = @"单例传值"; // 从页面一 给单例对象赋值
[self presentViewController:secondViewController animated:YES completion:nil];
第二个页面取出相应的值
@implementation SecondviewController
- (UITextField *)textField {
if(!_textField) {
_textField = [[UITextField alloc] initWithFrame:CGRectMake(100, 100, 200, 40)];
_textField.textColor = [UIColor blackColor];
_textField.backgroundColor = [UIColor whiteColor];
_textField.borderStyle = UITextBorderStyleLine;
//单例传值 -- 接收 显示
_textField.text = [MyInstance sharedInstance].str;
}
return _textField;
}
3、NSUserDefaults传值
利用 NSUserDefaults类 将数据存储起来,在第二个页面中读取。
NSUserDefaluts根单例类似,只不过NSUserDefaluts是将数据写入到文件中(沙盒文件)
如上图,我们可以看出沙盒文件传流程。同样我们在A跟B之间的传值,方式如上图,在A跳转到B的时候将数据写入文件中,在B中读取。
关键代码 A跳转B前写入数据:
//获取单例对象
NSUserDefaults * ud = [NSUserDefaults standardUserDefaults];
//设置存储的数据
[ud setObject:@"value" forKey:@"key"];
//立即写入
[ud synchronize];
读取数据:
//获取单例对象
NSUserDefaults * ud = [NSUserDefaults standardUserDefaults];
//打印读取数据
NSLog(@"%@",[ud objectForKey:@"key"]);
4、代理传值
在第二个页面中定义一个协议,并调用。让第一个页面也遵守这个协议,并实现传递数据的方法。
//委托方创建一个协议
@protocol passValueDelegate <NSObject>
// 定义一个传值的方法
- (void)passValue: (NSString *) str;
@end
//委托方调用并传值
//代理传值 -- 反向
[self.delegate passValue:self.textField.text];
//接收者需要遵守这个协议
@interface ViewController () <passValueDelegate>
@property(nonatomic, strong)UILabel *label;
@property(nonatomic,strong) UIButton *btn;
@end
......
//代理传值实现协议方法,接收来自委托方的值
- (void)passValue:(NSString *)str{
self.label.text = str;
}
5、block传值
在第二个页面中定义一个block,并调用。并且在第一个页面中实现。
//定义一个block进行页面反向传值
@property(nonatomic,strong) void(^Myblcok) (NSString *);
//第二个页面调用定义的block,并传值
self.Myblcok(_textField.text);
//btn点击事件,跳转到页面2
- (void)btnClick{
BUIViewController *bUIViewController = [[BUIViewController alloc] init];
//第一个页面实现这个block,接收来自页面二的值
bUIViewController.Myblcok = ^(NSString *str){
self.label.text = str;
};
[self presentViewController:bUIViewController animated:YES completion:nil];
}
6、通知传值
第一个页面监听 消息中心,第二个页面发送消息给消息中心。
// 添加监听,等待页面B的传值
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(notHandle:) name:@"notify" object:nil];
......
//接收到通知之后的处理
- (void) notHandle: (NSNotification *) not{
self.label.text = not.userInfo[@"not"];
}
//通知传值 --- 发送通知
[[NSNotificationCenter defaultCenter] postNotificationName:@"notify" object: nil userInfo: @{@"not": self.textField.text}];
//返回上一个页面
[self dismissViewControllerAnimated:YES completion:nil];
以上是关于iOS几种常见的页面传值方式的主要内容,如果未能解决你的问题,请参考以下文章
iOS 页面间几种传值方式(属性,代理,block,单例,通知)
iOS 页面间几种传值方式(属性,代理,block,单例,通知)
iOS 页面间几种传值方式(属性,代理,block,单例,通知)