2010-05-26 5 views
32

WPF 폼을 만듭니다. 요구 사항 중 하나는 컨트롤이 섹터/셀 중 하나에 명시 적으로 배치 될 수 있도록 섹터 기반 레이아웃이 있다는 것입니다.ItemsControl 및 Grid를 사용하는 WPF 동적 레이아웃

내가 아래에있는 내 문제를 전달하기 위해 틱택 토 예제를 만들었습니다

:

public class XMoveViewModel : MoveViewModel 
{ 
} 
public class OMoveViewModel : MoveViewModel 
{ 
} 
public class MoveViewModel 
{ 
    public int Row { get; set; } 
    public int Column { get; set; } 
} 

형태의 DataContext에이 인스턴스로 설정되어

이 두 가지 유형의 하나 개의 기본 유형이 있습니다를 의 :

public class MainViewModel : ViewModelBase 
{ 
    public MainViewModel() 
    { 
     Moves = new ObservableCollection<MoveViewModel>() 
     { 
      new XMoveViewModel() { Row = 0, Column = 0 }, 
      new OMoveViewModel() { Row = 1, Column = 0 }, 
      new XMoveViewModel() { Row = 1, Column = 1 }, 
      new OMoveViewModel() { Row = 0, Column = 2 }, 
      new XMoveViewModel() { Row = 2, Column = 2} 
     }; 
    } 
    public ObservableCollection<MoveViewModel> Moves 
    { 
     get; 
     set; 
    } 
} 

그리고 마지막으로, XAML은 다음과 같습니다

<Window.Resources> 
    <DataTemplate DataType="{x:Type vm:XMoveViewModel}"> 
     <Image Source="XMove.png" Grid.Row="{Binding Path=Row}" Grid.Column="{Binding Path=Column}" Stretch="None" /> 
    </DataTemplate> 
    <DataTemplate DataType="{x:Type vm:OMoveViewModel}"> 
     <Image Source="OMove.png" Grid.Row="{Binding Path=Row}" Grid.Column="{Binding Path=Column}" Stretch="None" /> 
    </DataTemplate> 
</Window.Resources> 
<Grid> 
    <ItemsControl ItemsSource="{Binding Path=Moves}"> 
     <ItemsControl.ItemsPanel> 
      <ItemsPanelTemplate> 
       <Grid ShowGridLines="True"> 
        <Grid.RowDefinitions> 
         <RowDefinition /> 
         <RowDefinition /> 
         <RowDefinition /> 
        </Grid.RowDefinitions> 
        <Grid.ColumnDefinitions> 
         <ColumnDefinition /> 
         <ColumnDefinition /> 
         <ColumnDefinition /> 
        </Grid.ColumnDefinitions> 
       </Grid> 
      </ItemsPanelTemplate> 
     </ItemsControl.ItemsPanel> 
    </ItemsControl> 
</Grid> 

처음 시작할 때 그리 명확하지 않은 점은 ItemsControl 요소가 컨테이너의 각 항목을 실제로 래핑한다는 것이었기 때문에 이미지가 그리드 내에 직접 포함되어 있지 않으므로 Grid.Row 및 Grid.Column 바인딩이 무시됩니다. 따라서 모든 이미지는 기본 행 및 열 (0, 0)에 배치됩니다.

무슨 일이 일어나고 무엇 :

What is happening http://i48.tinypic.com/29xyl9j.png

원하는 결과 :

The desired result http://i50.tinypic.com/2druhqd.png

그래서, 내 질문은 이것이다 : 내가 그리드에 내 컨트롤의 동적 배치를 달성 할 수있는 방법을 ? XAML/데이터 바인딩/MVVM 친화적 인 솔루션을 선호합니다.

감사합니다. http://www.centrolutions.com/downloads/TicTacToe.zip

+0

안녕하세요 Jason, tic-tac-toe의 전체 코드를 가져올 수있는 기회가 있으십니까? 나는보고 싶다. 감사합니다. – VitalyB

+2

불행히도,이 프로젝트는 단지 예일 뿐이며 완전히 기능하는 게임이 아닙니다. 이것은 더 큰 (tic-tac-toe가 아닌) 프로젝트의 프로토 타입이었습니다. 여전히 관심이 있으시면 원본 질문 아래의 마지막 코드에 대한 링크를 넣었습니다. –

+0

나는 그것을 줄 것이다. 감사! – VitalyB

답변

25

당신이 올바른 궤도에있어 : ​​

나는 여기에 최종 코드를 삽입했다. Style을 만들고 ItemsControl.ItemContainerStyle에 적용하면됩니다. 그런 다음 스타일에서 Grid.RowGrid.Column에 대한 설정기를 지정하십시오. ItemContainerStyle은 각 항목에 대해 생성 된 컨테이너에 적용됩니다.

+0

아하! 나는 뭔가를 놓친다는 것을 알았다. 도와 줘서 고마워. 그 일은 훌륭했습니다. –

+1

Silverlight에서 똑같은 작업을하려고합니다. 누구나 할 수있는 방법을 알고 있습니까? Silverlight에서는 ItemContainerStyle을 사용할 수 없습니다. –