(function () {
    if (context.file === undefined) {
        alert("You have to execute this macros on WLOG file");
        return;
    }

    const executor = new AsyncExecutor();
    const form = context.view = new FormView();
    const fan = new RangeView("Fan speed", "Set hotend temp to this value", 100, 0, 100, true, "%");
    form.append(fan);

    const endTemp = new RangeView("Hotend temp", "Set hotend temp to this value", 190, 100, 240, true, "°C");
    form.append(endTemp);

    const bedTemp = new RangeView("Bed temp", "Set bed temp to this value", 60, 20, 100, true, "°C");
    form.append(bedTemp);

    const speed = new TextInputView("Speed", "Movement rate on work cycle (mm/s)", 900, 100);
    form.append(speed);
    const status = new TextView("Configure setup");
    form.append(new ButtonView("Start", function (view) {
        view.enabled = false;
        endTemp.enabled = false;
        bedTemp.enabled = false;
        speed.enabled = false;
        fan.enabled = false;
        status.text = "Starting...";
        executor.yield();
    }));


    form.append(status);

    executor.addTask(function () {
        JSONRPC.PrintService.stopEverything(function () {
            executor.yield();
        });
    });

    //set hotend temp
    executor.addGcode("M104 S" + endTemp.value, false);
    //set bed temp
    executor.addGcode("M140 S" + bedTemp.value, true);
    //wait for heat
    executor.waitForHotendTemp(endTemp.value);
    executor.addGcode("G91", true);
    //move Z to +20mm
    executor.addGcode("G0 F6000 Z20", true);
    //home Y
    executor.addGcode("G28 Y", true);
    //home X
    executor.addGcode("G28 X", true);
    //home Z
    executor.addGcode("G28 Z", true);
    //set E zero position
    executor.addGcode("G92 E0", true);

    //wait for heat
    executor.waitForBedTemp(bedTemp.value);

    //set absolute positioning
    executor.addGcode("G90", true);

    //move Z to last position + 20mm
    executor.addGcode("G1 F700 Z" + (20.0 + context.position.z), true);

    //extrude some filament
    executor.addGcode("G1 E20", true);

    //move to last position XY
    executor.addGcode("G1 F700 X" + context.position.x + " Y" + context.position.y, true);

    //move to last position Z
    executor.addGcode("G1 F700 Z" + context.position.z, true);

    //initial setup for printing
    executor.addGcode("G1 F" + speed.value, true);
    executor.addGcode("M82", true);
    executor.addGcode("M106 S" + fan.value * 255 / 100, true);


    //continue printing
    executor.addTask(function () {
        JSONRPC.PrintService.printFile(context.file, context.line, function () {
            status.text = "Printing started!";
            executor.yield();
        });
    });

    executor.addTask(function () {
        setTimeout(function () {
            form.destroy();
        }, 10000);
    });
})();