動手實驗
實驗 8: Windows應用商店API
2012年9月
簡介
編寫Windows應用商店應用最令人矚目的理由之一是您可以方便地將它們發布到Windows應用商店。考慮到世界范圍內目前有超過7億台PC運行Windows 7,並且每台PC代表一個潛在的Windows 8升級,市場和收入潛力是巨大和多樣的。鑒於收入分享計劃將高達80%的銷售收益分配給作者,開發者具有編寫優秀應用並將它們提供給用戶的充分動機。
應用商店具有靈活的盈利選項:您可以提供試用,一次性購買,應用內購買,第三方電子商務和廣告。
對於試用,您可以使用位於Windows.ApplicationModel.Store命名空間的Windows應用商店API來檢測應用程序是否運行於試用許可證。Windows運行時同時提供其他API以輕松地從試用版升級到付費版本,檢索許可證信息並提供更多功能。Windows運行時中的CurrentAppSimulator類提供了方便的模擬購買和測試代碼的方法,它們依賴於Windows應用商店API並且全部位於一個受控的環境中。
在本實驗中您將使用Windows應用商店API來實現Contoso Cookbook的盈利。
首先,您將修改關於框以檢測試用版,如果應用程序尚未付費則包含一個購買按鈕。接著,當購買按鈕被單擊後您將使用CurrentAppSimulator模擬購買。最後,您將提供付費而不是免費的意大利食譜來模擬應用內購買。
目標
本實驗將向您展示如何:
檢測您的應用程序是否以試用版運行。
模擬在應用內部購買應用。
模擬應用內購買額外的產品。
檢索有關應用程序和產品的許可證信息。
系統要求
您需要下列軟件完成本實驗:
Microsoft Windows 8
Microsoft Visual Studio 2012
設置
您必須執行以下步驟來准備本實驗的計算機:
1.安裝 Microsoft Windows 8。
2.安裝 Microsoft Visual Studio 2012。
練習
本動手實驗包含以下練習:
1.檢測試用版
2.模擬應用購買
3.模擬產品購買
完成本實驗的預計時間:30至40分鐘。
練習 1:檢測試用版
在本練習中您將使用Windows運行時中的Windows應用商店API來自定義Contoso Cookbook的開始頁面內容。如果應用已經被購買,您將顯示許可證信息。如果還未被購買(即以試用版運行),您將顯示一個購買按鈕。此外,在購買按鈕上顯示的價格並未被寫死,而是來自從Windows應用商店檢索的列表信息。
任務 1 – 添加許可證文件
我們將使用CurrentAppSimulator類來完成模擬購買,檢索許可證信息以及其他工作。為了使模擬盡可能真實,我們將使用一個名稱為license.xml的文件來向CurrentAppSimulator提供價格、過期日期等信息。
1、在Visual Studio中打開您在實驗7中完成的ContosoCookbook項目。如果您尚未完成實驗7或希望從一個參考副本開始,您可以在開始材料中找到實驗已完成的版本。
2、如果項目中沒有Data文件夾,則在解決方案資源管理器中創建該文件夾。
3、右鍵單擊Data文件夾並使用Add > Existing Item命令從開始材料的data文件夾導入license.xml。
4、打開App.xaml.cs並向OnLaunched方法添加以下語句。將語句放在檢查連接和訂閱推送通知的if子句之後。
C#
// 初始化CurrentAppSimulator
var file = await Package.Current.InstalledLocation.GetFileAsync("Data\\license.xml");
await Windows.ApplicationModel.Store.CurrentAppSimulator.ReloadSimulatorAsync(file);
5、打開license.xml並花一些時間檢查其內容。<ListingInformation>元素包含有關應用程序自身和我們將在練習3中提供購買的意大利食譜產品的信息。<LicenseInformation>包含有關應用程序和產品的許可證信息。現實生活中所有這些信息將來自Windows應用商店。但是在模擬環境下,信息來自WindowsStoreProxy.xml。
查看本欄目
任務 2 – 修改關於頁面
現在讓我們修改您在實驗6中創建的關於頁面。目前單詞”試用版”出現在關於頁面的應用程序標題下面。我們將使用Windows應用商店API來確定它是否的確是試用版並根據結果對頁面進行自定義。
1、右鍵單擊項目的DataModel文件夾並使用Add > New Item命令向項目添加一個新的類。將文件命名為AppLicenseDataSource.cs。
2、將文件內容替換如下。
C#
using Windows.ApplicationModel.Store; using Windows.Foundation; namespace ContosoCookbook { class AppLicenseDataSource : INotifyPropertyChanged { public event PropertyChangedEventHandler PropertyChanged; private bool _licensed = false; private string _price; public AppLicenseDataSource() { if (CurrentAppSimulator.LicenseInformation.IsTrial) { CurrentAppSimulator.LicenseInformation.LicenseChanged += OnLicenseChanged; GetListingInformationAsync(); } else _licensed = true; } private async void GetListingInformationAsync() { var listing = await CurrentAppSimulator.LoadListingInformationAsync(); _price = listing.FormattedPrice; } private void OnLicenseChanged() { if (!CurrentAppSimulator.LicenseInformation.IsTrial) { _licensed = true; CurrentAppSimulator.LicenseInformation.LicenseChanged -= OnLicenseChanged; ((ContosoCookbook.App)App.Current).Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () => { if (PropertyChanged != null) { PropertyChanged(this, new PropertyChangedEventArgs("IsLicensed")); PropertyChanged(this, new PropertyChangedEventArgs("IsTrial")); PropertyChanged(this, new PropertyChangedEventArgs("LicenseInfo")); } }); } } public bool IsLicensed { get { return _licensed; } } public bool IsTrial { get { return !_licensed; } } public string LicenseInfo { get { if (!_licensed) return "Trial Version"; else return ("Valid until " + CurrentAppSimulator.LicenseInformation.ExpirationDate.LocalDateTime.ToString("dddd, MMMM d, yyyy")); } } public string FormattedPrice { get { if (!String.IsNullOrEmpty(_price)) return "Upgrade to the Full Version for " + _price; else return "Upgrade to the Full Version"; } } } } }
注意:您剛添加的AppLicenseDataSource類實現了INotifyPropertyChanged接口並公開了名稱為IsLicensed, IsTrial, LicenseInfo和 FormattedPrice的屬性。前面兩個使用CurrentAppSimulator.LicenseInformation.IsTrial來確定現在運行的應用程序是否已經購買或以試用版運行。如果應用程序是試用版,LicenseInfo返回“Trial Version”字符串,或者如果不是試用版,返回包含許可證的過期日期的字符串。FormattedPrice返回一個包含應用程序價格的按鈕標簽,該價格從Windows應用商店獲得(或者在這裡來自WindowsStoreProxy.xml)。價格信息來自通過CurrentAppSimulator.LoadListingInformationAsync 檢索獲得的ListingInformation對象。
3、打開AboutUserControl.xaml並向頁面頂部的UserControl元素添加xmlns:common="using:ContosoCookbook.Common"屬性。
XAML
<UserControl x:Class="ContosoCookbook.AboutUserControl" xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:local="using:ContosoCookbook" xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:common="using:ContosoCookbook.Common" mc:Ignorable="d" d:DesignHeight="300" d:DesignWidth="400">
查看本欄目
4、現在在Grid元素上方添加以下語句。
XAML
<UserControl.Resources>
<local:AppLicenseDataSource x:Key="License" />
<common:BooleanToVisibilityConverter x:Key="BooleanToVisibilityConverter" />
</UserControl.Resources>
注意:BooleanToVisibilityConverter是一個簡單的值轉換器,它將布爾值true轉換為Visibility.Visible,將false轉換為Visibility.Collapsed。它在Visual Studio創建項目時已經被包含在其中。
5、將text屬性為“Trial Version”的TextBlock替換為以下語句。
XAML
<TextBlock Text="{Binding LicenseInfo, Source={StaticResource License}}" FontFamily="Segoe UI" FontWeight="SemiLight" FontSize="18" TextWrapping="Wrap" /> <Button x:Name="PurchaseButton" Width="225" Height="120" Margin="0,24,0,0" Visibility="{Binding IsTrial, Source={StaticResource License}, Converter={StaticResource BooleanToVisibilityConverter }}"> <Button.Content> <TextBlock Text="{Binding FormattedPrice, Source={StaticResource License}}" TextWrapping="Wrap" TextAlignment="Center" /> </Button.Content> </Button>
</Button>
6、花一些時間檢查您剛添加的XAML。TextBlock的文本現在來自AppLicenseDataSource對象的LicenseInfo屬性。按鈕的文本來自相同對象的FormattedPrice屬性,並且按鈕是否可見被鏈接到IsTrial屬性。結果是按鈕甚至不會在頁面中顯示,除非應用程序以試用版運行。
現在讓我們測試這些修改以查看CurrentAppSimulator和WindowsStoreProxy.xml的運行。
1、按F5啟動應用程序。
2、顯示超級按鈕並點擊設置超級按鈕。
3、在設置菜單點擊About以顯示關於頁面。
4、確認購買按鈕顯示在關於頁面上,並且價格是$12.99,如圖1所示。
圖 1 應用程序試用版的關於頁面
查看本欄目
5、返回Visual Studio並停止調試。
6、打開license.xml並在<App>部分的<Price>元素中將購買價格由$12.99修改為$8.99。
7、再次啟動應用程序並轉到關於頁面。現在購買按鈕上顯示的價格是多少?
8、再次返回Visual Studio並停止調試。
9、再次打開license.xml並將價格修改回$12.99。同樣將<IsTrial>從“true”修改為“false”。
10、啟動應用程序並轉到關於頁面。驗證購買按鈕已經消失並且您現在將看到消息“Valid until Saturday, December 31, 2022”(在2022年12月31日周六前一直有效),如圖2所示。
圖 2 應用程序已購買版本的關於頁面
11、返回Visual Studio並停止調試。
12、為准備下一個練習,在license.xml中將<IsTrial>從“false”改回到“true”。
練習 2: 模擬應用購買
您可以使用license.xml來測試基於應用程序是否為試用版的用戶界面的改變,但是它並不能代替對實際購買的模擬。在本練習中您將為購買按鈕編寫處理程序,這樣您就可以從Windows應用商店“購買”應用程序了。
為模擬應用程序購買,我們將在用戶單擊關於頁面的購買按鈕時調用CurrentAppSimulator.RequestAppPurchaseAsync。並且為了對購買成功完成進行檢測,我們將使用已經存在於AppLicenseDataSource中的LicenseChanged事件處理程序。
1、打開AboutUserControl.xaml。
2、向購買按鈕添加以下Click屬性。
XAML
Click="OnPurchaseButtonClicked"
3、打開AboutUserControl.xaml.cs並添加以下using語句。
C#
using Windows.ApplicationModel.Store;
4、然後添加以下事件處理程序。
C#
private void OnPurchaseButtonClicked(object sender, RoutedEventArgs e)
{
// 購買應用程序
CurrentAppSimulator.RequestAppPurchaseAsync(false);
}
注意:RequestAppPurchaseAsync是一個異步方法。為了確定購買是否執行,您將處理LicenseChanged事件。您沒有在這裡處理該事件是因為您已經在AppLicenseDataSource.cs中進行了處理。當LicenseChanged事件被觸發時,處理程序驗證應用程序已經不再是試用版並觸發PropertyChanged事件來更新綁定到IsTrial和其他AppLicenseDataSource屬性的控件。
查看本欄目
5、在測試許可證之前,我們需要緩存App對象的調度程序(dispatcher),因為LicenseChanged事件可以在後台線程中觸發,並且我們在事件中使用數據綁定來更新用戶界面。打開App.xaml.cs並向App類添加以下成員和屬性。
C#
Windows.UI.Core.CoreDispatcher _dispatcher = null; public Windows.UI.Core.CoreDispatcher Dispatcher { get { return _dispatcher; } }
6、在App類重寫OnWindowCreated方法,這樣我們就可以捕獲到窗口的dispatcher。
C#
protected override void OnWindowCreated(WindowCreatedEventArgs args)
{
_dispatcher = args.Window.Dispatcher;
base.OnWindowCreated(args);
}
任務 2 – 購買應用
現在讓我們模擬應用程序購買。請注意CurrentAppSimulator將購買和許可證狀態的更改信息存儲在內存中,它並未將它們記錄在WindowsStoreProxy.xml中。當您購買應用程序後,只要應用程序在運行,它將保持“已購買”狀態;但是當您重新啟動應用程序時,您將再次運行試用版。
1、按F5以啟動應用程序。
2、轉到關於頁面並點擊購買按鈕以模擬應用程序購買。
3、在Windows應用商店對話框中點擊Continue(繼續)按鈕完成模擬購買。
4、再次顯示關於頁面並確認購買按鈕已經消失。
注意:在被購買後Contoso Cookbook並未向用戶公開額外的功能,它僅用許可證信息替換購買按鈕。在現實生活中,您可以選擇限制試用版用戶的功能並在購買後公開所有的功能。
5、返回Visual Studio並停止調試。
練習 3: 模擬產品購買
除了允許應用程序購買以外,Windows應用商店還支持應用內的產品購買。例如某個游戲在用戶完成上一個級別後可以允許用戶購買游戲的其他級別。在Windows應用商店術語中,以這種方式購買的功能稱為產品,並且Windows運行時為產品購買、確定哪些產品已經被購買、這些產品的許可證狀態等內容提供了您所需要的API。
在本練習中您將修改Contoso Cookbook以使意大利食譜不再免費,即查看前必須購買。您將添加一個簡單的購買它們的用戶界面,這個用戶界面基於CurrentAppSimulator,同時您還將添加在產品購買之後才能顯示所有意大利食譜的邏輯。
任務 1 – 修改項-明細頁面
第一步是添加一個數據源類以提供產品許可證信息。然後我們將添加一個購買按鈕並使用數據綁定來確保對於意大利食譜,購買按鈕或食譜指南只有其中之一被顯示,而不是兩者都被顯示。
1、右鍵單擊項目的DataModel文件夾並使用Add > New Item命令向項目添加一個新的類。將文件命名為ProductLicenseDataSource.cs。
2、將文件內容替換如下。
C#
using System; using System.Collections.Generic; using System.ComponentModel; using System.Linq; using System.Text; using System.Threading.Tasks; using Windows.ApplicationModel.Store; namespace ContosoCookbook { class ProductLicenseDataSource : INotifyPropertyChanged { public event PropertyChangedEventHandler PropertyChanged; private const string _name = "ItalianRecipes"; private bool _licensed = false; private string _price; public string GroupTitle { set { if (value != "Italian") _licensed = true; else if (CurrentAppSimulator.LicenseInformation.ProductLicenses[_name].IsActive) _licensed = true; else { CurrentAppSimulator.LicenseInformation.LicenseChanged += OnLicenseChanged; GetListingInformationAsync(); } } } private async void GetListingInformationAsync() { var listing = await CurrentAppSimulator.LoadListingInformationAsync(); _price = listing.ProductListings[_name].FormattedPrice; } private void OnLicenseChanged() { if (CurrentAppSimulator.LicenseInformation.ProductLicenses[_name].IsActive) { _licensed = true; CurrentAppSimulator.LicenseInformation.LicenseChanged -= OnLicenseChanged; ((ContosoCookbook.App)App.Current).Dispatcher.RunAsync(Windows.UI.Core.CoreDispatcherPriority.Normal, () => { if (PropertyChanged != null) { PropertyChanged(this, new PropertyChangedEventArgs("IsLicensed")); PropertyChanged(this, new PropertyChangedEventArgs("IsTrial")); } }); } } public bool IsLicensed { get { return _licensed; } } public bool IsTrial { get { return !_licensed; } } public string FormattedPrice { get { if (!String.IsNullOrEmpty(_price)) return "Purchase Italian Recipes for " + _price; else return "Purchase Italian Recipes"; } } } }
注意:ProductLicenseDataSource類似於您之前添加的AppLicenseDataSource類。ProductLicenseDataSource對名稱為“ItalianRecipes”的產品狀態信息進行封裝,而AppLicenseDataSource對應用程序的許可證狀態數據進行封裝。該產品在license.xml中定義。
查看本欄目
3、打開ItemDetailPage.xaml並向<Page.Resources>部分添加以下語句。
XAML
<local:ProductLicenseDataSource x:Key="License" />
<common:BooleanToVisibilityConverter x:Key="BooleanToVisibilityConverter" />
4、找到兩個Text屬性是“{Binding Directions}”的TextBlock元素。將每個TextBlock替換為以下語句。
XAML
<TextBlock FontSize="20" FontWeight="Light" Text="{Binding Directions}" TextWrapping="Wrap" Visibility="{Binding IsLicensed, Source={StaticResource License}, Converter={StaticResource BooleanToVisibilityConverter }}" /> <Button Width="225" Height="120" Background="#30ffffff" Click="OnPurchaseProduct" Visibility="{Binding IsTrial, Source={StaticResource License}, Converter={StaticResource BooleanToVisibilityConverter }}"> <Button.Content> <TextBlock Text="{Binding FormattedPrice, Source={StaticResource License}}" TextWrapping="Wrap" TextAlignment="Center" /> </Button.Content> </Button>
5、打開ItemDetailPage.xaml.cs並在文件頂部添加以下using語句。
C#
using Windows.ApplicationModel.Store;
6、在LoadState方法的結束處添加以下語句。
C#
// 將組標題傳遞給LicenseDataSource (重要!)
ProductLicenseDataSource license = (ProductLicenseDataSource)this.Resources["License"];
license.GroupTitle = item.Group.Title;
注意:上述代碼很重要,因為它使得ProductLicenseDataSource知道當前顯示的食譜是否是意大利食譜或是其他食譜。
7、向ItemDetailPage.xaml.cs添加以下方法以在購買按鈕被單擊時請求產品購買。
C#
private void OnPurchaseProduct(object sender, RoutedEventArgs e) { // 首先檢查是否是試用版,您不能在試用版購買產品 if (CurrentAppSimulator.LicenseInformation.IsTrial) new Windows.UI.Popups.MessageDialog("Please go into About page in Settings and license first", "You must upgrade from trial first").ShowAsync(); else { // 購買意大利食譜產品 CurrentAppSimulator.RequestProductPurchaseAsync("ItalianRecipes", false); } }
現在所有剩下的工作就是測試您的修改並觀察產品購買的運行。
1、按F5啟動應用程序。
2、點擊某個意大利食譜以轉到項-明細頁面。
3、確認購買按鈕出現在烹饪指南處,如圖3所示。
圖 3 產品購買用戶界面
4、點擊按鈕以啟動產品購買。
5、在Windows應用商店對話框中點擊Continue以模擬產品購買。
6、確認按鈕消失並且烹饪指南出現在它的位置。
7、查看一些其他的意大利食譜並驗證烹饪指南按預期方式顯示。
8、返回Visual Studio並停止調試。
總結
您在本實驗中進行的練習演示了一些Windows應用商店API最重要的方面:如何檢測試用版,如何模擬應用程序購買,如何模擬應用內的產品購買以及如何檢索有關這些產品的信息。當然在實際的應用程序中,您將以CurrentApp調用替換CurrentAppSimulator調用。這樣您將具備通過應用程序盈利的所有工具。請繼續前行並創造收益!
祝您在Windows 8中編程快樂!
作者:cnblogs zigzagPath