如何自定义 Visual Studio 模板数据 (XAML)

Applies to Windows and Windows Phone

数据已显示在“中心”、“网格”、“拆分”和“透视”项目的页面中。这是因为这些模板包含可以实现此目的的文件、代码和 XAML 标记。 修改这些文件以显示数据比开始一个空页面并从头开始添加所有内容更方便。

有关更深入的示例,请参阅快速入门:从服务中读取数据

项目和组

“中心”、“网格”、“拆分”和“透视”项目将数据整理到项目组中。 项目中的 SampleDataSource 文件包含以下项目组。 它通过定义以下三个类执行此操作:

  • SampleDataGroup
  • SampleDataItem
  • SampleDataSource

The SampleDataSource 将创建组和项目的实例,并通过使用项目的 SampleData.json 文件中的数据填充它们。

如果数据近似于 SampleDataItem 和 SampleDataGroup 类的结构,你可以在 GetSampleDataAsync 函数中更新代码以检索数据。如果你决定添加新数据属性,你将需要更新 SampleDataItem 和 SampleDataGroup 构造函数。

如果连接到在设计时可能不可用(或者加载速度可能不够快)的实时数据,则可以更改 DesignData 源以提供备用示例数据。这样,你可以在 XAML 设计器的设计图面上看到数据。下面是 GroupDetailPage.xaml 在“网格应用”模板中的示例。该示例还使用 SampleData.json 中在设计时定义的默认示例数据。


<CollectionViewSource
    x:Name="itemsViewSource"
    Source="{Binding Items}"
    d:Source="{Binding Groups[0].Items, Source={d:DesignData Source=/DataModel/SampleData.json}}"/>


如果你将 DesignData 源原封不动地与任何其他 DesignData 引用一起放置在 XAML 文件中,将从 SampleData.json 中提取设计时值。

如何将组和项目数据绑定到用户界面

在模板中,数据通常通过默认 DataContext 绑定到 UI。 DataContext 绑定到 DefaultViewModel,后者在每页中定义。

在每页中,数据加载到 LoadState 事件中,同时调用 SampleDataSource。在检索数据时,会将数据分配给 DefaultViewModel,如下例所示。


var sampleDataGroups = await SampleDataSource.GetGroupsAsync((String)e.NavigationParameter);
this.DefaultViewModel["Groups"] = sampleDataGroups;

通常使用在 XAML 页面中实现的数据模板,它们可以用于格式化并显示多个数据实例。每个数据模板都绑定到以 XAML 显式定义的属性,如以下示例所示:


<DataTemplate>
    <Grid HorizontalAlignment="Left" Width="250" Height="250">
        <Border Background="{StaticResource ListViewItemPlaceholderBackgroundThemeBrush}">
            <Image Source="{Binding ImagePath}" Stretch="UniformToFill" AutomationProperties.Name="{Binding Title}"/>
        </Border>
        <StackPanel VerticalAlignment="Bottom" Background="{StaticResource ListViewItemOverlayBackgroundThemeBrush}">
             <TextBlock Text="{Binding Title}" Foreground="{StaticResource ListViewItemOverlayForegroundThemeBrush}"
                 Style="{StaticResource TitleTextBlockStyle}" Height="60" Margin="15,0,15,0"/>
             <TextBlock Text="{Binding Subtitle}" Foreground="{StaticResource ListViewItemOverlaySecondaryForegroundThemeBrush}"
                 Style="{StaticResource CaptionTextBlockStyle}" TextWrapping="NoWrap" Margin="15,0,15,10"/>
        </StackPanel>
    </Grid>
</DataTemplate>>

尤其需要了解的是,项目模板预期数据中显示某些属性,这些属性以 XAML 显式命名。在前面用于 GroupedItemsPage 的 XAML 代码中,你可以找到诸如标题、副标题以及图像路径之类的属性。如果你的自定义应用数据不使用这些特定属性名称,则需要执行下列操作之一:

  • 将你的数据映射到这些属性名称(一般在 SampleDataSource 中)。
  • 修复模板代码中这些属性的所有 XAML 和代码引用,以使它们与你的数据中使用的属性名称相匹配。

如何将数据合并到项目中的示例

首先,更新 SampleDataSource 文件,以便组和项目从你的数据定义字段。然后,将该数据绑定到你的页面中的字段。本部分使用请求生成 RSS 数据。

