//
// FlightInfoEditController.m
// Project
//
// Created by Ziv on 15/11/17.
//
//

#import "TourFlightInfoEditViewController.h"
#import "Lang.h"
#import "SDK.h"
#import "BeanUtils.h"
#import "CocoaUtils.h"
#import "Collectors.h"
#import "DrawUtils.h"
#import "UIConstants.h"
#import "UIToolkit.h"
#import <BlocksKit/BlocksKit.h>
#import <BlocksKit/BlocksKit+UIKit.h>
#import <libextobjc/EXTScope.h>
#import <PureLayout/PureLayout.h>
#import "Utility.h"
#import "SalesEntryRoom.h"
#import "SoldStock.h"
#import "PerlWS.h"
#import "FlightInfoViewController.h"
#import "Vars.h"

@interface TourFlightInfoEditViewController () {
	BOOL isNotFirst;
}

@property (nonatomic, strong) NSArray *cellDataArrays;
@property (nonatomic, strong) NSMutableArray *flightInfoCellDataArray;

@property (nonatomic, strong) NSMutableArray *selectedPerson;
@property (nonatomic, strong) NSArray *personArrays;
@property (nonatomic, strong) FlightInfo *selectedFlightInfo;
@property (nonatomic, strong) NSMutableArray *flightInfos;

@end

@implementation TourFlightInfoEditViewController

- (instancetype)init {
	if (self = [super init]) {
		// Custom initialization
		self.title = [NSString stringWithFormat:IMLocalizedString(@"Edit %@"), IMLocalizedString(@"Flight Information")];
		[[Vars appDelegate] applyDefaultConfigurationForViewController:self];
	}
	return self;
}

