//
//  VFYSelfieFinalPreviewWrapper.m
//  Verif-y
//
//  Created by MTN on 16/11/20.
//

#import "VFYSelfieFinalPreviewWrapper.h"
#import "VFYVerifyApp.h"
#import "VFYFrontGuideWrapper.h"
#import "VFYButton.h"
#import "VFYConstant.h"
#import <MobileCoreServices/MobileCoreServices.h>
#import "VFYAuditManager.h"

@interface VFYSelfieFinalPreviewWrapper ()

@property (weak, nonatomic) IBOutlet UILabel *LbFnImagePreview;
@property (weak, nonatomic) IBOutlet VFYButton *LbBtFnRetake;
@property (weak, nonatomic) IBOutlet VFYButton *LbBtFnContinue;
@property (weak, nonatomic) IBOutlet UIView *LoaderView;
@property (weak, nonatomic) IBOutlet UILabel *LbLogoPow;
@property (weak, nonatomic) IBOutlet UILabel *LbLogoBy;
@property (weak, nonatomic) IBOutlet UIView *RoundLoaderView;
@property (weak, nonatomic) IBOutlet UIScrollView *BodyScrollView;
@property (nonatomic, retain) VFYVerifyApp *sharedInstance;
@property (nonatomic) NSString* Source;
@property (nonatomic) NSString* Target;
@property (nonatomic) CFTimeInterval elapsedTime;
@property (nonatomic) CFTimeInterval audit_scan_Duration;

@end

@implementation VFYSelfieFinalPreviewWrapper

@synthesize selectedOption;
@synthesize imagePreview;
@synthesize imagePicker;
@synthesize passImage;
@synthesize idSuccess;

- (void)viewDidLoad {
    [super viewDidLoad];
    if (@available(iOS 13.0, *)) {
         self.view.overrideUserInterfaceStyle = UIUserInterfaceStyleLight;
    }
    self.LoaderView.backgroundColor = [UIColor clearColor];
    self.sharedInstance = [VFYVerifyApp sharedInstance];
    self.LbFnImagePreview.text = NSLocalizedStringWithDefaultValue(@"mb_identityFailed_imagepreview", [self.sharedInstance language], [self.sharedInstance languageBundlePath], @"Image Preview", nil);
    [self.LbBtFnRetake setTitle:NSLocalizedStringWithDefaultValue(@"mb_identity_button_2", [self.sharedInstance language], [self.sharedInstance languageBundlePath], @"Retake", nil) forState:UIControlStateNormal];
    [self.LbBtFnContinue setTitle:NSLocalizedStringWithDefaultValue(@"mb_identity_button_1", [self.sharedInstance language], [self.sharedInstance languageBundlePath], @"Continue", nil) forState:UIControlStateNormal];
    if(self.passImage != nil){
       self.imagePreview.image = self.passImage;
    }
    [self CustomTitle];
    [self.BodyScrollView setBackgroundColor:[Utilities colorFromColorString:self.sharedInstance.bodyColor]];
    [self setBrandingColor];
    self.audit_scan_Duration = CACurrentMediaTime();
}

- (void)viewWillDisappear:(BOOL)animated {
  
}

- (void) setBrandingColor
{
    /* Set title label text color */
    [self.LbFnImagePreview setTextColor:[Utilities colorFromColorString:self.sharedInstance.bodyTitleColor]];
    /* Set branding color */
    [self.LbLogoPow setTextColor:[Utilities colorFromColorString:VFY_LOGO_POWER]];
    [self.LbLogoBy setTextColor:[Utilities colorFromColorString:VFY_LOGO_BY]];
    /* Set button style */
    [self.LbBtFnContinue animateOnPress:FALSE borderColor:[Utilities colorFromColorString:[self.sharedInstance buttonBorderColor]] backGroundColor:[Utilities colorFromColorString:[self.sharedInstance buttonBackgroundColor]] textColor:[Utilities colorFromColorString:[self.sharedInstance buttonTextColor]]];
    [self.LbBtFnRetake animateOnPress:FALSE borderColor:[Utilities colorFromColorString:[self.sharedInstance buttonBorderColor]] backGroundColor:[Utilities colorFromColorString:[self.sharedInstance buttonBackgroundColor]] textColor:[Utilities colorFromColorString:[self.sharedInstance buttonTextColor]]];
    /* Set rounded corner of loderview */
    self.RoundLoaderView.layer.cornerRadius = 8.0f;
    self.RoundLoaderView.layer.masksToBounds = true;
}

