1
/
5

Electronでデスクトップアプリ開発!APIの動向を追いかける

はじめに

こんにちは!Wantedlyでエンジニアをしています、山田です。Wantedlyのグループチャット機能Syncの開発を担当しています。

Sync | A group chat app for successful teams
Mentions Anyone can call out a member by his or her name in group chat threads to ensure they will receive notifications of high-priority conversations and tasks. File Sharing Share any file, instantly and indefinitely. With built-in file viewing capabili
https://www.wantedly.com/sync

ElectronはJavaScriptやHTML/CSSでデスクトップアプリが作成できると知られているOSSです。Node.jsとChromiumベースであり、様々なプロジェクトで採用されています。大きなプロジェクトだとSlackやAtom、Visual Studio Codeなどが採用していますよね。WantedlyのグループチャットのSyncでもElectronを採用しており、macOS版 / Windows版両方のアプリケーションの配布をしています。この記事では、ElectronのAPI最前線について書いていきます。

macOS版 Sync

Windows版 Sync

ElectronはChromeベース

2016/08/22現在、Electronはバージョン 1.3.3 がリリースされています。 7月25日にリリースされた1.3.0では、Node.jsのバージョン6.3.0を採用、Chrome52にアップグレードされました。これらのアップグレードで、ChromeやNode.jsのAPIが新しいものが利用できるのはとても嬉しいことです。また、Chromeの最新バージョンに追従してくれることで、Electronモジュールをアップデートすることでセキュリティやパフォーマンスの向上が見込めます。

Electron1.3以上で新しく加わった便利なAPI

ここからは、Electronに最近追加されたAPIについて幾つか紹介していきます。

Trayアイコンのハイライト

以下のPul Requestで追加されました。

