// Copyright 2021 Google LLC
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//      http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

#include "main.hpp"

#include "analyzer.hpp"
#include "bargraph.hpp"
#include "dbus_capture.hpp"
#include "histogram.hpp"
#include "menu.hpp"
#include "sensorhelper.hpp"
#include "views.hpp"

#include <ncurses.h>
#include <stdio.h>
#include <unistd.h>

#include <cassert>
#include <format>
#include <iomanip>
#include <mutex>
#include <sstream>
#include <thread>

DBusTopWindow* g_current_active_view;
SummaryView* g_summary_window;
SensorDetailView* g_sensor_detail_view;
DBusStatListView* g_dbus_stat_list_view;
FooterView* g_footer_view;
BarGraph<float>* g_bargraph = nullptr;
Histogram<float>* g_histogram;
std::vector<DBusTopWindow*> g_views;
int g_highlighted_view_index = INVALID;
sd_bus* g_bus = nullptr;
SensorSnapshot *g_sensor_snapshot, *g_sensor_snapshot_staging = nullptr;
DBusConnectionSnapshot *g_connection_snapshot,
    *g_connection_snapshot_staging = nullptr;
DBusTopStatistics* g_dbus_statistics; // At every update interval,
                                      // dbus_top_analyzer::g_dbus_statistics's
                                      // value is copied to this one for display

// Whenever an update of SensorSnapshot and DBusConnectionSnapshot is needed,
// they are populated into the "staging" copies and a pointer swap is done
// by the main thread (the thread that constructs the snapshots shall not touch
// the copy used for UI rendering)
bool g_sensor_update_thread_active = false;
std::string g_snapshot_update_bus_cxn =
    ""; // The DBus connection used by the updater thread.
int g_snapshot_update_bus_cxn_id = -999;
std::mutex g_mtx_snapshot_update;

int GetConnectionNumericID(const std::string& unique_name)
{
    size_t idx = unique_name.find('.');
    if (idx == std::string::npos)
    {
        return -999;
    }
    try
    {
        int ret = std::atoi(unique_name.substr(idx + 1).c_str());
        return ret;
    }
    catch (const std::exception& e)
    {
        return -999;
    }
}

void ReinitializeUI();
int maxx, maxy, halfx, halfy;

void ActivateWindowA()
{
    g_views[0]->visible_ = true;
    g_views[0]->maximize_ = true;
    g_views[1]->visible_ = false;
    g_views[2]->visible_ = false;
}

void ActivateWindowB()
{
    g_views[1]->visible_ = true;
    g_views[1]->maximize_ = true;
    g_views[0]->visible_ = false;
    g_views[2]->visible_ = false;
}
void ActivateWindowC()
{
    g_views[2]->visible_ = true;
    g_views[2]->maximize_ = true;
    g_views[0]->visible_ = false;
    g_views[1]->visible_ = false;
}
void ActivateAllWindows()
{
    g_views[0]->maximize_ = false;
    g_views[1]->maximize_ = false;
    g_views[2]->maximize_ = false;
    g_views[0]->visible_ = true;
    g_views[1]->visible_ = true;
    g_views[2]->visible_ = true;
}

void InitColorPairs()
{
    init_pair(1, COLOR_WHITE, COLOR_BLACK); // Does not work on actual machine
    init_pair(2, COLOR_BLACK, COLOR_WHITE);
}

// Returns number of lines drawn
int DrawTextWithWidthLimit(WINDOW* win, std::string txt, int y, int x,
                           int width,
                           [[maybe_unused]] const std::string& delimiters)
{
    int ret = 0;
    std::string curr_word, curr_line;
    while (txt.empty() == false)
    {
        ret++;
        if (static_cast<int>(txt.size()) > width)
        {
            mvwaddstr(win, y, x, txt.substr(0, width).c_str());
            txt = txt.substr(width);
        }
        else
        {
            mvwaddstr(win, y, x, txt.c_str());
            break;
        }
        y++;
    }
    return ret;
}

void UpdateWindowSizes()
{
    /* calculate window sizes and locations */
    if (getenv("FIXED_TERMINAL_SIZE"))
    {
        maxx = 100;
        maxy = 30;
    }
    else
    {
        getmaxyx(stdscr, maxy, maxx);
        halfx = maxx >> 1;
        halfy = maxy >> 1;
    }
    for (DBusTopWindow* v : g_views)
    {
        v->OnResize(maxx, maxy);
        if (v->maximize_)
        {
            v->rect = {0, 0, maxx, maxy - MARGIN_BOTTOM};
            v->UpdateWindowSizeAndPosition();
        }
    }
}