- (IBAction)BTNRetake:(id)sender {
    if(selectedOption == Camera){
        [self.navigationController popViewControllerAnimated:YES];
    } else if(selectedOption == Upload){
        self.imagePicker = [[UIImagePickerController alloc] init];
        self.imagePicker.delegate = self;
        self.imagePicker.sourceType = UIImagePickerControllerSourceTypePhotoLibrary;
        [self presentViewController:self.imagePicker animated:YES completion:nil];
   }
}
- (IBAction)BTNContinue:(id)sender {
    
    [self compareImage:self.imagePreview.image];
}

-(void) CustomTitle {
    if([self.sharedInstance.headerTitleImage length]>0){
       [Utilities customTitleImage:self.navigationItem Logo:self.sharedInstance.headerTitleImage];
    } else if([self.sharedInstance.headerTitleText length]){
        [Utilities customTitleText:self.navigationItem TitleText:self.sharedInstance.headerTitleText FontColor:self.sharedInstance.headerTextColor];
    }
}

- (void) callAudit {
    NSMutableDictionary *setting = [NSMutableDictionary dictionary];
    self.elapsedTime = CACurrentMediaTime() - self.audit_event_Duration;
    self.audit_scan_Duration = CACurrentMediaTime() - self.audit_scan_Duration;
    if(self.elapsedTime) {
        NSString *eventDuration = [Utilities stringFromTimeInterval:self.elapsedTime];
        NSString *scanDuration = [Utilities stringFromTimeInterval:self.audit_scan_Duration];
        [setting setValue:eventDuration forKey:@"audit_event_duration"];
        [setting setValue:scanDuration forKey:@"audit_scan_Duration"];
    } else {
        [setting setValue:@"" forKey:@"audit_event_duration"];
        [setting setValue:@"" forKey:@"audit_scan_Duration"];
    }
    [VFYAuditManager selfieAudit:self.idSuccess settings:setting completed:^(NSString *response) {
        NSLog(@"Selfie success response %@",response);
    } failure:^(NSError *error){
        NSLog(@"Selfie fail response : %@",error);
    }];
}

#pragma mark UIImagePickerControllerDelegate
 
