* * *
WINDOWS 10 特殊問題 (2015)
# 游戲開發 - 使用 Unity 為通用 Windows 平臺編寫游戲
作者?[Jaime Rodriguez](https://msdn.microsoft.com/zh-cn/magazine/mt149362?author=Jaime+Rodriguez)、[Brian Peek](https://msdn.microsoft.com/zh-cn/magazine/mt149362?author=Brian+Peek)?| Windows 2015
Windows 10 為游戲開發者和玩家提供了許多新功能。借助通用 Windows 平臺 (UWP),開發者可以使用一段基本代碼來定位 Windows 10 平板電腦和 PC、Windows 10 移動設備(即手機)、Xbox One 和 HoloLens。此外,我們還已將 Windows 應用商店融合為一,且 Microsoft 已在 Windows 10 中引入了 Xbox Live 服務以及 Xbox 應用,以提高玩家跨所有 Windows 設備系列的參與度。
對于游戲開發者,Unity 是最常用的游戲開發引擎之一。它支持 21 個平臺,提供了目前所有可用中間件的最佳跨平臺開發支持。結合 C# 腳本支持,它的編輯器可以實現極高效率的游戲開發環境。資產應用商店、Unity 社區以及 Unity 不斷增加的廣告、互動和分析功能讓沉浸式游戲的開發變得空前容易。
一切進展得都十分順利,我們必須寫下來! 本文介紹了讓 Unity 游戲在 Windows 10 上完美運行您所需知道的全部詳情。這并非是對 Unity 或 UWP 應用的簡單介紹。要理解本文的內容,您需要熟悉這兩個主題。相反,我們將重點介紹 Windows 10 的變化,以及創建精彩的通用 Windows 游戲 (UWG) 的必知提示和技巧。為此,我們將以實戰方式進行介紹,逐個講解我們為了優化 Chomp 這一示例游戲(見圖 1)以適應 Windows 10 所做的一些更改。
?
圖 1:Chomp
Chomp 最初是一款使用 Unity 進行編寫的 Windows 8.1 游戲。從圖 1?中的屏幕截圖可以看出,它是一款相當小型的迷宮游戲,類似于 Pac-Man。此示例旨在為開發者提供指導,向他們展示如何使用 Unity 編寫游戲,因此簡明易懂就很關鍵。不過,隨著 Windows 10 的推出以及 Unity 支持新的操作系統,我們不得不對 Chomp 進行更新。有關 Chomp 的源代碼,請訪問?[bit.ly/UnityChomp](http://bit.ly/UnityChomp)。請下載源代碼,并在我們的演示過程中繼續參考。
若要獲取游戲的 UWP 版本,我們只需使用 Unity 中的 Windows 10 配置文件,即可導出游戲,但這樣做無法生成針對 Windows 10 運行方式優化的應用程序。它無法在全屏窗口模式下運行,也無法供用戶觸控等。那么,接下來就看看我們是如何將這款游戲從 Windows 8.1 遷移到 Windows 10 的。
## 入門(前提條件)
UWP 應用(和 UWG)要求您使用 Windows 10 和 Visual Studio 2015 進行開發和測試。所有 Visual Studio 2015 版本都會為您提供創建游戲所需的一切功能,包括免費的 Visual Studio Community 2015!
在 Unity 方面,您需要獲得 Unity 5.2.1p2 或更高版本。Unity 5.2 現在安裝有 Visual Studio Community 2015 和 Visual Studio 2015 Tools for Unity (VSTU)。因此,在實踐中,您只需安裝 Unity,并在安裝過程中選擇正確的選項即可入門。有關詳情,請參閱圖 2。
?
圖 2:只需安裝 Unity 并選擇正確的選項即可入門
注意: 對于使用 Mac 的開發者,新的備選方法是對 Unity 項目使用 Visual Studio Code 編輯器。有關此選項的更多詳細信息,請訪問?[bit.ly/UnityVSCode](http://bit.ly/UnityVSCode)。
## 針對 Windows 10 構建
針對 Windows 10 構建的過程與您熟悉的過程完全相同。新增的 SDK 可以將 UWP 應用定位到 Windows 應用商店平臺(見圖 3)下,從而將游戲導出為 UWP 應用。
?
圖 3:在 Unity 中定位 Windows 10
對于 Windows 10 和 UWP 開發,導出期間后臺發生了下面一些重要變化:
* 您可以使用新增的 UNITY_UWP 和 UNITY_WSA_10_0 預處理器,調整游戲的 UWP 邏輯和體驗。
* Unity 5.2 現在包含全新的簡化 WinRTLegacy DLL,其中所含的類型比舊版更少。有了 Windows 10,Microsoft 已將多個類型重新引入 .NET Core 配置文件,導致 WinRTLegacy 中包含的某些解決方法不再是必需方法。
* Unity 5.2 使用的是 Unity 5 中引入的全新插件模型。這極大地簡化了參與工作流的插件,本文后面對此進行了介紹。
* Unity 5.2 包括對 DirectX 12 的實驗支持(Windows 10 自帶)。若要嘗試實驗支持,請打開 Unity 中的“播放器設置”,取消選中“自動圖形 API”選項,然后手動添加 Direct3D12 支持。
## 新項目模板
Unity 構建過程現在會生成與 UWP 兼容的 Visual Studio 2015 項目。您可能已經知道,這一全新的項目系統具有一些顯著變化。
例如,每個 UWP 應用現在都自帶各自的 .NET Core 副本,因此您始終可以獲取用來測試的 .NET 版本。為了適應此變化,Unity 會生成相應的 project.json 文件。此文件會通過 NuGet 來提取合適的 .NET 部分。
此外,UWP 應用使用的是 .NET 本機,這樣可以在將應用下載到客戶計算機之前生成優化的本機計算機代碼,并縮短啟動時間,同時降低游戲的耗電量。雖然這些優化的影響因游戲的復雜程度而異,但是絕對不會影響性能的。唯一需要注意的是,.NET 本機確實會(顯著)延長 Visual Studio 內的編譯時。對于常規應用,Visual Studio 使用 .NET 本機僅編譯項目的“發布”配置。對于 Unity 生成的項目文件,實現的是類似方法,僅“主機”配置是使用 .NET 本機進行編譯。如果您不熟悉 Unity 中的配置目標,請參閱下文,配置目標分為三種:
* 調試配置是不含優化的完整調試項目。
* 發布配置是含優化的編譯項目,但也包含探查器支持。
* 主機配置是您應提交給應用商店的配置。由于不含調試代碼,因此所有優化都會啟用,并且分析支持會遭刪除。
您絕對應該在開發周期的早期使用 .NET 本機進行編譯和測試。Unity 可以編輯許多高級中間語言 (IL)。因此,如果有可以充分利用 .NET 本機的應用類型,那一定就是 Unity 游戲。為了確保達到預期效果,請在 .NET 本機編譯期間注意輸出窗口中的警告。
雖然之前提到的區別在運行時非常顯著,但新的 Unity 模板讓這些變化對開發者一目了然,因此我們要重點介紹的是如何調整和優化 Windows 10 游戲。
## 調整和優化 Windows 10 游戲
跨多個外形規格的一段基本代碼是 UWP 的重要特性,但提到游戲,可能仍有必要針對特定的外形規格進行一些調整和優化。最常見的調整和優化包括:輸入機制(如觸控、鍵盤、鼠標和游戲板);窗口重設大小;優化資源和資產;以及對每個特定外形規格實現本機平臺集成(如動態磁貼、通知或 Cortana)。我們將探討與 UWG 相關的調整和優化。
窗口化:通用 Windows 應用現在托管在可重設大小的窗口中,而不是像在 Windows 8 和 8.1 中一樣以全屏模式運行。因此,可以考慮對游戲和應用程序使用窗口化。其中大多數區別對 Unity 開發者來說都一目了然,因為 Screen.height 和 Screen.width 屬性仍可報告本機(像素)尺寸的可用空間。
Windows 10 還新增了用于進入和退出全屏的 API,設置 Screen.fullScreen 屬性后可通過 Unity 屏幕類來公開這些 API。窗口化的最佳做法是實現標準鍵加速器,以進入和退出全屏。雖然最佳做法在發布服務器中的差異很大,但進入和退出全屏的常用加速器是 F11 或 Alt+Enter。對于 Chomp,我們想為玩家提供此選項以便他們可以全屏玩游戲,因此我們通過以下方式切換全屏模式:
~~~
if (Input.GetKeyUp (KeyCode.F11))
{
? Screen.fullScreen = !Screen.fullScreen;
}
if (Input.GetKeyUp (KeyCode.F11))
{
? Screen.fullScreen = !Screen.fullScreen;
}
~~~
配備多窗口桌面需要對 Windows 10 游戲進行另一項更改: 必須處理焦點變化。在多窗口桌面中,如果您的游戲窗口沒有焦點,那么您應暫停游戲和音樂,因為用戶可能在與其他窗口進行交互。Unity 使用在其他平臺中公開的同一 API 對此交互進行抽象:OnApplicationPause 方法。當焦點變化時,系統會對所有有效的 MonoBehaviours 調用此方法。我們在 Chomp 中對此進行處理,如圖 4?所示。
圖 4:當焦點變化時暫停游戲
~~~
public void OnApplicationPause(bool pause)
{
? FocusChanged(!pause);
}
public void FocusChanged(bool isFocused)
{
? if (isFocused)
??? musicSource.UnPause();
? else
? {
??? musicSource.Pause();
??? GameState.Instance.SetState(GameState.GameStatus.Paused);
? }
}
~~~
請注意以下不對稱性: 當游戲失去焦點時,游戲和音頻會暫停,但在游戲獲得焦點時,我們只會取消暫停音頻。這是因為,當游戲暫停時,我們還會在游戲本身中顯示一個暫停的對話框;在焦點恢復時,游戲會等待用戶確認是否要繼續玩游戲。此對話框用于將游戲狀態從“暫停”設置回“正在運行”。
在執行這兩項更改后,我們可以正確處理進入/退出全屏,以及在窗口失去焦點時暫停游戲。
輸入:舊版 Unity 非常支持 Windows 游戲輸入,這一點在 Windows 10 中保持不變。Unity 中的輸入類和輸入管理器仍可方便地對鼠標、觸控和游戲板進行抽象。
關于輸入最重要的一點是,確保實現盡可能多對游戲有意義的輸入機制。對于 Chomp,我們希望支持鍵盤、游戲板和觸控。請注意,由于 UWG 可以在任意位置上運行,因此盡可能為玩家提供最佳輸入/游戲體驗。有關輸入的最常見問題是,如何檢測您是否需要在使用觸控設備(如手機)時顯示觸控控件(如虛擬游戲桿或方向鍵)。
確定是否應顯示觸控游戲桿的一種方法是,確定游戲是否是在手機上運行。如果是,可以默認顯示并啟用游戲桿。若要確定游戲是否是在特定平臺(如手機或 Xbox)上運行,您可以檢查是否實現了相應的協定。下面介紹了 Chomp 如何檢測自身是否是在 Windows 10 移動版上運行:
~~~
public static bool IsWindowsMobile
{
? get
? {
??? #if UNITY_WSA_10_0 && NETFX_CORE
????? return Windows.Foundation.Metadata.ApiInformation.
??????? IsApiContractPresent ("Windows.Phone.PhoneContract", 1);
??? #else
????? return false;
??? #endif
? }
}
~~~
請注意,在此代碼中,我們使用 UNITY_WSA_10_0 預處理器來確定我們是否針對 Windows 10 進行編譯。如果未執行此檢查,則代碼將無法在非 Windows 10 版本上進行編譯。
雖然始終顯示虛擬游戲桿是一種方法,但最好只當用戶在設備上實際使用的是觸控時才顯示游戲桿。Windows 10 新增的 API 可以確定用戶是在平板電腦模式(觸控)下還是在傳統桌面模式(鼠標/鍵盤)下運行 Windows 10: Windows.UI.ViewManagement.UIViewSettings.User-InteractionMode。此 API 必須在 Windows UI 線程上運行,因此必須從 Unity 內部封送對 UI 線程的調用。我們已向 Chomp 添加了圖 5?中的代碼,以確定用戶是否在使用觸控與應用進行交互。
圖 5:確定用戶是否在使用觸控的代碼
~~~
public static bool IsWindows10UserInteractionModeTouch
{
? get
? {
??? bool isInTouchMode = false;
#if UNITY_WSA_10_0 && NETFX_CORE
??? UnityEngine.WSA.Application.InvokeOnUIThread(() =>
??? {
????? isInTouchMode =
??????? UIViewSettings.GetForCurrentView().UserInteractionMode ==
??????? UserInteractionMode.Touch;
??? }, true);????????
#endif
??? return isInTouchMode;
? }
}
~~~
現在,我們已實現了這兩種方法,可以更新 Chomp 以更為完善地估算游戲桿的顯示時間了。如果游戲是在移動設備上運行,或用戶交互模式是觸控,則 UseJoystick 會返回 true,然后我們會顯示游戲桿:
~~~
public static bool UseJoystick
{
? get
? {
??? return (IsWindowsMobile || IsWindows10UserInteractionModeTouch) ;?
? }
}
~~~
通過處理窗口化和輸入,我們現在可以繼續利用新本機 Windows API 來為游戲添加更多功能。
與 Windows 10 本機集成: 平臺觸發?- 從 Unity 游戲內與操作系統本機集成的處理方式與之前相同: 如果您要在 Unity 中使用 .NET Core 編譯選項進行編譯(使用 NETFX_CORE 預處理器),則可以內聯本機代碼,如前面的示例所示。
如果要添加的代碼多于要內聯的代碼,或需要對行為進行抽象(跨平臺),則您仍可以使用插件。對于 Windows 10,Microsoft 開發者體驗游戲傳播團隊(我們屬于這個團隊)開放了多個新插件的源代碼,以便您可以更輕松地與 Windows 10 集成。有關這些插件,請訪問?[bit.ly/Win10UnityPlugins](http://bit.ly/Win10UnityPlugins)。目前,已共享以下插件:
* 應用商店: 適用于應用內購買的應用商店插件,支持應用模擬器、消費品、耐用品和收據。其中有您需要與 Windows 應用商店交易的任何內容。
* AzureMobile: Microsoft Azure 插件,可執行 Azure 存儲空間的創建、讀取、更新和刪除 (CRUD) 基本操作。
* 核心: 提供與核心操作系統功能(如動態磁貼、本地通知、推送通知和 Cortana)的本機集成的“核心”插件。
* 廣告: 封裝新的 Windows 10 Microsoft 廣告 SDK 的插件,現在支持視頻插頁式廣告。
以前,Chomp 不含應用內購買,因此我們決定了使用應用商店插件向游戲添加應用內購買。現在,Chomp 支持購買消費品(增強程序)和耐用品(迷宮)。
使用這些插件的最簡單方法是,從 GitHub 下載 Unity 包,然后使用 Unity 編輯器中的“資產 | 導入包 | 自定義包”將此包導入 Chomp。在您導入包后,Unity 的“插件”文件夾中包含正確的二進制文件。安裝后,這些二進制文件位于“插件\WSA”目錄中;Unity 需要在編輯器內使用占位符程序集(與 Microsoft .NET Framework 3.5 兼容),因此這些程序集也會納入和復制到“插件”文件夾本身中。
在您導入包后,我們現在可以從 Chomp 內引用應用商店 API。我們先調用 Store.LoadListingInformation,提供在完成后立即運行的回叫方法,以獲取可以購買的所有項目的列表。如果調用成功,則我們會循環訪問返回的 ProductListing 項目,然后使用這些項目來填充 UI 中的價格,如圖 6?所示。
圖 6:列出可以進行應用內購買的項目
~~~
void Start()
{???
? Store.LoadListingInformation(OnListingInformationCompleted);
? ...
}
void OnListingInformationCompleted(
? CallbackResponse<ListingInformation> response)
{
? if (response.Status == CallbackStatus.Success)
? {
??? ListingInformation result = response.Result;
??? PopulatePrices(result.ProductListings);
? }
}
~~~
在用戶選擇了要購買的項目后,只需再添加幾行代碼即可執行交易。圖 7?展示了我們添加用來購買耐用品(游戲的新迷宮)的代碼。
圖 7:執行應用內購買
~~~
public void OnDurablePurchase(GameObject buttonClicked)
{
? string productId = GetProductId(buttonClicked.name);
? if (!string.IsNullOrEmpty (productId))
? {
??? Store.RequestProductPurchase(productId, (response) =>
??? {???????????????
????? if (response.Status == CallbackStatus.Success)
????? {
??????? // response.Status just tells us if callback was successful.
??????? // The CallbackResponse tells us the actual Status
??????? // as returned from store.
??????? // Check both.
??????? if (response.Result.Status == ProductPurchaseStatus.Succeeded)
??????? {
????????? EnableLevels(productId);
????????? return;
??????? }?????????????????
????? }
??? });
? }
}
~~~
如您所見,使用這些新插件實現本機功能很簡單。
## 提交至應用商店
提交至 Windows 應用商店不再是難事。您現在可以提交一個包含所有二進制文件的包,也可以為每個平臺/體系結構都提交一個包(如果需要)。
如果您想拆分包或僅在特定平臺上支持游戲,則可以手動編輯 package.appxmanifest 文件,并調整 TargetDeviceFamily 元素:
~~~
<Dependencies>
? <TargetDeviceFamily Name="Windows.Universal" MinVersion="10.0.10240.0"?
??? MaxVersionTested="10.0.10240.0" />
</Dependencies>
~~~
三種可能的設備系列:
* Windows.Universal: 方便您在滿足硬件要求的所有位置上部署二進制文件。
* Windows.Mobile: 應該對進入 Windows 10 移動版 SKU(即 Windows Phone)的二進制文件使用,盡管將來可能有其他并非手機但運行此 SKU 的小型設備(六英寸或更小),因此請勿假設只有手機。
* Windows.Desktop: 應對只能在桌面設備和平板電腦上運行的游戲使用。
如果您想定位移動設備和桌面設備,而不是控制臺或其他更高版本的 Windows 系列,則可以在清單中添加兩個設備系列(替換相應的“x”和“y”)。
~~~
<Dependencies>
? <TargetDeviceFamily Name="Windows.Mobile" MinVersion="10.0.x.0"
??? MaxVersionTested="10.0.y.0"/>
? <TargetDeviceFamily Name="Windows.Desktop" MinVersion="10.0.x.0"
??? MaxVersionTested="10.0.y.0"/>
</Dependencies>
~~~
請注意,每個設備系列均可以有不同的 MinVersion 和 MaxVersion。將來會很方便,因為 Windows 10 移動版將自帶版本號高于 Windows 10 的桌面版。不過,目前我們建議您保留默認版本 (10.0.10240.0)。
如我們之前在討論 .NET 本機時所述,提交包時應務必提交主機配置。此外,我們還建議您添加完整的程序數據庫 (PDB) 符號文件進行故障分析。新的應用商店不提供下載 cab 文件進行本地分析的選項。相反,您必須將 PDB 提交至 Windows 應用商店,然后應用商店會為您完成相關工作,同時提供故障的堆棧跟蹤(見圖 8)。

圖 8:添加程序數據庫符號文件
最后,當您通過開發者門戶提交至 Windows 應用商店時,請務必選擇正確的硬件配置。應用商店現在允許您指定硬件要求(如觸控或鍵盤),以便游戲只在正確的設備上安裝(見圖 9)。

圖 9:開發者門戶中的硬件首選項
## 相關內容還有很多!
本文通過展示我們如何將簡單的游戲移植到了 Windows 10 中以及如何添加了一些新功能,概述了面向 Unity 開發者的“新增功能探秘”。在有限的篇幅內,我們重點介紹了基礎知識和游戲的“必做之事”,而不是向您展示 Windows 10 平臺中的每個新功能。如果您想開發酷炫的沉浸式游戲,請考慮利用其他功能,如桌面上的新通知中心(旨在提高參與度)、Cortana、新動態磁貼模板和新 Xbox Live 服務 API。借助 Windows 10,Microsoft 正在逐步開放對 Xbox Live 服務的訪問。您無需編寫控制臺游戲,只需有在 Windows 10 上運行的酷炫游戲,并希望利用排行榜、成就、跨設備運行等服務即可。若要申請訪問權限,請注冊 ID@Xbox 計劃(網址為?[xbox.com/id](http://xbox.com/id))。
### Visual Studio 2015 Tools for Unity
對于第 5.2 版及更高版本,Unity 包括 Visual Studio 2015 Tools for Unity (VSTU),讓 Visual Studio 成為 Windows 上 Unity 項目的新默認代碼編輯器。此變化將帶來改進后的 IntelliSense、編輯器中的語法著色,以及出色的 C# 調試程序。若要配置默認的腳本編輯器,請選擇 Unity 編輯器中的“編輯 | 首選項”菜單選項。您可以選擇 MonoDevelop(內置)、Visual Studio 2015、Visual Studio 2013,也可以選擇瀏覽更多選項。
VSTU 也包括一些快捷方式,以便您可以更輕松地編寫 Unity 代碼。例如,如果您在 MonoBehaviour 類中右鍵單擊,則上下文菜單會顯示新的“實現 MonoBehaviours”條目,以便您可以快速地將 MonoBehaviour 方法簽名插入類。
相同的上下文菜單中還包含“快速 MonoBehaviours”條目,以便您可以執行類似功能(但您會看到一個干擾程度較低的對話框,您可以在其中鍵入要搜索的方法名稱),然后即可再次插入簽名。以上兩種方法均可通過快捷鍵加速器使用,以提高使用速度(Ctrl+Shift+M 和 Ctrl+Shift+Q)。
除了編輯器增強功能之外,使用 VSTU 時的最佳功能之一就是,簡化了與 Unity 編輯器的調試程序集成。在 Visual Studio 中打開 Unity 項目時,您會自動看到“附加到 Unity”按鈕(用于在標準調試工具欄進行調試)。圖 A 展示了此按鈕的位置。此按鈕會自動查找 Unity 編輯器的進程并附加到其中。從此,您可以順暢設置斷點、分析變量值,并能執行其他所有大部分的 Visual Studio 預期操作。VSTU 甚至包括對中斷異常的實驗支持。有關 VSTU 2.0 功能的更多詳細信息,請查看博客文章“Visual Studio Tools for Unity 2.0”([bit.ly/VSTUInfo](http://bit.ly/VSTUInfo))。
注意: 如果您定位的不是 Windows 10,也沒有使用 Visual Studio 2013 ,則可通過可下載的包將此處所述的全部優勢帶給 Visual Studio 2013 社區版用戶。您可以訪問?[bit.ly/VSTU2013](http://bit.ly/VSTU2013),下載此擴展程序。
* * *
Jaime Rodriguez?*是 Microsoft 開發者體驗游戲傳播團隊的負責人。您可以通過以下方式與他聯系:Twitter?[@jaimerodriguez](https://twitter.com/@jaimerodriguez)?和博客?[jaimerodriguez.com](http://jaimerodriguez.com/)。*
Brian Peek?*是 Microsoft 高級游戲開發者傳播團隊成員。他是一位資深玩家,自有記憶起他便在 Windows、控制臺以及其他任何可以編程的平臺上開發游戲。您可以在開發者會議的全國巡講中看到他,也可以通過以下方式關注他:Twitter?[@BrianPeek](https://twitter.com/@BrianPeek)?和博客?[brianpeek.com](http://brianpeek.com/)。*
- 介紹
- Microsoft .NET - .NET 和通用 Windows 平臺開發
- 圖形和動畫 - Windows 組合支持 10 倍縮放
- 應用生命周期 - 通過后臺任務和擴展執行使應用處于活動狀態
- 通知 - Windows 10 中的自適應和交互式通知
- 應用集成 - 在 Windows 10 上鏈接和集成應用
- Visual Studio 工具 - NuGet 功能增強了 Windows 10 的開發功能
- UI 設計 - 通用 Windows 應用的響應式設計
- UI 設計 - 適用于 Windows 10 的自適應應用
- 數字墨跡 - Windows 10 中的墨跡交互
- 游戲開發 - 使用 Unity 為通用 Windows 平臺編寫游戲
- 結束語 - 歡迎使用 Windows 10 應用開發
- 編者寄語 - 從 3.0 開始的發展之路