In the code below you will se a page showing:
a canvas named "# of Lines";
a slider (min 1, max 360, step 1);
By moving the slider, you can display from 1 to 360 lines on the canvas.
There are four entry fields, representing values for the slider:
Value From (default), Value To (default), Increment (default), and Speed (ms).
These fields are used to run two processes:
An animation, which automatically displays consecutive images on the canvas,
from "Value From" to "Value To" with the "Increment" value from one image to the next,
at the speed indicated by Speed, or
Saving subsequent images using the same parameters.
The question I have is about the second process:
If you click on "Run Saving Images", the following will happen:
Two windows open:

One asks: "This file is asking you to download multiple files allow block". This window might not open, depending on your settings (see the "You can change your site permissions at any time.")
The other window:

asks where and with what name the image must be saved. The main question I ask is: Is it possible to bypass this window and let the image be saved with the suggested name? This is because I want to avoid having to click on "Save" 50 times if the sequence of images numbers 50. Here is the code:
var TAU = 2 * Math.PI;
var DEGTORAD = TAU / 360.0;
var num_of_lines = 1;
var caller_first_name = "number_of_lines_";
function update() {
// console.log("In update...");
var preview_canvas = document.getElementById('preview_canvas');
var ctx_preview = preview_canvas.getContext('2d');
var width_preview = parseFloat(preview_canvas.width);
var height_preview = parseFloat(preview_canvas.height);
var X_center_preview = width_preview / 2;
var Y_center_preview = height_preview / 2;
// CLEAR THE CANVAS
preview_canvas.width = preview_canvas.width;
ctx_preview.lineWidth = 1;
document.getElementById("number_of_lines_value").innerHTML = document.getElementById("number_of_lines_id").value;
number_of_lines = parseFloat(document.getElementById('number_of_lines_id').value);
for (angle = 0; angle <= TAU; angle += TAU / number_of_lines) {
draw_line(ctx_preview, X_center_preview, Y_center_preview, X_center_preview + X_center_preview * Math.cos(angle), Y_center_preview + Y_center_preview * Math.sin(angle), ctx_preview.lineWidth, "red");
}
} // end of update(0) function
// end of update(0) function
function init() {
document.getElementById('number_of_lines_id').oninput = update;
update();
} // end of init() function
// end of init() function
window.onload = init;
function draw_line(ctx_given, x_from, y_from, x_to, y_to, line_width, line_color) {
ctx_given.lineWidth = line_width;
ctx_given.strokeStyle = line_color;
ctx_given.beginPath();
ctx_given.moveTo(x_from, y_from);
ctx_given.lineTo(x_to, y_to);
ctx_given.stroke();
ctx_given.closePath();
} // end of draw_line(6) function
// end of draw_line(6) function
function prepare_animation_or_saving_images(caller) {
// console.log("caller: " + caller + ":" + caller_first_name + "id");
document.getElementById(caller_first_name + "id").value = document.getElementById(caller_first_name + "value_to_use_from").value;
document.getElementById(caller_first_name + "value").innerHTML = document.getElementById(caller_first_name + "id").value;
stop_animation = false;
if (caller == "animation") {
run_animation();
} else {
save_images_set();
}
}
function run_animation() {
// console.log("In Run Animation and running for this parameter: " + Rows[document.getElementById("parameter_select_id").value].id);
// console.log("And I have\nfrom: " + parseFloat(document.getElementById(caller_first_name + "value_to_use_from").value) + " and\nto: " + parseFloat(document.getElementById(caller_first_name + "value_to_use_to").value) + " and\ninc: " + parseFloat(document.getElementById(caller_first_name + "value_to_use_inc").value));
update();
document.getElementById(caller_first_name + "id").value = parseFloat(document.getElementById(caller_first_name + "id").value) + parseFloat(document.getElementById(caller_first_name + "value_to_use_inc").value);
if ((document.getElementById(caller_first_name + "id").value <= parseFloat(document.getElementById(caller_first_name + "value_to_use_to").value)) && (!stop_animation)) {
// console.log("speed value: " + document.getElementById("speed_value").value + " of type: " + typeof(document.getElementById("speed_value").value));
setTimeout(run_animation, document.getElementById("speed_value").value);
}
}
var file_name_number = 1;
// This function is called when the "Save Image Set" button is clicked on
function save_images_set() {
console.log(caller_first_name + "id is " + document.getElementById(caller_first_name + "id").value + " of type: " + typeof(document.getElementById(caller_first_name + "id").value))
// document.getElementById(caller_first_name + "id").value = 3;
update();
document.getElementById(caller_first_name + "id").value = parseFloat(document.getElementById(caller_first_name + "id").value) + parseFloat(document.getElementById(caller_first_name + "value_to_use_inc").value);
file_name_number_string = file_name_number.toString().padStart(3, "0");
save_canvas_as_image(caller_first_name + file_name_number_string);
file_name_number += 1;
// document.getElementById(caller_first_name + "id").value = parseFloat(document.getElementById(caller_first_name + "id").value) + 3;
if ((document.getElementById(caller_first_name + "id").value <= parseFloat(document.getElementById(caller_first_name + "value_to_use_to").value)) && (!stop_animation)) {
console.log("speed value: " + document.getElementById("speed_value").value + " of type: " + typeof(document.getElementById("speed_value").value));
setTimeout(save_images_set, document.getElementById("speed_value").value);
}
}
function save_canvas_as_image(image_name) {
// This code will automatically save the current canvas as a .png file.
// Its useful as it can be placed in a loop to grab multiple canvas frames, I use it to create thumbnail gifs for my blog
// Only seems to work with Chrome
// From https://gist.github.com/Kaundur/2aca9a9edb003555f44195e826af4084
console.log("In save canvas as image");
// Get the canvas
var preview_canvas = document.getElementById("preview_canvas");
// Convert the preview_canvas to data
var image = preview_canvas.toDataURL();
// Create a link
var aDownloadLink = document.createElement('a');
// Add the name of the file to the link
aDownloadLink.download = image_name + '.png';
// Attach the data to the link
aDownloadLink.href = image;
// Get the code to click the download link
aDownloadLink.click();
}
document.getElementById("number_of_lines_min").innerHTML = document.getElementById("number_of_lines_id").getAttribute("min");
document.getElementById("number_of_lines_max").innerHTML = document.getElementById("number_of_lines_id").getAttribute("max");
document.getElementById("number_of_lines_inc").innerHTML = document.getElementById("number_of_lines_id").getAttribute("step");
input[type=range] {
width: 510px;
}
body {
background-color: #9a9a9a;
}
.title_div {
float: left;
width: 200px;
color: white;
margin-bottom: 5px;
margin-left: 20px;
background-color: red;
padding-bottom: 5px;
}
.top_div {
float: left;
background-color: rgb(255, 255, 255);
width: 503px;
height: 500px;
margin-left: 20px;
margin-bottom: 50px;
}
<div class="top_div">
<canvas id="preview_canvas" width=500; height=500; class="preview_canvas_style"></canvas><br/>
</div><!-- end of preview_canvas div -->
<div class="title_div">
<span class="title_span">Minimal</span>
</div><!-- end of title div -->
<!-- Number of lines Slider -->
<div class="all_params_divs">
<div style="width: 120px;">
<span class="param_name_span_black"><span id="number_of_lines_reset" onclick="reset_parameter('number_of_lines_')" style="cursor: pointer;"> # of Lines</span></span>
</div>
<div id="number_of_lines_value" class="slider_value_div_black"><!-- value put here later -->
</div>
<div class="slidercontainer">
<div>
<input type="range" id="number_of_lines_id" min="1" max="360" value="7" step="1" class="slider">
</div>
</div>
</div>
<div>
<!-- <span class="TableHead">
# of Lines -->
<span class="TableHead">
Value From (default)
</span>
<span class="TableHead">
Value To (default)
</span>
<span class="TableHead">
Increment (default)
</span>
</div>
<input type="text" size="6" id="number_of_lines_value_to_use_from" value="1"/> (<span id="number_of_lines_min"></span>)
<input type="text" size="6" id="number_of_lines_value_to_use_to" value="17"/> (<span id="number_of_lines_max"></span>)
<input type="text" size="6" id="number_of_lines_value_to_use_inc" value="1"/> (<span id="number_of_lines_inc"></span>) <span class="TableHead">Speed (ms): <input type="number" style="width: 55px;" id="speed_value" value="100"/></span><br/><br/>
<input type="button" value="Run Animation" onclick="prepare_animation_or_saving_images('animation');"/> <input type="button" value="Run Saving Images" onclick="prepare_animation_or_saving_images('save_image_set');"/> <span onclick="stop_animation = true;" style="cursor: pointer;"> Stop Animation</span>