- (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info
{
    [self dismissViewControllerAnimated:YES completion:^{
        // MediaType can be kUTTypeImage or kUTTypeMovie.
        NSString* mediaType = [info objectForKey:UIImagePickerControllerMediaType];// NSString* videoUrl = [info objectForKey:UIImagePickerControllerMediaURL];
        if (CFStringCompare((CFStringRef) mediaType, kUTTypeImage, 0) == kCFCompareEqualTo) {
            //UIImage* picture = [info objectForKey:UIImagePickerControllerEditedImage];
            UIImage* picture = [info objectForKey:UIImagePickerControllerOriginalImage];
            if (picture){
                //NSString *temp = [self encodeToBase64String:picture];
                //picture = [self decodeBase64ToImage:temp];
                self.imagePreview.image = picture;
                self.imagePicker = nil;
                //[self compareImage:picture];
             }
          }
    }];
}

- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker
{
    [self dismissViewControllerAnimated:YES completion:nil];
    self.imagePicker = nil;
}

-(void)compareImage:(UIImage *) image {
    if(image == nil){
        [self.idSuccess setValue:@"" forKey:@"selfieConfidenceScore"];
        [self.idSuccess setValue:[NSNumber numberWithBool:FALSE] forKey:@"selfieCompareFlag"];
        [self.idSuccess setValue:@"Empty selfie image" forKey:@"selfieCompareMessage"];
        [[NSNotificationCenter defaultCenter] postNotificationName:VFY_OBSERVER_IDSUCCESS object:self.idSuccess];
        return;
    }
    if([[self.idSuccess valueForKey:@"faceImage"] length] == 0){
        [self.idSuccess setValue:@"" forKey:@"selfieConfidenceScore"];
        [self.idSuccess setValue:[NSNumber numberWithBool:FALSE] forKey:@"selfieCompareFlag"];
        [self.idSuccess setValue:@"Empty identity image" forKey:@"selfieCompareMessage"];
        [[NSNotificationCenter defaultCenter] postNotificationName:VFY_OBSERVER_IDSUCCESS object:self.idSuccess];
        return;
    }
    self.Source=nil;
    self.Target=nil;
    
    if ([Utilities checkInternetConnection]) {
        self.LoaderView.hidden = false;
        [self.view bringSubviewToFront:self.LoaderView];
        //UIImage *rotateImage = [self scaleAndRotateImage:image]; // uncomment to fix the rotation issue
        NSString *base64Str = [Utilities compressPNGBase64:image];
        if([base64Str length]==0) {
           dispatch_async(dispatch_get_main_queue(), ^{
                self.LoaderView.hidden = true;
           });
           return;
        }
        self.Source = base64Str;
        self.Target = [self.idSuccess valueForKey:@"faceImage"];
        //[self setSource];
        
        NSLog(@"Target Length: %lu",[self.Target length]);
        NSLog(@"Source Length: %lu",[self.Source length]);
        if([self.Target length] > 10485760){
            [self.idSuccess setValue:@"" forKey:@"selfieConfidenceScore"];
            [self.idSuccess setValue:[NSNumber numberWithBool:FALSE] forKey:@"selfieCompareFlag"];
            [self.idSuccess setValue:@"Picture size exceeds limit" forKey:@"selfieCompareMessage"];
            [[NSNotificationCenter defaultCenter] postNotificationName:VFY_OBSERVER_IDSUCCESS object:self.idSuccess];
            return;
        }
        
        NSURLSessionConfiguration *defaultSessionConfiguration = [NSURLSessionConfiguration defaultSessionConfiguration];
        NSURLSession *defaultSession = [NSURLSession sessionWithConfiguration:defaultSessionConfiguration];
        NSURL *url = [NSURL URLWithString:VFY_IMAGE_COMPARE_API];
        NSMutableURLRequest *urlRequest = [NSMutableURLRequest requestWithURL:url];
        NSString *baseString = [NSString stringWithFormat:@"%@%@",VFY_IMAGE_COMPARE_AUTHORIZATION,[Utilities encodeStringTo64:VFY_IMAGE_COMPARE_CREDENTIAL]];
        NSDictionary *jsonData = [[NSDictionary alloc] initWithObjectsAndKeys:self.Target, VFY_IMAGE_TARGET, self.Source, VFY_IMAGE_SOURCE,nil];
        NSError *error;
        NSData *postData = [NSJSONSerialization dataWithJSONObject:jsonData options:0 error:&error];
        [urlRequest setValue:VFY_HEADER_CONTENT_VALUE forHTTPHeaderField:VFY_HEADER_CONTENT_KEY];
        [urlRequest setValue:baseString forHTTPHeaderField:VFY_HEADER_AUTH_KEY];
        [urlRequest setHTTPMethod:VFY_METHOD];
        [urlRequest setHTTPBody:postData];
      
        NSURLSessionDataTask *dataTask = [defaultSession dataTaskWithRequest:urlRequest completionHandler:^(NSData *data, NSURLResponse *response, NSError *error) {
            
            NSString *base64Decoded = [[NSString alloc] initWithData:data encoding:NSUTF8StringEncoding];
            NSError *e;
            NSDictionary *responseDict = [NSJSONSerialization JSONObjectWithData:data options:nil error:&e];
            
            if(responseDict != nil) {
                if([responseDict valueForKey:@"matchStatus"]){
                    [self.idSuccess setValue:[responseDict valueForKey:@"confidenceScore"] forKey:@"selfieConfidenceScore"];
                    [self.idSuccess setValue:[NSNumber numberWithBool:TRUE] forKey:@"selfieCompareFlag"];
                    [self.idSuccess setValue:@"Successful match!" forKey:@"selfieCompareMessage"];
                } else {
                    [self.idSuccess setValue:[responseDict valueForKey:@"confidenceScore"] forKey:@"selfieConfidenceScore"];
                    [self.idSuccess setValue:[NSNumber numberWithBool:FALSE] forKey:@"selfieCompareFlag"];
                    [self.idSuccess setValue:@"Unsuccessful match" forKey:@"selfieCompareMessage"];
                }
            } else {
                if([base64Decoded length]>0){
                    if([base64Decoded isEqualToString:VFY_RESPONSE_TRUE]){
                        [self.idSuccess setValue:@"100" forKey:@"selfieConfidenceScore"];
                        [self.idSuccess setValue:[NSNumber numberWithBool:TRUE] forKey:@"selfieCompareFlag"];
                        [self.idSuccess setValue:@"Successful match" forKey:@"selfieCompareMessage"];
                    } else if([base64Decoded isEqualToString:VFY_RESPONSE_FALSE]){
                        [self.idSuccess setValue:@"0" forKey:@"selfieConfidenceScore"];
                        [self.idSuccess setValue:[NSNumber numberWithBool:FALSE] forKey:@"selfieCompareFlag"];
                        [self.idSuccess setValue:@"Unsuccessful match" forKey:@"selfieCompareMessage"];
                    } else if([base64Decoded isEqualToString:VFY_RESPONSE_FAILED]){
                        [self.idSuccess setValue:@"" forKey:@"selfieConfidenceScore"];
                        [self.idSuccess setValue:[NSNumber numberWithBool:FALSE] forKey:@"selfieCompareFlag"];
                        [self.idSuccess setValue:@"Error occurred, please try again..." forKey:@"selfieCompareMessage"];
                    } else {
                        [self.idSuccess setValue:@"" forKey:@"selfieConfidenceScore"];
                        [self.idSuccess setValue:[NSNumber numberWithBool:FALSE] forKey:@"selfieCompareFlag"];
                        [self.idSuccess setValue:[NSString stringWithFormat:@"Error occurred %@",base64Decoded] forKey:@"selfieCompareMessage"];
                    }
                } else {
                    [self.idSuccess setValue:@"" forKey:@"selfieConfidenceScore"];
                    [self.idSuccess setValue:[NSNumber numberWithBool:FALSE] forKey:@"selfieCompareFlag"];
                    [self.idSuccess setValue:@"Null response from image compare API" forKey:@"selfieCompareMessage"];
                }
            }
            dispatch_async(dispatch_get_main_queue(), ^{
                self.LoaderView.hidden = true;
                [self callAudit];
                [[NSNotificationCenter defaultCenter] postNotificationName:VFY_OBSERVER_IDSUCCESS object:self.idSuccess];
                [self.navigationController popToRootViewControllerAnimated:YES];
            });
        }];
        // Fire the request
        [dataTask resume];
    }
}

- (UIImage *)scaleAndRotateImage:(UIImage *) image {
    int kMaxResolution = 320;

    CGImageRef imgRef = image.CGImage;

    CGFloat width = CGImageGetWidth(imgRef);
    CGFloat height = CGImageGetHeight(imgRef);


    CGAffineTransform transform = CGAffineTransformIdentity;
    CGRect bounds = CGRectMake(0, 0, width, height);
    if (width > kMaxResolution || height > kMaxResolution) {
        CGFloat ratio = width/height;
        if (ratio > 1) {
            bounds.size.width = kMaxResolution;
            bounds.size.height = bounds.size.width / ratio;
        }
        else {
            bounds.size.height = kMaxResolution;
            bounds.size.width = bounds.size.height * ratio;
        }
    }

    CGFloat scaleRatio = bounds.size.width / width;
    CGSize imageSize = CGSizeMake(CGImageGetWidth(imgRef), CGImageGetHeight(imgRef));
    CGFloat boundHeight;
    UIImageOrientation orient = image.imageOrientation;
    switch(orient) {

        case UIImageOrientationUp: //EXIF = 1
            transform = CGAffineTransformIdentity;
            break;

        case UIImageOrientationUpMirrored: //EXIF = 2
            transform = CGAffineTransformMakeTranslation(imageSize.width, 0.0);
            transform = CGAffineTransformScale(transform, -1.0, 1.0);
            break;

        case UIImageOrientationDown: //EXIF = 3
            transform = CGAffineTransformMakeTranslation(imageSize.width, imageSize.height);
            transform = CGAffineTransformRotate(transform, M_PI);
            break;

        case UIImageOrientationDownMirrored: //EXIF = 4
            transform = CGAffineTransformMakeTranslation(0.0, imageSize.height);
            transform = CGAffineTransformScale(transform, 1.0, -1.0);
            break;

        case UIImageOrientationLeftMirrored: //EXIF = 5
            boundHeight = bounds.size.height;
            bounds.size.height = bounds.size.width;
            bounds.size.width = boundHeight;
            transform = CGAffineTransformMakeTranslation(imageSize.height, imageSize.width);
            transform = CGAffineTransformScale(transform, -1.0, 1.0);
            transform = CGAffineTransformRotate(transform, 3.0 * M_PI / 2.0);
            break;

        case UIImageOrientationLeft: //EXIF = 6
            boundHeight = bounds.size.height;
            bounds.size.height = bounds.size.width;
            bounds.size.width = boundHeight;
            transform = CGAffineTransformMakeTranslation(0.0, imageSize.width);
            transform = CGAffineTransformRotate(transform, 3.0 * M_PI / 2.0);
            break;

        case UIImageOrientationRightMirrored: //EXIF = 7
            boundHeight = bounds.size.height;
            bounds.size.height = bounds.size.width;
            bounds.size.width = boundHeight;
            transform = CGAffineTransformMakeScale(-1.0, 1.0);
            transform = CGAffineTransformRotate(transform, M_PI / 2.0);
            break;

        case UIImageOrientationRight: //EXIF = 8
            boundHeight = bounds.size.height;
            bounds.size.height = bounds.size.width;
            bounds.size.width = boundHeight;
            transform = CGAffineTransformMakeTranslation(imageSize.height, 0.0);
            transform = CGAffineTransformRotate(transform, M_PI / 2.0);
            break;

        default:
            [NSException raise:NSInternalInconsistencyException format:@"Invalid image orientation"];

    }

    UIGraphicsBeginImageContext(bounds.size);

    CGContextRef context = UIGraphicsGetCurrentContext();

    if (orient == UIImageOrientationRight || orient == UIImageOrientationLeft) {
        CGContextScaleCTM(context, -scaleRatio, scaleRatio);
        CGContextTranslateCTM(context, -height, 0);
    }
    else {
        CGContextScaleCTM(context, scaleRatio, -scaleRatio);
        CGContextTranslateCTM(context, 0, -height);
    }

    CGContextConcatCTM(context, transform);

    CGContextDrawImage(UIGraphicsGetCurrentContext(), CGRectMake(0, 0, width, height), imgRef);
    UIImage *imageCopy = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();

    return imageCopy;
}


- (void) setSource
{
    NSString *temp = @"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";
    self.Source = temp;
    self.Target = temp;
}

@end
