天天看點

nw.js桌面軟體開發系列 第0.1節 HTML5和桌面軟體開發的碰撞

因為Node Js使用的也是V8引擎,是以改造浏覽器去相容Node Js,同時再根據桌面視窗的特性去擴充些API出來,從技術上講小團隊也是可以實作的。前端開發者也很容易加入到桌面軟體開發的大潮中。同樣一款應用,web端和桌面端可以共享一套設計和互動,甚至是同樣的HTML和CSS以及負責互動的Javascript代碼。基于Node Js去實作後端業務邏輯,可以和前端代碼無縫整合,這是目前理想狀态下的桌面軟體開發環境。

第0.1節 HTML5和桌面軟體開發的碰撞

當我們談論桌面軟體開發技術的時候,你會想到什麼?如果不對技術本身進行更為深入的探讨,在我的世界裡,有這麼多技術概念可以被羅列出來(請原諒我本質上是一個Windows程式員的事實)。

作業系統 API。作業系統發展到今日,幾乎桌面應用的所有功能,都是基于系統API建構的。調用API和語言及技術無關,哪怕是使用彙編。例如(代碼來源于網絡,本地重新編譯):

;我的第一個win32彙程式設計式

;一個經典的hello world !程式

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

.386

.model flat,stdcall

option casemap:none

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

;頭檔案的定義

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

include windows.inc

include user32.inc

include kernel32.inc

includelib user32.lib

includelib kernel32.lib

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

;資料段

.data

szCaption db '我的第一個win32程式',0

szText db 'hello world !',0

;>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>

;代碼段

.code

start:

invoke MessageBox,NULL,offset szText,offset

szCaption,MB_OK

invoke ExitProcess,NULL

end start

代碼清單0-1 

彙編MessageBox

在代碼清單0-1中,通過彙編調用MessageBox Api來呈現一個簡單視窗程式。

代碼清單0-1的運作結果如下:

圖0-1 代碼清單0-1運作結果

同樣的,我們使用c/c++來調用這樣一個win32 API,代碼可能是如下這樣的:

#include "windows.h"

int main()

{

     MessageBox(NULL,

(LPCWSTR)L"Hello world!",

            (LPCWSTR)L"我的第一個win32應用程式", MB_OK);

    return 0;

}

代碼清單0-2 

c/c++版MessageBox

代碼清單0-2運作結果如下圖:

圖0-2  代碼清單0-2運作結果

在系統API之上,經過抽象與封裝在各個作業系統上,形成了各自的所謂的庫和架構。比如windows的MFC和Delphi等,Linux的Gnome、GTK+、KDE等,Max OS X平台的Cocoa開發庫。對于系統API的強依賴性,直接導緻的問題是桌面應用的可移植性,開發人員不得不針對不同平台的作業系統(即使同一平台也不一定能良好相容)編寫不同的代碼。另外即使你已經編寫了不同的代碼來适配不同的作業系統和平台,仍然沒有辦法保證桌面應用的UI和互動是一緻的,這一點上有的開發者認為一緻反而是障礙,因為不同平台下的使用者的桌面應用的使用習慣是不一樣的。但是UI呢?我覺得保證UI一緻是極其有必要的。

筆者接觸到的最早的跨平台桌面UI庫是Qt。

Qt 是一個跨平台的 C++ 圖形使用者界面庫,由挪威 TrollTech 公司出品,目前包括Qt,基于 Framebuffer 的 Qt Embedded,快速開發工具 Qt Designer,國際化工具 Qt Linguist 等部分 Qt 支援所有 Unix 系統,當然也包括 Linux,還支援 WinNT/Win2k,Win95/98 平台。

圖0-3 Qt

上文中提到的Linux的KDE就是Qt的傑作。Qt做出了兩方面的努力,都很成功,一個是軟體UI,Qt在UI方面展現了獨特的效果,這種效果脫離了所依賴的作業系統的桌面風格,提現了桌面軟體在互動體驗方面的需求;另一個方面是跨平台性,它同時支援windows和Linux,在跨平台的同時保證了自身UI和互動效果的獨立性。

值的一提的是,對于桌面軟體的UI和使用者體驗,Linux和Os X從一開始就做得很好,相反windows一直在快速開發上做文章,這一點一直到.NET 的Winform都沒有什麼大的改變。我們不能說在windows上做不出炫酷的或者互動良好的桌面軟體,畢竟強大的系統API能讓我們無所不能,但是這是開發者的追求,不是這個技術體系的給我們的引導,結果是大多數windows桌面軟體都是灰色的,幾乎沒什麼好的互動效果(這可能有點偏激)。

