本篇文章介紹了借助 Jasonette 將 Web 視圖和原生元件融合建立真正「混合」應用程式的做法,讓你的網站變成行動應用程式。有一定的參考價值,有需要的朋友可以參考一下,希望對你們有幫助。
如果我告訴你,只需要 上述 7 行橘色的 JSON 程式碼 就可以將一個網站變成行動應用,你相信嗎?完全不需要使用某種框架 API 重寫網站,就可以獲得與行動應用程式相同的行為。如果你已經有一個現成的網站,只需要簡單地引用 URL 就可以「打包」為原生應用程式。
而如果在此基礎上,只需要稍微調整 JSON 程式碼內容,就可以直接存取所有原生 API、原生 UI 元件以及原生視圖切換(View Transition)。
最簡化的範例效果如下圖所示:
#從中可以看出,我嵌入了一個GitHub.com 的Web 頁面,但介面上其餘佈局均為原生UI 元件,例如導覽條以及底部的標籤列。而我們並不需要使用任何 API 重寫網站,就可以自動獲得原生的切換效果。
在介紹具體做法前你可能會問:「看著挺酷,但除了在原生應用程式框架內展示Web 頁面之外,這種技術還有什麼意義?
問得好!這也是本文要講的重點。我們只需要創建一個無縫的Web 視圖與應用間雙向通信,藉此,父應用就可以觸發Web 視圖內的任何JavaScript 函數,隨後Web 視圖即可從外部呼叫原生API。
例如:
請注意,這個視圖包含:
原生導航條,以及內建的切換功能
一個Web 視圖,其中嵌入了一個可以產生二維碼的Web 應用程式
在底部包含一個原生的文字輸入元件
上述所有這一切只需要略微調整JSON 程式碼的屬性即可實現。
最後請注意,隨著在文字輸入區輸入不同內容,二維碼也會產生相應變化。輸入的文字可觸發二維碼生成器Web 應用內部的JavaScript 函數重新生成二維碼圖像。
#目前還沒有任何一個開發框架曾試圖從根本上解決「Web 視圖與原生應用程式無縫整合」的問題,因為這些框架都專注於完全原生,或完全HTML5 的做法
無論何時當我們聽到有人在討論行動應用的未來時,很可能會聽到類似「到底是HTML5 還是原生方法會最終勝出呢? 」這樣的說法。
似乎沒人覺得native和html可以共存,而且二者的協同和最終實現似乎也不容易。
本文將要給大家介紹:
為何Web 引擎與原生元件的融合通常是一種更好的做法。
為何HTML 與原生的無縫整合那麼難,具體又該如何實現。
更重要的是,該如何使用這樣的技術快速建立自己的應用。
為何要在原生應用程式中使用HTML?
在進一步介紹前,先一起看看這樣做是好是壞,以及什麼時候適合使用這種方法。這種做法的一些潛在用例如下:
1. 使用Web 原生功能
應用程式中的部分內容使用Web 引擎來實現也許是一種更適合的做法。例如WebSocket 是一種原生的Web 功能,主要面向Web 環境而設計。這種情況下就更適合使用內建的Web 引擎(iOS 的WKWebView 以及Android 的WebView),而非安裝某些只能「模擬」WebSocket 的第三方函式庫。
無需額外安裝任何程式碼,使用免費工具即可實現目標,這樣豈不是更好。同時這也催生了下一個原因。
2. 避免二進位檔案體積過大
有些功能也許需要藉助龐大的第三方函式庫,而你可能希望能快速用上這樣的功能。
例如,為了以原生方式包含二維碼圖像生成器,可能需要安裝某些第三方庫,這會導致二進位檔案體積增大。但如果使用Web 視圖引擎並透過一個簡單的
3. 缺乏可靠的移動庫
對於一些前沿技術,可能暫時並不具備穩定可靠的行動端實作。
好在大部分此類技術都具備 Web 實現,因此最高效的整合方法就是使用 JavaScript 函式庫。
4. 建構部分原生,部分基於Web 的應用程式
許多新手開發者想要將自己的網站移植為行動應用,但在發現自己現有網站的部分功能過於複雜,無法面向每種行動平台快速重寫時,往往會感到沮喪或受挫。
例如你可能有一個非常複雜的 Web 頁面無法快速轉換為行動應用,但網站的其他內容可以輕鬆轉換。
面對這種情況,如果透過某種方法將應用程式的大部分內容以原生方式構建,對於特別複雜的頁面直接將其以HTML 的形式無縫集成到應用程式中,是不是很棒啊。
這是如何實現的?
A. Jasonette
Jasonette 是一種基於標記語言,建構跨平台原生應用程式的開源方法。
該技術看似 Web 瀏覽器,但並不會將 HTML 標記語言解釋為 Web 頁面,而是將 JSON 標記解釋為 iOS 和 Android 上的原生應用程式。
正如所有Web 瀏覽器都有完全相同的程式碼,但只要按需解釋不同類型的HTML 標記,即可為用戶提供所有不同類型的Web 應用,所有Jasonette 應用也有著完全相同的庫,可按需解釋不同類型的JSON 標記並建立出你的應用程式。開發者完全無需觸及程式碼本身,只需要編寫標記,將程式碼即時「翻譯」為原生應用,即可開發出自己的應用程式。
雖然 Jasonette 的核心作用在於建立原生應用,但本文的重點在於介紹如何將 HTML 整合到核心原生引擎中,接下來就一起了解一下。
B. Jasonette Web 容器
原生應用程式很棒,但有時候我們依然需要使用 Web 功能。
但 Web 視圖與原生應用程式的整合是個麻煩的過程。無縫的整合需求:
Web 視圖應作為原生佈局的一部分進行整合:Web 視圖應作為原生佈局的一部分納入應用中,並且操作方式應與其他任何原生UI 元件保持一致。否則會讓用戶感覺很笨拙,並且感覺上就像自己實際上正在訪問網站一樣。
父應用程式可以控制子 Web 容器:父應用程式應能隨意控制子 Web 視圖。
子 Web 容器可觸發父應用程式的原生事件:子應用程式應該能觸發父應用的事件以執行原生 API。
這是一個非常繁重的工作,因此先從第一個環節著手介紹:直接將Web 容器嵌入原生佈局 —並將其作為第1 版發布:
JSON Web 容器,JSON 中的HTML 將變成原生應用程式元件。
光是這一點就已經很實用了,但由於無法交互,依然存在著一定的限制。
父應用無法控制子 Web 容器,子容器無法向父應用程式發送任何事件通知,這 導致 Web 容器與外界完全隔離。
C. Jasonette Web 容器 2.0:使其可互動
#發布第 1 版之後,我們開始處理第二個問題:為 Web 容器新增互動能力。
下文將介紹如何為先前建立的靜態 Web 容器新增互動能力,讓它變得更強大。
實作:互動式Web 容器
#1. 透過URL 載入
問題
之前在第1 版中,為了使用Web 容器作為後台視圖元件,我們首先需要將$jason.body.background.type設為"html",然後在$jason.body .background.text屬性下添加硬編碼的HTML 文本,例如這樣:
#一般來說,人們往往更希望直接使用Web URL 對容器進行實例化,而不希望將整個HTML 代碼以硬編碼的方式作為一行代碼加入。
解決方案
Web 容器2.0 增加了url屬性,我們可以嵌入file://形式的本地HTML,例如這樣(可以從伴隨應用程式發布的本地HTML 檔案載入):
或也可以嵌入遠端的http[s]:// URL,例如這樣(可以從遠端HTML 載入):
2. 父應用與Web 容器的雙向通訊
問題
之前, Web 容器只能用於展示內容,無法互動。這表示 下列做法全部無法實現:
Jasonette 到 Web 容器的通訊:從 Jasonette 中呼叫 Web 容器內部的 JavaScript 函數。
Web 容器到 Jasonette 的通訊:從 Web 容器程式碼中呼叫原生 API。
此時我們只能展示 Web 容器的內容。這就像網頁中嵌入的 iframe 框架,主頁面完全無法存取 iframe 框架中的內容。
解決方案:
Jasonette 最大的目標在於設計一種可以描述跨平台行動應用程式的標準化標記語言。因此我們需要這個標記語言能夠全面地描述父應用和子 Web 容器之間的雙向通訊。
為此我在父應用程式和子 Web 容器之間使用了一種基於 JSON-RPC 的通訊管道。由於 Jasonette 中的一切都是透過 JSON 物件表達的,因此使用 JSON-RPC 標準格式作為通訊協定就成了一種非常自然合理的方式。
為了讓JavaScript 函數能夠呼叫Web 容器,需要宣告一個名為$agent.request的運算:
$agent.request 是一種原生API,可觸發JSON-RPC 請求並傳送給Web 容器。為了使用該 API,必須將options物件作為參數傳遞。
options物件實際上是傳送給 Web 容器的 JSON-RPC 請求。每個屬性的意義如下:
id:Web 容器建構在一個名為Agent 的底層架構基礎上,通常來說,我們可以為一個視圖使用多個Agent,每個Agent 可以有自己的唯一ID。但 Web 容器是一種特殊類型的 Agent,只能使用 $webcontainer 作為 ID,因此這裡需要使用 ID。
method:要呼叫的 JavaScript 函數名稱。
params:傳遞給 JavaScript 函數的參數陣列。
因此完整來看,所用的標記應該是類似這樣的:
這串標記其實是在說:
當視圖載入($jason.head.actions.$load)時,向Web 容器Agent 發送一個JSON-RPC 請求($agent.request),而具體的請求是透過options指定的。
Web 容器在 $jason.body.background 下定義,本例中將會載入一個名為file://index.html的本機檔案。
接著會尋找一個名為 login 的 JavaScript 函數並傳遞params下的兩個參數("alice"和"1234")。
上文介紹了父應用如何觸發子Web 容器的JavaScript 函數調用,我們還可以反著來,讓Web 容器觸發父應用的原生API 。
詳情請參閱 Agent 文件。
Agent 文件: https://docs.jasonette.com/agents/
範例
繼續回到上文介紹的二維碼產生器範例:
#其中底部的文字輸入元件是100% 原生的。
二維碼由 作為 Web 應用程式運行 的 Web 容器產生。
當使用者輸入內容並按下“生成”,將呼叫 Web 容器 Agent 中的$agent.request操作,進而呼叫 JavaScript 函數“qr”。
具體範例可以參考:
https://github.com/Jasonette/Jasonpedia/blob/gh-pages/webcontainer/agent/fn/index.json
3. 腳本注入
問題
有時候我們可能需要在Web 容器完成初始HTML 加載後,動態地將JavaScript 程式碼注入Web 容器。
假設要建立一個自訂的Web 瀏覽器應用,我們可能希望將自己的自訂JavaScript 注入到每個Web 視圖,藉此自訂Web 視圖的行為,這有點類似於Web 瀏覽器的擴展。
就算不需要建立 Web 瀏覽器,當希望為所包含的內容不由我們控制的 URL 實作自訂行為時,同樣需要使用腳本注入的方法。原生應用程式和 Web 容器只能透過$agent API 通信,但如果無法變更 HTML 內容,只能透過動態注入的方式將$agent介面加入 Web 容器。
解決方案
如上文所述,$jason.body.background這個Web 容器也是一個agent,這表示我們可以使用與普通Agent 完全相同的$agent.inject 方法。
4. 對 URL 點選的處理
#以往,Web 容器只能透過兩種方式處理連結點擊操作:
#只讀:將Web 容器視為唯讀的,忽略所有諸如觸控或滾動等事件。此時所有 Web 容器都是唯讀的,除非明確令其表現得像是普通瀏覽器,具體做法見下文。
普通瀏覽器行為:像是普通瀏覽器那樣,允許使用者與頁面互動。為此需要進行聲明,將"type": "$default"設定為action屬性。
問題
兩者皆為 「全無或全有(All or nothing)」解決方案。
對於“唯讀”,Web 容器會忽略使用者的所有互動操作。
對於“普通瀏覽器行為”,Web 容器的表現將與瀏覽器一致。點擊連結後,將像普通網頁一樣刷新頁面展示連結內容,但無法劫持該點擊並呼叫其他原生 API。
解決方案
透過使用新的Web 容器,可以將任何action附加到$jason.body.background這個Web 容器,進而處理連結點擊之類的事件。
一起看一個例子:
#在這裡我們為Web 容器附加了" trigger": "displayBanner",這表示當使用者點擊Web 容器內的任何連結後,將觸發displayBanner操作,而非直接交由Web 視圖處理。
此外如果查看displayBanner操作會發現,這裡出現了變數$jason。在本例中,點擊的連結將透過$jason變數傳遞。例如,如果點擊一個名為"https://google.com"的URL,$jason將獲得下列值:
這表示我們可以檢查$jason.url 的值進而選擇性地觸發不同操作。
用自訂Web 瀏覽器的實作當作另一個範例一起來看看:
我們會檢查URL 是否包含字串signin ,並根據結果執行兩個不同操作。
如果包含signin,開啟一個新視圖並以原生方式完成登入操作。
如果不包含signin,則直接執行"type": "$default"操作,實作類似普通瀏覽器的行為。
用法示範
#建立自訂Web 瀏覽器
利用新版Web 容器的下列特性,可以實現許多有趣的操作:
#透過url屬性實作自我加載,並充當一個功能齊全的瀏覽器。
根據 URL 的不同,選擇性地處理連結點擊操作。
我們甚至可以透過數十行 JSON 程式碼建立一個自訂的 Web 瀏覽器。由於現在可以劫持每個連結點擊,因此可以檢查$jason.url,並根據結果運行我們需要的任何操作。
例如下面的範例:
#從上圖可以看到,點擊連結後的行為與一般瀏覽器無異("type": "$default")。
從下圖可以看到,點擊連結後可以用原生方式轉換至另一個 JASON 視圖。
這一切都可以根據$jason.url的值選擇性地觸發實作。
第1 步:向Web 容器附加一個名為visit的操作:
#第2 步:根據$jason.url的值執行visit內部的相關操作
在下列程式碼中,我們會檢查$jason.url是否與newest、show、ask等內容(皆為頂層選單項目連結)相符。如果相符,設定"type": "$default"即可讓 Web 容器做出與一般瀏覽器相同的行為。
如果模式不符,則可透過原生的$href轉換開啟一個新視圖,並將點擊的連結作為參數傳遞過去。
該Web 瀏覽器的完整JSON 標記請參閱(僅48 行!):
https://github.com/Jasonette /Jasonpedia/blob/gh-pages/webcontainer/agent/hijack.json
瞬間建立「混合」應用程式
人們通常在說「混合」應用程式時,主要是指封裝在原生應用程式框架內部的 HTML Web 應用。
但這裡說的並不是這種應用。這裡所謂的「混合」是指真正的混合應用,也就是可以同時包含多個原生視圖以及多個基於 Web 的視圖的應用程式。在這種應用程式中,一個視圖可以有多個原生 UI 元件,以及一個用相同原生佈局渲染的 Web 容器。
Web 視圖與原生視圖的交織應盡可能無縫,使得使用者完全無法分辨。
在這個範例中,我建立了一個可以在 Web 容器中顯示 jasonbase.com 的內容,並將其作為主頁視圖的應用程式。
Jasonbase 是我開發的免費 JSON 託管服務,該服務可以簡單地用於託管 Jasonette 應用程式所用到的 JSON 標記。
當然,這本身是個網站,但我將其嵌入到 Jasonette 中,因此在點擊連結後並不會打開網頁,而是會透過原生的$href轉換展示原生的 JASON 視圖。
完全不需要觸及 Jasonbase.com 的程式碼就可以建立出這個應用程式。
只需要將網站作為 Web 容器嵌入 Jasonette,隨後劫持連結點擊操作的原生處理方式,這樣就可以實現原生應用程式所具備的各類功能,例如觸發原生 API 以及進行原生轉換。
完整程式碼可參考這裡:https://github.com/Jasonette/Jasonpedia/blob/gh-pages/webcontainer/agent/hybrid.json
結論
在我看來,讓這一切如此令人讚嘆的原因在於,在框架層面上即可妥善處理好一切。所有最困難的工作都是在後台完成的。
應用程式開發者並不需要自行費時費力從零開始實現下列這一切:
##建立JavaScript 橋,以便讓應用程式能夠呼叫Web 視圖中的函數
#建立原生事件處理架構,以便讓Web 視圖能夠觸發父應用程式的原生事件整個解決方案創建了下列內容組成的抽象:
#########」聲明式標記語言:用於描述如何將Web 視圖嵌入原生應用。 ############通訊協定(JSON-RPC):用於在應用程式及其子 Web 視圖之間實作極為簡單的通訊。 ############我並不覺得這種方法可以解決所有問題,但從自己的用例來看,至少可以說這是個不錯的解決方案。 ######我試著以非常前沿的技術來構建應用,而這些技術已經前沿到在移動端還沒有任何穩定可靠的實現(由於協議的一些本質,甚至不清楚最終是否會有移動端的實現)。還好這些技術都有 JavaScript 實現,因此不費什麼事就可以輕鬆地將其與應用程式整合。 ######總的來說,這種技術很棒,我對目前的效果非常滿意。最新版文件 已經包含了所有新功能,歡迎大家深入研究並嘗試。 #########聲明:能力越大,需要擔負的責任也就越大#########最後我想說:雖然這種新技術確實很強大,但我覺得大家在開發應用程式時都應該在使用者體驗方面進行更全面的權衡。 ######有些人可能會藉助這種技術建立完全由 Web 視圖組成的應用,但說到底這樣的做法,你的應用實際上就只是一個網站,已經與開發專屬應用的本意背道而馳了。 ######要強調的是,我並不認為你的每個應用程式都應同時包含 HTML 和原生元件。我只是認為,這樣的做法對許多面臨某些具體狀況的人會顯得較為有用,只不過別過火就好。 ######總結:以上就是這篇文章的全部內容,程式碼很簡單,大家可以動手試試。希望能對大家的學習有所幫助,更多相關教學請造訪###JavaScript影片教學###,###jQuery影片教學###,###bootstrap教學###! ###以上是JSON實作七行程式碼讓網站變成行動應用的詳細內容。更多資訊請關注PHP中文網其他相關文章!

