Surface Dial 交互

Surface Dial 与 Surface Studio 的图像
配备 Surface Studio 和触控笔的 Surface Dial (可在 Microsoft Store 购买)。

概述

Windows 滚轮设备(如 Surface Dial)是一种新型输入设备,可为 Windows 和 Windows 应用带来出色且独特的用户交互体验。

重要

本主题虽然具体介绍了 Surface Dial 交互,但信息适用于所有 Windows 滚轮设备。

Surface Dial 有着基于 旋转 操作(或手势)的外形规格,可以用作辅助多模式输入设备,作为主要输入设备的补充。 在大多数情况下,用户使用非惯用手操控该设备,使用惯用手执行任务(如用笔进行墨迹书写)。 该设备不适用于进行精确指针型输入(如触摸、笔或鼠标)。

Surface Dial 还支持长按操作和单击操作。 长按只有一个功能:显示命令菜单。 如果菜单处于活动状态,则会处理旋转和单击输入。 否则,这些输入将交由应用进行处理。

与所有 Windows 输入设备一样,你可以为你的应用自定义和定制 Surface Dial 交互体验,以适应应用功能。

提示

同时使用 Surface Dial 和新的 Surface Studio 可以提供更独特的用户体验。

除了前面已介绍的默认长按菜单体验之外,Surface Dial 还可以直接放置在 Surface Studio 的屏幕上。 这将启用特殊的“屏幕”菜单。

系统会检测 Surface Dial 的接触位置和边界,利用这些信息处理设备的遮挡,并环绕 Dial 显示一个更大的菜单。 你的应用也可以使用这些信息来调整 UI,以便应用适配该设备及其预期用法,例如用户放置手部和手臂的位置。

Surface Dial 屏幕外菜单

Surface Dial 屏幕外菜单的屏幕截图。

Surface Dial 屏幕菜单

Surface Dial 屏幕菜单的屏幕截图。

系统集成

Surface Dial 与 Windows 紧密集成,支持一系列内置的菜单工具:系统音量、滚动、放大/缩小和撤消/重做。

这些内置工具适应当前系统环境以包括:

  • 当用户在 Windows 桌面时的系统亮度工具
  • 播放媒体时的上一首/下一首工具

除了通用的平台支持之外,Surface Dial 还与 Windows Ink 平台控件(InkCanvasInkToolbar)紧密集成。

配合 Surface 触控笔使用 Surface Dial
配合 Surface 触控笔使用 Surface Dial

这些控件在与 Surface Dial 一起使用时会启用附加功能,能够修改墨迹属性和控制墨迹工具栏的标尺模具。

在墨迹工具栏的墨迹书写应用程序中打开 Surface Dial 菜单时,该菜单会包含用于控制笔类型和画笔粗细的工具。 启用标尺后,菜单中会显示相应的工具,允许该设备控制标尺的位置和角度。

Windows Ink 工具栏的 Surface Dial 菜单包含笔选择工具
Windows Ink 工具栏的 Surface Dial 菜单包含笔选择工具

Windows Ink 工具栏的 Surface Dial 菜单包含笔划大小工具
Windows Ink 工具栏的 Surface Dial 菜单包含笔划大小工具

Windows Ink 工具栏的 Surface Dial 菜单包含标尺工具
Windows Ink 工具栏的 Surface Dial 菜单包含标尺工具

用户自定义

用户可以通过“Windows 设置”->“设备”->“滚轮”页自定义其 Dial 体验的某些方面,包括默认工具、振动(或触觉反馈)和书写(或惯用)手。

自定义 Surface Dial 用户体验时,请确保该功能或行为可用,并由用户启用。

自定义工具

本文将讨论自定义 Surface Dial 菜单上公开工具的 UX 和开发人员指南。

自定义工具的 UX 指南

将工具与当前上下文相对应。明确直观地说明工具的作用以及它如何与 Surface Dial 有助于用户快速学习并专注于任务。

