2016-11-09 27 views
0

私はC#を学んでいて、現在UWPアプリでISupportIncrementalLoadingに取り組んでいますが、傾けることはできません。コンパイルする前からエラーが出ます。私はhereからアイディアを得ました。しかし、私は自分のアプリケーションでそれをどのように実装できるのか理解できません。ISupportIncrementalLoadingインターフェイスを実装する - UWP - C#

私はIIncrementalLoadingインターフェイスと、ObservableCollection<T>にコンテンツを動的に追加する別のクラスを持っています。 Incremental Loadingを実装していない場合、私のObservableCollectionSearchPage.xamlに動的にコンテンツを提供します.にはコンテンツが追加されますが、以前に生成されたアイテムが置き換えられ、代わりに新しいアイテムのみが表示されます。 SearchPage.xaml

コード:SearchPage.xaml.cs

<Page 
x:Class="WatchfreeWebsite.SearchPage" 
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
xmlns:local="using:WatchfreeWebsite" 
xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
xmlns:data="using:WatchfreeWebsite" 
mc:Ignorable="d"> 

<Grid Background="{ThemeResource ApplicationPageBackgroundThemeBrush}"> 

    <Grid.RowDefinitions> 
     <RowDefinition Height="Auto"/> 
     <RowDefinition Height="Auto"/> 
     <RowDefinition/> 
    </Grid.RowDefinitions> 

    <StackPanel> 
     <TextBlock Text="Search Results" 
        FontSize="20" 
        TextAlignment="Center"/> 
     <TextBlock Text="Search for Movies and TV Shows" 
        TextAlignment="Center" 
        TextWrapping="Wrap"/> 
     <HyperlinkButton x:Name="IndexPageLink" 
         Content="Go to Index" 
         HorizontalAlignment="Center" 
         Click="IndexPageLink_Click"/> 
    </StackPanel> 
    <StackPanel Grid.Row="1"> 
     <TextBox x:Name="SearchInputBox" 
       TextAlignment="Left" 
       Width="280" 
       PlaceholderText="search" 
       TextChanged="SearchInputBox_TextChanged"></TextBox> 
     <TextBlock x:Name="ErrorTextBox" 
        TextWrapping="Wrap" 
        TextAlignment="Center"/> 
    </StackPanel> 
    <GridView Grid.Row="2" 
       x:Name="SearchGrid" 
       HorizontalAlignment="Center" 
       ItemsSource="{x:Bind SearchList, Mode=OneWay}" 
       IsItemClickEnabled="True" 
       ItemClick="SearchGrid_ItemClick"> 
     <GridView.Header> 
      <StackPanel BorderBrush="Red" 
         BorderThickness="0,0,0,1" 
         Margin="5" 
         HorizontalAlignment="Center"> 
       <TextBlock Text="" 
          x:Name="SearchGridHeader" 
          TextAlignment="Center" 
          Margin="0"/> 
      </StackPanel> 
     </GridView.Header> 
     <GridView.ItemTemplate> 
      <DataTemplate x:DataType="data:SearchItems"> 
       <StackPanel BorderThickness="0,1,0,0" 
          BorderBrush="Red" 
          Margin="5"> 
        <TextBlock Text="{x:Bind SearchTitle, Mode=OneWay}" 
           TextAlignment="Center" 
           TextWrapping="Wrap" 
           Width="140" 
           Height="40"/> 
        <StackPanel BorderBrush="Red" BorderThickness="0,0,0,1" 
           Margin="0"> 
         <Image x:Name="CoverImage" 
           Source="{x:Bind SearchImageLink, Mode=OneWay}" 
           Width="130" 
           Height="200" 
           Margin="0"/> 
        </StackPanel> 
       </StackPanel> 
      </DataTemplate> 
     </GridView.ItemTemplate> 
     <GridView.Footer> 
      <HyperlinkButton x:Name="MoreItemsLink" 
          Content="Load more items" 
          Click="MoreItemsLink_Click" 
          Visibility="Collapsed"/> 
     </GridView.Footer> 
    </GridView> 
</Grid> 

コード:IncrementalLoadingInterface

using System; 
using System.Collections.Generic; 
using System.Collections.ObjectModel; 
using System.IO; 
using System.Linq; 
using System.Runtime.InteropServices.WindowsRuntime; 
using Windows.Foundation; 
using Windows.Foundation.Collections; 
using Windows.UI.Xaml; 
using Windows.UI.Xaml.Controls; 
using Windows.UI.Xaml.Controls.Primitives; 
using Windows.UI.Xaml.Data; 
using Windows.UI.Xaml.Input; 
using Windows.UI.Xaml.Media; 
using Windows.UI.Xaml.Navigation; 
using HtmlAgilityPack; 
using static WatchfreeWebsite.HtmlDocs; 



