import { NgForOf, NgIf } from '@angular/common';
import { ChangeDetectorRef, Component, inject } from '@angular/core';
import { FormBuilder, FormGroup, ReactiveFormsModule } from '@angular/forms';
import { MatCheckbox } from '@angular/material/checkbox';
import { MatFormField } from '@angular/material/form-field';
import { MatOption, MatSelect } from '@angular/material/select';
import { BaseFormComponent } from '@common-ui/form';
import { AsControl } from '@common-ui/utils';
import { IconButtonComponent } from '@iqser/common-ui';
import { TranslateModule } from '@ngx-translate/core';
import { PreferencesKeys, UserPreferenceService } from '@users/user-preference.service';
import {
    RedactOrHintOption,
    RedactOrHintOptions,
    RemoveRedactionOption,
    RemoveRedactionOptions,
} from '../../../../file-preview/utils/dialog-types';
import {
    hintAddOptions,
    recommendationRemoveOptions,
    redactionAddOptions,
    redactionRemoveOptions,
    removeOptions,
    SystemDefaultType,
} from '../../../utils/dialog-defaults';

interface DefaultOptionsForm {
    addRedaction: RedactOrHintOption | SystemDefaultType;
    addHint: RedactOrHintOption | SystemDefaultType;
    removeRedaction: RemoveRedactionOption | SystemDefaultType;
    removeRecommendation: RemoveRedactionOption | SystemDefaultType;
    removeHint: RemoveRedactionOption | SystemDefaultType;
    addRedactionApplyToAll: boolean;
    removeRedactionApplyToAll: boolean;
    removeRecommendationApplyToAll: boolean;
    addHintApplyToAll: boolean;
    removeHintApplyToAll: boolean;
}