JavaScript在現實世界中的應用包括前端和後端開發。 1)通過構建TODO列表應用展示前端應用,涉及DOM操作和事件處理。 2)通過Node.js和Express構建RESTfulAPI展示後端應用。

JavaScript在Web開發中的主要用途包括客戶端交互、表單驗證和異步通信。 1)通過DOM操作實現動態內容更新和用戶交互;2)在用戶提交數據前進行客戶端驗證,提高用戶體驗;3)通過AJAX技術實現與服務器的無刷新通信。

理解JavaScript引擎內部工作原理對開發者重要,因為它能幫助編寫更高效的代碼並理解性能瓶頸和優化策略。 1)引擎的工作流程包括解析、編譯和執行三個階段;2)執行過程中,引擎會進行動態優化,如內聯緩存和隱藏類;3)最佳實踐包括避免全局變量、優化循環、使用const和let,以及避免過度使用閉包。

Python更適合初學者,學習曲線平緩,語法簡潔;JavaScript適合前端開發,學習曲線較陡,語法靈活。 1.Python語法直觀,適用於數據科學和後端開發。 2.JavaScript靈活,廣泛用於前端和服務器端編程。

Python和JavaScript在社區、庫和資源方面的對比各有優劣。 1)Python社區友好,適合初學者,但前端開發資源不如JavaScript豐富。 2)Python在數據科學和機器學習庫方面強大,JavaScript則在前端開發庫和框架上更勝一籌。 3)兩者的學習資源都豐富,但Python適合從官方文檔開始,JavaScript則以MDNWebDocs為佳。選擇應基於項目需求和個人興趣。