現在我們簡單總結下,桌面軟體開發有兩方面的問題成為制約:

1)   跨平台性

2)   低成本的UI和互動自定義

對于跨平台性,上面我們提到應用程式的底層是系統API,系統API具有天然的系統隔離性,對于開發人員處理這種相容問題難度往往要大于實作應用程式本身。即使是Qt這樣的UI庫,也根本解決不了問題,UI庫可以移植,單應用程式本身不能移植。随着python和Java這樣的具有獨立運作時的架構出現之後,跨平台的問題似乎看到了曙光。在作業系統API和應用之間加了一個隔離層,解放了開發者。微軟的.NET也模仿了Java,但是隻是實作了在windows 各個不同的系統之間的可移植性(微軟現在也加入了開源大軍,.NET也可以支援在Linux,OS X上運作了)。雖然運作時本身還具有系統的強依賴性,但是大多數開發者而言我們可以忽略這些,關注架構提供的基礎類庫而不是系統API。

跨平台性似乎暫時得到了好的解決方案(雖然并不完美,但是從生産力的角度确實得到了空前的提高,我們暫且認為問題得到了解決),那麼UI和互動呢?順着剛才的路線去想,在可跨平台的語言基礎上,建構強大的UI庫是不是就解決了這個問題呢?确實有人在這樣做,但是卻沒有真正的成功者。問題出在哪裡了呢?

在語言和架構發展的過程中,尤其是網際網路的發展,專家們抽象和發展了應用程式的基礎功能,比如檔案通路、網絡請求、壓縮解壓縮、加密解密等等,這些内容都被內建到了可跨平台的基礎類庫中,UI和互動一直做為附屬品,在這些語言和架構中沒有得到足夠的重視。但是是人們不重視UI和互動嗎?答案是否定的,随着網際網路的發展,UI和互動越發的得到重視,而且空前發展,UI和互動有了單獨的語言來處理和定義——HTML和CSS。可是遺憾的是這兩門語言并沒有運用到桌面應用裡來,在程式設計領域出現了前端和後端的劃分,出現了C/S和B/S的劃分,出現了專門的前端程式員和後端程式員,卻沒有桌面程式員。這是曆史的發展,我們無可厚非,而且要快樂的接受。HTML和CSS是全新的語言,和c/c++、Java/C#、Python都有本質的差別,首先它面向UI和互動,可以近乎精準的還原設計;其次它們是聲明性語言,不是指令性語言。聲明性語言為設計而生,你隻需告訴它我要個黑色背景就可以了,這是語言層級的支援,而不像指令式語言想的是如何實作一個黑色背景。除了HTML和CSS之外,和它們綁定到一起的還有Javascript,一門很長一段時間隻能運作在浏覽器中同DOM進行互動的語言。

現在我們再回頭看桌面軟體開發,在UI和互動方面沒有辦法和網頁端應用相比,這是從誕生開始就注定的宿命。在網頁端應用飛速發展這些年裡,尤其是HTML5出現之後,人們仿佛覺得桌面應用已經日落西山了,早晚有一天會消亡。雖然桌面應用的開發者數量在減少,建構在純桌面環境的的應用也越來越少,但是桌面環境并沒有要消失的迹象,即使是浏覽器本身也仍然是一個桌面應用,它也隻能完成桌面應用的一小部分功能,隻要你要使用桌面,就會有桌面應用的需求。

桌面應用開發技術也沒有止步,并和浏覽器技術一步步融合。

融入網際網路,融入web是人類生活的需求,同時也是桌面軟體開發技術的需求,在軟體内部嵌入和控制網頁成為最初的訴求。于是浏覽器的功能被精簡,成為元件被引入桌面軟體中,微軟憑借自家浏覽器技術的強項在.NET 中引入了WebBrowser控件,這一舉措友善了開發者,同時因為WebBrowser控件強依賴系統安裝的浏覽器,微軟的浏覽器又和系統依賴過強,導緻控件在不同的客戶系統上的展現行為也會有差别。當然離跨平台又遠了一步。

圖0-4 WebBrower控件示例

同時我們也應該看到控件的方式雖然精簡了浏覽器功能,但是也擴充了Web應用的能力,控件是可以和調用者進行通信的,也就意味着控件是可以通過“後端代碼”通路本地資源的。但是在這一方面并沒有長足的發展。同時Google開源了Chromium項目,基于C++的CEF項目,将Chromium進行改造使之成為一個控件,相對于微軟的WebBrowser控件,這一舉措意義很大。Chromium是開源的,可以更好的和調用代碼進行互動,甚至可以擴充javascript接口,使之可以調用作業系統資源。