JJ655409.wedge(zh-cn,WIN.10).gif更新 SampleDataSource

  1. 在 Visual Studio 菜单上,单击“文件”>“新建项目”
  2. 在“新建项目”对话框的左侧窗格中,展开 Visual C#Visual BasicVisual C++ 节点。
  3. 在中心窗格中,单击“中心应用”、“网格应用”或“拆分应用”。
  4. 在“名称”框中,键入 DataModelExample,然后单击“确定”。

    此刻,解决方案已创建并且项目文件显示在“解决方案资源管理器”中。有关项目文件的详细信息,请参阅 C#、VB 和 C++ 项目模板

    要点  首次运行 Visual Studio 时,它会提示你获取开发人员许可证。有关详细信息,请参阅获取开发人员许可证

  5. DataModel 文件夹中,打开 SampleDataSource。
  6. 在 SampleDataItem 中,添加发布日期、作者和链接的属性,并更新此构造函数。下面是用于 SampleDataItem 的新构造函数代码:
    
    public SampleDataItem(String uniqueId, String title, String subtitle, String imagePath,
         String description, String content, String pubDate, String author, String uriLink)
    {
        this.UniqueId = uniqueId;
        this.Title = title;
        this.Subtitle = subtitle;
        this.Description = description;
        this.ImagePath = imagePath;
        this.Content = content;
        // Added
        this.PubDate = pubDate;
        this.Author = author;
        this.Link = uriLink;
    }
    
    
    
  7. 将以下用于新属性的声明添加到 SampleDataItem:
    
        // Added
        public string PubDate { get; private set; }
        public string Author { get; private set; }
        public string Link { get; private set; }
    
    
  8. 在 SampleDataGroup 中,为发布的日期添加一个新属性,并更新此构造函数。下面是用于 SampleDataGroup 的新构造函数代码:
    
    public SampleDataGroup(String uniqueId, String title, String subtitle, String imagePath,
        String description, String pubDate)
    {
        this.UniqueId = uniqueId;
        this.Title = title;
        this.Subtitle = subtitle;
        this.Description = description;
        this.ImagePath = imagePath;
        // Added
        this.PubDate = pubDate;
    
        this.Items = new ObservableCollection<SampleDataItem>();
    
    }
    
    
  9. 将以下用于新属性的声明添加到 SampleDataGroup:
    
        public string PubDate { get; private set; }
    
    
  10. 在 SampleDataSource 中,删除 GetSampleDataAsync 函数及其包含的所有代码。使用以下函数替换这个同样称为 GetSampleDataAsync 的函数:
    
    private async Task GetSampleDataAsync()
    {
        if (this._allGroups.Count != 0)
            return;
    
        await GetFeedsAsync();
    
    }
    
    

    提示  如果可以检索 JSON 格式的数据,则也许能够在 GetSampleDataAsync 中重用更多示例代码。

  11. 在 SampleDataSource 中,添加以下函数:
    
    
    public async Task GetFeedsAsync()
    {
        Task<SampleDataGroup> feed1 =
            GetFeedAsync("http://windowsteamblog.com/windows/b/developers/atom.aspx");
        Task<SampleDataGroup> feed2 =
            GetFeedAsync("http://windowsteamblog.com/windows/b/windowsexperience/atom.aspx");
        Task<SampleDataGroup> feed3 =
            GetFeedAsync("http://windowsteamblog.com/windows/b/extremewindows/atom.aspx");
        Task<SampleDataGroup> feed4 =
            GetFeedAsync("http://windowsteamblog.com/windows/b/business/atom.aspx");
        Task<SampleDataGroup> feed5 =
            GetFeedAsync("http://windowsteamblog.com/windows/b/bloggingwindows/atom.aspx");
        Task<SampleDataGroup> feed6 =
            GetFeedAsync("http://windowsteamblog.com/windows/b/windowssecurity/atom.aspx");
        Task<SampleDataGroup> feed7 =
            GetFeedAsync("http://windowsteamblog.com/windows/b/springboard/atom.aspx");
        Task<SampleDataGroup> feed8 =
            GetFeedAsync("http://windowsteamblog.com/windows/b/windowshomeserver/atom.aspx");
        // There is no Atom feed for this blog, so we use the RSS feed.
        Task<SampleDataGroup> feed9 =
            GetFeedAsync("http://windowsteamblog.com/windows_live/b/windowslive/rss.aspx");
        Task<SampleDataGroup> feed10 =
            GetFeedAsync("http://windowsteamblog.com/windows_live/b/developer/atom.aspx");
        Task<SampleDataGroup> feed11 =
            GetFeedAsync("http://windowsteamblog.com/ie/b/ie/atom.aspx");
        Task<SampleDataGroup> feed12 =
            GetFeedAsync("http://windowsteamblog.com/windows_phone/b/wpdev/atom.aspx");
        Task<SampleDataGroup> feed13 =
            GetFeedAsync("http://windowsteamblog.com/windows_phone/b/wmdev/atom.aspx");
    
        this._allGroups.Add(await feed1);
        this._allGroups.Add(await feed2);
        this._allGroups.Add(await feed3);
        this._allGroups.Add(await feed4);
        this._allGroups.Add(await feed5);
        this._allGroups.Add(await feed6);
        this._allGroups.Add(await feed7);
        this._allGroups.Add(await feed8);
        this._allGroups.Add(await feed9);
        this._allGroups.Add(await feed10);
        this._allGroups.Add(await feed11);
        this._allGroups.Add(await feed12);
        this._allGroups.Add(await feed13);
    }
    
    
  12. 将以下 using 语句添加到页首:
    
    using Windows.Web.Syndication;
    
    
    
  13. 将以下方法添加到 SampleDataSource:
    
    private async Task<SampleDataGroup> GetFeedAsync(string feedUriString)
    {
        // using Windows.Web.Syndication;
        SyndicationClient client = new SyndicationClient();
        Uri feedUri = new Uri(feedUriString);
    
        try
        {
            SyndicationFeed feed = await client.RetrieveFeedAsync(feedUri);
    
            string description = "tbd";
            // Use the date of the latest post as the last updated date.
            string date = feed.Items[0].PublishedDate.DateTime.ToString();
    
    
            if (feed.Subtitle != null && feed.Subtitle.Text != null)
            {
                description = feed.Subtitle.Text;
            }
    
            // This code is executed after RetrieveFeedAsync returns the SyndicationFeed.
            // Process it and copy the data we want into our FeedData and FeedItem classes.
            SampleDataGroup feedData = new SampleDataGroup(feed.Id, feed.Title.Text, 
                feed.Subtitle.Text, null, description, date);
    
            foreach (SyndicationItem item in feed.Items)
            {
                string content = "tbd";
                string uriLink = "tbd";
                string author = item.Authors[0].Name.ToString();
                string datePub = item.PublishedDate.DateTime.ToString();
    
                // Handle the differences between RSS and Atom feeds.
                if (feed.SourceFormat == SyndicationFormat.Atom10)
                {
                    content = item.Content.Text;
                    uriLink = new Uri("http://windowsteamblog.com" + item.Id).ToString();
                }
                else if (feed.SourceFormat == SyndicationFormat.Rss20)
                {
                    content = item.Summary.Text;
                    uriLink = item.Links[0].Uri.ToString();
                }
    
                SampleDataItem feedItem = new SampleDataItem(item.Id, item.Title.Text, "tbd",
                    null, null, content, datePub, author, uriLink);
               
                feedData.Items.Add(feedItem);
            }
    
            return feedData;
        }
        catch (Exception)
        {
           return null;
        }
    }
    
    
    
  14. 单击“构建”>“生成解决方案”,或者按 F7 确保生成解决方案且没有错误。

