AI帶來的最大改變之一就是人們交互方式的改變。從傳統的鍵盤/鼠標到觸摸屏點擊操控,終於迎來了智能語音交互。隨着智能語音應用逐漸普及和發展,我們彷彿可以捕捉到到智能交互發展軌跡。在一次大會分享中,我們談到了智能語音交互發展的5G,具體可以參考《揭祕“語音交互”背後的AI硬核黑科技!》。
在智能語音交互發展的過程中,多模態交互是一個必經階段。所謂“模態”,英文是modality,用通俗的話說,就是“感官”,多模態即將多種感官融合,即通過文字、語音、視覺、動作、環境等多種方式進行人機交互,充分模擬人與人之間的交互方式。
那麼,DuerOS是如何支持多模態交互的呢?一個集中的體現就是DuerOS 新推出的DPL 2.0。
1. 什麼是DPL?
DPL 是 DuerOS Presentation Language 的縮寫,是爲面向有屏音箱的技能開發者提供的一個解決方案,採用 DPL 方式開發可以讓你能夠輕鬆的創造展現豐富、交互靈活的 DuerOS 有屏端技能。本質上,DPL 是一種領域特定語言(DSL,Domain Specified Language)。
A specialized computer language designed for a specific task. 爲了解決某一類任務而專門設計的計算機語言。--- 來自wikipedia
DSL以極其高效的方式描述特定領域的對象、規則和運行方式的語言,需要有特定的解釋器與其配合。與通用語言相比能極大降級理解和使用難度,同時極大提高開發效率的語言。DSL 通過在表達能力上做的妥協換取在某一領域內的高效。
爲什麼不在有屏音箱上可以直接支持H5開發語音技能而採用DPL呢?本質上,是資源使用效率和運行效率的折衷。儘管DuerOS是直接支持H5開發語音技能的,但是用DPL 來開發語音技能和多模態交互更加高效,從而可以獲得更好的性能效率,從而獲得更好的用戶體驗。
2. DPL 的特點
DPL 提供了一套完整的有屏幕智能語音技能開發解決方案,使用 DPL 可以在開發技能中提供如下的優勢:
◦ 豐富的組件資源:
DPL 以組件的形式定義頁面佈局與事件交互,可以使用 文本、圖片、Pager、視頻、音頻多種的組件來構建你的技能模板,並可通過在頁面或組件中的事件觸發或基於服務端下發的指令執行,完成所希望實現的完整交互邏輯;
◦ 彈性的設計:
DPL 中的內容和佈局展現具有靈活性,可以通過指令來定義和動態切換在不同交互階段時,你所希望呈現在屏幕上的可視組件以及它們的不同展現內容,來滿足所需的不同需求場景,並可非常方便的移植複用到其他擁有類似交互和呈現的其他 DPL 技能中;
◦ 易用性:
爲了方便快速上手,我們提供了豐富的、已經在實際應用中穩定可用的 DPL documents 實例模板以及相關的組件實例模板,你可以通過簡單的修改來構建屬於你自己的技能。儘管 DPL 看起來是一個全新的語言類型,但是它也遵守了一般化的編程規範,語法和協議上也儘可能的兼顧了服務端開發人員與前端開發人員的理解習慣,因此很容易上手熟悉。
3. DPL 2.0 與DPL 1.0 的區別
DuerOS 在去年就推出了DPL1.0,現在推出的DPL2.0 和 DPL 1.0 有什麼區別呢?
DPL1.0 BOT JSON格式 和 終端上渲染的格式差異較大,對解釋器的效率有影響。DPL 1.0 的數據表達格式稍顯扁平,樣式、屬性、事件、類型都在一層平鋪,導致在組件定義屬性時,容易出現命名衝突,且不易檢查。另外,DPL 1.0更多是由業務驅動的功能升級,存在一些不合理的設計。
而DPL 2.0 有效地解決了DPL1.0的不足:
-
組件結構清晰,功能明確, 相當於對不同分段有了命名空間
-
對渲染友好,解釋器基本無需映射,效率高
-
組件頂層命名空間乾淨,不存在屬性與樣式衝突的問題
-
組件不針對特定業務,可複用性高,例如
-
Video組件和彈幕組件拆分成兩個組件,在技能輸出的時候進行組合。彈幕組件可以應用於任何場景,不再侷限於Video組建。
-
組件的功能直接以Method的方式開放給技能,開發者可以通過InvokeMethod的方式進行調用
4. DPL 2.0 的功能特點
DPL 2.0 的整體功能框架如下圖:
4.1 功能指令
核心是兩個功能指令:RenderDocument 和 ExecuteCommands。
RenderDocument 用於渲染 DPL 模板指令,通過下發該指令在設備端上渲染一個 DPL 頁面。
{
"type":"DPL.RenderDocument",
"token": "{{STRING}}",
"document": {{DPL_DOCUMENT}}
}
DPL document 是一個基於 bot 協議的描述、有着完整結構定義的 JSON 對象數據,它定義了協議中對應於在頁面中需要渲染展現的動態渲染模板部分(包括在頁面上渲染展示的所有組件、數據內容和佈局結構)以及設定頁面模板的默認配置和交互能力(無交互超時退出時間、預設事件綁定指令執行機制等)。
ExecuteCommands在一個 DPL 頁面模板渲染完成後,基於構造 RenderDocument 協議時的事件綁定交互邏輯和用戶與服務端的語音交互邏輯,可以在當前頁面上接收、執行指令,完成頁面內的交互功能,比如可以在頁面渲染完之後,對列表進行翻頁、滾屏等功能。
{
"type":"DPL.ExecuteCommands",
"token": "{{STRING}}",
"commands": [
{
"type": "{{ENUM}}",
"componentId": "{{STRING}}"
}
]
}
可以執行的指令目前已經擴充到了6類:
-
組建私有指令
-
模版控制指令
-
媒體組件指令
-
數據更新指令
-
特殊類的指令
-
信息交互指令
其中信息交互指令非常重要,是終端上頁面與DuerOS技能服務通信的重要手段。當組件綁定 SendEvent 類型的 Command 時,點擊會觸發組件上報 UserEvent 事件, 用戶可以自定義參數。技能服務可以通過監聽該事件類型,基於獲取的組件id、事件類型、事件參數與綁定參數,執行下一步預期進行的交互邏輯。UserEvent 的消息樣例如下:
{
"type": "UserEvent",
"requestId": "{{STRING}}",
"timestamp": "{{STRING}}",
"token": "{{STRING}}",
"payload": {
"componentId": "{{STRING}}",
"source": {
"type": "{{ENUM}}",
"handler": "{{ENUM}}",
"value": "{{STRING}}",
"selfArguments": ["{{STRING}}", ...]
}
}
}
4.2 樣式
所有組建都支持CSS盒模型的通用樣式。需要注意的是,盒模型的 box-sizing 默認爲 border-box,即盒子的寬高包含內容、內邊距和邊框的寬度,不包含外邊距的寬度。設備端樣式屬性支持佈局模型基於 CSS Flexbox,以便所有頁面元素的排版能夠一致可預測,同時頁面佈局能適應各種設備或者屏幕尺寸(強烈推薦使用 flex 而非使用絕對定位的方式來進行頁面結構的佈局)。
設備端樣式屬性支持 position 定位,用法與 CSS position 類似。爲元素設置 position 後,可通過 top、right、bottom、left 四個屬性設置元素座標,支持百分比。
可以按照以下步驟來規劃頁面的樣式:
-
全局樣式規劃:將整個頁面分割成合適的模塊。
-
flex 佈局:排列和對齊頁面模塊。
-
定位盒子:定位並設置偏移量。
-
細節樣式處理:增加特定的具體樣式。
4.3 屏幕適配
DPL模板中使用的 dp 單位和 px 單位是1:1的對應關係。模板中應用的默認自適應方式是以設定 viewport中寬爲 960dp的方式,並以在document文檔協議描述中,基於使用具體樣式寬高屬性數值對各個組件使用和佈局使用,來實現各個設備上以寬度鋪滿情況下的默認渲染展現。
viewport的示例代碼如下:
// dpl 中使用 viewport 的方式
{
"type":"DPL",
"version":"2.0",
"duration": {{INTEGER}},
"renderConfig": {
"viewport": {
"width": 960,
"height": 562
}
}
...
}
端上渲染DPL 模板時,會通過判斷是否存在viewport後,通過調用 defineWindow, 去設置當前的屏幕展示寬高(windowWidth = viewport.width || windowheight = viewport.height),注意,在viewport中,當同時存在 width 和 height 屬性時,width 屬性取值優先(端設定只能基於這兩個屬性中的其中一個來確定實際視圖大小)。
由於使用 DuerOS 且能支持 DPL 模板使用的設備和類型(不同寬高佔比)越來越多,通過一套設計無法完美的兼容各類寬高比例的設備,因此,需要 stylesheet 通過使用 mediaquery 的方式,來配置在不同寬高範圍內的樣式屬性,以達到基於不同設備端,進行不同樣式渲染展現,更好呈現內容的目的。
5. DPL 2.0 的特性實踐
DPL2.0 中提供了大量的組件及其示例代碼,我們可以輕鬆地參考範例實現各種的多模態交互,具體的組件列表如下:
-
Audio 音頻
-
Container 容器
-
Counter 倒計時
-
FrameAnimation 逐幀動畫
-
Image 圖片
-
Input 輸入框
-
List 列表
-
Pager 分頁
-
Scrollview 滾動容器
-
Text 文本
-
Timer 計時器
-
WebView 瀏覽器
-
Video 視頻播放器
-
Section 內容隨tts滾動組件
-
Header 標題欄
-
Footer 底部欄
其中多個組件在DPL 1.0 的時候就已經提供了有效的支持,這裏主要介紹一下DPL 2.0 中的新特性。
5.1 提交Form 表單
語音輸入有其特有的便利性,但是在某些場景,觸屏輸入能夠更多地提高精確性。DPL2.0中提高了form表單進行數據提交、狀態切換的控制能力, 目前支持接入表單作爲可操控表的組件有Input 組件。
示例代碼如下:
{
"type": "dpl",
"version": "2.0",
"duration": 66000,
"stylesheet": [],
"dataSource": {},
"events": [],
"abilities": [
{
// 能力類型:表單
"type": "Form",
// 對應能力的id,在組件中若需要接入該表單,需要明確聲明:formId:該表單Id
"componentId": "form_validate_code",
"events": {
// 從存在表單項未完成驗證到所有表單項均完成驗證時觸發
"onReady": [{{COMMANDS}}, ...],
// 從所有表單項均完成驗證到存在表單項未完成驗證時觸發
"onPrepare": [{{COMMANDS}}, ...],
// 通過調用 submit 方法,驗證通過時觸發
"onSubmit": [{{COMMANDS}}, ...],
// 通過調用 submit 方法,驗證失敗時觸發
"onValidateFail": [{{COMMANDS}}, ...],
}
},
...
],
"mainTemplate": {
"items":[
...,
{
"type":"Input",
"componentId": "demo_input1",
"styles": {
...
},
"props": {
// 聲明該可用作表單項的組件註冊到 componentId 爲 form_validate_code 的表單上
"formId": "form_validate_code",
"type": "number",
"theme": "dark",
"maxLength":1,
"placeholder": "",
"value": "",
// 數據驗證規則,組件或表單的submit方法提交表單項輸入值時會先通過該規則進行驗證(正則匹配), 不填默認不驗證提交
"rule": {
"pattern": "^\\d{1}$"
},
// 輸入組件內部樣式
"inputStyle": {
...
},
...
}
]
},
...
}
5.2 手勢
在語音技能中支持手勢交互是一件很酷的事,DPL 2.0可以對當前頁面監聽識別手勢動作,並基於手勢動作可觸發相應的事件(onPalm, onOk等), 基於事件觸發執行綁定指令。
示例代碼如下:{ "type": "Gesture", "componentId": "demo-gesture", "props": { "enable": true }, "events": { "onOk": [ { "type": "SendEvent", "componentId": "demo-gesture-ok" }, { "type": "SetProps", "componentId": "demo-gesture-text", "delay": 111, "props": { "text": "識別到有人比劃出一個OK手勢: ????" } } ], "onPalm": [ { "type": "SendEvent", "componentId": "demo-gesture-palm" }, { "type": "SetProps", "componentId": "demo-gesture-text", "delay": 111, "props": { "text": "識別到有人比劃出一個手掌手勢: ????" } } ] } }
5.3 端上語音控制
DPL2.0 提供了一種在端上進行註冊語音話術來提供基礎頁面語音交互能力的規範和基礎框架,通過更易使用的API,讓用戶可以快速在組件上賦予更豐富的語音交互能力。
相對於DBP雲端意圖語音識別能力,在DPL2.0中可以使用的終端側語音識別支持具有如下特點:
-
以組件爲單位,不同組件中同樣話術後者覆蓋前者,最終作爲同一份註冊信息上報給雲端;
-
基於端上註冊的內容,存在不同的執行方式
當註冊內容不包含 url的時候, 如果用戶的語音請求匹配到了註冊的內容,則服務端下發指令到設備端,設備端執行對應的行爲(如執行點擊(Container)、滾動(List、ScrollView)、翻頁(Pager)等)。
當註冊內容包含 url(注:url 是以 dueros:// 開頭的鏈接地址)的時候, 如果用戶的語音請求匹配到了註冊的內容,則雲端會根據此意圖轉換query請求爲轉發給對應技能的 LinkClicked 事件。
舉個例子,如果展示給用戶的頁面有一個名爲“蘋果”的按鈕, 我們希望用戶說“蘋果”來執行點擊操作,那它的示例代碼如下:
{
"type":"Container",
"componentId":"container-box",
"props": {
"enableVoice": true,
"voiceAction": "click",
"voiceConfig": "click.name: 蘋果;"
},
"events": {
"onClick": [{
"type":"SendEvent",
"componentId":"container-box"
}]
}
}
關於DPL2.0 中更多有趣的用法,可以在技能開發過程中逐漸體會到的。
小結
作爲DuerOS 多模態交互的一種特定領域語言,DPL 以簡潔明快的方式提供了高效開發和高效運行的能力。DPL 2.0 僅僅是DuerOS 多模態交互的另一個起點而已,在DPL 中進一步使用本地引擎執行計算的能力已經在路上了。
關聯閱讀
-
DPL2.0 的詳細文檔參考:http://xiaodu.baidu.com/saiya/dpl/2.0/introduction.html
-
https://dueros.baidu.com/dbp