Xamarin 中的 watchOS 主动建议
本文介绍如何使用 watchOS 3 应用中的“主动建议”让系统主动向用户自动呈现有用的信息,从而提高参与度。
作为 watchOS 3 的新功能,“主动建议”通过在适当的时候主动向用户自动呈现有用的信息,为用户提供了与 Xamarin.iOS 应用互动的新方法。
关于主动建议
作为 watchOS 3 的新功能,NSUserActivity
包含一个 MapItem
属性,允许应用提供可在其他上下文中使用的位置信息。 例如,如果应用显示酒店评论并提供 MapItem
位置,则如果用户切换到地图应用,其刚刚查看的酒店的位置就会可用。
应用使用一系列技术(例如 NSUserActivity
、MapKit、媒体播放器和 UIKit)向系统公开此功能。 此外,通过为应用提供主动建议支持,可以免费获取更深入的 Siri 集成。
基于位置的建议
NSUserActivity
类是 watchOS 3 的新功能,它包含一个 MapItem
属性,允许开发人员提供可在其他上下文中使用的位置信息。 例如,如果应用显示餐厅评论,开发人员可以将 MapItem
属性设置为用户在应用中查看的餐厅位置。 如果用户切换到地图应用,则餐厅的位置将自动可用。
如果应用支持应用搜索,则可以使用 CSSearchableItemAttributesSet
类的新地址组件来指定用户可能想要访问的位置。 通过设置 MapItem
属性,其他属性会自动填充。
除了设置地址组件属性的 Latitude
和 Longitude
外,建议应用也提供 NamedLocation
和 PhoneNumbers
属性,以便 Siri 可以启动对位置的调用。
上下文 Siri 提醒
允许用户使用 Siri 快速发出提醒,以便稍后在应用中查看他们当前正在查看的内容。 例如,如果他们正在应用中查看餐厅评论,则可以调用 Siri 并说“回家后提醒我”。Siri 会生成提醒,其中包含指向应用中评论的链接。
实现主动建议
向 Xamarin.iOS 应用添加主动建议支持通常与实现几个 API 或扩展应用可能已实现的一些 API 一样简单。
主动建议主要通过三种方式与应用配合使用:
NSUserActivity
- 可帮助系统了解用户当前在屏幕上使用的信息。- 位置建议 - 如果应用提供或使用基于位置的信息,这些 API 扩展提供了跨应用共享此信息的新方法,
并且通过实现以下内容在应用中受支持:
- 上下文 Siri 提醒 - iOS 10 中扩展了
NSUserActivity
,允许 Siri 快速发出提醒,以便稍后查看用户当前在应用中查看的内容。 - 位置建议 - iOS 10 增强了
NSUserActivity
,以捕获应用内查看的位置,并在系统中的许多位置推广它们。 - 上下文 Siri 请求 -
NSUserActivity
为 Siri 提供应用内呈现的信息的上下文,以便用户可以通过从应用内调用 Siri 来获得方向或拨打电话。
所有这些功能都有一个共同点,它们都以一种形式或另一种形式使用 NSUserActivity
来提供其功能。
NSUserActivity
如上所述,NSUserActivity
可帮助系统了解用户当前在屏幕上使用的信息。 NSUserActivity
是一种轻型状态缓存机制,用于在用户浏览应用时捕获用户的活动。 例如,看看餐厅应用:
通过以下交互:
- 当用户使用应用时,会创建一个
NSUserActivity
,以便稍后重新创建应用的状态。 - 如果用户搜索餐厅,则会遵循相同的创建活动模式。
- 同样,当用户查看结果时。 在最后一种情况下,用户正在查看位置,在 iOS 10 中,系统更了解某些概念(如位置或通信交互)。
仔细看看最后一个屏幕:
在这里,应用正在创建一个 NSUserActivity
并且已填充了信息,以便稍后重新创建状态。 该应用还包含一些元数据,例如位置的名称和地址。 创建此活动后,应用会让 iOS 知道它代表用户的当前状态。
然后,应用决定是否无线会 Handoff 播发该活动,将其保存为位置建议的临时值,或添加到设备上的聚焦索引,以便在搜索结果中显示。
有关 Handoff 和聚焦搜索的详细信息,请参阅我们的 Handoff 简介和 iOS 9 新搜索 API 指南。
创建活动
在创建活动之前,需要创建一个活动类型标识符来标识它。 活动类型标识符是添加到应用的 Info.plist
文件的 NSUserActivityTypes
数组中的一个短字符串,用于唯一识别给定的用户活动类型。 对于应用支持并向应用搜索公开的每个活动,数组中都会有一个条目。 有关更多详细信息,请参阅创建活动类型标识符参考。
看看一个活动示例:
// Create App Activity
var activity = new NSUserActivity ("com.xamarin.platform");
// Define details
var info = new NSMutableDictionary ();
info.Add(new NSString("link"),new NSString("http://xamarin.com/platform"));
// Populate Activity
activity.Title = "The Xamarin Platform";
activity.UserInfo = info;
// Enable capabilities
activity.EligibleForSearch = true;
activity.EligibleForHandoff = true;
activity.EligibleForPublicIndexing = true;
// Inform system of Activity
activity.BecomeCurrent();
使用活动类型标识符创建新活动。 接下来,将创建定义活动的一些元数据,以便以后可以还原此状态。 然后,为活动提供有意义的标题并附加到用户信息。 最后,启用某些功能,并将活动发送到系统。
通过进行以下更改,可以进一步增强上面的代码,以包括为活动提供上下文的元数据:
...
// Provide context
var attributes = new CSSearchableItemAttributeSet ("com.xamarin.location");
attributes.ThumbnailUrl = myThumbnailURL;
attributes.Keywords = new string [] { "software", "mobile", "language" };
activity.ContentAttributeSet = attributes;
// Inform system of Activity
activity.BecomeCurrent();
如果开发人员的网站能够显示与应用相同的信息,则应用可以包含 URL,并且内容可以显示在未安装应用的其他设备上(通过 Handoff):
// Restore on the web
activity.WebPageUrl = new NSUrl("http://xamarin.com/platform");
还原活动
若要响应用户点击应用的搜索结果 (NSUserActivity
),请编辑 AppDelegate.cs 文件并替代 ContinueUserActivity
方法。 例如:
public override bool ContinueUserActivity (UIApplication application, NSUserActivity userActivity, UIApplicationRestorationHandler completionHandler)
{
// Take action based on the activity type
switch (userActivity.ActivityType) {
case "com.xamarin.platform":
// Restore the state of the app here...
break;
}
return true;
}
确保这是与上面创建的活动相同的活动类型标识符 (com.xamarin.platform
)。 应用使用存储在 NSUserActivity
中的信息将状态还原回用户离开的位置。
创建活动的好处
通过上面提供的最少量代码,应用现在可以利用三个新的 iOS 10 功能:
- Handoff
- 聚焦搜索
- 上下文 Siri 提醒
以下部分将介绍如何启用另外两项新的 iOS 10 功能:
- 位置建议
- 上下文 Siri 请求
基于位置的建议
以上面的餐厅搜索应用为例。 如果它已实现 NSUserActivity
并正确填充了所有元数据和属性,则用户将能够执行以下操作:
- 在应用中找到一家想要与朋友见面的餐厅。
- 如果用户切换到“地图”应用,则餐厅的地址将自动建议为目的地。
- 这甚至适用于第三方应用(支持
NSUserActivity
),因此用户可以切换到拼车应用,餐厅的地址也会自动建议为目的地。 - 它还为 Siri 提供上下文,因此用户可以在餐厅应用中调用 Siri 并询问“获取路线…”,Siri 将提供用户正查看的餐厅的路线。
以上所有功能都有一个共同点,它们都指示了建议最初的来源。 在上面的例子中,它是一个虚构的餐厅评论应用。
watchOS 3 经过增强,可通过对现有框架进行多项小型修改和添加,为应用启用此功能:
NSUserActivity
具有用于捕获在应用内查看的位置信息的其他字段。- 对 MapKit 和 CoreSpotlight 进行了一些添加以捕获位置。
- 系统中的 Siri、地图、多任务处理和其他应用都添加了位置感知功能。
若要实现基于位置的建议,请从上面显示的相同活动代码开始:
// Create App Activity
var activity = new NSUserActivity ("com.xamarin.platform");
// Define details
var info = new NSMutableDictionary ();
info.Add(new NSString("link"),new NSString("http://xamarin.com/platform"));
// Populate Activity
activity.Title = "The Xamarin Platform";
activity.UserInfo = info;
// Enable capabilities
activity.EligibleForSearch = true;
activity.EligibleForHandoff = true;
activity.EligibleForPublicIndexing = true;
// Provide context
var attributes = new CSSearchableItemAttributeSet ("com.xamarin.location");
attributes.ThumbnailUrl = myThumbnailURL;
attributes.Keywords = new string [] { "software", "mobile", "language" };
activity.ContentAttributeSet = attributes;
// Restore on the web
activity.WebPageUrl = new NSUrl("http://xamarin.com/platform");
// Inform system of Activity
activity.BecomeCurrent();
如果应用使用 MapKit,则只需将当前映射 MKMapItem
添加到活动即可:
// Save MKMapItem location
activity.MapItem = myMapItem;
如果应用未使用 MapKit,则可以采用应用搜索并为位置指定以下新属性:
// Provide context
var attributes = new CSSearchableItemAttributeSet ("com.xamarin.location");
...
attributes.NamedLocation = "Apple Inc.";
attributes.SubThoroughfare = "1";
attributes.Thoroughfare = "Infinite Loop";
attributes.City = "Cupertino";
attributes.StateOrProvince = "CA";
attributes.Country = "United States";
attributes.Latitude = 37.33072;
attributes.Longitude = 122.029674;
attributes.PhoneNumbers = new string[]{"(800) 275-2273"};
attributes.SupportsPhoneCalls = true;
attributes.SupportsNavigation = true;
详细看看上述代码。 首先,每个实例都需要位置的名称:
attributes.NamedLocation = "Apple Inc.";
然后,基于文本的实例(如 QuickType 键盘)需要基于文本的说明:
attributes.SubThoroughfare = "1";
attributes.Thoroughfare = "Infinite Loop";
attributes.City = "Cupertino";
attributes.StateOrProvince = "CA";
attributes.Country = "United States";
纬度和经度是可选的,但请确保将用户路由到应用要向其发送的确切位置:
attributes.Latitude = 37.33072;
attributes.Longitude = 122.029674;
通过设置电话号码,应用可以访问 Siri,因此用户可以通过说“给这个地方打电话”之类的话从应用调用 Siri:
attributes.PhoneNumbers = new string[]{"(800) 275-2273"};
最后,应用可以指示实例是否适合导航和电话呼叫:
attributes.SupportsPhoneCalls = true;
attributes.SupportsNavigation = true;
活动最佳做法
Apple 建议在处理活动时采用以下最佳做法:
- 使用
NeedsSave
进行延迟有效负载更新。 - 确保保持对当前活动的强引用。
- 仅传输包含足够信息以还原状态的小型有效负载。
- 通过使用反向 DNS 表示法指定活动类型标识符,确保它们是唯一的和描述性的。
使用位置建议
下一部分将介绍使用来自系统其他部分(如“地图”应用)或其他第三方应用的位置建议。
路线规划应用和位置建议
本部分将介绍如何直接从路线规划应用中使用位置建议。 若要使路线规划应用添加此功能,开发人员将按如下所示利用现有的 MKDirectionsRequest
框架:
- 在多任务处理中推广应用。
- 将应用注册为路线规划应用。
- 处理使用 MapKit
MKDirectionsRequest
对象启动应用。 - 让 watchOS 能够学习根据用户参与度推荐应用。
当应用使用 MapKit MKDirectionsRequest
对象启动时,它应该自动开始向用户提供前往请求位置的路线,或者提供一个用户界面,让用户可以轻松地开始获取路线。 例如:
using System;
using Foundation;
using UIKit;
using MapKit;
using CoreLocation;
namespace MonkeyChat
{
[Register ("AppDelegate")]
public class AppDelegate : UIApplicationDelegate, IUISplitViewControllerDelegate
{
...
public override bool OpenUrl (UIApplication app, NSUrl url, NSDictionary options)
{
if (MKDirectionsRequest.IsDirectionsRequestUrl (url)) {
var request = new MKDirectionsRequest (url);
var coordinate = request.Destination?.Placemark.Location?.Coordinate;
var address = request.Destination.Placemark.AddressDictionary;
if (coordinate.IsValid()) {
var geocoder = new CLGeocoder ();
geocoder.GeocodeAddress (address, (place, err) => {
// Handle the display of the address
});
}
}
return true;
}
}
}
详细看看此代码。 它测试它是否是有效的目的地请求:
if (MKDirectionsRequest.IsDirectionsRequestUrl(url)) {
如果是,则从 URL 创建 MKDirectionsRequest
:
var request = new MKDirectionsRequest(url);
可以向应用发送没有地理坐标的地址,这是 watchOS 3 中的新功能,但这会导致开发人员需要对地址进行编码:
var geocoder = new CLGeocoder();
geocoder.GeocodeAddress(address, (place, err)=> {
// Handle the display of the address
});
总结
本文介绍了主动建议,并介绍了开发人员如何使用它们来驱动适用于 watchOS 的 Xamarin.iOS 应用的流量。 它介绍了实现主动建议的步骤并提供了使用指南。