-
-
Save xiangwan/c95549295517d98fe29c43e62fd3eddd to your computer and use it in GitHub Desktop.
Revisions
-
Will Knowles created this gist
Jun 27, 2016 .There are no files selected for viewing
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -0,0 +1,96 @@ <!DOCTYPE html> <html> <head> <meta charset="utf-8"> <title>Test App</title> </head> <style> html, body { height: 100%; } body { margin: 0px; box-sizing: border-box; } #mount { width: 100%; height: 100%; } </style> <body> <div id="mount"></div> <script src="./node_modules/react/dist/react.js"></script> <script src="./node_modules/react-dom/dist/react-dom.js"></script> <scriot src="./node_modules/es6-shim/es6-shim.js"></script> <script src="./node_modules/babel-standalone/babel.js"></script> <script type="text/babel"> const { Component } = React; const { render } = ReactDOM; const { ipcRenderer } = require('electron'); const mount = document.getElementById('mount'); const containerStyle = { width: '100%', height: '100%', backgroundColor: 'white', textAlign: 'center', padding: '10px', boxSizing: 'border-box' }; class App extends Component { constructor () { super(...arguments); this.state = { counter: 0 }; } onClick () { this.setState({ counter: this.state.counter + 1 }); } setChildCss (rule) { ipcRenderer.send( 'ClickableRegion::set-child-css', `body { ${rule} !important; }` ); } render () { return ( <div style={containerStyle}> <p>This window has setIgnoreMouseEvents(true)</p> <h1>{ this.state.counter }</h1> { /** * One drawback here is that :hover css pseudoclass is not picked up * setChildCss is a hacky workaround which sets { cursor: pointer } * on the body of the transparent child */ } <button onClick={ () => this.onClick() } onMouseEnter={ () => this.setChildCss('cursor:pointer') } onMouseLeave={ () => this.setChildCss('cursor:initial') } > Click me </button> </div> ); } } render( <App/>, mount ); </script> </body> </html> This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -0,0 +1,94 @@ const { app, BrowserWindow, ipcMain } = require('electron'); const path = require('path'); const INDEX_HTML = path.join('file://', __dirname, 'index.html'); const TRANSPARENT_HTML = path.join('file://', __dirname, 'transparent.html'); const CHILD_PADDING = 50; const addClickableRegion = options => { const { parent } = options; const parentBounds = parent.getBounds(); const { width = parentBounds.width, height = parentBounds.height, x = 0, y = 0 } = options; // create a child window, setting the position based on the parent's bounds const childWindow = new BrowserWindow({ parent, x: parentBounds.x + x, y: parentBounds.y + y, width: width || parentBounds.width, height: height || parentBounds.height, // disable pretty much everything transparent: true, frame: false, skipTaskbar: true, movable: false, resizable: false, maximizable: false, minimizable: false }); // this is a dirty workaround to set the cursor style when hovering over the button ipcMain.on( 'ClickableRegion::set-child-css', (e, css) => childWindow.webContents.insertCSS(css) ); // When the transpoarent child captures a mouse event, it is forwarded to the parent // and mapped to it's coordinates ipcMain.on( 'ClickableRegion::mouse-event', (e, data) => { parent.webContents.sendInputEvent(Object.assign( data, { x: x + data.x, y: y + data.y } )); } ); childWindow.loadURL(TRANSPARENT_HTML); }; const onAppReady = function () { let parent = new BrowserWindow({ width: 300, height: 300, show: false, resizable: false, transparent: true, frame: false }); // make the parent window ignore all mouse events so we can click through it parent.setIgnoreMouseEvents(true); parent.once('close', () => { parent = null; }); parent.webContents.once('did-finish-load', () => { // add a transparent clickable child window to capture the mouse events addClickableRegion({ parent, x: CHILD_PADDING, y: CHILD_PADDING, width: 200, height: 200 }); // could do this in index.html parent.webContents.insertCSS(`body { padding:${CHILD_PADDING}px !important; }`); parent.show(); }); parent.loadURL(INDEX_HTML); }; app.on('ready', onAppReady); This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -0,0 +1,18 @@ { "name": "window-resize-issue", "version": "1.0.0", "description": "", "main": "index.js", "scripts": { "app": "npm install && node_modules/.bin/electron --disable-gpu --enable-transparent-visuals ." }, "author": "stickycube", "license": "ISC", "dependencies": { "babel-standalone": "^6.10.3", "electron-prebuilt": "1.2.5", "es6-shim": "^0.35.1", "react": "^15.1.0", "react-dom": "^15.1.0" } } This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters. Learn more about bidirectional Unicode charactersOriginal file line number Diff line number Diff line change @@ -0,0 +1,59 @@ <!DOCTYPE html> <html> <head> <style> html, body { margin: 0px; width: 100%; height: 100%; } </style> </head> <!-- handlers for supported mouse events on body --> <body onmouseup="onEvent('mouseUp', event)" onmousedown="onEvent('mouseDown', event)" onmouseenter="onEvent('mouseEnter', event)" onmouseleave="onEvent('mouseLeave', event)" onmousemove="onEvent('mouseMove', event)" > <script> const {ipcRenderer} = require('electron'); const getEventModifiers = evt => [ { field: 'ctrlKey', name: 'control' }, { field: 'shiftKey', name: 'shift' }, { field: 'altKey', name: 'alt' }, { field: 'metaKey', name: 'meta' } ].filter(elm => evt[elm.field]).map(elm => elm.name); const getEventButton = evt => { switch (evt.button) { case 2: return 'right'; case 1: return 'middle'; case 0: default: return 'left'; } } window.onEvent = function (type, evt) { // send the event to ipcMain return ipcRenderer.send('ClickableRegion::mouse-event', { type, modifiers: getEventModifiers(evt), button: getEventButton(evt), x: evt.clientX, y: evt.clientY, globalX: evt.screenX, globalY: evt.screenY, movementX: evt.movementX, movementY: evt.movementY, clickCount: evt.detail, }); } </script> </body> </html>