0



問題が発生した場所を示すために、短い例を作成しました。それらは、ObservableCollection にバインドされた LongsListSelector に関係します (アイテムのタイプに関係なく)。長いリスト アイテム テンプレートを (たとえば) テキストブロックとして設定し、3 つのボタンも作成しました。1 つの要素をコレクションに追加し、最後の 1 つを削除し、ビジュアル ツリーを検索します。コードはそれほど長くないので、以下に投稿します (例全体が必要な場合は、http://sdrv.ms/163TYEGにあります)。

XAML (ヘッダーを除く):

    <phone:PhoneApplicationPage.Resources>
    <DataTemplate x:Key="ElementStyle">
        <TextBlock x:Name="elemBlck" Text="Element"/>
    </DataTemplate>
</phone:PhoneApplicationPage.Resources>
<Grid x:Name="LayoutRoot" Background="Transparent">
    <Grid.RowDefinitions>
        <RowDefinition Height="30*"/>
        <RowDefinition Height="30*"/>
        <RowDefinition Height="30*"/>
    </Grid.RowDefinitions>
    <Grid.ColumnDefinitions>
        <ColumnDefinition Width="70*"/>
        <ColumnDefinition Width="30*"/>
    </Grid.ColumnDefinitions>

    <Button x:Name="addBtn" Content="Add" Grid.Row="0" Grid.Column="1"/>
    <Button x:Name="delBtn" Content="Del" Grid.Row="1" Grid.Column="1"/>
    <Button x:Name="showBtn" Content="Show" Grid.Row="2" Grid.Column="1"/>       
    <phone:LongListSelector x:Name="phoneLLS" HorizontalAlignment="Left" Height="700" Margin="0" Grid.Row="0" 
                            VerticalAlignment="Top" Grid.RowSpan="3" Grid.Column="0" Width="300"
                            LayoutMode="Grid" GridCellSize="300,100" IsGroupingEnabled="False"
                            ItemTemplate="{StaticResource ElementStyle}" />
</Grid>

およびC#:

 public partial class MainPage : PhoneApplicationPage
 {
  private ObservableCollection<string> collection = new ObservableCollection<string>();

  public MainPage()
  {
     InitializeComponent();
     phoneLLS.ItemsSource = collection;
     addBtn.Click += addBtn_Click;
     delBtn.Click += delBtn_Click;
     showBtn.Click += showBtn_Click;
  }

  private void addBtn_Click(object sender, RoutedEventArgs e)
  {
     collection.Add("element");
  }

  private void delBtn_Click(object sender, RoutedEventArgs e)
  {
     collection.RemoveAt(collection.Count - 1);
  }

  private void showBtn_Click(object sender, RoutedEventArgs e)
  {
     List<TextBlock> controlList = new List<TextBlock>();
     SearchForControls<TextBlock>(phoneLLS, ref controlList);
  }

  private static void SearchForControls<T>(DependencyObject parent, ref List<T> controlList) where T : DependencyObject
  {
     int numberOfChildreen = VisualTreeHelper.GetChildrenCount(parent);
     for (int i = 0; i < numberOfChildreen; i++)
     {
        var child = VisualTreeHelper.GetChild(parent, i);

        if (child is T)
           controlList.Add((T)child);
        else SearchForControls<T>(child, ref controlList);
     }
  }
}

問題はどこにありますか?

  1. 「追加」ボタンを押すと、コレクションが 1 要素ずつ拡大されます。わかりました、LLSに要素アイテムが追加されたのでわかりました。でももっと押してみてください。その後、ボタンを 1 回押すだけで、いくつかの要素が表示されますか? どうしたの?コレクションは 1 つの要素で拡大されますが、LLS ははるかに高速に設定されます。

  2. 削除と同じ - 1 つの要素を削除しますが、LLS からはアイテムのグループが消えることがあります。

  3. そして主な問題 - showBtn_Click の 2 行目でブレークポイントを切り替えます。いくつかの要素を追加し、ビジュアル ツリーを検索してみます (表示ボタンを押します)。デバッグが停止し、2 行目以降に、ビジュアル ツリー内の要素の正確な数が表示されます (collection.Count とは異なります)。そして 2 番目の大きな驚き - en 要素を削除し、もう一度ビジュアル ツリーを検索すると、次のことがわかります。- ビジュアル ツリー要素の数は変更されませんでした (!)。どうしたの?

    これらは何らかのバグですか?それとも、私は何かを理解していないのでしょうか?

4

2 に答える 2

0

また、LLS を使用してページを再入力すると、すべてが正しく更新されることをさらに調査しました。ビジュアル ツリーには、コレクションなどの多くの要素があります。例を変更しました ( http://sdrv.ms/169kRqI ):

Main_Page を second_page にしましょう:

Xaml:

<phone:PhoneApplicationPage.Resources>
    <DataTemplate x:Key="ElementStyle">
        <TextBlock x:Name="elemBlck" Text="Element"/>
    </DataTemplate>
</phone:PhoneApplicationPage.Resources>
<Grid x:Name="LayoutRoot" Background="Transparent">
    <Grid.RowDefinitions>
        <RowDefinition Height="30*"/>
        <RowDefinition Height="30*"/>
        <RowDefinition Height="30*"/>
    </Grid.RowDefinitions>
    <Grid.ColumnDefinitions>
        <ColumnDefinition Width="70*"/>
        <ColumnDefinition Width="30*"/>
    </Grid.ColumnDefinitions>

    <Button x:Name="addBtn" Content="Add" Grid.Row="0" Grid.Column="1"/>
    <Button x:Name="delBtn" Content="Del" Grid.Row="1" Grid.Column="1"/>
    <Button x:Name="showBtn" Content="Show" Grid.Row="2" Grid.Column="1"/>
    <phone:LongListSelector x:Name="phoneLLS" HorizontalAlignment="Left" Height="700" Margin="0" Grid.Row="0" 
                            VerticalAlignment="Top" Grid.RowSpan="3" Grid.Column="0" Width="300"
                            LayoutMode="Grid" GridCellSize="300,100" IsGroupingEnabled="False"
                            ItemTemplate="{StaticResource ElementStyle}" ItemsSource="{Binding}"/>

</Grid>

コードビハインド:

public partial class second_page : PhoneApplicationPage
{
  public second_page()
  {
     InitializeComponent();
     phoneLLS.DataContext = MainPage.collection;
     addBtn.Click += addBtn_Click;
     delBtn.Click += delBtn_Click;
     showBtn.Click += showBtn_Click;
  }

  private void addBtn_Click(object sender, RoutedEventArgs e)
  {
     MainPage.collection.Add("element");
  }

  private void delBtn_Click(object sender, RoutedEventArgs e)
  {
     MainPage.collection.RemoveAt(MainPage.collection.Count - 1);
  }

  private void showBtn_Click(object sender, RoutedEventArgs e)
  {
     List<TextBlock> controlList = new List<TextBlock>();
     SearchForControls<TextBlock>(phoneLLS, ref controlList);
  }

  private static void SearchForControls<T>(DependencyObject parent, ref List<T> controlList) where T : DependencyObject
  {
     int numberOfChildreen = VisualTreeHelper.GetChildrenCount(parent);
     for (int i = 0; i < numberOfChildreen; i++)
     {
        var child = VisualTreeHelper.GetChild(parent, i);

        if (child is T)
           controlList.Add((T)child);
        else SearchForControls<T>(child, ref controlList);
     }
  }
}

および Main_Page - ナビゲーションのみ:

Xaml:

<Grid x:Name="LayoutRoot" Background="Transparent">
    <Button x:Name="goToPage" Content="SecondPage" Width="Auto" Height="Auto"
            HorizontalAlignment="Center" VerticalAlignment="Center"/>
</Grid>

コードビハインド:

public partial class MainPage : PhoneApplicationPage
{
  public static ObservableCollection<string> collection = new ObservableCollection<string>();

  public MainPage()
  {
     InitializeComponent();
     goToPage.Click+=goToPage_Click;
  }

  private void goToPage_Click(object sender, RoutedEventArgs e)
  {
     NavigationService.Navigate(new Uri("/second_page.xaml", UriKind.Relative));
  }
}

ページを再入力して、または再入力せずに同じことを試してみてください。

  1. たとえば 3 つの要素を追加し、デバッガーで showBtn_Click の 2 行目にブレークポイントを切り替えてボタンをクリックすると、6 つの要素が表示されます。戻る以外には何も触れないでください。

  2. 2 番目のページに再び入ると、正しい LLS が表示されます。ブレークポイントで showBtn をクリックすると、3 つの要素が表示され、ビジュアル ツリーに 3 つの要素が表示されます。

    誰もこれを試しましたか?

于 2013-10-16T06:34:25.203 に答える
0

List にデータ コンテキストを設定し、ItemsSource プロパティで Bindings を使用してみてください。

Xaml:

<phone:LongListSelector ItemsSource={Binding} x:Name="phoneLLS"  HorizontalAlignment="Left" Height="700" Margin="0" Grid.Row="0" 
                        VerticalAlignment="Top" Grid.RowSpan="3" Grid.Column="0" Width="300"
                        LayoutMode="Grid" GridCellSize="300,100" IsGroupingEnabled="False"
                        ItemTemplate="{StaticResource ElementStyle}" />

コードビハインド:

public partial class MainPage : PhoneApplicationPage
{
   private ObservableCollection<string> collection = new ObservableCollection<string>();
   public MainPage()
   {
     InitializeComponent();
     phoneLLS.DataContext = collection;
     addBtn.Click += addBtn_Click;
     delBtn.Click += delBtn_Click;
     showBtn.Click += showBtn_Click;
   }
   ...
}

これがうまくいくかどうか教えてください。

于 2013-10-14T12:50:13.760 に答える