import { shell, dialog, app, BrowserWindow, OpenDialogOptions } from "electron";
import { NotificationService } from "../services/notification.service";
import { IpcService } from "../services/ipc.service";
import { from, of } from "rxjs";
import { readFileSync } from "fs-extra";
import log from "electron-log";
import path from "path";

// TODO IMPROVE WINDOW CONTROL BY USING WINDOW SERVICE

const ipc = IpcService.getInstance();

ipc.on("new-window", (args, reply) => {
    reply(from(shell.openExternal(args)));
});

ipc.on("open-dialog", (args, reply) => {
    // Use this ipc instead of "choose-folder" or "choose-file" to have more control over the dialog
    reply(from(dialog.showOpenDialog(args)));
})

ipc.on("choose-folder", (args, reply) => {
    const options: OpenDialogOptions = {
        properties: ["openDirectory"],
        defaultPath: args?.defaultPath ?? ""
    };

    if (args?.showHidden) {
        options.properties.push("showHiddenFiles");
    }

    if (args?.parent) {
        options.defaultPath = path.join(app.getPath(args.parent), options.defaultPath);
    }

    reply(from(dialog.showOpenDialog(options)));
});

ipc.on("choose-file", async (args, reply) => {
    reply(from(dialog.showOpenDialog({ properties: ["openFile"], defaultPath: args ?? "" })));
});

ipc.on("window.progression",(args, reply, sender) => {
    BrowserWindow.fromWebContents(sender)?.setProgressBar(args / 100);
    reply(of(undefined));
});

ipc.on("save-file", (args, reply) => {
    reply(from(dialog.showSaveDialog({ properties: ["showOverwriteConfirmation"], defaultPath: args.filename, filters: args.filters }).then(res => {
        if (res.canceled || !res.filePath) {
            throw new Error("No file path selected");
        }
        return res.filePath;
    })));
});

ipc.on("current-version", (_, reply) => {
    reply(of(app.getVersion()));
});

ipc.on("open-logs", (_, reply) => {
    reply(from(shell.openPath(app.getPath("logs"))));
});

ipc.on("notify-system", (args, reply) => {
    const systemNotification = NotificationService.getInstance();
    reply(of(systemNotification.notify(args)));
});

ipc.on("view-path-in-explorer", (args, reply) => {
    reply(of(shell.showItemInFolder(args)));
});

ipc.on("choose-image", (args, reply) => {
    reply(from(dialog.showOpenDialog({ properties: ["openFile", "multiSelections"], filters: [{ name: "Images", extensions: ["jpg", "png", "jpeg"] }] }).then(res => {
        if (res.canceled || !res.filePaths) {
            return [];
        }
        if(args.base64){
            return res.filePaths.map(path => Buffer.from(readFileSync(path)).toString("base64"));
        }
        return res.filePaths;
    })));
});

ipc.on("restart-app", (_, reply) => {
    log.info("App was requested to restart");

    reply(of()); // Reply before restarting to avoid any issue

    app.relaunch();
    app.quit();
});
