//
//  ChatSDKViewController.swift
//  base-chatsdk-ios
//
//  Created by Bruno Martinez on 2/12/20.
//

import UIKit
import ChatSDK
import ChatSDKFirebase
import Kingfisher

struct ChatMember {
  var uuid: String
  var name: String
  var lastName: String
  var cellphone: String
  var imageURL: String
}

struct ChatConstants {
  static let placeholderImageAssetsUrl = "userProfilePhotoPlaceholder"
  static let allMembersImageStr = "allMembers"
}

class ChatSDKViewController: UIViewController {
  
  @IBOutlet weak var membersTableView: UITableView!
  @IBOutlet weak var chatNameView: UIView!
  
  static var chatSdkIdentifier = "ChatTableViewCell"
  static var chatMessageTableViewCell = "ChatMessageTableViewCell"
  /// Members: NOT INCLUDE yourself
  private var members: [ChatMember] = []
  /// Members: INCLUDE yourself
  private var membersWithMe: [ChatMember] = []
  /// List of threads
  private var threads: [PThread] = []
  
  override func viewDidLoad() {
    super.viewDidLoad()
    members = SessionManager.shared.userContacts
    var membersCopy = members
    membersCopy.append(SessionManager.shared.user)
    membersWithMe = membersCopy
    membersTableView.tableFooterView = UIView()
    setUp()
  }
  
  override func viewWillAppear(_ animated: Bool) {
    super.viewWillAppear(animated)
    self.navigationController?.setNavigationBarHidden(true, animated: false)
  }
  
  override func viewWillDisappear(_ animated: Bool) {
    self.navigationController?.setNavigationBarHidden(false, animated: animated)
    super.viewWillDisappear(animated)
  }
  
  
  func setUp() {
    DispatchQueue.main.async {
      self.membersTableView.delegate = self
      self.membersTableView.dataSource = self
      self.membersTableView.register(UINib(nibName: ChatSDKViewController.chatSdkIdentifier, bundle: nil),
                                     forCellReuseIdentifier: ChatSDKViewController.chatSdkIdentifier)
      self.membersTableView.tableFooterView = UIView()
    }
  }
  
}

extension ChatSDKViewController: UITableViewDelegate, UITableViewDataSource {
  func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
    if members.count == 0 {
      return 0
    } else if members.count == 1 {
      return 1
    } else {
      return members.count + 1
    }
  }
  func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
    return 80
  }
  func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
    let cell = tableView.dequeueReusableCell(withIdentifier: "ChatTableViewCell") as! ChatTableViewCell
    cell.memberCellphone.isHidden = false
    if members.count == 1 { // if i have 2 members on circle, all members chat is off (members ref not include me)
      let caregiver = members[indexPath.row]
        cell.memberImageView.kf.setImage(with: URL(string: caregiver.imageURL), completionHandler:  { _ in })
      cell.memberNameLabel.text = "\(caregiver.name) \(caregiver.lastName)"
      cell.memberCellphone.text = caregiver.cellphone
    } else { //if i have 3 or more members on circle, all members chat is on
      if indexPath.row == 0 {
        cell.memberImageView.image = UIImage(named: ChatConstants.allMembersImageStr)!
        cell.memberNameLabel.text = "All members"
        cell.memberCellphone.isHidden = true
      } else {
        let caregiver = members[indexPath.row - 1]
        cell.memberImageView.kf.setImage(with: URL(string: caregiver.imageURL), completionHandler:  { _ in })
        cell.memberNameLabel.text = "\(caregiver.name) \(caregiver.lastName)"
        cell.memberCellphone.text = caregiver.cellphone
      }
    }
    
    if indexPath.row == 0, let last = self.threads.last {
      let thread = last
      cell.messageIndicator.isHidden = thread.unreadMessageCount() == 0
    } else {
      let thread = threads.filter { (pthread) -> Bool in
        if let users = pthread.users() {
          return users.contains(where: { (hashUser) -> Bool in
            if let pUser = hashUser as? PUser {
              if members.count == 1 {
                let caregiver = members[indexPath.row]
                return caregiver.uuid == pUser.entityID()
              } else {
                let caregiver = members[indexPath.row - 1]
                return caregiver.uuid == pUser.entityID()
              }
            }
            return false
          })
        }
        return false
      }
      cell.messageIndicator.isHidden = (thread.first?.unreadMessageCount() ?? 0) == 0
    }
    
    cell.selectionStyle = .none
    return cell
  }
  func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
    DispatchQueue.main.async {
      
      if self.members.count == 1 {
        ChatManager.startThreadWith([self.members.first!.uuid, SessionManager.shared.user.uuid], result: { (thread, users) in
          let chatViewController = self.getChatController(from: thread)! as! CustomChatViewController
          chatViewController.members = self.membersWithMe
          let chatMember = self.members.first!
          chatViewController.changeTitleTo("\(chatMember.name) \(chatMember.lastName)")
          self.presentChat(chatViewController)
        }) { (error) in
          print("error")
        }
      } else {
        if indexPath.row == 0 { // all members
          if let allMembersThreadEntityId = UserDefaults.standard.string(forKey: "allMembersThreadEntityId")  {
            if let allMembersThread = BChatSDK.db()?.thread(forEntityID: allMembersThreadEntityId) {
              let chatViewController = self.getChatController(from: allMembersThread)! as! CustomChatViewController
              chatViewController.members = self.membersWithMe
              chatViewController.changeTitleTo("All members")
              self.presentChat(chatViewController)
            }
          } else {
            ChatManager.startThreadWith(self.membersWithMe.map( { $0.uuid }), result: { (thread, users) in
              let chatViewController = self.getChatController(from: thread)! as! CustomChatViewController
              chatViewController.members = self.membersWithMe
              chatViewController.changeTitleTo("All members")
              UserDefaults.standard.set(thread.entityID(), forKey: "allMembersThreadEntityId")
              self.presentChat(chatViewController)
            }) { (error) in
              print(error)
            }
          }
        } else {
          ChatManager.startThreadWith([self.members.map({ $0.uuid })[indexPath.row - 1], SessionManager.shared.user.uuid], result: { (thread, users) in
            let chatViewController = self.getChatController(from: thread)! as! CustomChatViewController
            chatViewController.members = self.membersWithMe
            let chatMember = self.members[indexPath.row - 1]
            chatViewController.changeTitleTo("\(chatMember.name) \(chatMember.lastName)")
            self.presentChat(chatViewController)
          }) { (error) in
            print("error")
          }
        }
      }
    }
  }
  
  func presentChat(_ chat: CustomChatViewController) {
    self.present(chat, animated: true)
  }
  
  func getChatController(from thread: PThread) -> UIViewController? {
    if BChatSDK.ui().chatViewController(with: thread) != nil {
      let customVC = CustomChatViewController.init(thread: thread)
      customVC?.setUp()
      customVC?.tableView.layoutIfNeeded()
      return customVC
    }
    return nil
  }
}