std::string FloatToString(float value)
{
    return std::format("{:.2f}", value);
}

void DBusTopRefresh()
{
    g_mtx_snapshot_update.lock();
    UpdateWindowSizes();
    for (DBusTopWindow* v : g_views)
    {
        v->Render();
    }
    DBusTopWindow* focused_view = g_current_active_view;
    if (focused_view)
    {
        focused_view->DrawBorderIfNeeded(); // focused view border: on top
    }
    refresh();
    g_mtx_snapshot_update.unlock();
}

void DBusTopUpdateFooterView()
{
    g_mtx_snapshot_update.lock();
    g_footer_view->Render();
    g_mtx_snapshot_update.unlock();
}

// This function is called by the Capture thread
void DBusTopStatisticsCallback(DBusTopStatistics* stat, Histogram<float>* hist)
{
    if (stat == nullptr)
        return;
    // Makes a copy for display
    // TODO: Add a mutex here for safety
    stat->Assign(g_dbus_statistics);
    hist->Assign(g_histogram);
    float interval_secs = stat->seconds_since_last_sample_;
    if (interval_secs == 0)
    {
        interval_secs = GetSummaryIntervalInMillises() / 1000.0f;
    }
    g_summary_window->UpdateDBusTopStatistics(stat);

    stat->SetSortFieldsAndReset(g_dbus_stat_list_view->GetSortFields());

    g_mtx_snapshot_update.lock();
    if (g_sensor_snapshot_staging != nullptr &&
        g_connection_snapshot_staging != nullptr)
    {
        std::swap(g_sensor_snapshot_staging, g_sensor_snapshot);
        std::swap(g_connection_snapshot_staging, g_connection_snapshot);

        delete g_connection_snapshot_staging;
        delete g_sensor_snapshot_staging;

        g_sensor_snapshot_staging = nullptr;
        g_connection_snapshot_staging = nullptr;
    }
    g_mtx_snapshot_update.unlock();
    g_sensor_detail_view->UpdateSensorSnapshot(g_sensor_snapshot);

    // ReinitializeUI(); // Don't do it here, only when user presses [R]
    DBusTopRefresh();
}

void CycleHighlightedView()
{
    int new_index = 0;
    if (g_highlighted_view_index == INVALID)
    {
        new_index = 0;
    }
    else
    {
        new_index = g_highlighted_view_index + 1;
    }
    while (new_index < static_cast<int>(g_views.size()) &&
           g_views[new_index]->selectable_ == false)
    {
        new_index++;
    }
    if (new_index >= static_cast<int>(g_views.size()))
    {
        new_index = INVALID;
    }
    // Un-highlight all
    for (DBusTopWindow* v : g_views)
    {
        v->focused_ = false;
    }
    if (new_index != INVALID)
    {
        g_views[new_index]->focused_ = true;
        g_current_active_view = g_views[new_index];
    }
    else
    {
        g_current_active_view = nullptr;
    }
    g_highlighted_view_index = new_index;
    DBusTopRefresh();
}

int UserInputThread()
{
    while (true)
    {
        int c = getch();
        DBusTopWindow* curr_view = g_current_active_view;
        // If a view is currently focused on
        if (curr_view)
        {
            switch (c)
            {
                case 0x1B: // 27 in dec, 0x1B in hex, escape key
                {
                    getch();
                    c = getch();
                    switch (c)
                    {
                        case 'A':
                            curr_view->OnKeyDown("up");
                            break;
                        case 'B':
                            curr_view->OnKeyDown("down");
                            break;
                        case 'C':
                            curr_view->OnKeyDown("right");
                            break;
                        case 'D':
                            curr_view->OnKeyDown("left");
                            break;
                        case 0x1B:
                            curr_view->OnKeyDown("escape");
                            break;
                    }
                    break;
                }
                case '\n': // 10 in dec, 0x0A in hex, line feed
                {
                    curr_view->OnKeyDown("enter");
                    break;
                }
                case 'q':
                case 'Q': // Q key
                {
                    curr_view->OnKeyDown("escape");
                    break;
                }
                case 'a':
                case 'A': // A key
                {
                    curr_view->OnKeyDown("a");
                    break;
                }
                case 'd':
                case 'D': // D key
                {
                    curr_view->OnKeyDown("d");
                    break;
                }
                case 33: // Page up
                {
                    curr_view->OnKeyDown("pageup");
                    break;
                }
                case 34: // Page down
                {
                    curr_view->OnKeyDown("pagedown");
                    break;
                }
                case ' ': // Spacebar
                {
                    curr_view->OnKeyDown("space");
                    break;
                }
            }
        }
        // The following keys are registered both when a view is selected and
        // when it is not
        switch (c)
        {
            case '\t': // 9 in dec, 0x09 in hex, tab
            {
                CycleHighlightedView();
                break;
            }
            case 'r':
            case 'R':
            {
                ReinitializeUI();
                DBusTopRefresh();
                break;
            }
            case 'x':
            case 'X':
            {
                clear();
                ActivateWindowA();
                break;
            }
            case 'y':
            case 'Y':
            {
                clear();
                ActivateWindowB();
                break;
            }
            case 'z':
            case 'Z':
            {
                clear();
                ActivateWindowC();
                break;
            }
            case 'h':
            case 'H':
            {
                ActivateAllWindows();
                DBusTopRefresh();
            }
            default:
                break;
        }
    }
    exit(0);
}

void ReinitializeUI()
{
    endwin();
    initscr();
    use_default_colors();
    noecho();
    for (int i = 0; i < static_cast<int>(g_views.size()); i++)
    {
        g_views[i]->RecreateWindow();
    }
}

void ListAllSensorsThread()
{
    // Create a temporary connection
    assert(g_sensor_update_thread_active == false);
    sd_bus* bus;
    AcquireBus(&bus);

    const char* bus_name;
    sd_bus_get_unique_name(bus, &bus_name);
    g_snapshot_update_bus_cxn = std::string(bus_name);
    g_snapshot_update_bus_cxn_id =
        GetConnectionNumericID(g_snapshot_update_bus_cxn);

    g_sensor_update_thread_active = true;
    DBusConnectionSnapshot* cxn_snapshot;
    SensorSnapshot* sensor_snapshot;
    dbus_top_analyzer::ListAllSensors(bus, &cxn_snapshot, &sensor_snapshot);

    g_mtx_snapshot_update.lock();
    g_connection_snapshot = cxn_snapshot;
    g_sensor_snapshot = sensor_snapshot;
    g_mtx_snapshot_update.unlock();
    g_sensor_update_thread_active = false;
    g_snapshot_update_bus_cxn = "";
    g_snapshot_update_bus_cxn_id = -999;

    sd_bus_close(bus);
}

int main([[maybe_unused]] int argc, [[maybe_unused]] char** argv)
{
    int r = AcquireBus(&g_bus);
    if (r <= 0)
    {
        printf("Error acquiring bus for monitoring\n");
        exit(0);
    }

    printf("Listing all sensors for display\n");
    // ListAllSensors creates connection snapshot and sensor snapshot
    g_connection_snapshot = new DBusConnectionSnapshot();
    g_sensor_snapshot = new SensorSnapshot(g_connection_snapshot);

    g_bargraph = new BarGraph<float>(300);
    g_histogram = new Histogram<float>();

    initscr();
    use_default_colors();
    start_color();
    noecho();

    clear();
    g_dbus_statistics = new DBusTopStatistics();
    g_summary_window = new SummaryView();
    g_sensor_detail_view = new SensorDetailView();
    g_dbus_stat_list_view = new DBusStatListView();
    g_footer_view = new FooterView();
    g_views.push_back(g_summary_window);
    g_views.push_back(g_sensor_detail_view);
    g_views.push_back(g_dbus_stat_list_view);
    g_views.push_back(g_footer_view);

    // Do the scan in a separate thread.
    std::thread list_all_sensors_thread(ListAllSensorsThread);

    g_sensor_detail_view->UpdateSensorSnapshot(g_sensor_snapshot);
    UpdateWindowSizes();
    dbus_top_analyzer::SetDBusTopStatisticsCallback(&DBusTopStatisticsCallback);
    std::thread capture_thread(DbusCaptureThread);
    std::thread user_input_thread(UserInputThread);
    capture_thread.join();

    return 0;
}