@Component({
    selector: 'redaction-dialog-defaults',
    templateUrl: './dialog-defaults.component.html',
    styleUrl: './dialog-defaults.component.scss',
    standalone: true,
    imports: [ReactiveFormsModule, TranslateModule, MatFormField, MatSelect, MatOption, NgForOf, MatCheckbox, NgIf, IconButtonComponent],
})
export class DialogDefaultsComponent extends BaseFormComponent {
    readonly #formBuilder = inject(FormBuilder);
    readonly #userPreferences = inject(UserPreferenceService);
    readonly #changeDetectorRef = inject(ChangeDetectorRef);
    form: FormGroup<AsControl<DefaultOptionsForm>> = this.#formBuilder.group({
        addRedaction: this.#userPreferences.getAddRedactionDefaultOption(),
        addHint: this.#userPreferences.getAddHintDefaultOption(),
        removeRedaction: this.#userPreferences.getRemoveRedactionDefaultOption(),
        removeRecommendation: this.#userPreferences.getRemoveRecommendationDefaultOption(),
        removeHint: this.#userPreferences.getRemoveHintDefaultOption(),
        addRedactionApplyToAll: this.#userPreferences.getBool(PreferencesKeys.addRedactionDefaultExtraOption),
        removeRedactionApplyToAll: this.#userPreferences.getBool(PreferencesKeys.removeRedactionDefaultExtraOption),
        removeRecommendationApplyToAll: this.#userPreferences.getBool(PreferencesKeys.removeRecommendationDefaultExtraOption),
        addHintApplyToAll: this.#userPreferences.getBool(PreferencesKeys.addHintDefaultExtraOption),
        removeHintApplyToAll: this.#userPreferences.getBool(PreferencesKeys.removeHintDefaultExtraOption),
    });
    initialFormValue = this.form.getRawValue();

    readonly redactionAddOptions = redactionAddOptions;
    readonly hintAddOptions = hintAddOptions;
    readonly removeOptions = removeOptions;
    readonly redactionRemoveOptions = redactionRemoveOptions;
    readonly recommendationRemoveOptions = recommendationRemoveOptions;

    constructor() {
        super();
    }

    get displayExtraOptionAddRedaction() {
        return RedactOrHintOptions.IN_DOSSIER === this.form.controls.addRedaction.value;
    }

    get displayExtraOptionAddHint() {
        return RedactOrHintOptions.IN_DOSSIER === this.form.controls.addHint.value;
    }

    get displayExtraOptionRemoveRedaction() {
        return (
            [RemoveRedactionOptions.IN_DOSSIER, RemoveRedactionOptions.FALSE_POSITIVE] as Partial<
                RemoveRedactionOption | SystemDefaultType
            >[]
        ).includes(this.form.controls.removeRedaction.value);
    }

    get displayExtraOptionRemoveHint() {
        return RemoveRedactionOptions.IN_DOSSIER === this.form.controls.removeHint.value;
    }

    get displayExtraOptionRemoveRecommendation() {
        return RemoveRedactionOptions.DO_NOT_RECOMMEND === this.form.controls.removeRecommendation.value;
    }

    async save(): Promise<any> {
        const formValue = this.form.value;

        if (this.initialFormValue.addRedaction !== this.form.controls.addRedaction.value) {
            await this.#userPreferences.saveAddRedactionDefaultOption(this.form.controls.addRedaction.value);
        }
        if (this.initialFormValue.addHint !== this.form.controls.addHint.value) {
            await this.#userPreferences.saveAddHintDefaultOption(this.form.controls.addHint.value);
        }
        if (this.initialFormValue.removeRedaction !== this.form.controls.removeRedaction.value) {
            await this.#userPreferences.saveRemoveRedactionDefaultOption(this.form.controls.removeRedaction.value);
        }
        if (this.initialFormValue.removeRecommendation !== this.form.controls.removeRecommendation.value) {
            await this.#userPreferences.saveRemoveRecommendationDefaultOption(this.form.controls.removeRecommendation.value);
        }
        if (this.initialFormValue.removeHint !== this.form.controls.removeHint.value) {
            await this.#userPreferences.saveRemoveHintDefaultOption(this.form.controls.removeHint.value);
        }

        if (this.displayExtraOptionAddRedaction) {
            if (this.initialFormValue.addRedactionApplyToAll !== this.form.controls.addRedactionApplyToAll.value) {
                await this.#userPreferences.saveAddRedactionDefaultExtraOption(this.form.controls.addRedactionApplyToAll.value);
            }
        } else {
            await this.#userPreferences.saveAddRedactionDefaultExtraOption('undefined');
        }

        if (this.displayExtraOptionAddHint) {
            if (this.initialFormValue.addHintApplyToAll !== this.form.controls.addHintApplyToAll.value) {
                await this.#userPreferences.saveAddHintDefaultExtraOption(this.form.controls.addHintApplyToAll.value);
            }
        } else {
            await this.#userPreferences.saveAddHintDefaultExtraOption('undefined');
        }

        if (this.displayExtraOptionRemoveRedaction) {
            if (this.initialFormValue.removeRedactionApplyToAll !== this.form.controls.removeRedactionApplyToAll.value) {
                await this.#userPreferences.saveRemoveRedactionDefaultExtraOption(this.form.controls.removeRedactionApplyToAll.value);
            }
        } else {
            await this.#userPreferences.saveRemoveRedactionDefaultExtraOption('undefined');
        }

        if (this.displayExtraOptionRemoveHint) {
            if (this.initialFormValue.removeHintApplyToAll !== this.form.controls.removeHintApplyToAll.value) {
                await this.#userPreferences.saveRemoveHintDefaultExtraOption(this.form.controls.removeHintApplyToAll.value);
            }
        } else {
            await this.#userPreferences.saveRemoveHintDefaultExtraOption('undefined');
        }

        if (this.displayExtraOptionRemoveRecommendation) {
            if (this.initialFormValue.removeRecommendationApplyToAll !== this.form.controls.removeRecommendationApplyToAll.value) {
                await this.#userPreferences.saveRemoveRecommendationDefaultExtraOption(
                    this.form.controls.removeRecommendationApplyToAll.value,
                );
            }
        } else {
            await this.#userPreferences.saveRemoveRecommendationDefaultExtraOption('undefined');
        }

        await this.#userPreferences.reload();
        this.#patchValues();
        this.initialFormValue = this.form.getRawValue();
        this.#changeDetectorRef.markForCheck();
    }

    #patchValues() {
        this.form.patchValue({
            addRedaction: this.#userPreferences.getAddRedactionDefaultOption(),
            addHint: this.#userPreferences.getAddHintDefaultOption(),
            removeRedaction: this.#userPreferences.getRemoveRedactionDefaultOption(),
            removeRecommendation: this.#userPreferences.getRemoveRecommendationDefaultOption(),
            removeHint: this.#userPreferences.getRemoveHintDefaultOption(),
            addRedactionApplyToAll: this.#userPreferences.getBool(PreferencesKeys.addRedactionDefaultExtraOption),
            removeRedactionApplyToAll: this.#userPreferences.getBool(PreferencesKeys.removeRedactionDefaultExtraOption),
            removeRecommendationApplyToAll: this.#userPreferences.getBool(PreferencesKeys.removeRecommendationDefaultExtraOption),
            addHintApplyToAll: this.#userPreferences.getBool(PreferencesKeys.addHintDefaultExtraOption),
            removeHintApplyToAll: this.#userPreferences.getBool(PreferencesKeys.removeHintDefaultExtraOption),
        });
    }
}
