简体   繁体   English

WP7/ Silverlight - 无法使用 Linq 和 WebClient 显示 XML 元素

[英]WP7/ Silverlight - Unable to display XML element using Linq and WebClient

I am trying to display elements from an XML file hosted remotely and display in a list box.我正在尝试显示远程托管的 XML 文件中的元素并显示在列表框中。

When I press the button I am getting a Formal Exception was unhandled.当我按下按钮时,我得到一个未处理的正式异常。 I have attached a screenshot of error![enter image description here][1]我附上了错误截图![在此处输入图片描述][1]

using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Animation;
using System.Windows.Shapes;
using Microsoft.Phone.Controls;
using Microsoft.Phone.Tasks;
using System.Xml;
using System.Xml.Linq;

namespace tvGuide
{
    public partial class MainPage : PhoneApplicationPage
    {
        // Constructor
        public MainPage()
        {
            InitializeComponent();

         }



        private void button1_Click(object sender, RoutedEventArgs e)
        {
            WebClient c = new WebClient();
            c.DownloadStringCompleted += new DownloadStringCompletedEventHandler(c_DownloadStringCompleted);
            c.DownloadStringAsync(new Uri("http://www.designized.com/tv/freeview.xml?"));
        }

        void c_DownloadStringCompleted(object sender, DownloadStringCompletedEventArgs e)
        {
            if (e.Error != null)
                return;

            XElement r = XElement.Parse(e.Result);


            listBox1.ItemsSource = from tv in r.Descendants("programme")
                                   select new TVNZ
                                   {
                                       DisplayName = Convert.ToInt32(tv.Element("title").Value),
                                       ChannelURL = Convert.ToInt32(tv.Element("category").Value),
                                      ImageSource = Convert.ToInt32(tv.Element("url").Value),



                                   };
        }
        }

        public class TVNZ
        {
            public int DisplayName { get; set; }
            public int ChannelURL { get; set; }
            public int ImageSource { get; set; }



        }





    }

mainpage.xaml next...主页.xaml 下一个...

<phone:PhoneApplicationPage 
    x:Class="tvGuide.MainPage"
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:phone="clr-namespace:Microsoft.Phone.Controls;assembly=Microsoft.Phone"
    xmlns:task="clr-namespace:Microsoft.Phone.Tasks;assembly=Microsoft.Phone"
    xmlns:shell="clr-namespace:Microsoft.Phone.Shell;assembly=Microsoft.Phone"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
    xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
    mc:Ignorable="d" d:DesignWidth="480" d:DesignHeight="768"
    FontFamily="{StaticResource PhoneFontFamilyNormal}"
    FontSize="{StaticResource PhoneFontSizeNormal}"
    Foreground="{StaticResource PhoneForegroundBrush}"
    SupportedOrientations="Portrait" Orientation="Portrait"
    shell:SystemTray.IsVisible="True">

    <!--LayoutRoot is the root grid where all page content is placed-->
    <Grid x:Name="LayoutRoot" Background="Transparent">
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto"/>
            <RowDefinition Height="*"/>
        </Grid.RowDefinitions>

        <!--TitlePanel contains the name of the application and page title-->
        <StackPanel x:Name="TitlePanel" Grid.Row="0" Margin="12,17,0,28">
            <TextBlock x:Name="ApplicationTitle" Text="MY APPLICATION" Style="{StaticResource PhoneTextNormalStyle}"/>
            <TextBlock x:Name="PageTitle" Text="page name" Margin="9,-7,0,0" Style="{StaticResource PhoneTextTitle1Style}"/>
        </StackPanel>

        <!--ContentPanel - place additional content here-->
        <Grid x:Name="ContentPanel" Grid.Row="1" Margin="12,0,12,0">
            <ListBox Height="595" HorizontalAlignment="Left" Margin="6,6,0,0" Name="listBox1" VerticalAlignment="Top" Width="444">
                <ListBox.ItemTemplate>
                    <DataTemplate>
                        <StackPanel Orientation="Horizontal" Height="132">
                            <Image Source="{Binding ImageSource}" Height="73" Width="73" VerticalAlignment="Top" Margin="0,10,8,0"/>
                            <StackPanel Width="370">
                                <TextBlock Text="{Binding DisplayName}" Foreground="#FFC8AB14" FontSize="28" />
                                <TextBlock Text="{Binding ChannelURL}" TextWrapping="Wrap" FontSize="24" />
                            </StackPanel>
                        </StackPanel>
                    </DataTemplate>
                </ListBox.ItemTemplate>
            </ListBox>
        </Grid>
    </Grid>

    <!--Sample code showing usage of ApplicationBar-->
    <!--<phone:PhoneApplicationPage.ApplicationBar>
        <shell:ApplicationBar IsVisible="True" IsMenuEnabled="True">
            <shell:ApplicationBarIconButton IconUri="/Images/appbar_button1.png" Text="Button 1"/>
            <shell:ApplicationBarIconButton IconUri="/Images/appbar_button2.png" Text="Button 2"/>
            <shell:ApplicationBar.MenuItems>
                <shell:ApplicationBarMenuItem Text="MenuItem 1"/>
                <shell:ApplicationBarMenuItem Text="MenuItem 2"/>
            </shell:ApplicationBar.MenuItems>
        </shell:ApplicationBar>
    </phone:PhoneApplicationPage.ApplicationBar>-->

