import {
	FormWidgetType,
} from "qrc:/js/lib/generated/enum";
import {itemAt} from "./array_util";

/**
 * Type-safe wrapper to create a check box form row
 */
export function createCheckBoxRow(key: string, name: string, initialValue: boolean): FormRowConfig {
	const configContent: FormWidgetCheckBoxConfig = {
		initialValue: initialValue,
	};

	const config: FormWidgetConfig = {
		type: FormWidgetType.checkBox,
		content: configContent,
	};

	return {
		key: key,
		name: name,
		config: config,
	};
}

export interface SpinBoxConfigParams {
	key: string;
	name: string;
	min: number;
	max: number;
	decimals: number;
	initialValue: number;
}

/**
 * Type-safe wrapper to create a spin box form row
 */
export function createSpinBoxRow(params: Readonly<SpinBoxConfigParams>): FormRowConfig {
	const configContent: FormWidgetSpinBoxConfig = {
		min: params.min,
		max: params.max,
		decimals: params.decimals,
		initialValue: params.initialValue,
	};

	const config: FormWidgetConfig = {
		type: FormWidgetType.spinBox,
		content: configContent,
	};

	return {
		key: params.key,
		name: params.name,
		config: config,
	};
}

export interface CheckBoxConfigParams<T> {
	key: string;
	name: string;
	values: readonly Readonly<T>[];
	toId(arg: Readonly<T>): string;
	toName(arg: Readonly<T>): string;
	computeInitialValueIndex(arg: readonly Readonly<T>[]): number;
}

/**
 * Type-safe wrapper to create a drop down form row
 */
export function createDropDownRow<T>(params: Readonly<CheckBoxConfigParams<T>>): FormRowConfig {
	const configContent: FormWidgetDropDownConfig = (() => {
		const entries = params.values.map(value => ({
			id: params.toId(value),
			text: params.toName(value),
		}));

		const initialValue = (() => {
			const index = Math.max(
				0,
				Math.min(
					params.values.length - 1,
					params.computeInitialValueIndex(params.values),
				),
			);
			return params.toId(itemAt(index, params.values));
		})();

		return {
			entries: entries,
			initialValue: initialValue,
		};
	})();

	const config: FormWidgetConfig = {
		type: FormWidgetType.dropDown,
		content: configContent,
	};

	return {
		key: params.key,
		name: params.name,
		config: config,
	};
}

/**
 * Type-safe wrapper to create a line edit form row
 */
export function createLineEditRow(key: string, name: string, initialValue: string): FormRowConfig {
	const configContent: FormWidgetLineEditConfig = {
		initialValue: initialValue,
	};

	const config: FormWidgetConfig = {
		type: FormWidgetType.lineEdit,
		content: configContent,
	};

	return {
		key: key,
		name: name,
		config: config,
	};
}

/**
 * Type-safe wrapper to create a text edit form row
 */
export function createTextEditRow(key: string, name: string, initialValue: string): FormRowConfig {
	const configContent: FormWidgetTextEditConfig = {
		initialValue: initialValue,
	};

	const config: FormWidgetConfig = {
		type: FormWidgetType.textEdit,
		content: configContent,
	};

	return {
		key: key,
		name: name,
		config: config,
	};
}

/**
 * Type-safe wrapper to create a label form row
 */
export function createLabelRow(key: string, name: string, initialValue: string): FormRowConfig {
	const configContent: FormWidgetLabelConfig = {
		initialValue: initialValue,
	};

	const config: FormWidgetConfig = {
		type: FormWidgetType.label,
		content: configContent,
	};

	return {
		key: key,
		name: name,
		config: config,
	};
}