这些步骤假设你使用“网格”项目模板创建了项目。

JJ655409.wedge(zh-cn,WIN.10).gif如何将数据绑定到页面的示例

  1. 若要在“网格”应用项目模板中使用示例代码,请打开 GroupedItemsPage.xaml。
  2. 在 GroupedItemsPage.xaml 中,打开 XAML 设计器的快捷菜单中的“GridView”,然后依次选择“编辑其他模板”、“编辑通用项(ItemTemplate)”、“编辑当前”

    在 XAML 编辑器中将选中 GridView 的 DataTemplate。

  3. 将对 Subtitle 属性的绑定替换为对 PubDate 属性的绑定。

    包含此绑定的 TextBox 控件应该类似于以下示例:

    
    <TextBlock Text="{Binding Subtitle}" Foreground="{StaticResource ListViewItemOverlaySecondaryForegroundThemeBrush}"
        Style="{StaticResource CaptionTextBlockStyle}" TextWrapping="NoWrap" Margin="15,0,15,10"/>
    
    
  4. 打开 GroupDetailPage.xaml。
  5. 打开 XAML 设计器的快捷菜单中的“GridView”,然后依次选择“编辑其他模板”、“编辑通用项(ItemTemplate)”、“编辑当前”

    在 XAML 编辑器中将选中 GridView 的 DataTemplate。

  6. 在 DataTemplate 中找到 StackPanel,然后将 Subtitle 更改为 Author。

    包含此绑定的 TextBox 控件应该类似于以下示例:

    
    <TextBlock Text="{Binding Subtitle}" Style="{StaticResource CaptionTextBlockStyle}"
        TextWrapping="NoWrap"/>
    
    
  7. 在 XAML 设计器的左窗格中,选择“组副标题: 1”

    在 XAML 编辑器中将选中对应的 TextBlock。

  8. 将对 Subtitle 属性的绑定替换为对组 PubDate 属性的绑定。

    包含此绑定的 TextBox 控件应该类似于以下示例:

    
    <TextBlock Text="{Binding PubDate}" Margin="0,0,0,20" Style="{StaticResource SubheaderTextBlockStyle}"
        MaxHeight="60"/>
    
    
  9. 保存项目并选择 F5 键来调试应用。

    将立即显示页面标题,但检索源数据可能需要几秒钟。满足所有承诺时,将在主页中显示每个博客。选择组标题之一来显示组详细信息页面。

 

 

显示:
© 2014 Microsoft