namespace WatchfreeWebsite 
{ 
public sealed partial class SearchPage : Page 
{ 
    HtmlDocument SearchDoc; 
    public static string[] SearchLinks = new string[500]; 
    public static string[] SearchTitles = new string[500]; 
    public static string[] SearchImageLinks = new string[500]; 
    public static string[] SearchNextPagesLinks = new string[50]; 

    public static int numberOfLinks = 0; 
    int numberOfTitles = 0; 
    int numberOfImages = 0; 
    int nextPage = 2; 
    int numberOfPages = 0; 
    public static int lastListItems = 0; 


    //IIncrementalSource<SearchItems> SearchList = new IncrementalLoadingCollection<GetTVShows(),SearchItems>(); 

    int listItems = 0; 
    DispatcherTimer sTimer = new DispatcherTimer(); 

    public SearchPage() 
    { 
     this.InitializeComponent(); 
     NavigationCacheMode = NavigationCacheMode.Enabled; 
    } 

    private void DeleteList(int count) 
    { 
     for (int x = 0; x < count; x++) 
     { 
      SearchList.RemoveAt(0); 
     } 
    } 

    private async void LoadHtmlDocument(string url) 
    { 
     try 
     { 
      if (NetworkInformatiom()) 
      { 
       SearchDoc = await new HtmlWeb().LoadFromWebAsync(url); 
      } 
      else 
      { 
       SearchDoc = null; 
      } 
      if (SearchDoc != null) 
      { 
       Links(SearchDoc); 
      } 
     } 
     catch (Exception ex) 
     { 
      ErrorDialog("SearchDoc_Download_Failed\n" + ex.Message); 
     } 
    } 

    private void Links(HtmlDocument doc) 
    { 
     listItems = 0; 
     try 
     { 
      foreach (var link in doc.DocumentNode.Descendants("a").Where(pl => pl.Attributes.Contains("href"))) 
      { 
       string dataValue = link.GetAttributeValue("href", ""); 
       //dataValue = ReplaceLinkStrings(dataValue); 
       if (dataValue.StartsWith("/watch") && dataValue.EndsWith(".html")) 
       { 
        SearchLinks[numberOfLinks] = MoviesPage.MoviesBaseLink + dataValue.Trim(); 
        listItems++; 
        numberOfLinks++; 
       } 
      } 
      ImageLinks(doc); 
     } 
     catch (Exception ex) 
     { 
      ErrorDialog("There was a problem while acquiring search links.\n" + ex.Message); 
     } 
    } 

    private void ImageLinks(HtmlDocument doc) 
    { 
     try 
     { 
      //int LinkID = 0; 
      foreach (var link in doc.DocumentNode.Descendants("img").Where(d => d.Attributes.Contains("src"))) 
      { 
       if (link != null) 
       { 
        if (link.Attributes["src"].Value == "/images/noposter.jpg") 
        { 
         SearchImageLinks[numberOfImages] = @"ms-appx:///Assets/noposter.jpg"; 
        } 
        else 
        { 
         SearchImageLinks[numberOfImages] = string.Format("http:{0}", link.Attributes["src"].Value); 
        } 
        numberOfImages++; 
       } 
       if (numberOfImages == numberOfLinks) 
       { 
        break; 
       } 
      } 
      Titles(doc); 
     } 
     catch (Exception ex) 
     { 
      ErrorDialog("There was a problem in Image links.\n" + ex.Message); 
     } 
    } 

    public void Titles(HtmlDocument doc) 
    { 
     try 
     { 
      //int a = 0; 
      foreach (var link in doc.DocumentNode.Descendants("a").Where(t => t.Attributes.Contains("title"))) 
      { 
       if (link != null && link.InnerText != "WatchFree.to" && link.InnerText != "Movies" && link.InnerText != "TV Shows") 
       { 
        string x = link.GetAttributeValue("title", null); 
        x = x.Replace("Watch Putlocker", ""); 
        x = x.Trim(); 
        SearchTitles[numberOfTitles] = x; 
        numberOfTitles++; 
        if (numberOfTitles == numberOfLinks) 
        { 
         break; 
        } 
       } 
      } 
      SearchList = SearchManager.GetTVShows(lastListItems, numberOfLinks); 
      // += or =  we will find out 
      this.Bindings.Update(); 
      lastListItems = numberOfLinks; 
      CheckNextPageLinks(doc); 
     } 
     catch (Exception ex) 
     { 
      ErrorDialog("There was a problem while acquiring movie titles.\n" + ex.Message); 
     } 
    } 

    private void SearchGrid_ItemClick(object sender, ItemClickEventArgs e) 
    { 
     var clickedItem = (SearchItems)e.ClickedItem; 
     if (SearchImageLinks[clickedItem.SearchID - 1] != null && clickedItem.SearchLink != null) 
     { 
      if (clickedItem.SearchLink.Contains("tv-show")) 
      { 
       string[] itemDetails = { clickedItem.SearchTitle, SearchImageLinks[(clickedItem.SearchID - 1)], clickedItem.SearchLink }; 
       Frame.Navigate(typeof(TVShowDetailsPage), itemDetails); 
      } 
      else if (clickedItem.SearchLink.Contains("movie")) 
      { 
       string[] itemDetails = { clickedItem.SearchTitle, SearchImageLinks[(clickedItem.SearchID - 1)], clickedItem.SearchLink }; 
       Frame.Navigate(typeof(MovieDetails), itemDetails); 
      } 
     } 
     else 
     { 
      ; 
     } 
    } 

    private void SearchInputBox_TextChanged(object sender, TextChangedEventArgs e) 
    { 
     string input = SearchInputBox.Text.Trim(); 
     string output = ""; 
     if (input.Length < 3) 
     { 
      SearchGridHeader.Text = ""; 
      if (SearchNextPagesLinks[0] != null || SearchLinks[0] != null || SearchImageLinks[0] != null || SearchTitles[0] != null) 
      { 
       DefaultVariablesValues(); 
      } 
      if (SearchList != null) 
      { 
       if (SearchList.Count > 0) 
       { 
        DeleteList((SearchList.Count)); 
       } 
      } 
     } 
     if (!(input.Length < 3)) 
     { 
      //sTimer = new DispatcherTimer(); 
      if (!sTimer.IsEnabled) 
      { 
       sTimer.Interval = TimeSpan.FromSeconds(1); 
       //sTimer.Start(); 
      } 

      ErrorTextBox.Text = ""; 
      SearchGridHeader.Text = "Search Results"; 
      if (input.Contains(" ")) 
      { 
       output = input.Replace(" ", "+"); 
       output = MoviesPage.MoviesBaseLink + @"/?keyword=" + output + @"&search_section=1"; 
       ErrorTextBox.Text = output; 
       ErrorTextBox.IsTextSelectionEnabled = true; 
      } 
      else 
      { 
       output = MoviesPage.MoviesBaseLink + @"/?keyword=" + input + @"&search_section=1"; 
       //ErrorTextBox.Text = output; 
      } 
      SearchList = new ObservableCollection<SearchItems>(); 
      LoadHtmlDocument(output); 

     } 
     else 
     { 
      ErrorTextBox.Text = "the length of the input should not be less than 3"; 
      if (input.Length == 0) 
      { 
       ErrorTextBox.Text = ""; 
      } 
      if (sTimer.IsEnabled) 
       sTimer.Stop(); 
     } 
    } 

    private void IndexPageLink_Click(object sender, RoutedEventArgs e) 
    { 
     Frame.Navigate(typeof(IndexPage)); 
    } 

    private void MoreItemsLink_Click(object sender, RoutedEventArgs e) 
    { 
     LoadHtmlDocument(MoviesPage.MoviesBaseLink + SearchNextPagesLinks[numberOfPages - 1]); 
    } 

    private void DefaultVariablesValues() 
    { 
     numberOfLinks = 0; 
     numberOfTitles = 0; 
     numberOfImages = 0; 
     nextPage = 2; 
     numberOfPages = 0; 
     lastListItems = 0; 
     int a = 0; 
     foreach (var item in SearchLinks) 
     { 
      if (item != null) 
      { 
       SearchLinks[a] = null; 
      } 
      a++; 
     } 
     a = 0; 
     foreach (var item in SearchTitles) 
     { 
      if (item != null) 
      { 
       SearchTitles[a] = null; 
      } 
      a++; 
     } 
     a = 0; 
     foreach (var item in SearchImageLinks) 
     { 
      if (item != null) 
      { 
       SearchImageLinks[a] = null; 
      } 
      a++; 
     } 
     a = 0; 
     foreach (var item in SearchNextPagesLinks) 
     { 
      if (item != null) 
      { 
       SearchNextPagesLinks[a] = null; 
      } 
      a++; 
     } 
    } 

    private void CheckNextPageLinks(HtmlDocument doc) 
    { 
     string lastLink = ""; 
     foreach (var link in doc.DocumentNode.Descendants("a").Where(t => t.Attributes.Contains("href"))) 
     { 
      string value = link.GetAttributeValue("href", ""); 
      if (value.StartsWith("/?keyword") && value.Contains("page=" + nextPage)) 
      { 
       SearchNextPagesLinks[numberOfPages] = value; 
       lastLink = value; 
       numberOfPages++; 
       break; 
      } 
     } 
     //-------------------------------------- 
     // checking for the availability of next page 
     if (lastLink.StartsWith(@"/?keyword") && lastLink.Contains("page=" + nextPage)) 
     { 
      MoreItemsLink.Visibility = Visibility.Visible; 
     } 
     else 
     { 
      MoreItemsLink.Visibility = Visibility.Collapsed; 
     } 
     //-------------------------------------- 
     foreach (var item in SearchNextPagesLinks) 
     { 
      if (item == lastLink) 
      { 
       nextPage++; 
      } 
     } 

    } 
} 
} 

コード:

using System; 
using System.Collections.Generic; 
using System.Collections.ObjectModel; 
using System.Linq; 
using System.Text; 
using System.Threading.Tasks; 
using Windows.Foundation; 
using Windows.UI.Core; 
using Windows.UI.Xaml; 
using Windows.UI.Xaml.Data; 

namespace WatchfreeWebsite 
{ 
public interface IIncrementalSource<T> 
{ 
    Task<IEnumerable<T>> GetPagedItems(int pageIndex, int pageSize); 
} 

public class IncrementalLoadingCollection<T, I> : ObservableCollection<I>, 
ISupportIncrementalLoading 
where T : IIncrementalSource<I>, new() 
{ 
    private T source; 
    private int itemsPerPage; 
    private bool hasMoreItems; 
    private int currentPage; 

    public IncrementalLoadingCollection(int itemsPerPage = 1) 
    { 
     this.source = new T(); 
     this.itemsPerPage = itemsPerPage; 
     this.hasMoreItems = true; 
    } 

    public bool HasMoreItems 
    { 
     get { return hasMoreItems; } 
    } 

    public IAsyncOperation<LoadMoreItemsResult> LoadMoreItemsAsync(uint count) 
    { 
     var dispatcher = Window.Current.Dispatcher; 

     return Task.Run(
      async() => 
      { 
       uint resultCount = 0; 
       var result = await source.GetPagedItems(currentPage++, itemsPerPage); 

       if (result == null || result.Count() == 0) 
       { 
        hasMoreItems = false; 
       } 
       else 
       { 
        resultCount = (uint)result.Count(); 

        await dispatcher.RunAsync(
         CoreDispatcherPriority.Normal, 
         () => 
         { 
          foreach (I item in result) 
           this.Add(item); 
         }); 
       } 

       return new LoadMoreItemsResult() { Count = resultCount }; 

      }).AsAsyncOperation(); 
    } 
} 
} 
(別のクラス)で

コード:

using System.Collections.Generic; 
using System.Collections.ObjectModel; 
using System.ComponentModel; 
using System.Runtime.CompilerServices; 
using System.Threading.Tasks; 

namespace WatchfreeWebsite 
{ 
public class SearchItems 
{ 
    public int SearchID 
    { 
     get; set; 
    } 

    public string SearchTitle 
    { 
     get; set; 
    } 

    public string SearchImageLink 
    { 
     get; set; 
    } 

    public string SearchLink { get; set; } 
} 

public class SearchManager : IIncrementalSource<SearchItems> 
{ 
    private ObservableCollection<SearchItems> items; 

    public async Task<IEnumerable<SearchItems>> GetPagedItems(int pageIndex, int pageSize) 
    { 
     return await Task.Run<IEnumerable<SearchItems>>(() => 
     { 
      if (SearchPage.lastListItems == 0 && SearchPage.numberOfLinks == 0) 
      { 
       var shows = new ObservableCollection<SearchItems>(); 
       shows.Add(new SearchItems { SearchID = 1, SearchTitle = "No Search Results", SearchImageLink = @"ms-appx:///Assets/noposter.jpg" }); 
       return shows; 
      } 
      else 
      { 
       var result = GetTVShows(SearchPage.lastListItems, SearchPage.numberOfLinks); //(from p in persons select p).Skip(pageIndex * pageSize).Take(pageSize); 
       return result; 
      } 

     }); 
    } 

    public static ObservableCollection<SearchItems> GetTVShows(int start, int finish) 
    { 
     var movies = new ObservableCollection<SearchItems>(); 
     for (int x = start; x < finish; x++) 
     { 
      movies.Add(new SearchItems { SearchID = (x + 1), SearchTitle = SearchPage.SearchTitles[x], SearchImageLink = SearchPage.SearchImageLinks[x], SearchLink = SearchPage.SearchLinks[x] }); 
     } 

     //if (start == 0 && finish == 0) 
     { 
      //movies.Add(new SearchItems { SearchID = 1, SearchTitle = "No Search Results", SearchImageLink = @"ms-appx:///Assets/noposter.jpg" }); 
     } 
     return movies; 
    } 
} 

} 

説明:アイテムの必要量を得るために、私はstartfinishパラメータでGetTVShows()を呼び出し、増分ロードを実装する前に、まず 。検索で何も得られない場合は、両方ともzeroですので、GetTVShows()No Resultsで1つのアイテムのみを生成します。

インクリメンタルロードでは、コンパイル時に必要なアイテムの数を指定する必要があります。アイテムを検索する必要があるため、アイテム数は指定できませんが、最大アイテム数は24です。

私もSearchResults+=を使用しようとしましたが、VSはこれがObservableCollectionで利用できないというエラーを生成するため、インターネットを検索してインクリメンタルロードを検出しました。しかし、可能であれば、エッジをスクロールするのではなく、リンクをクリックして結果を追加したいと思っています。インクリメンタルロードがどのように機能しているのか、私のGetTVShows()関数を呼び出す必要があるので、現在のように望ましい結果が得られるとは思えません。

私はhyperlinkクリックでさらに多くのDMを取得するためにインクリメンタルロードを使用しているので、これはWindows 10用のTwitterからもリコールされています。しかし、それらのDMは既にデータベースに格納されているので、動的に追加されません(少なくとも私が思うものであり、間違っている可能性があります)。

誰かが私がそれを動作させるためにできることを指摘できれば、それは本当に感謝しています。どのように私が正しい方向に私を指すように私を助けるためのあらゆる情報、またはISupportIncrementalLoadingが実際にどのように働くかの影響を理解することができます。ありがとう。

答えて

0

私はそれを自分で考え出しました...

public static ObservableCollection<SearchItems> GetTVShows(int start, int finish) 
{ 
    var movies = new ObservableCollection<SearchItems>(); 
    for (int x = start; x < finish; x++) 
    { 
     movies.Add(new SearchItems { SearchID = (x + 1), SearchTitle = SearchPage.SearchTitles[x], SearchImageLink = SearchPage.SearchImageLinks[x], SearchLink = SearchPage.SearchLinks[x] }); 
    } 

    if (start == 0 && finish == 0) 
    { 
     movies.Add(new SearchItems { SearchID = 1, SearchTitle = "No Search Results", SearchImageLink = @"ms-appx:///Assets/noposter.jpg" }); 
    } 
    return movies; 
} 

私は私のGridViewと、それは関数が呼び出されたたびに空だったのでvar moviesはローカルスコープの中にあった結局のところに項目を追加するために上記のコードを使用していました。それが、それが求められたアイテムだけをロードした理由です。今度は、GetTVShows()も静的関数であり、hyperlinkボタンをクリックすると、ビューに項目が追加されるため、private staticというファイルスコープで宣言しました。

私のケースでは、インクリメンタルロードに費やされた時間はすべて無駄になりました。とにかく私はエッジインクリメンタルロードを必要としなかったからです。

今、私のコードは次のようになります。

private static ObservableCollection<SearchItems> movies = new ObservableCollection<SearchItems>(); 
public static ObservableCollection<SearchItems> GetTVShows(int start, int finish) 
{ 
//var movies = new ObservableCollection<SearchItems>(); 
for (int x = start; x < finish; x++) 
{ 
    movies.Add(new SearchItems { SearchID = (x + 1), SearchTitle = SearchPage.SearchTitles[x], SearchImageLink = SearchPage.SearchImageLinks[x], SearchLink = SearchPage.SearchLinks[x] }); 
} 

if (start == 0 && finish == 0) 
{ 
    movies.Add(new SearchItems { SearchID = 1, SearchTitle = "No Search Results", SearchImageLink = @"ms-appx:///Assets/noposter.jpg" }); 
} 
return movies; 
} 

うまくいけば、それは

...道に沿って他の誰かを助けます
関連する問題