随着web應用的發展,浏覽器由于本身的定位和安全特性的限制,很多需要和用戶端互動的功能無法完成,于是出現了浏覽器擴充的概念,但是擴充也不是無限制的。這方面微軟對浏覽器的擴充最為粗暴,它直接支援Activex控件,幾乎可以無限制通路本地資源,但是同時也打破了浏覽器安全特性,這也是一直到現在很多銀行的網銀隻支援IE浏覽器的原因。其他浏覽器也在這一方面做出了妥協,浏覽器的Js或者本地擴充功能都被支援起來,不過僅僅是妥協而已,因為浏覽器的使命不是開發桌面應用。

在這期間,微軟做了很大的嘗試,首先是基于.NET架構的WPF,微軟推出了XAML語言,全新的聲明性語言,想讓開發者像寫HTML一樣編寫軟體的界面和互動,這不正是廣大開發者的心聲嗎?可以說WPF是很成功的産品,使用WPF我們已經可以能夠開發出炫酷的桌面軟體了。但是從跨平台性角度講,受.NET本身的制約,另外并沒有斬掉開發者和設計師之間的鴻溝。它仍然是傳統桌面軟體的延伸,面向的是仍然是後端開發人員,前端開發、互動設計師、UI設計師并沒有被引入進來。

圖0-5 WPF

微軟在這個方向上并沒有止步,随着windows8作業系統的推出,Windows Runtime浮出水面。微軟運作使用HTML5和Javascript開發WinRT的應用,看起來非常美好的一件事情,但是在微軟手裡卻多出了很多遺憾。雖然我們可以使用HTML5和Javascript開發應用,甚至在移動端,但是這些應用隻能運作于Windows

Runtime環境,連Windows8的傳統桌面環境都不可以,更不要談什麼跨平台了。原因是微軟直接擴充了Javascript類庫,映射到Windows Runtime的底層API上。

圖0-6  Windows

Runtime

這期間很多人也在嘗試直接把B/S開發模型轉移到桌面開發中,簡單了解就是在本地啟動一個WebServer 負責通路本地檔案系統,UI端通過擴充将請求發送到Server再回調回來。這種方式看起來簡單,實則實作起來很複雜,涉及到通信機制的改造。豆瓣曾經釋出OneRing項目,使用類似的機制,後端使用Python來處理業務。

不論在兩個方向上如何融合,前與後的本質差別并沒有被打破。因為通過修改浏覽器代碼去一點點擴充Javascript使之成為超級浏覽器,也不是不可取,隻不過這期間的工程量還是很大的,騰訊的Webtop項目就是基于這個想法進行的,不過已經夭折了。本質上還是由于HTML的發展制約,浏覽器廠商不去讓浏覽器足夠強大,第三方很難做到。所幸HTML5和Node.js出現了,并被認可和發展壯大起來。

關于Html5的新特性,這裡我不展開論述,讀者自行搜尋,總之一句話,Html5帶來了翻天覆地的變化,使web應用在功能上可以更像桌面應用了。而Node.js的誕生,直接打破了Javascript隻能寄宿于浏覽器端的限制,直接走到了大後方,在Node運作時上,Javascript可以和其他後端語言一樣通路本地資源,“為所欲為”(目前Node Js的基礎類庫還沒有辦法和其他後端語言相比,但是語言的功能本質發生了變化,在一個方向上了)。

圖0-7 Html5新特性

圖0-8 Node js

這裡要再次提到Google開源,它開源了浏覽器引擎及Javascript引擎V8,開源使得很多有夢想的程式員可以插上翅膀。于是乎這樣的想法——打破浏覽器的安全沙箱,讓浏覽器支援Node Js,前後端通吃——也就正常了。

因為Node

Js使用的也是V8引擎,是以改造浏覽器去相容Node Js,同時再根據桌面視窗的特性去擴充些API出來,從技術上講小團隊也是可以實作的。前端開發者也很容易加入到桌面軟體開發的大潮中。同樣一款應用,web端和桌面端可以共享一套設計和互動,甚至是同樣的HTML和CSS以及負責互動的Javascript代碼。基于Node Js去實作後端業務邏輯,可以和前端代碼無縫整合,這是目前理想狀态下的桌面軟體開發環境。我們可以寫類似這樣的代碼:

<!DOCTYPE

html>

<html

lang="en" xmlns="http://www.w3.org/1999/xhtml">

<head>

<meta charset="utf-8" />

<title></title>

</head>

