fix: navigator.keyboard.lock() fullscreen exit handling (#40365)
		
	fix: navigator.keyboard.lock() fullscreen exit handling
This commit is contained in:
		
					parent
					
						
							
								4b1c31e4db
							
						
					
				
			
			
				commit
				
					
						fcdd5cba71
					
				
			
		
					 5 changed files with 86 additions and 16 deletions
				
			
		|  | @ -1334,12 +1334,6 @@ bool WebContents::HandleKeyboardEvent( | |||
| bool WebContents::PlatformHandleKeyboardEvent( | ||||
|     content::WebContents* source, | ||||
|     const content::NativeWebKeyboardEvent& event) { | ||||
|   // Escape exits tabbed fullscreen mode.
 | ||||
|   if (event.windows_key_code == ui::VKEY_ESCAPE && is_html_fullscreen()) { | ||||
|     ExitFullscreenModeForTab(source); | ||||
|     return true; | ||||
|   } | ||||
| 
 | ||||
|   // Check if the webContents has preferences and to ignore shortcuts
 | ||||
|   auto* web_preferences = WebContentsPreferences::From(source); | ||||
|   if (web_preferences && web_preferences->ShouldIgnoreMenuShortcuts()) | ||||
|  |  | |||
|  | @ -42,12 +42,6 @@ bool WebContents::PlatformHandleKeyboardEvent( | |||
|       event.GetType() == content::NativeWebKeyboardEvent::Type::kChar) | ||||
|     return false; | ||||
| 
 | ||||
|   // Escape exits tabbed fullscreen mode. | ||||
|   if (event.windows_key_code == ui::VKEY_ESCAPE && is_html_fullscreen()) { | ||||
|     ExitFullscreenModeForTab(source); | ||||
|     return true; | ||||
|   } | ||||
| 
 | ||||
|   // Check if the webContents has preferences and to ignore shortcuts | ||||
|   auto* web_preferences = WebContentsPreferences::From(source); | ||||
|   if (web_preferences && web_preferences->ShouldIgnoreMenuShortcuts()) | ||||
|  |  | |||
|  | @ -606,6 +606,63 @@ describe('chromium features', () => { | |||
|     }); | ||||
|   }); | ||||
| 
 | ||||
|   describe('navigator.keyboard', () => { | ||||
|     afterEach(closeAllWindows); | ||||
| 
 | ||||
|     it('getLayoutMap() should return a KeyboardLayoutMap object', async () => { | ||||
|       const w = new BrowserWindow({ show: false }); | ||||
|       await w.loadFile(path.join(fixturesPath, 'pages', 'blank.html')); | ||||
|       const size = await w.webContents.executeJavaScript(` | ||||
|         navigator.keyboard.getLayoutMap().then(map => map.size) | ||||
|       `);
 | ||||
| 
 | ||||
|       expect(size).to.be.a('number'); | ||||
|     }); | ||||
| 
 | ||||
|     it('should lock the keyboard', async () => { | ||||
|       const w = new BrowserWindow({ show: false }); | ||||
|       await w.loadFile(path.join(fixturesPath, 'pages', 'modal.html')); | ||||
| 
 | ||||
|       // Test that without lock, with ESC:
 | ||||
|       // - the window leaves fullscreen
 | ||||
|       // - the dialog is not closed
 | ||||
|       const enterFS1 = once(w, 'enter-full-screen'); | ||||
|       await w.webContents.executeJavaScript('document.body.requestFullscreen()', true); | ||||
|       await enterFS1; | ||||
| 
 | ||||
|       await w.webContents.executeJavaScript('document.getElementById(\'favDialog\').showModal()', true); | ||||
|       const open1 = await w.webContents.executeJavaScript('document.getElementById(\'favDialog\').open'); | ||||
|       expect(open1).to.be.true(); | ||||
| 
 | ||||
|       w.webContents.sendInputEvent({ type: 'keyDown', keyCode: 'Escape' }); | ||||
|       await setTimeout(1000); | ||||
|       const openAfter1 = await w.webContents.executeJavaScript('document.getElementById(\'favDialog\').open'); | ||||
|       expect(openAfter1).to.be.true(); | ||||
|       expect(w.isFullScreen()).to.be.false(); | ||||
| 
 | ||||
|       // Test that with lock, with ESC:
 | ||||
|       // - the window does not leave fullscreen
 | ||||
|       // - the dialog is closed
 | ||||
|       const enterFS2 = once(w, 'enter-full-screen'); | ||||
|       await w.webContents.executeJavaScript(` | ||||
|         navigator.keyboard.lock(['Escape']); | ||||
|         document.body.requestFullscreen(); | ||||
|       `, true);
 | ||||
| 
 | ||||
|       await enterFS2; | ||||
| 
 | ||||
|       await w.webContents.executeJavaScript('document.getElementById(\'favDialog\').showModal()', true); | ||||
|       const open2 = await w.webContents.executeJavaScript('document.getElementById(\'favDialog\').open'); | ||||
|       expect(open2).to.be.true(); | ||||
| 
 | ||||
|       w.webContents.sendInputEvent({ type: 'keyDown', keyCode: 'Escape' }); | ||||
|       await setTimeout(1000); | ||||
|       const openAfter2 = await w.webContents.executeJavaScript('document.getElementById(\'favDialog\').open'); | ||||
|       expect(openAfter2).to.be.false(); | ||||
|       expect(w.isFullScreen()).to.be.true(); | ||||
|     }); | ||||
|   }); | ||||
| 
 | ||||
|   describe('navigator.languages', () => { | ||||
|     it('should return the system locale only', async () => { | ||||
|       const appLocale = app.getLocale(); | ||||
|  |  | |||
							
								
								
									
										26
									
								
								spec/fixtures/pages/modal.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										26
									
								
								spec/fixtures/pages/modal.html
									
										
									
									
										vendored
									
									
										Normal file
									
								
							|  | @ -0,0 +1,26 @@ | |||
| <!DOCTYPE html> | ||||
| <html lang="en"> | ||||
| 
 | ||||
| <body> | ||||
|   <dialog id="favDialog"> | ||||
|     <form> | ||||
|       <p> | ||||
|         <label> | ||||
|           Favorite animal: | ||||
|           <select> | ||||
|             <option value="default">Choose…</option> | ||||
|             <option>Brine shrimp</option> | ||||
|             <option>Red panda</option> | ||||
|             <option>Spider monkey</option> | ||||
|           </select> | ||||
|         </label> | ||||
|       </p> | ||||
|       <div> | ||||
|         <button value="cancel" formmethod="dialog">Cancel</button> | ||||
|         <button id="confirmBtn" value="default">Confirm</button> | ||||
|       </div> | ||||
|     </form> | ||||
|   </dialog> | ||||
| </body> | ||||
| 
 | ||||
| </html> | ||||
|  | @ -547,17 +547,16 @@ describe('<webview> tag', function () { | |||
|       await close; | ||||
|     }); | ||||
| 
 | ||||
|     // Sending ESC via sendInputEvent only works on Windows.
 | ||||
|     ifit(process.platform === 'win32')('pressing ESC should unfullscreen window', async () => { | ||||
|     it('pressing ESC should unfullscreen window', async () => { | ||||
|       const [w, webview] = await loadWebViewWindow(); | ||||
|       const enterFullScreen = once(w, 'enter-full-screen'); | ||||
|       await webview.executeJavaScript('document.getElementById("div").requestFullscreen()', true); | ||||
|       await enterFullScreen; | ||||
| 
 | ||||
|       const leaveFullScreen = once(w, 'leave-full-screen'); | ||||
|       w.webContents.sendInputEvent({ type: 'keyDown', keyCode: 'Escape' }); | ||||
|       webview.sendInputEvent({ type: 'keyDown', keyCode: 'Escape' }); | ||||
|       await leaveFullScreen; | ||||
|       await setTimeout(); | ||||
|       await setTimeout(1000); | ||||
|       expect(w.isFullScreen()).to.be.false(); | ||||
| 
 | ||||
|       const close = once(w, 'closed'); | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 Shelley Vohr
				Shelley Vohr