2015-01-13 2 views
3

Bind 두 개의 ListViews에서 ViewModel까지 시도했습니다. 두 목록 모두 항목을 올바르게로드하고 있습니다. 그러나 놀랍게도 나는 약간의 문제가 발생했습니다.SelectedItem은 WPF의 ListView에서 바인딩하지 않습니다

첫 번째 ListViewSelectedItem은 올바르게 바인딩되지만 두 번째는 바인딩되지 않습니다. 아래 그림과 같이 그 이유는 무엇일까요?

enter image description here

XAML :

<Window x:Class="SazehAfzar.Dialogs.BeamElevationsWindow" 
     xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
     xmlns:converters="clr-namespace:SazehAfzar.Dialogs.Converters" 
     Title="Select Beam Elevation" Height="350" Width="460" 
     Style="{StaticResource DialogStyle}" 
     WindowStartupLocation="CenterScreen"> 
    <Window.Resources> 
     <converters:ElevationValueConverter x:Key="ElevationValueConverter"/> 
    </Window.Resources> 

    <Grid Margin="10"> 
     <Grid.RowDefinitions> 
      <RowDefinition Height="Auto"></RowDefinition> 
      <RowDefinition Height="Auto"></RowDefinition> 
     </Grid.RowDefinitions> 
     <GroupBox> 
      <Grid Margin="5"> 
       <Grid.ColumnDefinitions> 
        <ColumnDefinition Width="175"/> 
        <ColumnDefinition Width="10"/> 
        <ColumnDefinition Width="215"/> 
       </Grid.ColumnDefinitions> 
       <GroupBox Header="Typs"> 
        <ListView ItemsSource="{Binding TypIds}" 
           SelectedItem="{Binding CurrentTypId}"> 
         <ListView.View> 
          <GridView AllowsColumnReorder="False" 
          ColumnHeaderContainerStyle="{StaticResource DialogsGridViewColumnHeaderStyle}" > 
           <GridViewColumn Header="Typ."/> 
          </GridView> 
         </ListView.View> 
        </ListView> 
       </GroupBox> 

       <GroupBox Grid.Row="0" Grid.Column="2" Header="Elevations"> 
        <ListView ItemsSource="{Binding Elevations}" 
           SelectedItem="{Binding CurrentBeamElevation}"> 
         <ListView.View> 
          <GridView AllowsColumnReorder="False" 
          ColumnHeaderContainerStyle="{StaticResource DialogsGridViewColumnHeaderStyle}" > 
           <GridViewColumn Header="Typ." /> 
          </GridView> 
         </ListView.View> 
        </ListView> 
       </GroupBox> 
      </Grid> 
     </GroupBox> 
     <Grid Grid.Row="1"> 
      <Button Content="OK"/> 
     </Grid> 
    </Grid> 
</Window> 

코드 숨김 :

public partial class BeamElevationsWindow 
{ 
    private BeamElevationsViewModel ViewModel { get; set; } 

    public BeamElevationsWindow() 
    { 
     InitializeComponent(); 
     ViewModel = new BeamElevationsViewModel(); 
     DataContext = ViewModel; 
    } 
} 

뷰 모델 :

,691,363
using System; 
using System.Collections.Generic; 
using System.ComponentModel; 
using System.Linq; 
using SazehAfzar.Mathmatics; 
using SazehAfzar.Objects.Building; 
using SazehAfzar.Objects.Structural; 

namespace SazehAfzar.Dialogs.ViewModels 
{ 
    public class BeamElevationsViewModel : INotifyPropertyChanged 
    { 
     public event PropertyChangedEventHandler PropertyChanged; 

     public BeamElevationsViewModel() 
     { 
      var frames = Building.Frames 
       .GroupBy(f => f.TypId) 
       .Select(group => group.First()) 
       .OrderBy(f => f.TypId) 
       .ToList(); 

      typIds = new List<int>(); 
      foreach (var frame in frames) 
      { 
       typIds.Add(frame.TypId); 
      } 

      TypIds = typIds; 
      CurrentTypId = Building.CurrentFrame.TypId; 

      GetElevations(CurrentTypId); 
      CurrentBeamElevation = Building.CurrentBeamElevation; 
     } 

     public void GetElevations(int typId) 
     { 
      var frames = Building.Frames 
       .Where(f => f.TypId == typId) 
       .OrderByDescending(f => f.Elevation) 
       .ToList(); 

      elevations = new List<Elevation>(); 
      foreach (var fr in frames) 
      { 
       foreach (var elevation in Building.Elevations) 
       { 
        if (Math.Abs(fr.Elevation - elevation.El) < Arithmetics.Tolerance) 
        { 
         elevations.Add(elevation); 
         break; 
        } 
       } 
      } 

      Elevations = elevations; 
     } 

     private List<int> typIds; 
     public List<int> TypIds 
     { 
      get { return typIds; } 
      private set 
      { 
       typIds = value; 
       RaisePropertyChanged("TypIds"); 
      } 
     } 

     private int currentTypId; 
     public int CurrentTypId 
     { 
      get { return currentTypId; } 
      private set 
      { 
       currentTypId = value; 
       RaisePropertyChanged("CurrentTypId"); 
      } 
     } 

     private List<Elevation> elevations; 
     public List<Elevation> Elevations 
     { 
      get { return elevations; } 
      private set 
      { 
       elevations = value; 
       RaisePropertyChanged("Elevations"); 
      } 
     } 

     private Elevation currentBeamElevation; 
     public Elevation CurrentBeamElevation 
     { 
      get { return currentBeamElevation; } 
      private set 
      { 
       currentBeamElevation = value; 
       RaisePropertyChanged("CurrentBeamElevation"); 
      } 
     } 

     private void RaisePropertyChanged(string propertyName) 
     { 
      var handler = PropertyChanged; 
      if (handler != null) 
      { 
       handler(this, new PropertyChangedEventArgs(propertyName)); 
      } 
     } 
    } 
} 
+0

표시되는 내용 중에 오류가 있음을 나타냅니다. 많은 양의 코드를 감안할 때 기대하는 바에 비해 좀 더 구체적 일 수 있습니까? – BradleyDotNET

+0

@BradleyDotNET 왼쪽 ListView의 SelectedItem이 올바르게 바인딩되어 있고 [1]이 선택되어있는 것을 볼 수 있듯이 Bradley에게 관심을 가져 주셔서 감사합니다. 그러나 올바른 ListView SelectedItem 올바르게 바인딩 된 및 아무것도 선택되어 있지 않습니다! – Vahid

+1

그래, 그 해명 해줘서 고마워. 나는 * 문제가 평등 체크라고 생각한다.'Building.CurrentElevation'이리스트에있는 똑같은 오브젝트 * 일지 말해 줄 수 있겠는가? 아니면 같은 속성을 가지고 있습니까? – BradleyDotNET

답변

4

바인딩 (210)는 실제로 잘 작동 :)

그러나, object에 대한 기본 비교는 참조 비교를 수행합니다. 즉, 목록에서 기존 객체를 찾으려고 할 때 사용자가 동일한 인스턴스가 아니기 때문에 (사용자의 의견에 따라) 해당 객체를 선택하지 않습니다.

해결 방법은 Object.Equals이며, 재정의 할 때는 Object.GetHashCode을 재정의해야합니다. 객체의 고유 한 속성을 기반으로 동등성을 테스트해야하므로 가양 성을 얻지 못합니다.

+0

고맙습니다. 브래들리, 네가 못을 박았다! 그게 내 문제를 완전히 해결해 줬어. Building.CurrentBeamElevation은 목록의 항목과 다릅니다. 나는 이것이 코드 냄새일지도 모른다고 생각하지만, 지금은'LINQ'를 사용하여 목록에서 선택한 항목을 반환하고 SelectedItem을 바인딩하는 약간의 해킹을했습니다! – Vahid

+0

@Vahid 방금'Equals' 오버라이드를 했었을 것입니다. 아마도 그것보다 쉽고 확실히 버그가 발생하기 쉽습니다. 다행 이네. – BradleyDotNET

+0

'Elevation' 클래스의'Equals' 메소드를 의미합니까? – Vahid

관련 문제