</phone:PhoneApplicationPage>

And now the XML file in questions:现在有问题的 XML 文件:

<tv date="20110708031152" generator-info-name="epgsnoop/0.84" generator-info-url="http://launchpad.net/epgsnoop">
- <channel id="maori-tv.freeviewnz.tv">
  <display-name>Maori TV</display-name> 
  <icon src="http://nzepg.org/logos/maori.jpg" /> 
  <url>http://www.freeviewnz.tv/</url> 
  </channel>
- <channel id="georgefm.freeviewnz.tv">
  <display-name>GeorgeFM</display-name> 
  </channel>
- <channel id="basefm.freeviewnz.tv">
  <display-name>BaseFM</display-name> 
  </channel>
- <channel id="rnz-concert.freeviewnz.tv">
  <display-name>RNZ Concert</display-name> 
  </channel>
- <channel id="stratos.freeviewnz.tv">
  <display-name>Stratos</display-name> 
  <icon src="http://nzepg.org/logos/stratos.jpg" /> 
  <url>http://www.stratostv.co.nz/</url> 
  </channel>
- <channel id="tv3.freeviewnz.tv">
  <display-name>TV 3</display-name> 
  <icon src="http://nzepg.org/logos/tv3.jpg" /> 
  <url>http://www.tv3.co.nz/</url> 
  </channel>
- <channel id="four.freeviewnz.tv">
  <display-name>Four</display-name> 
  <icon src="http://nzepg.org/logos/four.jpg" /> 
  </channel>
- <channel id="tvnz7.freeviewnz.tv">
  <display-name>TVNZ 7</display-name> 
  <icon src="http://nzepg.org/logos/tvnz7.jpg" /> 
  <url>http://www.freeviewnz.tv/</url> 
  </channel>
- <channel id="parliament.freeviewnz.tv">
  <display-name>Parliament</display-name> 
  <icon src="http://nzepg.org/logos/parliament.jpg" /> 
  <url>http://www.freeviewnz.tv/</url> 
  </channel>

Any help would be greatly appreciated.任何帮助将不胜感激。

I tried to run it but there were some issues in your code我尝试运行它,但您的代码中存在一些问题

  1. all those field must be string not int!所有这些字段都必须是字符串而不是 int!
  2. all are optional to need to check against null所有都是可选的,需要检查 null
  3. attribute names were reading something different than the ones in xml!属性名称读取的内容与 xml 中的不同!

This works:这有效:

var r = XDocument.Parse(e.Result);
listBox1.ItemsSource = from tv in r.Root.Descendants("channel")
                        let nameEl = tv.Element("display-name")
                        let urlEl = tv.Element("url")
                        let iconEl = tv.Element("icon")
                        select new TVNZ
                        {
                            DisplayName = nameEl == null ? null : nameEl.Value,
                            ChannelURL = urlEl == null ? null : urlEl.Value,
                            ImageSource = iconEl == null ? null : iconEl.Attribute("src").Value,
                        };

also change class to:还将 class 更改为:

public class TVNZ
{
    public string DisplayName { get; set; }
    public string ChannelURL { get; set; }
    public string ImageSource { get; set; }
}

Conclusion: First define your problem domain before start coding.结论:在开始编码之前首先定义您的问题域。


Just one side point, using WebClient runs completely on UI thread and your application is unresponsive untill the response is back.一方面,使用 WebClient 完全在 UI 线程上运行,并且您的应用程序在响应返回之前没有响应。 So it's recommended to use HttpWebRequest instead which can run on a separate thread.所以建议使用 HttpWebRequest 代替它可以在单独的线程上运行。

Here in my blog post I have prepared a helper class for async web download purposes.在我的博客文章中,我为异步 web 下载目的准备了一个助手 class。 Feel free to use.随意使用。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM