fix: emit focus/blur events for webview (#14344)
* fix: emit focus/blur events for webview * test: webview can emit focus event
This commit is contained in:
parent
edd5c4b9bb
commit
459a2304b4
5 changed files with 53 additions and 21 deletions
|
@ -30,6 +30,7 @@ class WebViewImpl {
|
|||
v8Util.setHiddenValue(this.webviewNode, 'internal', this)
|
||||
this.elementAttached = false
|
||||
this.beforeFirstNavigation = true
|
||||
this.hasFocus = false
|
||||
|
||||
// Check for removed attributes.
|
||||
for (const attributeName of removedAttributes) {
|
||||
|
@ -41,13 +42,21 @@ class WebViewImpl {
|
|||
// on* Event handlers.
|
||||
this.on = {}
|
||||
|
||||
// Create internal iframe element.
|
||||
this.internalElement = this.createInternalElement()
|
||||
const shadowRoot = this.webviewNode.attachShadow({mode: 'open'})
|
||||
shadowRoot.innerHTML = '<!DOCTYPE html><style type="text/css">:host { display: flex; }</style>'
|
||||
this.setupWebViewAttributes()
|
||||
this.setupFocusPropagation()
|
||||
this.viewInstanceId = getNextId()
|
||||
shadowRoot.appendChild(this.internalElement)
|
||||
|
||||
// Provide access to contentWindow.
|
||||
Object.defineProperty(this.webviewNode, 'contentWindow', {
|
||||
get: () => {
|
||||
return this.internalElement.contentWindow
|
||||
},
|
||||
enumerable: true
|
||||
})
|
||||
}
|
||||
|
||||
createInternalElement () {
|
||||
|
@ -91,26 +100,6 @@ class WebViewImpl {
|
|||
})
|
||||
}
|
||||
|
||||
setupFocusPropagation () {
|
||||
if (!this.webviewNode.hasAttribute('tabIndex')) {
|
||||
// <webview> needs a tabIndex in order to be focusable.
|
||||
// TODO(fsamuel): It would be nice to avoid exposing a tabIndex attribute
|
||||
// to allow <webview> to be focusable.
|
||||
// See http://crbug.com/231664.
|
||||
this.webviewNode.setAttribute('tabIndex', -1)
|
||||
}
|
||||
|
||||
// Focus the BrowserPlugin when the <webview> takes focus.
|
||||
this.webviewNode.addEventListener('focus', () => {
|
||||
this.internalElement.focus()
|
||||
})
|
||||
|
||||
// Blur the BrowserPlugin when the <webview> loses focus.
|
||||
this.webviewNode.addEventListener('blur', () => {
|
||||
this.internalElement.blur()
|
||||
})
|
||||
}
|
||||
|
||||
// This observer monitors mutations to attributes of the <webview> and
|
||||
// updates the BrowserPlugin properties accordingly. In turn, updating
|
||||
// a BrowserPlugin property will update the corresponding BrowserPlugin
|
||||
|
@ -185,6 +174,15 @@ class WebViewImpl {
|
|||
}
|
||||
}
|
||||
|
||||
// Emits focus/blur events.
|
||||
onFocusChange () {
|
||||
const hasFocus = document.activeElement === this.webviewNode
|
||||
if (hasFocus !== this.hasFocus) {
|
||||
this.hasFocus = hasFocus
|
||||
this.dispatchEvent(new Event(hasFocus ? 'focus' : 'blur'))
|
||||
}
|
||||
}
|
||||
|
||||
onAttach (storagePartitionId) {
|
||||
return this.attributes[webViewConstants.ATTRIBUTE_PARTITION].setValue(storagePartitionId)
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue