I am wanting to replace Magento's implementation of the alert() and confirm() dialog boxes. While the alert() replacement was trivial, I am unsure of how to handle the confirm() dialog. Is there a way to prevent JavaScript from continuing until a function is returned? Will this require looping that could crash a browser?
So for example, I need to replace code like this:
<form action="" method="POST">
<input type="submit" onclick="return confirm('Are you sure?');" value="Delete">
</form>
with...
<form action="" method="POST">
<input type="submit" onclick="return myCustomConfirm('Are you sure?');" value="Delete">
</form>
Or other scenarios such as:
<script>
var delete = confirm('Are you sure?');
if (delete) {
doSomething();
}
</script>
with...
<script>
var delete = myCustomConfirm('Are you sure?');
if (delete) {
doSomething();
}
</script>
In both scenarios, myCustomConfirm() will open a Bootstrap modal where the user must click "Okay", "Cancel", or close the modal. The value returns true if "Okay" and false if otherwise.
I don't want to do callbacks as that will cause more refactoring than desirable. Is this possible to do in another way?
Thanks!
It is not possible. You cannot write a JavaScript function that blocks execution, gathers user input and returns a value based on user input. The only way to block execution and wait for user input is to use confirm.
You have to refactor your code to use callbacks if you want to use custom dialogs.
See Emulate Javascript 'alert' blocking nature
You can do something similar to this using async/await which is part of ES7.
async function stepTwo()
{
return new Promise((resolve) =>
{
let stop = false;
$('input[type=checkbox]').one('change', (event) =>
{
// Will only stop the loop when the checkbox is checked
if (event.target.checked === true)
{
stop = true;
}
});
loop();
// Continues looping until stop is set to true (i.e. input has been done)
function loop()
{
if (stop === true)
{
resolve();
return;
}
// Keeps checking if stop is true
setTimeout(loop, 100);
}
});
}
async function stepOne()
{
$('div').text('Waiting for input..');
// Waits for promise returned from stepTwo() to resolve
await stepTwo();
$('div').text('Input checked!');
}
// Starts the async function (any lines below this continue execution)
stepOne();
Fiddle: https://jsfiddle.net/1rvn5bfp/7/
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With