- (void)viewDidLoad {
	[super viewDidLoad];

	[self initResourceArray];

	@weakify(self)
	self.navigationItem.rightBarButtonItem = [[UIBarButtonItem alloc] im_initWithBarButtonSystemItem:UIBarButtonSystemItemEdit handler:^(UIBarButtonItem *barButtonItem) {
		@strongify(self)
		if (![self validateFlightInfoSelection]) {
			return;
		}
		[self changeFlightInfo:self.selectedFlightInfo];
	}];

	self.tableView.editing = YES;
	if (YES) {
		UIView *footerView = [[UIView alloc] initWithFrame:CGRectMake(0, 0, CGRectGetWidth([UIScreen mainScreen].bounds), [UIConstants defaultTableViewRowHeight] + 15 * 2)];
		UIButton *button = [UIButton buttonWithType:UIButtonTypeSystem];
		button.frame = CGRectMake(15, 15, CGRectGetWidth([UIScreen mainScreen].bounds) - 15 * 2, [UIConstants defaultTableViewRowHeight]);
		button.backgroundColor = [Vars defaultTintColor];
		button.titleLabel.font = [UIFont boldSystemFontOfSize:[UIFont buttonFontSize]];
		[button setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
		[button setTitle:IMLocalizedString(@"Proceed") forState:UIControlStateNormal];
		[button addTarget:self action:@selector(submitFlightInfo) forControlEvents:UIControlEventTouchUpInside];
		[Utility addRoundedBorderToButton:button];
		[footerView addSubview:button];
		self.tableView.tableFooterView = footerView;
	}
	[self buildCellDataSource];
}

- (void)viewWillAppear:(BOOL)animated {
	[super viewWillAppear:animated];

	if (!isNotFirst) {
		[self autoCheckFlightInfo:self.selectedFlightInfo];
		isNotFirst = YES;
	}
}

#pragma mark - Network

- (void)editFlightInfo {
	NSArray *selectedStocks = [self.selectedPerson valueForKeyPath:@"@unionOfArrays.self"];
	EditFlightInfo *editFlightInfo = [[EditFlightInfo alloc] init];
	editFlightInfo.passengerNo = [[selectedStocks valueForKeyPath:@"stock_id"] componentsJoinedByString:@";"];
	editFlightInfo.flightInfo = self.selectedFlightInfo;

	NSDictionary *requestDict = [Utility perlParamXml:[editFlightInfo innerXML] action:editFlightInfo.name];

	[Utility getXMLFromRequestWithMethod:@"GET" url:editFlightInfo.address parameters:requestDict success:^(NSString *xml) {
		NSString *responseStr = xml;
		// NSLog(@"%@", responseStr);
		WebServiceResponseJsonMapper *mapper = [[WebServiceResponseJsonMapper alloc] init];
		NSDictionary *jsonDict = [Utility JSONObjectWithXMLString:responseStr objectMapping:mapper.objectMapping];
		// NSLog(@"%@", jsonDict);
		if (![mapper parseWithJSONObject:jsonDict]) {
			WebServiceResponse *response = mapper.response;
			if (response.error_code > 0) {
				[CocoaUtils showAlertWithTitle:IMLocalizedString(@"Error") message:response.error_message];
			} else {
				for (SoldStock *stock in selectedStocks) {
					stock.flight_info = self.selectedFlightInfo;
				}
				NSNotificationCenter *notificationCenter = [NSNotificationCenter defaultCenter];
				[notificationCenter postNotificationName:FlightInformationDidEditingNotification object:nil];
				[self.navigationController popViewControllerAnimated:YES];
			}
		}
	}];
}

#pragma mark - Action

- (void)submitFlightInfo {
	if (![self validateFlightInfoSelection]) {
		return;
	}
	NSArray *selectedStocks = [self.selectedPerson valueForKeyPath:@"@unionOfArrays.self"];
	if (selectedStocks.count == 0) {
		[CocoaUtils showAlertWithTitle:IMLocalizedString(@"Information") message:IMLocalizedString(@"Please select traveler(s)")];
		return;
	}
	if ([selectedStocks bk_all:^BOOL (SoldStock *stock) {
		return [stock.flight_info isEqual:self.selectedFlightInfo];
	}]) {
		[CocoaUtils showAlertWithTitle:IMLocalizedString(@"Information") message:IMLocalizedString(@"Nothing has been changed")];
		return;
	}
	[self editFlightInfo];
}

- (void)addNewFlightInfo {
	[self changeFlightInfo:nil];
}

#pragma mark - Private

- (void)initResourceArray {
	NSDictionary *flightInfoStocks = [Collectors groupingBy:self.entry.rooms.count > 0 ? [self.entry.rooms valueForKeyPath:@"@unionOfArrays.stocks"] : self.entry.stocks classifierWithKeyPath:@"flight_info"];
	self.flightInfos = [NSMutableArray arrayWithArray:flightInfoStocks.allKeys];

	self.personArrays = self.entry.rooms.count > 0 ? [self.entry.rooms valueForKeyPath:@"stocks"] : @[self.entry.stocks];
	NSMutableArray *arrays = [NSMutableArray array];
	for (int i = 0; i < self.personArrays.count; i++) {
		[arrays addObject:[NSMutableArray array]];
	}
	self.selectedPerson = [NSArray arrayWithArray:arrays];

	if (self.flightInfos.count == 1) {
		self.selectedFlightInfo = self.flightInfos.firstObject;
		for (int i = 0; i < self.personArrays.count; i++) {
			[self.selectedPerson[i] addObjectsFromArray:self.personArrays[i]];
		}
	}
}

- (void)autoCheckTravelersWithFlightInfo:(FlightInfo *)flightInfo {
	[self.selectedPerson makeObjectsPerformSelector:@selector(removeAllObjects)];
	if (flightInfo) {
		for (int i = 0; i < self.selectedPerson.count; i++) {
			NSArray *stocks = [self.personArrays[i] bk_select:^BOOL (SoldStock *stock) {
				return [stock.flight_info isEqual:flightInfo];
			}];
			[self.selectedPerson[i] addObjectsFromArray:stocks];
		}
	}
	[self.tableView reloadSections:[NSIndexSet indexSetWithIndex:1] withRowAnimation:UITableViewRowAnimationNone];
}

- (void)autoCheckFlightInfo:(FlightInfo *)flightInfo {
	if ([self.flightInfos containsObject:flightInfo]) {
		[self.tableView selectRowAtIndexPath:[NSIndexPath indexPathForRow:[self.flightInfos indexOfObject:flightInfo] + 1 inSection:0] animated:NO scrollPosition:UITableViewScrollPositionNone];
	}
}

- (void)autoUncheckFlightInfo:(FlightInfo *)flightInfo {
	if ([self.flightInfos containsObject:flightInfo]) {
		[self.tableView deselectRowAtIndexPath:[NSIndexPath indexPathForRow:[self.flightInfos indexOfObject:flightInfo] + 1 inSection:0] animated:NO];
	}
}

- (BOOL)isSameCount:(NSArray *)array1 withOtherArray:(NSArray *)array2 {
	if (array1.count != array2.count) {
		return NO;
	} else {
		for (int i = 0; i < array1.count; ++i) {
			if ([array1[i] count] != [array2[i] count]) {
				return NO;
			}
		}
	}
	return YES;
}

- (BOOL)validateFlightInfoSelection {
	if (!self.selectedFlightInfo) {
		[CocoaUtils showAlertWithTitle:IMLocalizedString(@"Information") message:IMLocalizedString(@"Please select flight information")];
		return NO;
	}
	return YES;
}

- (void)updateTableViewCellDataArrayForAddingFlightInfo:(FlightInfo *)flightInfo {
	NSMutableArray *array = self.cellDataArrays[0];
	@weakify(self)
	TableViewCellData *data = [[TableViewCellData alloc] init];
	[data setTextBlock:^NSString *{
		return flightInfo.shortDescription;
	}];
	data.allowsTextLineWrapping = YES;
	[data setDidSelectBlock:^(UITableView *tableView, NSIndexPath *indexPath, TableViewCellData *data) {
		@strongify(self)
		[self autoUncheckFlightInfo: self.selectedFlightInfo];
		[self autoCheckTravelersWithFlightInfo:flightInfo];
		self.selectedFlightInfo = flightInfo;
	}];
	[data setDidDeselectBlock:^(UITableView *tableView, NSIndexPath *indexPath, TableViewCellData *data) {
		@strongify(self)
		[self autoCheckTravelersWithFlightInfo: nil];
		self.selectedFlightInfo = nil;
	}];
	[array addObject:data];
}

- (void)buildCellDataSource {
	NSMutableArray *arrays = [NSMutableArray array];
	@weakify(self)
	if (YES) {
		Label *flightInfoLabel = [self.entry.product.labels bk_match:^BOOL (Label *label) {
			return [label isTypeOfFlightInfo];
		}];
		TableViewCellData *data = [[TableViewCellData alloc] init];
		data.text = flightInfoLabel.name;
		[data setAccessoryViewBlock:^UIView *(UITableView *tableView, NSIndexPath *indexPath, TableViewCellData *data){
			@strongify(self)
			UIButton *button = [UIButton buttonWithType:UIButtonTypeContactAdd];
			[button addTarget:self action:@selector(addNewFlightInfo) forControlEvents:UIControlEventTouchUpInside];
			return button;
		}];
		[arrays addObject:[NSMutableArray arrayWithObject:data]];
	}
	if (YES) {
		NSMutableArray *array = [NSMutableArray array];
		if (YES) {
			TableViewCellData *data = [[TableViewCellData alloc] init];
			data.text = self.entry.shortDescription;
			[data setAccessoryTypeBlock:^UITableViewCellAccessoryType {
				@strongify(self)
				if ([self isSameCount:self.selectedPerson withOtherArray:self.personArrays]) {
					return UITableViewCellAccessoryCheckmark;
				}
				return UITableViewCellAccessoryNone;
			}];
			[data setDidSelectBlock:^(UITableView *tableView, NSIndexPath *indexPath, TableViewCellData *data) {
				@strongify(self)
				if (![self validateFlightInfoSelection]) {
					return;
				}
				if ([self isSameCount:self.selectedPerson withOtherArray:self.personArrays]) {
					[self.selectedPerson makeObjectsPerformSelector:@selector(removeAllObjects)];
				} else {
					for (int i = 0; i < self.selectedPerson.count; i++) {
						[self.selectedPerson[i] removeAllObjects];
						[self.selectedPerson[i] addObjectsFromArray:self.personArrays[i]];
					}
				}
				[self.tableView reloadSections:[NSIndexSet indexSetWithIndex:1] withRowAnimation:UITableViewRowAnimationNone];
			}];
			[array addObject:data];
		}
		for (int i = 0; i < self.personArrays.count; i++) {
			if (self.entry.rooms.count > 0) {
				SalesEntryRoom *room = self.entry.rooms[i];
				TableViewCellData *data = [[TableViewCellData alloc] init];
				data.text = room.shortDescription;
				data.textColor = [UIColor lightGrayColor];
				[data setAccessoryTypeBlock:^UITableViewCellAccessoryType {
					@strongify(self)
					if ([self.selectedPerson[i] count] == [self.personArrays[i] count]) {
						return UITableViewCellAccessoryCheckmark;
					}
					return UITableViewCellAccessoryNone;
				}];
				[data setDidSelectBlock:^(UITableView *tableView, NSIndexPath *indexPath, TableViewCellData *data) {
					@strongify(self)
					if (![self validateFlightInfoSelection]) {
						return;
					}
					if ([self.selectedPerson[i] count] == [self.personArrays[i] count]) {
						[self.selectedPerson[i] removeAllObjects];
					} else {
						[self.selectedPerson[i] removeAllObjects];
						[self.selectedPerson[i] addObjectsFromArray:self.personArrays[i]];
					}
					[self.tableView reloadSections:[NSIndexSet indexSetWithIndex:1] withRowAnimation:UITableViewRowAnimationNone];
				}];
				[array addObject:data];
			}
			for (SoldStock *stock in self.personArrays[i]) {
				TableViewCellData *data = [[TableViewCellData alloc] init];
				data.style = UITableViewCellStyleSubtitle;
				data.text = stock.sold_to_name;
				data.detailText = stock.otherShortDescription;
				[data setAccessoryTypeBlock:^UITableViewCellAccessoryType {
					@strongify(self)
					if ([self.selectedPerson[i] containsObject:stock]) {
						return UITableViewCellAccessoryCheckmark;
					}
					return UITableViewCellAccessoryNone;
				}];
				[data setDidSelectBlock:^(UITableView *tableView, NSIndexPath *indexPath, TableViewCellData *data) {
					@strongify(self)
					if (![self validateFlightInfoSelection]) {
						return;
					}
					if ([self.selectedPerson[i] containsObject:stock]) {
						[self.selectedPerson[i] removeObject:stock];
					} else {
						[self.selectedPerson[i] addObject:stock];
					}
					[self.tableView reloadSections:[NSIndexSet indexSetWithIndex:1] withRowAnimation:UITableViewRowAnimationNone];
				}];
				[array addObject:data];
			}
		}
		[arrays addObject:[NSArray arrayWithArray:array]];
	}
	self.cellDataArrays = [NSArray arrayWithArray:arrays];

	for (FlightInfo *flightInfo in self.flightInfos) {
		[self updateTableViewCellDataArrayForAddingFlightInfo:flightInfo];
	}
}

- (void)changeFlightInfo:(FlightInfo *)oldFlightInfo {
	Label *flightInfoLabel = [self.entry.product.labels bk_match:^BOOL (Label *label) {
		return [label isTypeOfFlightInfo];
	}];
	FlightInfoViewController *viewController = [[FlightInfoViewController alloc] initWithFlightInfo:oldFlightInfo ? oldFlightInfo : [[FlightInfo alloc] init]];
	viewController.title = flightInfoLabel.name;
	viewController.readonly = NO;
	viewController.allowIfNeededWhileEditing = YES;
	viewController.arrivalAirportOptions = [[self.entry.product.airport_stops filteredArrayUsingPredicate:[NSPredicate predicateWithFormat:@"is_return == NO"]] valueForKeyPath:@"airport.name"];
	viewController.returnAirportOptions = [[self.entry.product.airport_stops filteredArrayUsingPredicate:[NSPredicate predicateWithFormat:@"is_return == YES"]] valueForKeyPath:@"airport.name"];
	viewController.notNeedFlightOptions = self.entry.product.not_need_flight_options;
	viewController.airportPickUpTip = self.entry.product.airport_pick_up_tip;
	[viewController setDidCancelBlock:^{
		[self.navigationController popViewControllerAnimated:YES];
	}];
	[viewController setShouldDoneBlock:^BOOL (FlightInfo *newFlightInfo) {
		if (oldFlightInfo && [oldFlightInfo isEqual:newFlightInfo]) {
			return YES;
		}
		if (![self.flightInfos containsObject:newFlightInfo]) {
			return YES;
		}
		[CocoaUtils showAlertWithTitle:IMLocalizedString(@"Information") message:IMLocalizedString(@"The flight information is duplicated")];
		return NO;
	}];
	[viewController setDidDoneBlock:^(FlightInfo *newFlightInfo) {
		[self.navigationController popViewControllerAnimated:YES];
		if (oldFlightInfo) {
			if ([oldFlightInfo isEqual:newFlightInfo]) {
			} else {
				[BeanUtils copyProperties:oldFlightInfo origin:newFlightInfo];
				[self.tableView reloadRowsAtIndexPaths:@[[NSIndexPath indexPathForRow:[self.flightInfos indexOfObject:oldFlightInfo] + 1 inSection:0]] withRowAnimation:UITableViewRowAnimationNone];
				[self autoCheckFlightInfo:oldFlightInfo];
			}
		} else {
			[self autoUncheckFlightInfo:self.selectedFlightInfo];
			[self.flightInfos addObject:newFlightInfo];
			[self updateTableViewCellDataArrayForAddingFlightInfo:newFlightInfo];
			[self.tableView insertRowsAtIndexPaths:@[[NSIndexPath indexPathForRow:[self.flightInfos indexOfObject:newFlightInfo] + 1 inSection:0]] withRowAnimation:UITableViewRowAnimationNone];
			[self autoCheckTravelersWithFlightInfo:newFlightInfo];
			[self autoCheckFlightInfo:newFlightInfo];
			self.selectedFlightInfo = newFlightInfo;
		}
	}];
	[self.navigationController pushViewController:viewController animated:YES];
}

#pragma mark - Table view data source

- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
	return self.cellDataArrays.count;
}

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
	return [self.cellDataArrays[section] count];
}

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
	TableViewCellData *data = self.cellDataArrays[indexPath.section][indexPath.row];
	return [UIToolkit tableView:tableView atIndexPath:indexPath cellWithData:data];
}

- (BOOL)tableView:(UITableView *)tableView canEditRowAtIndexPath:(NSIndexPath *)indexPath {
	if (indexPath.section == 0 && indexPath.row > 0) {
		return YES;
	}
	return NO;
}

#pragma mark - Table view delegate

- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath {
	TableViewCellData *data = self.cellDataArrays[indexPath.section][indexPath.row];
	return [UIToolkit tableView:tableView atIndexPath:indexPath rowHeightWithData:data];
}

- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
	if (![self tableView:tableView canEditRowAtIndexPath:indexPath]) {
		[tableView deselectRowAtIndexPath:indexPath animated:YES];
	}
	TableViewCellData *data = self.cellDataArrays[indexPath.section][indexPath.row];
	[UIToolkit tableView:tableView atIndexPath:indexPath didSelectWithData:data];
}

- (void)tableView:(UITableView *)tableView didDeselectRowAtIndexPath:(NSIndexPath *)indexPath {
	if (![self tableView:tableView canEditRowAtIndexPath:indexPath]) {
		return;
	}
	TableViewCellData *data = self.cellDataArrays[indexPath.section][indexPath.row];
	[UIToolkit tableView:tableView atIndexPath:indexPath didDeselectWithData:data];
}

@end