從C/C 轉向JavaScript需要適應動態類型、垃圾回收和異步編程等特點。 1)C/C 是靜態類型語言,需手動管理內存,而JavaScript是動態類型,垃圾回收自動處理。 2)C/C 需編譯成機器碼,JavaScript則為解釋型語言。 3)JavaScript引入閉包、原型鍊和Promise等概念,增強了靈活性和異步編程能力。

不同JavaScript引擎在解析和執行JavaScript代碼時,效果會有所不同,因為每個引擎的實現原理和優化策略各有差異。 1.詞法分析:將源碼轉換為詞法單元。 2.語法分析:生成抽象語法樹。 3.優化和編譯:通過JIT編譯器生成機器碼。 4.執行:運行機器碼。 V8引擎通過即時編譯和隱藏類優化,SpiderMonkey使用類型推斷系統,導致在相同代碼上的性能表現不同。

JavaScript在現實世界中的應用包括服務器端編程、移動應用開發和物聯網控制:1.通過Node.js實現服務器端編程,適用於高並發請求處理。 2.通過ReactNative進行移動應用開發,支持跨平台部署。 3.通過Johnny-Five庫用於物聯網設備控制,適用於硬件交互。


熱AI工具

Undresser.AI Undress
人工智慧驅動的應用程序,用於創建逼真的裸體照片

AI Clothes Remover
用於從照片中去除衣服的線上人工智慧工具。

Undress AI Tool
免費脫衣圖片

Clothoff.io
AI脫衣器

AI Hentai Generator
免費產生 AI 無盡。

熱門文章

熱工具

SecLists
SecLists是最終安全測試人員的伙伴。它是一個包含各種類型清單的集合,這些清單在安全評估過程中經常使用,而且都在一個地方。 SecLists透過方便地提供安全測試人員可能需要的所有列表,幫助提高安全測試的效率和生產力。清單類型包括使用者名稱、密碼、URL、模糊測試有效載荷、敏感資料模式、Web shell等等。測試人員只需將此儲存庫拉到新的測試機上,他就可以存取所需的每種類型的清單。

EditPlus 中文破解版
體積小,語法高亮,不支援程式碼提示功能

禪工作室 13.0.1
強大的PHP整合開發環境

SublimeText3 英文版
推薦:為Win版本,支援程式碼提示!

PhpStorm Mac 版本
最新(2018.2.1 )專業的PHP整合開發工具