Add option to always highlight the tray icon by kevinsawicki · Pull Request #6620 · electron/electron
For applications showing "popover" style windows when the tray icon is clicked, it is nice to highlight the tray icon background for the entirety of when the window is open (like screenhero, dropbo...
https://github.com/electron/electron/pull/6620

今までTrayアイコンのハイライトについてはクリックされた時にしかハイライトされず、クリックし終わるとハイライトは消えてしまっていました。しかしこのPull Requestでいつハイライトするかが選択できるようになりました。
例えば、以下のようなアプリをこのAPIを利用して簡単にハイライトできるようになりました。


これは新しく加わったAPIを利用して以下のように記述することで実現できます。

const tray = new Tray('/path/to/icon');
tray.window = new BrowserWindow({ ... });

// ...

tray.window.on('show', () => {
  tray.setHighlightMode('always');
});

tray.window.on('hide', () => {
  tray.setHighlightMode('never');
});

これで1passwordやdocker for MacなどmacOSの他のアプリに似た動きになると思います。細かいAPIですが、僕は好きです。

MenuItemでのズーム関連の設定

以下のPull Requestで追加されました。

Add zoom menu item roles by kevinsawicki · Pull Request #6777 · electron/electron
This pull requests adds 3 new zoom-related menu item roles as a follow on to #6677 zoomin - Zooms in the page by 10%, CommandOrControl+- zoomout - Zooms out the page by 10%, CommandOrControl+...
https://github.com/electron/electron/pull/6777

ElectronにはmacOS / Windowsそれぞれのプラットフォームに向けたメニューを作成するAPIが存在します。しかしまだAPIが揃っているわけではなく、自分たちでメニューのラベルから、その項目を選択した時に動作する内容を自分たちで記述する必要がありました。バージョン1.3.2以前のElectronでは、メニューにおけるズームイン・ズームアウトの設定が大変になることが多いです。

例えばこのようなコードがあります。

Menu.buildFromTemplate([
  {
    label: 'View',
    submenu: [
      ...,
      {
        label: 'Actual Size',
        accelerator: 'CmdOrCtrl+0',
        click: (item, focusedWindow) => {
          if (focusedWindow) focusedWindow.webContents.setZoomLevel(0)
        }
      },
      {
        label: 'Zoom In',
        accelerator: 'CmdOrCtrl+Plus',
        click: (item, focusedWindow) => {
          if (focusedWindow) {
            const {webContents} = focusedWindow
            webContents.getZoomLevel((zoomLevel) => {
              webContents.setZoomLevel(zoomLevel + 0.5)
            })
          }
        }
      },
      {
        label: 'Zoom Out',
        accelerator: 'CmdOrCtrl+-',
        click: (item, focusedWindow) => {
          if (focusedWindow) {
            const {webContents} = focusedWindow
            webContents.getZoomLevel((zoomLevel) => {
              webContents.setZoomLevel(zoomLevel - 0.5)
            })
          }
        }
      },
    ]
  },
  ...
]);

ただズームに関するメニューの設定だけで40行ほどあります。これで実現できるのは以下の3行になります。

このようなズームの他にもメニューの設定はあるはずなので、それらも同じように記述していくと、メニューの内容を記述するだけで100行は簡単に超えてしまうと思います。メンテナンス性を確保するためには冗長な部分はなるべく避けたいのが本心です。そこで、この追加されたAPIのおかげで、上記の長いコードが以下のようになります。

Menu.buildFromTemplate([
  {
    label: 'View',
    submenu: [
      ...,
      {
        role: 'resetzoom'
      },
      {
        role: 'zoomin'
      },
      {
        role: 'zoomout'
      },
    ]
  },
  ...
]);

role が追加されたおかげで設定がこんなにも簡潔になりました。他のメニューのroleはAPIドキュメントに記載があるので参考にするともっと良いかもしれません。

MenuItem
Add items to native application menus and context menus.
http://electron.atom.io/docs/api/menu-item/#new-menuitemoptions

どのように最新のAPIに追従していくか

僕自身の調べ方になりますが、まずElectronのリリースが載っているページをよく確認しています。

Releases
Build cross platform desktop apps with JavaScript, HTML, and CSS.
http://electron.atom.io/releases/

GitHubの electron/electron/releases と同じ内容になっているので、どちらでも良いと思います。Electronが独自に用意しているリリースのページではChangeLogが綺麗に載っているので確認しやすいと思います。また、Electronの場合はクロスプラットフォーム向けの変更か、macOS か Windows かで分けられています。そのおかげでどのプラットフォーム向けに対応すべき変更があるかがわかりやすくなっています。

Electronは1週間程度のサイクルで細かなリリースがされているので、追従していくにはこまめにElectronモジュールをアップグレードしていくことが重要です。Electronは小さなリリースでもセキュリティやパフォーマンスの改善がなされていますし、今回紹介したようなAPIなどもリリースされています。

実際、Electronが様々な開発者によって改善されていく中でよく変更される部分は、Electronを使ってアプリケーションを開発している人々からのフィードバックによって変わっているようです。常日頃利用されている、上記でもあげたメニューの role については新しい変更が次々と改善されているようです。

- Add zoomin, zoomout, resetzoom to MenuItem’s roles. #6777
- Add startspeaking and stopspeaking to MenuItem’s roles. #6765
- accelerator and label are now optional when role is specified for MenuItem. #6190

他にも、Visual Studio Code や Nylas N1 や Brave Browser などのOSSで且つ大きなプロジェクトとして動いているElectron製のアプリケーションを開発する人たちから、欲しい機能があるということで、Pull Requestを受け付けて他のOSSと一緒に改善をしているようです。

- https://github.com/electron/electron/pull/4181
- https://github.com/electron/electron/pull/6686

また、Chromiumに追加された Chrome Web PushGoogle に拡張機能として加わった Google Cast などのChrome自体の新しい機能を、なるべくElectronにも取り入れていこうという姿勢があるようです。OSSであるため、意欲的な開発者たちがIssue上で議論しているところが見受けられます。これらのAPIがElectronのプラットフォームで使えるようになると、より一層Electronを用いたアプリケーションの開発がなされるのではないでしょうか。

終わりに

日本でもいろいろな採用事例が増えてきていますので、最近はElectronを開発するのもそこまで敷居が高いものではなくなってきているのではないでしょうか。皆さんもWebの技術があれば簡単に導入できるElectronでデスクトップアプリを開発してみてください!

Wantedly, Inc.'s job postings
20 Likes
20 Likes

Weekly ranking

Show other rankings
Like Yuki Yamada's Story
Let Yuki Yamada's company know you're interested in their content