We've implemented a custom editor service that opens a new editor on go to a reference event and returns it. If an opened editor is different from the current then ReferencesController focuses the current. In our case the current is not visible by that moment and calling focus on an underlying text area does not take effect, but View.hasFocus is set to true and the current editor is still considered to be focused. It leads to a bogus state with 2 focused editors simultaneously and other undesired effects, like typing in the opened editor applies changes to another editor.
It looks like a bug in View.focus, it should not set View.hasFocus to true if a text area cannot be focused.
It should be reproducible with 2 editors: one invisible and another visible.
The invisible editor should be focused programmatically, after that the visible editor should be focused by the user.
I expect that typing in the visible editor won't do anything, since the code editor service will pick the invisible editor as a focused and apply all edits to it.
I could reproduce with the following snippet:
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta http-equiv="Content-Type" content="text/html;charset=utf-8" />
</head>
<body>
<h2>Monaco Editor in fixed element</h2>
<div style="display:none; position: absolute; left: 100px; top: 100px; width: 300px; height: 200px; border:1px solid silver" id="Editor1"></div>
<div style="position: absolute; left: 500px; top: 100px; width: 300px; height: 200px; border:1px solid silver" id="Editor2"></div>
<script src="../metadata.js"></script>
<script src="dev-setup.js"></script>
<script>
loadEditor(function() {
var editor1 = monaco.editor.create(document.getElementById('Editor1'), {
value: 'editor1',
language: 'xml'
});
var editor2 = monaco.editor.create(document.getElementById('Editor2'), {
value: 'editor2',
language: 'xml'
});
setTimeout(function() {
editor1.focus();
console.log('FOCUSED editor1, try clicking in editor2 and typing');
}, 100);
});
</script>
</body>
</html>
Most helpful comment
I could reproduce with the following snippet: