5

この質問が何度も聞かれるのを見て、自分のコードを何度も調べてきました。しかしSelectedItem、オブジェクトを使用してバインドされたプロパティに割り当てると、ディスプレイの選択されたアイテムが更新されません。はListBox、割り当てたオブジェクトがそのアイテムのメンバーではないと考えているようです。

public class MainViewModel : ViewModelBase
{
    //...
    public SortedObservableCollection<TubeViewModel> Items { get; private set; }
    public TubeViewModel SelectedTube { //get, set, propertychanged, etc. }
}

<ListBox x:Name="TubeList"
         Margin="10"
         ItemsSource="{Binding Items}"
         ItemTemplate="{StaticResource TubeTemplate}"
         SelectedItem="{Binding SelectedTube, Mode=TwoWay}" 
         SelectionMode="Single"
         VirtualizingStackPanel.IsVirtualizing="False">
</ListBox>

これは、私が設定しようとしている場所の 1 つからの impl ですSelectedTube- 間違いなくメイン スレッドで発生します。

 var match =
    from t in Items
    where t.Model.DataFileName == filename
    select t;
 if (match.Any())
    SelectedTube = match.First();

手動でクリックしない限り強調表示されないことに気付きましたSelectedTubeが、無視していました。しかし、選択したアイテムをScrollIntoViewCenteredしたかったので、変更DependencyPropertyを監視するためにビューにa を追加しましたSelectedItem。ハンドラーは最初は次のように見えました。

private void OnSelectedItemChanged(DependencyObject target, DependencyPropertyChangedEventArgs e)
{
    if (TubeList.SelectedItem == null)
       return;

    TubeList.ScrollIntoViewCentered(TubeList.SelectedItem);
}

SelectedItemしかし、バインディングを介して設定すると機能しませんでした。画面上にない場合にのみスクロールしたいと判断した後、コードを次のように変更しました。

private void OnSelectedItemChanged(DependencyObject target, DependencyPropertyChangedEventArgs e)
{
    if (TubeList.SelectedItem == null)
       return;

    var container = TubeList.ItemContainerGenerator.ContainerFromItem(TubeList.SelectedItem) as FrameworkElement;

    if(!container.IsVisible)
       TubeList.ScrollIntoViewCentered(TubeList.SelectedItem);
}

が外部で設定されている場合SelectedItem、コンテナは null です。毎回。ItemsSourcenull をチェックするコードを追加してから、一致するファイル名を探して繰り返し処理し、更新してリストボックス内のオブジェクトが間違いないSelectedItemことを確認しました。SelectedItem運がない。

アイテムが画面上にある場合、それはまだ強調表示されません。ある種の等価関数を実装する必要がありますか? 私はこれについて、人が考えているよりも多くの時間を無駄にしました。

ありがとう。

4

3 に答える 3

5

ItemContainerGeneratorsたぶん、これは別のスレッドで生成されるという事実にも関連しています...(少なくとも TreeView で

ItemContainerGeneratorsプロパティに問い合わせる前に UpdateLayout() を呼び出してみてください。

于 2010-01-06T11:43:57.027 に答える
3

明らかに間違っていると私に飛びつくものは何もありませんが、あなたは多くのことを言い過ぎました。問題が見つかるか、完全に機能しない例を投稿できるようになるまで、物事を単純化することをお勧めします。

于 2009-12-15T18:08:30.330 に答える
1

設定しようとしているオブジェクトのハッシュコードに対して itemsource 内の各オブジェクトのハッシュコードをチェックしてみましたか? Linq クエリは別のものを返します。

SelectedTube を Items[0] に設定しようとするテストとして。

于 2010-01-06T01:26:46.687 に答える