尽量减少应用工具的数量
Surface Dial 菜单可容纳7个选项。 如果选项超过或等于8个,用户便需要旋转 Dial 以查看溢出浮出控件中的可用工具,这会造成菜单导航体验变差,用户难以发现并选择工具。

我们建议你为应用或应用上下文单独提供自定义工具。 这样做可以根据用户正在执行的操作设置工具,用户无需先激活 Surface Dial 菜单再选择工具。

动态更新工具集
由于 Surface Dial 菜单项不支持禁用状态,因此应基于用户上下文(当前视图或焦点窗口)动态添加和删除工具(包括内置默认工具)。 请删除与当前活动无关或冗余的工具。

重要

请勿向菜单中添加已存在的项。

请勿删除系统内置的音量设置工具
用户通常始终有控制音量的需求。 他们可能会在使用你的应用时收听音乐,因此 Surface Dial 菜单应该随时可访问音量和下一首工具。 (下一首工具会在播放媒体时自动添加到菜单中。)

与菜单组织保持一致
这有助于用户发现并了解使用应用时哪些工具可用,提高切换工具的效率。

提供与内置图标一致的高质量图标
图标可以传达专业性和卓越性,赢得用户的信任。

  • 提供高质量的 64 x 64 像素 PNG 图像(44 x 44 是受支持的最小尺寸)
  • 确保背景透明
  • 图标应尽量填充图像
  • 白色图标应具有在高对比度模式下可见的黑色轮廓

带有 alpha 背景的图标的屏幕截图。

alpha 背景的图标

带有默认主题的滚轮菜单上显示的图标的屏幕截图。

默认主题的滚轮菜单图标

带有高对比度白色主题的滚轮菜单上显示的图标的屏幕截图。

高对比度白色主题的滚轮菜单图标

使用简洁的描述性名称
工具名称和工具图标同时显示在工具菜单中,可供屏幕阅读器使用。

  • 名称应短,以适应轮菜单的中心圆圈
  • 名称应清楚地说明主要操作(可以暗示补充操作):
    • 滚动指示两个旋转方向的效果
    • 撤消指定的是主要操作,但用户可以轻松找到重做(补充操作)

开发者指南

可以通过一组全面的Windows 运行时 API 来自定义 Surface Dial 体验作为应用功能的补充。

前面已经提过,Surface Dial 默认菜单预填充了一组内置工具,涵盖各种基本系统功能,包括系统音量、系统亮度、滚动、缩放、撤消和媒体控制(当系统检测到正在进行的音频或视频播放时)。 但是,这些默认工具可能无法满足应用功能的需求。

接下来,我们将介绍如何向 Surface Dial 菜单添加自定义工具,并指定公开的内置工具。

RadialController 自定义下载此示例的更可靠版本。

添加自定义工具

在此示例中,我们添加了一个基本的自定义工具,用于将旋转和单击事件中的输入数据传递到 XAML UI 控件中。

  1. 首先,我们在 XAML 中声明 UI(只包含一个滑块和切换按钮)。

    径向控制器示例的屏幕截图,其中水平滑块设置为左侧。
    示例应用 UI

    <Grid Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
      <Grid.RowDefinitions>
        <RowDefinition Height="Auto"/>
        <RowDefinition Height="*"/>
      </Grid.RowDefinitions>
      <StackPanel x:Name="HeaderPanel" 
        Orientation="Horizontal" 
        Grid.Row="0">
          <TextBlock x:Name="Header"
            Text="RadialController customization sample"
            VerticalAlignment="Center"
            Style="{ThemeResource HeaderTextBlockStyle}"
            Margin="10,0,0,0" />
      </StackPanel>
      <StackPanel Orientation="Vertical" 
        VerticalAlignment="Center" 
        HorizontalAlignment="Center"
        Grid.Row="1">
          <!-- Slider for rotation input -->
          <Slider x:Name="RotationSlider"
            Width="300"
            HorizontalAlignment="Left"/>
          <!-- Switch for click input -->
          <ToggleSwitch x:Name="ButtonToggle"
            HorizontalAlignment="Left"/>
      </StackPanel>
    </Grid>
    
  2. 然后,我们使用代码隐藏,将自定义工具添加到 Surface Dial 菜单并声明 RadialController 输入处理程序。

    调用 CreateForCurrentView 获取 Surface Dial (myController)对 RadialController 对象的引用。

    调用 RadialControllerMenuItem.CreateFromIcon 来创建 RadialControllerMenuItem (myItem)的实例。

    接下来,我们将该项追加到菜单项的集合中。

    声明 RadialController 对象的输入事件处理程序 (ButtonClickedRotationChanged)。

    最后,我们定义事件处理程序。

    public sealed partial class MainPage : Page
    {
        RadialController myController;
    
        public MainPage()
        {
            this.InitializeComponent();
            // Create a reference to the RadialController.
            myController = RadialController.CreateForCurrentView();
    
            // Create an icon for the custom tool.
            RandomAccessStreamReference icon =
              RandomAccessStreamReference.CreateFromUri(
                new Uri("ms-appx:///Assets/StoreLogo.png"));
    
            // Create a menu item for the custom tool.
            RadialControllerMenuItem myItem =
              RadialControllerMenuItem.CreateFromIcon("Sample", icon);
    
            // Add the custom tool to the RadialController menu.
            myController.Menu.Items.Add(myItem);
    
            // Declare input handlers for the RadialController.
            myController.ButtonClicked += MyController_ButtonClicked;
            myController.RotationChanged += MyController_RotationChanged;
        }
    
        // Handler for rotation input from the RadialController.
        private void MyController_RotationChanged(RadialController sender,
          RadialControllerRotationChangedEventArgs args)
        {
            if (RotationSlider.Value + args.RotationDeltaInDegrees > 100)
            {
                RotationSlider.Value = 100;
                return;
            }
            else if (RotationSlider.Value + args.RotationDeltaInDegrees < 0)
            {
                RotationSlider.Value = 0;
                return;
            }
            RotationSlider.Value += args.RotationDeltaInDegrees;
        }
    
        // Handler for click input from the RadialController.
        private void MyController_ButtonClicked(RadialController sender,
          RadialControllerButtonClickedEventArgs args)
        {
            ButtonToggle.IsOn = !ButtonToggle.IsOn;
        }
    }
    

运行应用时,我们使用 Surface Dial 与其交互。 首先,长按 Surface Dial 打开菜单并选择自定义工具。 激活自定义工具后,旋转 Dial 可以调整滑块控件,单击 Dial 可以切换开关。

径向控制器示例的屏幕截图,其中水平滑块设置为中间。
使用 Surface Dial 自定义工具激活的示例应用 UI

指定内置工具

可以使用 RadialControllerConfiguration 类自定义应用的内置菜单项集合。

例如,如果你的应用没有任何滚动或缩放区域,并且不需要撤消/重做功能,则可以将其从菜单删除。 这将为应用添加自定义工具腾出空间。

重要

Surface Dial 菜单必须至少有一个菜单项。 如果在添加自定义工具之前删除了所有默认工具,则会还原默认工具,并将自定义工具追加到默认集合中。

根据设计指南,我们不建议删除媒体控制工具(音量和上一首/下一首),因为用户在执行其他任务时经常播放背景音乐。

下面介绍如何将 Surface Dial 菜单为仅包含音量和下一首/上一首媒体控件。

public MainPage()
{
  ...
  //Remove a subset of the default system tools
  RadialControllerConfiguration myConfiguration = 
  RadialControllerConfiguration.GetForCurrentView();
  myConfiguration.SetDefaultMenuItems(new[] 
  {
    RadialControllerSystemMenuItemKind.Volume,
      RadialControllerSystemMenuItemKind.NextPreviousTrack
  });
}

客户交互

前面已经提过,Surface Dial 支持三种手势(长按、旋转、单击)及其相应的默认交互。

确保基于这些手势的任何自定义交互对于选中操作或工具是合理的。

注意

交互体验依赖 Surface Dial 菜单的状态。 菜单在处于活动状态时将处理输入;否则由你的应用处理。

长按

此手势激活并显示 Surface Dial 菜单,该手势不关联任何应用功能。

菜单默认显示在用户屏幕的中心。 但是,用户可以抓取并将其移动到任何位置。

注意

当 Surface Dial 放置在 Surface Studio 的屏幕上时,菜单居中位于 Surface Dial 所在的屏幕位置。

旋转

Surface Dial 主要用于支持旋转交互,对模拟值或控件进行平滑增量调整。

设备可以顺时针和逆时针旋转,还可以提供触觉反馈来指示离散距离。

注意

用户可以在“Windows 设置”->“设备”->“滚轮”页中禁用触觉反馈。

自定义交互的 UX 指南

对旋转高度敏感的工具应禁用触觉反馈

触觉反馈与活动工具的旋转敏感度匹配。 建议为具有连续或高旋转敏感度的工具禁用触觉反馈,否则可能会影响用户体验的舒适度。

惯用手应该不影响旋转交互

Surface Dial 无法检测到用户正在使用哪只手,但用户可以在 Windows 设置 - > 设备 - > 笔 和 Windows Ink 中设置书写(或惯用手)。

应考虑所有旋转交互的位置

通过适应和调整交互以适应位置和从右向左布局,可以最大程度地提高客户满意度。

Dial 菜单上的内置工具和命令遵循以下旋转交互指南:

Left

Up

Surface Dial 的图像

Right

向下

In

概念方向 映射到 Surface Dial 顺时针旋转 逆时针旋转
水平 置于 Surface Dial 顶部的左右映射 Right Left
垂直 置于 Surface Dial 左侧的上下映射 向下 Up
Z 轴 映射到上/右侧的(或更接近)
映射到下/左的 Out (或更远)
In Out

开发者指南

当用户旋转设备时,RadialController.RotationChanged 事件根据相对于旋转方向的增量(RadialControllerRotationChangedEventArgs.RotationDeltaInDegrees)触发。 可以使用 RadialController.RotationResolutionInDegrees 属性设置数据的敏感度(或分辨率)。

注意

默认情况下,仅当设备旋转至少 10 度时,旋转输入事件才会传送到 RadialController 对象。 每个输入事件都会导致设备振动。

一般情况下,建议在旋转分辨率设置为小于 5 度时禁用触觉反馈。 这可以为持续交互提供更流畅的体验。

可以通过设置 RadialController.UseAutomaticHapticFeedback 属性为自定义工具启用和禁用触觉反馈。

注意

你无法修改系统工具(如音量控制)的触觉行为。 这些工具的触觉反馈只能由用户从滚轮设置页禁用。

下面是有关如何自定义旋转数据的分辨率以及启用或禁用触觉反馈的示例。

private void MyController_ButtonClicked(RadialController sender, 
  RadialControllerButtonClickedEventArgs args)
{
  ButtonToggle.IsOn = !ButtonToggle.IsOn;

  if(ButtonToggle.IsOn)
  {
    //high resolution mode
    RotationSlider.LargeChange = 1;
    myController.UseAutomaticHapticFeedback = false;
    myController.RotationResolutionInDegrees = 1;
  }
  else
  {
    //low resolution mode
    RotationSlider.LargeChange = 10;
    myController.UseAutomaticHapticFeedback = true;
    myController.RotationResolutionInDegrees = 10;
  }
}

单击

单击 Surface Dial 类似于单击鼠标左键(设备的旋转状态对此操作没有影响)。

UX 指南

如果用户无法从结果中轻松恢复,请不要将操作或命令映射到此手势

用户单击 Surface Dial 进行的任何应用操作都必须是可逆的。 用户始终应该能够轻松遍历应用后退堆栈并还原到之前的应用状态。

