The Chrome Developer Console won't call the user-defined error event listener if the error is thrown immediately (according to this answer by Paul S.).
Throwing the error "just in time":
> window.onerror = function () {console.log('error!');};
function () {console.log('error!');}
> throw new Error();
Error
Throwing the error deferred:
> window.setTimeout(function() {throw new Error()}, 0);
xxxx
error!
Uncaught Error
(xxxx is the specific return value of setTimeout())
Here is the original code snippet which led me to the point that the Chrome Dev Console changes the internal behaviour somehow:
// #btn is a simple button
document.getElementById("btn").addEventListener("click", function () {
var script = document.createElement("script");
script.innerHTML = "window.onerror=function(){alert('An error occurred!');};throw new Error('42');";
document.head.appendChild(script);
});
This code is to be executed in a normal HTML file.