Advanced Techniques for
Building Ext JS Apps
with Electron
Jason Cline
@clinejm
Build ‘native’ desktop applications with Web
technology
What is Electron?
What is Electron?
Chrome NodeJS
Sencha Uses Electron
Architect Themer Inspector
Test Studio
Who uses Electron?
Control the runtime
Why Electron?
Desktop integration
Why Electron?
Local access to NodeJS for real work
Why Electron?
Electron
Supported Platforms
• Applications can run on
- Windows (32 or 64)
- Mac OS X
- Linux (x86, x86_64, and armv7l)
•...
Electron
Build Process
• Builds use the electron-packager Node.js package.
• Uses npm scripts instead of gulp or grunt.
- ...
Render
Electron Processes
Main
./main.js ./app.js
new BrowserWindow()
process.type: 'browser' 'render'
System UI
Heavy Lif...
Electron
Organization
• Render process is almost a normal web app
- Entry point is “app.js” in root folder
- Other code is...
Inter-process Communication
(IPC)
var remote = require('electron').remote;
var service = remote.require('./main/service');
var v = service.heavyWork(42, res...
Native GUI Integration
Native GUI Integration
Electron provides access to many native elements such as:
• File Pickers
• Folder Pickers
• Tray Ic...
tbar: [{
xtype: 'electronfilefield',
options: {
filters: [{
name: 'Images',
extensions: ['jpg', 'png', 'gif']
},{
name: 'A...
Native Menus
Native Menus
Electron provides native menu access, but…
• Menu creation is easiest with a template
• Templates have no con...
mixins: [
'Ext.electron.menu.Manager'
],
nativeMenus: {
app: [{
label: 'File',
submenu: [{
label: 'Reopen',
submenu: 'getR...
getReopenMenu () {
var vm = this.getViewModel();
return this.recentFiles.map(file => {
return {
label: file,
click () {
vm...
onFileChange (picker, path) {
var recentFiles = this.recentFiles;
let i = recentFiles.indexOf(path);
if (i > -1) {
recentF...
Fit and Finish
const Path = require('path');
const COMPANY = 'Acme';
const COMPANY_LOWER = COMPANY.toLowerCase();
const profileDir = (fun...
win = new BrowserWindow({
width: initData.width || 1200,
height: initData.height || 900,
x: initData.x,
y: initData.y,
max...
Downside?
Enterprise Distribution
Challenges
Code Signing
Challenges
Create an Installer
Challenges
How to Update?
Challenges
User Adoption
Challenges
Code Security
Challenges
Build ‘native’ desktop applications with Web
technology
Summary
Questions?
github.com/sencha/electron-demo
SenchaCon 2016: Advanced Techniques for Buidling Ext JS Apps with Electron - Jason Cline
Upcoming SlideShare
Loading in …5
×

SenchaCon 2016: Advanced Techniques for Buidling Ext JS Apps with Electron - Jason Cline

65 views

Published on

By combining the cores of Chrome and Node.js, Electron opens the escape hatch on the itty-bitty living space of the web browser and gives your Ext JS application many of the phenomenal cosmic powers of native applications. In this session, you'll learn some of the key techniques Sencha has used to build native desktop applications, based on Electron​​.​​

Published in: Technology
0 Comments
0 Likes
Statistics
Notes
  • Be the first to comment

  • Be the first to like this

No Downloads
Views
Total views
65
On SlideShare
0
From Embeds
0
Number of Embeds
0
Actions
Shares
0
Downloads
5
Comments
0
Likes
0
Embeds 0
No embeds

No notes for slide
  • Functions are called to return the property value…
    …each time the menu need to be rebuilt

  • Functions are called to return the property value…
    …each time the menu need to be rebuilt

  • Functions are called to return the property value…
    …each time the menu need to be rebuilt

  • SenchaCon 2016: Advanced Techniques for Buidling Ext JS Apps with Electron - Jason Cline

    1. 1. Advanced Techniques for Building Ext JS Apps with Electron Jason Cline @clinejm
    2. 2. Build ‘native’ desktop applications with Web technology What is Electron?
    3. 3. What is Electron? Chrome NodeJS
    4. 4. Sencha Uses Electron Architect Themer Inspector Test Studio
    5. 5. Who uses Electron?
    6. 6. Control the runtime Why Electron?
    7. 7. Desktop integration Why Electron?
    8. 8. Local access to NodeJS for real work Why Electron?
    9. 9. Electron Supported Platforms • Applications can run on - Windows (32 or 64) - Mac OS X - Linux (x86, x86_64, and armv7l) • Applications can be built on: - Windows (32 or 64) - Mac OS X - Linux (x86 or x86_64) Don’t forget to sign your binaries!
    10. 10. Electron Build Process • Builds use the electron-packager Node.js package. • Uses npm scripts instead of gulp or grunt. - Simplicity is good… can always switch over if needs require. • The electron-packager wraps the compiled Ext JS application as produced by Sencha Cmd. • Application code will be stored in an “asar” file. - See http://electron.atom.io/docs/tutorial/application-packaging/ - Just for convenience, not as a secure storage mechanism.
    11. 11. Render Electron Processes Main ./main.js ./app.js new BrowserWindow() process.type: 'browser' 'render' System UI Heavy Lifting Presentation (DOM)
    12. 12. Electron Organization • Render process is almost a normal web app - Entry point is “app.js” in root folder - Other code is in “./app” folder • Main process logic is just Node.js code - Entry point is “main.js” in root folder - Other code is in “./main” folder
    13. 13. Inter-process Communication (IPC)
    14. 14. var remote = require('electron').remote; var service = remote.require('./main/service'); var v = service.heavyWork(42, result => { console.log(`Work is done: ${result}`); }); console.log(`Initial work value: ${v}`); // log: // > Initial work value: 21 // > Work is done: 427 Use remote To Off-load Work • Push heavy workloads to the main process. • Initial result is synchronously returned! • Callbacks can be used to return data asynchronously as well. • Very convenient compared to raw IPC methods. module.exports = { heavyWork (value, done) { setTimeout(() => { done(value * 10 + 7); }, 2500); return v / 2; } }; ./main/service.js ./app/...
    15. 15. Native GUI Integration
    16. 16. Native GUI Integration Electron provides access to many native elements such as: • File Pickers • Folder Pickers • Tray Icons • Notifications / “Balloons”
    17. 17. tbar: [{ xtype: 'electronfilefield', options: { filters: [{ name: 'Images', extensions: ['jpg', 'png', 'gif'] },{ name: 'All Files', extensions: ['*'] }] }, bind: '{filename}', listeners: { change: 'onFileChange' } }] electronfilefield • Replacement for filefield • Uses Electron’s dialog module • Supports data-binding
    18. 18. Native Menus
    19. 19. Native Menus Electron provides native menu access, but… • Menu creation is easiest with a template • Templates have no conditional pieces • API’s to maintain menu state (checked, visible, enabled) are rather new • Editing menus after creation is difficult
    20. 20. mixins: [ 'Ext.electron.menu.Manager' ], nativeMenus: { app: [{ label: 'File', submenu: [{ label: 'Reopen', submenu: 'getReopenMenu' }, { label: 'Exit', accelerator: 'CmdOrCtrl+Q', click: 'onExit' }] }, ... Ext.electron.menu.Manager • Declarative, dynamic menus • Menu and menu item properties can be specified via: - Value - Inline function - Named controller method • Click handlers can be: - Inline function - Named controller method
    21. 21. getReopenMenu () { var vm = this.getViewModel(); return this.recentFiles.map(file => { return { label: file, click () { vm.set('filename', file); } }; }); } ./app/…/MainController.js Ext.electron.menu.Manager • Submenus can be built in code nativeMenus: { app: [{ label: 'File', submenu: [{ label: 'Reopen', submenu: 'getReopenMenu' }, { ...
    22. 22. onFileChange (picker, path) { var recentFiles = this.recentFiles; let i = recentFiles.indexOf(path); if (i > -1) { recentFiles.splice(i, 1); } recentFiles.push(path); if (recentFiles.length > 3) { recentFiles.shift(); } this.getView().reloadNativeMenu('app'); } Ext.electron.menu.Manager • Call reload method when state changes to update the menu:
    23. 23. Fit and Finish
    24. 24. const Path = require('path'); const COMPANY = 'Acme'; const COMPANY_LOWER = COMPANY.toLowerCase(); const profileDir = (function () { var ret = os.homedir(); switch (os.platform()) { case 'win32': return Path.join(process.env.APPDATA, `${COMPANY}`); case 'darwin': return Path.join(ret, `Library/Application Support/${COMPANY}`); case 'linux': return Path.join(ret, `.local/share/data/${COMPANY_LOWER}`); } return Path.join(ret, `.${COMPANY_LOWER}`); })(); Respecting Native Conventions • User file locations vary by platform: - Windows • C:UsersJasonAppDataRoamingAcme - Mac OS X • /Users/Jason/Library/Application Support/Acme/ - Linux (may vary by distro) • /home/jason/.local/share/data/acme/ - When in doubt: • /home/jason/.acme/
    25. 25. win = new BrowserWindow({ width: initData.width || 1200, height: initData.height || 900, x: initData.x, y: initData.y, maximized: initData.maximized }); win.on('move', trackWindow); win.on('resize', trackWindow); function trackWindow () { if (win.isMaximized()) { ... } else { windowBox = win.getBounds(); } if (!syncTimer) { syncTimer = setTimeout(saveWindowState, 500); } } Tracking The BrowserWindow • Create the BrowserWindow using saved size information (no flicker) • Track move and resize events at the level of the BrowserWindow. • Buffer changes (they fire quickly)
    26. 26. Downside?
    27. 27. Enterprise Distribution Challenges
    28. 28. Code Signing Challenges
    29. 29. Create an Installer Challenges
    30. 30. How to Update? Challenges
    31. 31. User Adoption Challenges
    32. 32. Code Security Challenges
    33. 33. Build ‘native’ desktop applications with Web technology Summary
    34. 34. Questions?
    35. 35. github.com/sencha/electron-demo

    ×