使用单击手势提供良好的用户体验,例如静音/取消静音或显示/隐藏等二元操作。

不应通过单击 Surface Dial 启用或禁用模式工具

某些应用/工具模式可能会与依赖于旋转的交互有冲突,或禁用这类交互。 Windows Ink 工具栏中的标尺等工具应通过其他 UI 功能打开或关闭(墨迹工具栏提供内置的 ToggleButton 控件)。

对于模态工具,请将活动 Surface Dial 菜单项映射到目标工具或选择过的菜单项。

开发者指南

单击 Surface Dial 将触发 RadialController.ButtonClicked 事件。 RadialControllerButtonClickedEventArgs 包含 Contact 属性,该属性包含 Surface Dial 与Surface Studio 屏幕接触的位置和边界区域。 如果 Surface Dial 未与屏幕接触,则此属性为 null。

屏幕上

如前所述,Surface Dial 可与 Surface Studio 结合使用,可以在特殊的屏幕模式下显示 Surface Dial 菜单。

在此模式下,可以进一步集成并自定义 使用 Dial 的应用交互体验。 只有 Surface Dial 和 Surface Studio 才能提供的独特体验示例包括:

  • 基于 Surface Dial 的位置显示上下文工具(如调色板),这能让用户更轻松地查找和使用这些工具。
  • 根据 Surface Dial 所在 UI 设置活动工具
  • 根据 Surface Dial 的位置放大屏幕区域
  • 基于屏幕位置的游戏交互,提供独特体验

屏幕交互的 UX 指南

如果检测到 Surface Dial 在屏幕上,应用应做出响应

视觉反馈能够提示用户该应用已检测到 Surface Studio 屏幕上的设备。

根据设备位置调整 Surface Dial 相关 UI

放置位置不当时,该设备(和用户的身体)可能会遮挡关键 UI。

根据用户交互调整 Surface Dial 相关 UI

除了硬件遮挡之外,用户使用设备的手和手臂也可能会遮挡一部分屏幕。

遮挡面积取决于用户用哪只手操作设备。 由于该设备主要是为非惯用手设计,因此与 Surface Dial 有关的 UI 应根据用户指定的的另一只手进行调整。(Windows 设置 > 设备 > 笔和 Windows Ink > 选择书写时使用哪只手)

交互应响应 Surface Dial 位置,而不是其位移

由于该设备并不是精确指向设备,因此它的底部专为贴紧屏幕、避免滑动设计。 因此,我们希望用户更习惯拿起并放置 Surface Dial,而不是在屏幕上拖动。

使用屏幕位置确定用户意向

基于 UI 上下文设置活动工具(例如邻近感应控制画布或窗口)可以减少执行任务所需的步骤,从而提升用户体验。

开发者指南

当 Surface Dial 放置在 Surface Studio 的数字化器上时,会触发 RadialController.ScreenContactStarted 事件,应用收到接触信息 (RadialControllerScreenContactStartedEventArgs.Contact)。

类似地,当 Surface Dial 与 Surface Studio 数字化器接触时,用户点击会触发RadialController.ButtonClicked 事件,应用收到接触信息 (RadialControllerButtonClickedEventArgs.Contact)。

联系人信息(RadialControllerScreenContact)包括应用坐标空间(RadialControllerScreenContact.Position)中 Surface Dial 中心的 X/Y 坐标,以及设备独立像素(DIP)中的边界矩形(RadialControllerScreenContact.Bounds)。 此信息对于为活动工具提供上下文并向用户提供与设备相关的视觉反馈非常有用。

