// Copyright 2017 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include "ash/system/bluetooth/tray_bluetooth_helper.h"

#include "ash/shell.h"
#include "ash/system/tray/system_tray_controller.h"
#include "ash/system/tray/system_tray_notifier.h"
#include "base/bind.h"
#include "base/bind_helpers.h"
#include "base/metrics/user_metrics.h"
#include "device/bluetooth/bluetooth_adapter.h"
#include "device/bluetooth/bluetooth_adapter_factory.h"
#include "device/bluetooth/bluetooth_device.h"
#include "device/bluetooth/bluetooth_discovery_session.h"

namespace ash {
namespace {

// System tray shows a limited number of bluetooth devices.
const int kMaximumDevicesShown = 50;

void BluetoothSetDiscoveringError() {
  LOG(ERROR) << "BluetoothSetDiscovering failed.";
}

void BluetoothDeviceConnectError(
    device::BluetoothDevice::ConnectErrorCode error_code) {}

ash::SystemTrayNotifier* GetSystemTrayNotifier() {
  return Shell::Get()->system_tray_notifier();
}

BluetoothDeviceInfo GetBluetoothDeviceInfo(device::BluetoothDevice* device) {
  BluetoothDeviceInfo info;
  info.address = device->GetAddress();
  info.display_name = device->GetNameForDisplay();
  info.connected = device->IsConnected();
  info.connecting = device->IsConnecting();
  info.paired = device->IsPaired();
  info.device_type = device->GetDeviceType();
  return info;
}

}  // namespace

BluetoothDeviceInfo::BluetoothDeviceInfo()
    : connected(false), connecting(false), paired(false) {}

BluetoothDeviceInfo::BluetoothDeviceInfo(const BluetoothDeviceInfo& other) =
    default;

BluetoothDeviceInfo::~BluetoothDeviceInfo() = default;

TrayBluetoothHelper::TrayBluetoothHelper() : weak_ptr_factory_(this) {}

TrayBluetoothHelper::~TrayBluetoothHelper() {
  if (adapter_)
    adapter_->RemoveObserver(this);
}

void TrayBluetoothHelper::Initialize() {
  device::BluetoothAdapterFactory::GetAdapter(
      base::Bind(&TrayBluetoothHelper::InitializeOnAdapterReady,
                 weak_ptr_factory_.GetWeakPtr()));
}

void TrayBluetoothHelper::InitializeOnAdapterReady(
    scoped_refptr<device::BluetoothAdapter> adapter) {
  adapter_ = adapter;
  CHECK(adapter_);
  adapter_->AddObserver(this);
}

BluetoothDeviceList TrayBluetoothHelper::GetAvailableBluetoothDevices() const {
  BluetoothDeviceList device_list;
  device::BluetoothAdapter::DeviceList devices = adapter_->GetDevices();
  for (device::BluetoothDevice* device : devices) {
    if (device_list.size() == kMaximumDevicesShown)
      break;

    if (device->IsPaired() || device->IsConnecting())
      device_list.push_back(GetBluetoothDeviceInfo(device));
  }

  for (device::BluetoothDevice* device : devices) {
    if (device_list.size() == kMaximumDevicesShown)
      break;

    if (!device->IsPaired() && !device->IsConnecting())
      device_list.push_back(GetBluetoothDeviceInfo(device));
  }

  return device_list;
}

void TrayBluetoothHelper::StartBluetoothDiscovering() {
  if (HasBluetoothDiscoverySession()) {
    LOG(WARNING) << "Already have active Bluetooth device discovery session.";
    return;
  }
  VLOG(1) << "Requesting new Bluetooth device discovery session.";
  should_run_discovery_ = true;
  adapter_->StartDiscoverySession(
      base::Bind(&TrayBluetoothHelper::OnStartDiscoverySession,
                 weak_ptr_factory_.GetWeakPtr()),
      base::Bind(&BluetoothSetDiscoveringError));
}

void TrayBluetoothHelper::StopBluetoothDiscovering() {
  should_run_discovery_ = false;
  if (!HasBluetoothDiscoverySession()) {
    LOG(WARNING) << "No active Bluetooth device discovery session.";
    return;
  }
  VLOG(1) << "Stopping Bluetooth device discovery session.";
  discovery_session_->Stop(base::Bind(&base::DoNothing),
                           base::Bind(&BluetoothSetDiscoveringError));
}

void TrayBluetoothHelper::ConnectToBluetoothDevice(const std::string& address) {
  device::BluetoothDevice* device = adapter_->GetDevice(address);
  if (!device || device->IsConnecting() ||
      (device->IsConnected() && device->IsPaired())) {
    return;
  }
  if (device->IsPaired() && !device->IsConnectable())
    return;
  if (device->IsPaired() || !device->IsPairable()) {
    base::RecordAction(
        base::UserMetricsAction("StatusArea_Bluetooth_Connect_Known"));
    device->Connect(NULL, base::Bind(&base::DoNothing),
                    base::Bind(&BluetoothDeviceConnectError));
    return;
  }
  // Show pairing dialog for the unpaired device.
  Shell::Get()->system_tray_controller()->ShowBluetoothPairingDialog(
      device->GetAddress(), device->GetNameForDisplay(), device->IsPaired(),
      device->IsConnected());
}

bool TrayBluetoothHelper::GetBluetoothAvailable() {
  return adapter_ && adapter_->IsPresent();
}

bool TrayBluetoothHelper::GetBluetoothEnabled() {
  return adapter_ && adapter_->IsPowered();
}

bool TrayBluetoothHelper::HasBluetoothDiscoverySession() {
  return discovery_session_ && discovery_session_->IsActive();
}

////////////////////////////////////////////////////////////////////////////////
// BluetoothAdapter::Observer:

void TrayBluetoothHelper::AdapterPresentChanged(
    device::BluetoothAdapter* adapter,
    bool present) {
  GetSystemTrayNotifier()->NotifyRefreshBluetooth();
}

void TrayBluetoothHelper::AdapterPoweredChanged(
    device::BluetoothAdapter* adapter,
    bool powered) {
  GetSystemTrayNotifier()->NotifyRefreshBluetooth();
}

void TrayBluetoothHelper::AdapterDiscoveringChanged(
    device::BluetoothAdapter* adapter,
    bool discovering) {
  GetSystemTrayNotifier()->NotifyBluetoothDiscoveringChanged();
}

void TrayBluetoothHelper::DeviceAdded(device::BluetoothAdapter* adapter,
                                      device::BluetoothDevice* device) {
  GetSystemTrayNotifier()->NotifyRefreshBluetooth();
}

void TrayBluetoothHelper::DeviceChanged(device::BluetoothAdapter* adapter,
                                        device::BluetoothDevice* device) {
  GetSystemTrayNotifier()->NotifyRefreshBluetooth();
}

void TrayBluetoothHelper::DeviceRemoved(device::BluetoothAdapter* adapter,
                                        device::BluetoothDevice* device) {
  GetSystemTrayNotifier()->NotifyRefreshBluetooth();
}

void TrayBluetoothHelper::OnStartDiscoverySession(
    std::unique_ptr<device::BluetoothDiscoverySession> discovery_session) {
  // If the discovery session was returned after a request to stop discovery
  // (e.g. the user dismissed the Bluetooth detailed view before the call
  // returned), don't claim the discovery session and let it clean up.
  if (!should_run_discovery_)
    return;
  VLOG(1) << "Claiming new Bluetooth device discovery session.";
  discovery_session_ = std::move(discovery_session);
  GetSystemTrayNotifier()->NotifyBluetoothDiscoveringChanged();
}

}  // namespace ash