<body>

<script>

var process = require('./addon')

console.log(process.getProcessList());

</script>

</body>

</html>

代碼清單0-3

在html頁面中調用nodejs

在浏覽器中直接內建Node Js,是我們目前看起來技術實作上難度不高,同時可以為桌面軟體開發帶來新希望的方式。下面我們來看看開源界都做了什麼。

hex。官方網站http://hex.youdao.com/。heX 提供了一種全新的建構桌面應用的方式,可以使用 web 技術快速建構跨平台的桌面應用。heX 基于 CEF 并且融合了 Chromium 與 Node.js,是以我們可以在 web 頁面中使用各種 Node.js 原生子產品及第三方擴充,同時在這些子產品及擴充中還可以通路到

HTML 中的 DOM 元素。此外,heX 甚至可以以一種 web 容器的方式嵌入到桌面應用的工程中。

項目目前處于停滞狀态。

圖0-9 hex

appjs。官方網站http://appjs.com/。實作了Html+nodejs開發桌面軟體的功能,項目目前處于停滞狀态。

nw.js。官方網站http://nwjs.io/。引用作者話說“通過Node.js和WebKit技術的融合,開發者可以用HTML5技術編寫UI,同時又能利用Node.js平台上衆多library通路本地OS的能力,最終達到用Web技術就可以編寫桌面應用的目的。實作上是基于Chromium項目的Content Layer建構(Chromium Browser也同樣基于Content Layer);實作上的特點是把Node.js的消息循環(libuv)和Chromium Renderer程序的消息循環合并到一起,因為這樣才能從DOM(HTML)中直接調用Node.js提供的函數;把Node.js使用的V8引擎和Chromium的V8引擎合并,使得Node.js的Javascript和DOM裡面的Javascript可以互相通路;另外因為是支援本地應用,是以安全模型和Web程式有很大不同:nw.js程式可以做web應用不允許做的很多事情,除了通過node.js通路本地OS以外,還可以進行跨域通路等操作。”

圖0-10  nw.js

nw.js目前是該方向上受關注度最高的項目,而且一直在持續更新。

electron.js。官方網站http://electron.atom.io/。electron.js 和nw.js有着千絲萬縷的關系,其前身是github大名鼎鼎的atom shell。是目前最活躍的使用web技術開發桌面軟體的開源項目。包括github的atom和微軟的Visual Studio Code都基于electron.js開發。

圖0-11 

electron.js

目前為止,我覺得值得和大家介紹的項目就這麼多(當然可能有更好的),這些項目為桌面軟體開發打開了新天地,讓web開發技術和桌面軟體開發技術完美的融合在一起。大家可以到相關的網站去了解項目的詳細資訊。從此桌面軟體開發有了新的技術體系,html5+node.js。當然探索還沒有止步,比如edge.js(https://github.com/tjanczuk/edge),打通 了node js 和.NET運作時,可以實作互調,那麼我們也是可以node js 為橋梁把複雜的業務邏輯封裝到.NET中。微軟的開源項目.NET Core,也讓很多人産生了新的想法,是否可以将.NET Core 運作時直接打包到浏覽器中,将.NET 類庫直接生成Javascript 接口供網頁中的js調用呢?

圖0-12 .NET

Core 5

在将近兩年的HTML5桌面軟體開發過程中,雖然整體過程是愉快的,但是不可避免的遇到很多問題甚至是無法克服隻能繞過的“坑”。兩年裡我主要使用的架構是nw.js(那時還叫node-webkit),也在部落格上零星的寫了一些nw.js入門的教程,雖然不成體系,文章數量也不多,但是仍然是國内最全的教程了。nw.js 也在不斷的疊代更新,于是我産生了重新動手,寫一本完整的書來記錄兩年來的開發經驗,這裡面重要的不是nw.js如何使用,重要的是使用Html5和node.js開發桌面應用我們應該怎麼做,會遇到什麼問題,如何去解決。

在下一節,會給大家闡述下nw.js的基本實作原理。

nw.js,electron交流群 313717550 

作者:玄魂

出處:http://www.cnblogs.com/xuanhun/

原文連結:http://www.cnblogs.com/xuanhun/

更多内容,請通路我的個人站點 對程式設計,安全感興趣的,加qq群:hacking-1群:303242737,hacking-2群:147098303,nw.js,electron交流群 313717550。

本文版權歸作者和部落格園共有,歡迎轉載,但未經作者同意必須保留此段聲明,且在文章頁面明顯位置給出原文連接配接,否則保留追究法律責任的權利。

關注我:

繼續閱讀