//
//  ViewController.m
//  test_kvo_kvc_01
//
//  Created by admin on 4/7/16.
//  Copyright © 2016 jeffasd. All rights reserved.
//

#import "ViewController.h"
#import "Persion.h"
//#import <obj/runtime>

static NSString * const TESTSTRING = @"123";

#define KVOSTRING   @"321"

@interface ViewController ()

@property (nonatomic, strong, readonly) NSString *viewName;

@property (nonatomic, strong, readonly) Persion *xiaozhan;

@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];

    [self testForKVO];
}

- (void)testForKVO{
    
    _xiaozhan = [Persion new];
    
    [_xiaozhan addObserver:self forKeyPath:@"personName" options:NSKeyValueObservingOptionNew | NSKeyValueObservingOptionOld context:KVOSTRING ];
    
}

- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary<NSString *,id> *)change context:(void *)context{
    
    NSLog(@"the context is %@", context);
    
    if (context == KVOSTRING) {
        NSLog(@"kvo");
        return;
    }else{
        [super observeValueForKeyPath:keyPath ofObject:object change:change context:context];
    }
}

- (void)removeObservation{
    [_xiaozhan removeObserver:self forKeyPath:@"personName"];
}

- (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event{
    
//    [_xiaozhan setValue:[NSNumber numberWithInt:12] forKey:@"age"];
    
//    _xiaozhan.age = 122;
    
    _xiaozhan.personName = @"123";
    
//    [_xiaozhan setPersonName:@"xiaozhan"];
    
}

- (IBAction)buttonAction:(UIButton *)sender {
    
    [self removeObservation];
    
}

- (void)testForKVC{
    Persion *xiaoming = [Persion new];
    
    //    [xiaoming setValue:@"xiaoming1" forKey:@"name"];
    
    //    [xiaoming setValue:nil forKey:@"name"];
    
    [xiaoming setValue:nil forKey:@"age"];
    
    //    [xiaoming setValue:[NSNumber numberWithInt:12] forKey:@"name"];
    //    [xiaoming setValue:[NSNumber numberWithInt:12] forKey:@"name1"];
    
    //还有一个需要注意的是KVC 并没有类型检验,毕竟Object-C 还是动态的啦
    NSLog(@"the name is %@", xiaoming.name);
    
    NSLog(@"the class name is %@", [xiaoming.name class]);
    
    //    ViewController *VC = [ViewController new];
    //    [VC setValue:@"123" forKey:@"viewName"];
}

- (BOOL)validateValue:(inout id  _Nullable __autoreleasing *)ioValue forKey:(NSString *)inKey error:(out NSError * _Nullable __autoreleasing *)outError{

    return NO;
}

- (nullable id)valueForUndefinedKey:(NSString *)key{
    
    
    return @"123";
}

- (void)setNilValueForKey:(NSString *)key{
    
}

- (void)setValue:(nullable id)value forUndefinedKey:(NSString *)key{
    
//    NSLog(@"the value is %@", value);
//    NSLog(@"the key is %@", key);
    
}

- (void)didReceiveMemoryWarning {
    [super didReceiveMemoryWarning];
    // Dispose of any resources that can be recreated.
}

@end
//
//  Persion.h
//  test_kvo_kvc_01
//
//  Created by admin on 4/7/16.
//  Copyright © 2016 jeffasd. All rights reserved.
//

#import <Foundation/Foundation.h>

@interface Persion : NSObject

@property (nonatomic, strong, readonly) NSString *name;

@property (nonatomic, assign) NSUInteger age;

@property (nonatomic, strong) NSString *personName;

@end



//
//  Persion.m
//  test_kvo_kvc_01
//
//  Created by admin on 4/7/16.
//  Copyright © 2016 jeffasd. All rights reserved.
//

#import "Persion.h"

#define KVOSTRING   @"personName"

@interface Persion ()

@property (nonatomic, strong)NSString *identifier;

@end

@implementation Persion

//- (BOOL)validateName:(inout id  _Nullable __autoreleasing *)ioValue forKey:(NSString *)inKey error:(out NSError * _Nullable __autoreleasing *)outError{
//
//    NSLog(@"ioValue is %@", ioValue);
//    
//    NSLog(@"inkey is %@", inKey);
//    
//    return NO;
//}

- (BOOL)validateValue:(inout id  _Nullable __autoreleasing *)ioValue forKey:(NSString *)inKey error:(out NSError * _Nullable __autoreleasing *)outError{
    
    return NO;
}

- (nullable id)valueForUndefinedKey:(NSString *)key{
    
    
    return @"valueUndefinedKey";
}

- (void)setNilValueForKey:(NSString *)key{
    
    NSLog(@"the key is %@", key);
    
}

- (void)setValue:(nullable id)value forUndefinedKey:(NSString *)key{
    
    
}

//- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary<NSString *,id> *)change context:(void *)context{
//    
//    NSLog(@"the context is %@", context);
//    
//    if (context == KVOSTRING) {
//        NSLog(@"kvo");
//    }else{
//        [super observeValueForKeyPath:keyPath ofObject:object change:change context:context];
//    }
//}

@end