// SPDX-License-Identifier: GPL-2.0
#include <signal.h>
#include <stdbool.h>
#include <string.h>
#include <stdlib.h>
#include <sys/ttydefaults.h>

#include "../browser.h"
#include "../keysyms.h"
#include "../helpline.h"
#include "../ui.h"
#include "../util.h"
#include "../libslang.h"

static void ui_browser__argv_write(struct ui_browser *browser,
				   void *entry, int row)
{
	char **arg = entry;
	bool current_entry = ui_browser__is_current_entry(browser, row);

	ui_browser__set_color(browser, current_entry ? HE_COLORSET_SELECTED :
						       HE_COLORSET_NORMAL);
	ui_browser__write_nstring(browser, *arg, browser->width);
}

static int popup_menu__run(struct ui_browser *menu, int *keyp)
{
	int key;

	if (ui_browser__show(menu, " ", "ESC: exit, ENTER|->: Select option") < 0)
		return -1;

	while (1) {
		key = ui_browser__run(menu, 0);

		switch (key) {
		case K_RIGHT:
		case K_ENTER:
			key = menu->index;
			break;
		case K_LEFT:
		case K_ESC:
		case 'q':
		case CTRL('c'):
			key = -1;
			break;
		default:
			if (keyp) {
				*keyp = key;
				key = menu->nr_entries;
				break;
			}
			continue;
		}

		break;
	}

	ui_browser__hide(menu);
	return key;
}

int ui__popup_menu(int argc, char * const argv[], int *keyp)
{
	struct ui_browser menu = {
		.entries    = (void *)argv,
		.refresh    = ui_browser__argv_refresh,
		.seek	    = ui_browser__argv_seek,
		.write	    = ui_browser__argv_write,
		.nr_entries = argc,
	};
	return popup_menu__run(&menu, keyp);
}

int ui_browser__input_window(const char *title, const char *text, char *input,
			     const char *exit_msg, int delay_secs)
{
	int x, y, len, key;
	int max_len = 60, nr_lines = 0;
	static char buf[50];
	const char *t;

	t = text;
	while (1) {
		const char *sep = strchr(t, '\n');

		if (sep == NULL)
			sep = strchr(t, '\0');
		len = sep - t;
		if (max_len < len)
			max_len = len;
		++nr_lines;
		if (*sep == '\0')
			break;
		t = sep + 1;
	}

	mutex_lock(&ui__lock);

	max_len += 2;
	nr_lines += 8;
	y = SLtt_Screen_Rows / 2 - nr_lines / 2;
	x = SLtt_Screen_Cols / 2 - max_len / 2;

	SLsmg_set_color(0);
	SLsmg_draw_box(y, x++, nr_lines, max_len);
	if (title) {
		SLsmg_gotorc(y, x + 1);
		SLsmg_write_string(title);
	}
	SLsmg_gotorc(++y, x);
	nr_lines -= 7;
	max_len -= 2;
	SLsmg_write_wrapped_string((unsigned char *)text, y, x,
				   nr_lines, max_len, 1);
	y += nr_lines;
	len = 5;
	while (len--) {
		SLsmg_gotorc(y + len - 1, x);
		SLsmg_write_nstring(" ", max_len);
	}
	SLsmg_draw_box(y++, x + 1, 3, max_len - 2);

	SLsmg_gotorc(y + 3, x);
	SLsmg_write_nstring(exit_msg, max_len);
	SLsmg_refresh();

	mutex_unlock(&ui__lock);

	x += 2;
	len = 0;
	key = ui__getch(delay_secs);
	while (key != K_TIMER && key != K_ENTER && key != K_ESC) {
		mutex_lock(&ui__lock);

		if (key == K_BKSPC) {
			if (len == 0) {
				mutex_unlock(&ui__lock);
				goto next_key;
			}
			SLsmg_gotorc(y, x + --len);
			SLsmg_write_char(' ');
		} else {
			buf[len] = key;
			SLsmg_gotorc(y, x + len++);
			SLsmg_write_char(key);
		}
		SLsmg_refresh();

		mutex_unlock(&ui__lock);

		/* XXX more graceful overflow handling needed */
		if (len == sizeof(buf) - 1) {
			ui_helpline__push("maximum size of symbol name reached!");
			key = K_ENTER;
			break;
		}
next_key:
		key = ui__getch(delay_secs);
	}

	buf[len] = '\0';
	strncpy(input, buf, len+1);
	return key;
}

void __ui__info_window(const char *title, const char *text, const char *exit_msg)
{
	int x, y;
	int max_len = 0, nr_lines = 0;
	const char *t;

	t = text;
	while (1) {
		const char *sep = strchr(t, '\n');
		int len;

		if (sep == NULL)
			sep = strchr(t, '\0');
		len = sep - t;
		if (max_len < len)
			max_len = len;
		++nr_lines;
		if (*sep == '\0')
			break;
		t = sep + 1;
	}

	max_len += 2;
	nr_lines += 2;
	if (exit_msg)
		nr_lines += 2;
	y = SLtt_Screen_Rows / 2 - nr_lines / 2,
	x = SLtt_Screen_Cols / 2 - max_len / 2;

	SLsmg_set_color(0);
	SLsmg_draw_box(y, x++, nr_lines, max_len);
	if (title) {
		SLsmg_gotorc(y, x + 1);
		SLsmg_write_string(title);
	}
	SLsmg_gotorc(++y, x);
	if (exit_msg)
		nr_lines -= 2;
	max_len -= 2;
	SLsmg_write_wrapped_string((unsigned char *)text, y, x,
				   nr_lines, max_len, 1);
	if (exit_msg) {
		SLsmg_gotorc(y + nr_lines - 2, x);
		SLsmg_write_nstring(" ", max_len);
		SLsmg_gotorc(y + nr_lines - 1, x);
		SLsmg_write_nstring(exit_msg, max_len);
	}
}

void ui__info_window(const char *title, const char *text)
{
	mutex_lock(&ui__lock);
	__ui__info_window(title, text, NULL);
	SLsmg_refresh();
	mutex_unlock(&ui__lock);
}

int ui__question_window(const char *title, const char *text,
			const char *exit_msg, int delay_secs)
{
	mutex_lock(&ui__lock);
	__ui__info_window(title, text, exit_msg);
	SLsmg_refresh();
	mutex_unlock(&ui__lock);
	return ui__getch(delay_secs);
}

int ui__help_window(const char *text)
{
	return ui__question_window("Help", text, "Press any key...", 0);
}

int ui__dialog_yesno(const char *msg)
{
	return ui__question_window(NULL, msg, "Enter: Yes, ESC: No", 0);
}

static int __ui__warning(const char *title, const char *format, va_list args)
{
	char *s;

	if (vasprintf(&s, format, args) > 0) {
		int key;

		key = ui__question_window(title, s, "Press any key...", 0);
		free(s);
		return key;
	}

	fprintf(stderr, "%s\n", title);
	vfprintf(stderr, format, args);
	return K_ESC;
}

static int perf_tui__error(const char *format, va_list args)
{
	return __ui__warning("Error:", format, args);
}

static int perf_tui__warning(const char *format, va_list args)
{
	return __ui__warning("Warning:", format, args);
}

struct perf_error_ops perf_tui_eops = {
	.error		= perf_tui__error,
	.warning	= perf_tui__warning,
};
