情報
要求されたトピックは次のとおりです。しかし、このトピックはこのライブラリには含まれていません。

Windows Phone 8 用の基本的な RSS リーダーを作成する方法

2014/06/18

対象: Windows Phone 8 および Windows Phone Silverlight 8.1 | Windows Phone OS 7.1

次の手順を実行して、基本的な RSS リーダーを作成することができます。ここで示すガイドとコード例は、RSS リーダー サンプルというコード例を基にしています。

このトピックは、次のセクションで構成されています。

Visual Studio で、新しい Windows Phone アプリ プロジェクトを作成します。

SyndicationFeed クラスを使用するには、まず DLL 参照を追加する必要があります。

Syndication DLL に参照を追加するには

  1. Visual Studio で、[プロジェクト] メニューの [参照の追加] を選択し、[参照] タブを選択します。

  2. Program Files (x86) ディレクトリに移動します。

  3. Microsoft SDKs/Silverlight/v4.0/Libraries/Client/ に移動します。

  4. System.ServiceModel.Syndication.dll を選択して [OK] をクリックします。

    メモメモ:

    ここで、続行するかどうかを確認するメッセージが表示されたら、[はい] をクリックします。

RSS フィードの説明テキストには、HTML、エンコードされた文字、その他 RSS リーダーに表示したくないようなデータが含まれることがよくあります。HTML やその他の不要なデータを説明テキストから除去するためのクラスを作成し、XAML フィールドのコンバーターとしてクラスを設定することができます。

RSS テキスト トリマーを作成するには

  1. ソリューション エクスプローラーで、プロジェクト名を右クリックし、[追加] をクリックし、[新しい項目] をクリックします。

  2. [インストールされたテンプレート] ペインで、[Visual C#] を選択し、中央のペインで [クラス] を選択します。

  3. ファイルに RssTextTrimmer.cs という名前を付けて [追加] をクリックします。

  4. ソリューション エクスプローラーで、RssTextTrimmer.cs ファイルをダブルクリックします。

  5. 次の名前空間を追加します。

    using System.Windows.Data;
    using System.Globalization;
    using System.Text.RegularExpressions;
    
    
  6. IValueConverter インターフェイスを実装するようにクラス定義を更新します。

    public class RssTextTrimmer : IValueConverter
    
    
  7. RssTextTrimmer クラス内に次のコードを追加します。

    // Clean up text fields from each SyndicationItem. 
    public object Convert(object value, Type targetType, object parameter, CultureInfo culture)
    {
        if (value == null) return null;
    
        int maxLength = 200;
        int strLength = 0;
        string fixedString = "";
    
        // Remove HTML tags and newline characters from the text, and decode HTML encoded characters. 
        // This is a basic method. Additional code would be needed to more thoroughly  
        // remove certain elements, such as embedded Javascript. 
    
        // Remove HTML tags. 
        fixedString = Regex.Replace(value.ToString(), "<[^>]+>", string.Empty);
    
        // Remove newline characters.
        fixedString = fixedString.Replace("\r", "").Replace("\n", "");
    
        // Remove encoded HTML characters.
        fixedString = HttpUtility.HtmlDecode(fixedString);
    
        strLength = fixedString.ToString().Length;
    
        // Some feed management tools include an image tag in the Description field of an RSS feed, 
        // so even if the Description field (and thus, the Summary property) is not populated, it could still contain HTML. 
        // Due to this, after we strip tags from the string, we should return null if there is nothing left in the resulting string. 
        if (strLength == 0)
        {
            return null;
        }
    
        // Truncate the text if it is too long. 
        else if (strLength >= maxLength)
        {
            fixedString = fixedString.Substring(0, maxLength);
    
            // Unless we take the next step, the string truncation could occur in the middle of a word.
            // Using LastIndexOf we can find the last space character in the string and truncate there. 
            fixedString = fixedString.Substring(0, fixedString.LastIndexOf(" "));
        }
    
        fixedString += "...";
    
        return fixedString;
    }
    
    // This code sample does not use TwoWay binding, so we do not need to flesh out ConvertBack.  
    public object ConvertBack(object value, Type targetType, object parameter, CultureInfo culture)
    {
        throw new NotImplementedException();
    }
    
    
  8. ソリューション エクスプローラーApp.xaml をダブルクリックし、<Application.Resources> タグ内に以下のコードを追加して、RssTextTrimmer クラスをコンバーターとして設定します。

    <converter:RssTextTrimmer xmlns:converter="clr-namespace:namespace" x:Key="RssTextTrimmer" />
    
    

    namespace は自分のプロジェクトの名前空間で置き換えてください。たとえば、Windows Phone 8 用の基本的な RSS リーダーのサンプルでは、namespace は sdkBasicRSSReaderWP8CS で置き換えます。

XAML コードを更新するには

  1. ソリューション エクスプローラーで、MainPage.xaml ファイルをダブルクリックします。

  2. <Grid x:Name="ContentPanel" Grid.Row="1" Margin="12,0,12,0"></Grid> を次の XAML コードに置き換えます。

    <Grid x:Name="ContentPanel" Grid.Row="1" Margin="0,0,12,0">
        <Button Content="Load Feed" Height="72" HorizontalAlignment="Left" Margin="9,6,0,0" Name="loadFeedButton" VerticalAlignment="Top" Width="273" Click="loadFeedButton_Click" />
    
        <ListBox Name="feedListBox" Height="468" HorizontalAlignment="Left" Margin="20,100,0,0" VerticalAlignment="Top" Width="444" ScrollViewer.VerticalScrollBarVisibility="Auto" SelectionChanged="feedListBox_SelectionChanged">
            <ListBox.ItemTemplate>
                <DataTemplate>
                    <StackPanel VerticalAlignment="Top">
                        <TextBlock TextDecorations="Underline" FontSize="24" Name="feedTitle" TextWrapping="Wrap" Margin="12,0,0,0" HorizontalAlignment="Left" Foreground="{StaticResource PhoneAccentBrush}" Text="{Binding Title.Text, Converter={StaticResource RssTextTrimmer}}" />
                        <TextBlock Name="feedSummary" TextWrapping="Wrap" Margin="12,0,0,0" Text="{Binding Summary.Text, Converter={StaticResource RssTextTrimmer}}" />
                        <TextBlock Name="feedPubDate" Foreground="{StaticResource PhoneSubtleBrush}" Margin="12,0,0,10" Text="{Binding PublishDate.DateTime}" />
                    </StackPanel>
                </DataTemplate>
            </ListBox.ItemTemplate>
        </ListBox>
        <Border BorderBrush="{StaticResource PhoneSubtleBrush}" BorderThickness="1" Height="2" HorizontalAlignment="Left" Margin="20,88,0,0" Name="border1" VerticalAlignment="Top" Width="438" />
    </Grid>
    
    

分離コード ファイルを更新するには

  1. 次の名前空間を追加します。

    using System.IO;
    using System.ServiceModel.Syndication;
    using System.Xml;
    using Microsoft.Phone.Tasks;
    
    
  2. MainPage クラス内の MainPage コンストラクターの後に以下のコードを追加します。

    メモメモ:

    基本的な廃棄機能のサポートも以下のコード内に含まれます。

    // Click handler that runs when the 'Load Feed' or 'Refresh Feed' button is clicked. 
    private void loadFeedButton_Click(object sender, System.Windows.RoutedEventArgs e)
    {
        // WebClient is used instead of HttpWebRequest in this code sample because 
        // the implementation is simpler and easier to use, and we do not need to use 
        // advanced functionality that HttpWebRequest provides, such as the ability to send headers.
        WebClient webClient = new WebClient();
    
        // Subscribe to the DownloadStringCompleted event prior to downloading the RSS feed.
        webClient.DownloadStringCompleted += new DownloadStringCompletedEventHandler(webClient_DownloadStringCompleted);
    
        // Download the RSS feed. DownloadStringAsync was used instead of OpenStreamAsync because we do not need 
        // to leave a stream open, and we will not need to worry about closing the channel. 
        webClient.DownloadStringAsync(new System.Uri("http://windowsteamblog.com/windows_phone/b/windowsphone/rss.aspx"));
    }
    
    // Event handler which runs after the feed is fully downloaded.
    private void webClient_DownloadStringCompleted(object sender, DownloadStringCompletedEventArgs e)
    {
        if (e.Error != null)
        {
            Deployment.Current.Dispatcher.BeginInvoke(() =>
            {
                // Showing the exact error message is useful for debugging. In a finalized application, 
                // output a friendly and applicable string to the user instead. 
                MessageBox.Show(e.Error.Message);
            });
        }
        else
        {
            // Save the feed into the State property in case the application is tombstoned. 
            this.State["feed"] = e.Result;
    
            UpdateFeedList(e.Result);
        }
    }
    
    // This method determines whether the user has navigated to the application after the application was tombstoned.
    protected override void OnNavigatedTo(System.Windows.Navigation.NavigationEventArgs e)
    {
        // First, check whether the feed is already saved in the page state.
        if (this.State.ContainsKey("feed"))
        {
            // Get the feed again only if the application was tombstoned, which means the ListBox will be empty.
            // This is because the OnNavigatedTo method is also called when navigating between pages in your application.
            // You would want to rebind only if your application was tombstoned and page state has been lost. 
            if (feedListBox.Items.Count == 0)
            {
                UpdateFeedList(State["feed"] as string);
            }
        }
    }
    
    // This method sets up the feed and binds it to our ListBox. 
    private void UpdateFeedList(string feedXML)
    {
        // Load the feed into a SyndicationFeed instance.
        StringReader stringReader = new StringReader(feedXML);
        XmlReader xmlReader = XmlReader.Create(stringReader);
        SyndicationFeed feed = SyndicationFeed.Load(xmlReader);
    
        // In Windows Phone OS 7.1 or later versions, WebClient events are raised on the same type of thread they were called upon. 
        // For example, if WebClient was run on a background thread, the event would be raised on the background thread. 
        // While WebClient can raise an event on the UI thread if called from the UI thread, a best practice is to always 
        // use the Dispatcher to update the UI. This keeps the UI thread free from heavy processing.
        Deployment.Current.Dispatcher.BeginInvoke(() =>
        {
            // Bind the list of SyndicationItems to our ListBox.
            feedListBox.ItemsSource = feed.Items;
    
            loadFeedButton.Content = "Refresh Feed";
        });
    }
    
    // The SelectionChanged handler for the feed items 
    private void feedListBox_SelectionChanged(object sender, SelectionChangedEventArgs e)
    {
        ListBox listBox = sender as ListBox;
    
        if (listBox != null && listBox.SelectedItem != null)
        {
            // Get the SyndicationItem that was tapped.
            SyndicationItem sItem = (SyndicationItem)listBox.SelectedItem;
    
            // Set up the page navigation only if a link actually exists in the feed item.
            if (sItem.Links.Count > 0)
            {
                // Get the associated URI of the feed item.
                Uri uri = sItem.Links.FirstOrDefault().Uri;
    
                // Create a new WebBrowserTask Launcher to navigate to the feed item. 
                // An alternative solution would be to use a WebBrowser control, but WebBrowserTask is simpler to use. 
                WebBrowserTask webBrowserTask = new WebBrowserTask();
                webBrowserTask.Uri = uri;
                webBrowserTask.Show();
            }
        }
    }
    
    

その他の技術情報

表示: