// Copyright 2013 The Flutter 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 "include/flutter/flutter_engine.h"

#include <algorithm>
#include <iostream>

namespace flutter {

FlutterEngine::FlutterEngine() {}

FlutterEngine::~FlutterEngine() {}

bool FlutterEngine::Start(const std::string& icu_data_path,
                          const std::string& assets_path,
                          const std::vector<std::string>& arguments) {
  if (engine_) {
    std::cerr << "Cannot run an already running engine. Create a new instance "
                 "or call ShutDown first."
              << std::endl;
    return false;
  }

  FlutterDesktopEngineProperties c_engine_properties = {};
  c_engine_properties.assets_path = assets_path.c_str();
  c_engine_properties.icu_data_path = icu_data_path.c_str();
  std::vector<const char*> engine_switches;
  std::transform(
      arguments.begin(), arguments.end(), std::back_inserter(engine_switches),
      [](const std::string& arg) -> const char* { return arg.c_str(); });
  if (engine_switches.size() > 0) {
    c_engine_properties.switches = &engine_switches[0];
    c_engine_properties.switches_count = engine_switches.size();
  }

  engine_ = UniqueEnginePtr(FlutterDesktopRunEngine(c_engine_properties),
                            FlutterDesktopShutDownEngine);
  if (!engine_) {
    std::cerr << "Failed to start engine." << std::endl;
    return false;
  }
  return true;
}

void FlutterEngine::ShutDown() {
  engine_ = nullptr;
}

FlutterDesktopPluginRegistrarRef FlutterEngine::GetRegistrarForPlugin(
    const std::string& plugin_name) {
  if (!engine_) {
    std::cerr << "Cannot get plugin registrar on an engine that isn't running; "
                 "call Run first."
              << std::endl;
    return nullptr;
  }
  return FlutterDesktopGetPluginRegistrar(engine_.get(), plugin_name.c_str());
}

void FlutterEngine::RunEventLoopWithTimeout(std::chrono::milliseconds timeout) {
  if (!engine_) {
    std::cerr << "Cannot run event loop without a running engine; call "
                 "Run first."
              << std::endl;
    return;
  }
  uint32_t timeout_milliseconds;
  if (timeout == std::chrono::milliseconds::max()) {
    // The C API uses 0 to represent no timeout, so convert |max| to 0.
    timeout_milliseconds = 0;
  } else if (timeout.count() > UINT32_MAX) {
    timeout_milliseconds = UINT32_MAX;
  } else {
    timeout_milliseconds = static_cast<uint32_t>(timeout.count());
  }
  FlutterDesktopRunEngineEventLoopWithTimeout(engine_.get(),
                                              timeout_milliseconds);
}

}  // namespace flutter