在以下示例中,我们创建了一个基本应用,其中包含四个不同的部分,每个部分包括一个滑块和一个切换。 然后,我们使用 Surface Dial 的屏幕位置来指示 Surface Dial 控制哪些滑块和切换开关集。

  1. 首先,我们在 XAML 中声明 UI(四个部分,每个部分都有一个滑块和切换按钮)。

    径向控制器示例的屏幕截图,其中四个水平滑块设置为左侧。
    示例应用 UI

    <Grid Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
      <Grid.RowDefinitions>
        <RowDefinition Height="Auto"/>
        <RowDefinition Height="*"/>
      </Grid.RowDefinitions>
      <StackPanel x:Name="HeaderPanel" 
            Orientation="Horizontal" 
            Grid.Row="0">
        <TextBlock x:Name="Header"
          Text="RadialController customization sample"
          VerticalAlignment="Center"
          Style="{ThemeResource HeaderTextBlockStyle}"
          Margin="10,0,0,0" />
      </StackPanel>
      <Grid Grid.Row="1" x:Name="RootGrid">
        <Grid.RowDefinitions>
          <RowDefinition Height="*"/>
          <RowDefinition Height="*"/>
        </Grid.RowDefinitions>
        <Grid.ColumnDefinitions>
          <ColumnDefinition Width="*"/>
          <ColumnDefinition Width="*"/>
        </Grid.ColumnDefinitions>
        <Grid x:Name="Grid0"
          Grid.Row="0"
          Grid.Column="0">
          <StackPanel Orientation="Vertical" 
            VerticalAlignment="Center" 
            HorizontalAlignment="Center">
            <!-- Slider for rotational input -->
            <Slider x:Name="RotationSlider0"
              Width="300"
              HorizontalAlignment="Left"/>
            <!-- Switch for button input -->
            <ToggleSwitch x:Name="ButtonToggle0"
                HorizontalAlignment="Left"/>
          </StackPanel>
        </Grid>
        <Grid x:Name="Grid1"
          Grid.Row="0"
          Grid.Column="1">
          <StackPanel Orientation="Vertical" 
            VerticalAlignment="Center" 
            HorizontalAlignment="Center">
            <!-- Slider for rotational input -->
            <Slider x:Name="RotationSlider1"
              Width="300"
              HorizontalAlignment="Left"/>
            <!-- Switch for button input -->
            <ToggleSwitch x:Name="ButtonToggle1"
                HorizontalAlignment="Left"/>
          </StackPanel>
        </Grid>
        <Grid x:Name="Grid2"
          Grid.Row="1"
          Grid.Column="0">
          <StackPanel Orientation="Vertical" 
            VerticalAlignment="Center" 
            HorizontalAlignment="Center">
            <!-- Slider for rotational input -->
            <Slider x:Name="RotationSlider2"
              Width="300"
              HorizontalAlignment="Left"/>
            <!-- Switch for button input -->
            <ToggleSwitch x:Name="ButtonToggle2"
                HorizontalAlignment="Left"/>
          </StackPanel>
        </Grid>
        <Grid x:Name="Grid3"
          Grid.Row="1"
          Grid.Column="1">
          <StackPanel Orientation="Vertical" 
            VerticalAlignment="Center" 
            HorizontalAlignment="Center">
            <!-- Slider for rotational input -->
            <Slider x:Name="RotationSlider3"
              Width="300"
              HorizontalAlignment="Left"/>
            <!-- Switch for button input -->
            <ToggleSwitch x:Name="ButtonToggle3"
                HorizontalAlignment="Left"/>
          </StackPanel>
        </Grid>
      </Grid>
    </Grid>
    
  2. 下面是为 Surface Dial 屏幕位置定义的处理程序的代码隐藏。

    Slider ActiveSlider;
    ToggleSwitch ActiveSwitch;
    Grid ActiveGrid;
    
    public MainPage()
    {
      ...
    
      myController.ScreenContactStarted += 
        MyController_ScreenContactStarted;
      myController.ScreenContactContinued += 
        MyController_ScreenContactContinued;
      myController.ScreenContactEnded += 
        MyController_ScreenContactEnded;
      myController.ControlLost += MyController_ControlLost;
    
      //Set initial grid for Surface Dial input.
      ActiveGrid = Grid0;
      ActiveSlider = RotationSlider0;
      ActiveSwitch = ButtonToggle0;
    }
    
    private void MyController_ScreenContactStarted(RadialController sender, 
      RadialControllerScreenContactStartedEventArgs args)
    {
      //find grid at contact location, update visuals, selection
      ActivateGridAtLocation(args.Contact.Position);
    }
    
    private void MyController_ScreenContactContinued(RadialController sender, 
      RadialControllerScreenContactContinuedEventArgs args)
    {
      //if a new grid is under contact location, update visuals, selection
      if (!VisualTreeHelper.FindElementsInHostCoordinates(
        args.Contact.Position, RootGrid).Contains(ActiveGrid))
      {
        ActiveGrid.Background = new 
          SolidColorBrush(Windows.UI.Colors.White);
        ActivateGridAtLocation(args.Contact.Position);
      }
    }
    
    private void MyController_ScreenContactEnded(RadialController sender, object args)
    {
      //return grid color to normal when contact leaves screen
      ActiveGrid.Background = new 
      SolidColorBrush(Windows.UI.Colors.White);
    }
    
    private void MyController_ControlLost(RadialController sender, object args)
    {
      //return grid color to normal when focus lost
      ActiveGrid.Background = new 
        SolidColorBrush(Windows.UI.Colors.White);
    }
    
    private void ActivateGridAtLocation(Point Location)
    {
      var elementsAtContactLocation = 
        VisualTreeHelper.FindElementsInHostCoordinates(Location, 
          RootGrid);
    
      foreach (UIElement element in elementsAtContactLocation)
      {
        if (element as Grid == Grid0)
        {
          ActiveSlider = RotationSlider0;
          ActiveSwitch = ButtonToggle0;
          ActiveGrid = Grid0;
          ActiveGrid.Background = new SolidColorBrush( 
            Windows.UI.Colors.LightGoldenrodYellow);
          return;
        }
        else if (element as Grid == Grid1)
        {
          ActiveSlider = RotationSlider1;
          ActiveSwitch = ButtonToggle1;
          ActiveGrid = Grid1;
          ActiveGrid.Background = new SolidColorBrush( 
            Windows.UI.Colors.LightGoldenrodYellow);
          return;
        }
        else if (element as Grid == Grid2)
        {
          ActiveSlider = RotationSlider2;
          ActiveSwitch = ButtonToggle2;
          ActiveGrid = Grid2;
          ActiveGrid.Background = new SolidColorBrush( 
            Windows.UI.Colors.LightGoldenrodYellow);
          return;
        }
        else if (element as Grid == Grid3)
        {
          ActiveSlider = RotationSlider3;
          ActiveSwitch = ButtonToggle3;
          ActiveGrid = Grid3;
          ActiveGrid.Background = new SolidColorBrush( 
            Windows.UI.Colors.LightGoldenrodYellow);
          return;
        }
      }
    }
    

运行应用时,我们使用 Surface Dial 与其交互。 首先,我们将设备放置在 Surface Studio 屏幕上,应用将设备检测并与其关联到右下部分(请参阅图像)。 然后,长按 Surface Dial 打开菜单并选择自定义工具。 激活自定义工具后,可以通过旋转 Surface Dial 来调整滑块控件,并通过单击 Surface Dial 切换开关。

径向控制器示例的屏幕截图,其中四个水平滑块设置为左侧,第四个控制器突出显示。
使用 Surface Dial 自定义工具激活的示例应用 UI

总结

本主题概述 Surface Dial 输入设备,其中包含 UX 和开发人员指南,介绍如何在与 Surface Studio 一起使用时自定义屏幕外方案的用户体验以及屏幕方案。

请将你的问题、建议和反馈发送给 radialcontroller@microsoft.com

教程:在 Windows 应用中支持 Surface Dial(和其他滚轮设备)

API 参考

示例

主题示例

RadialController 自定义项

其他示例

Coloring Book 示例

入门教程:在 Windows 应用中支持 Surface Dial(和其他滚轮设备)

通用 Windows 平台示例(C# 和 C++)

Windows 桌面示例