2008-09-17 29 views
7

Tôi có lưới 3 cột trong cửa sổ có GridSplitter trên cột đầu tiên. Tôi muốn đặt MaxWidth của cột đầu tiên thành một phần ba của Cửa sổ chính hoặc Trang Width (hoặc ActualWidth) và tôi muốn thực hiện điều này trong XAML nếu có thể.Cách đặt cột lưới MaxWidth tùy thuộc vào cửa sổ hoặc kích thước màn hình trong XAML

Đây là một số mẫu XAML để chơi trong XamlPad (hoặc tương tự) thể hiện những gì tôi đang làm.

<Page xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:sys="clr-namespace:System;assembly=mscorlib" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" > 
    <Grid> 
     <Grid.ColumnDefinitions> 
      <ColumnDefinition x:Name="Column1" Width="200"/> 
      <ColumnDefinition x:Name="Column2" MinWidth="50" /> 
      <ColumnDefinition x:Name="Column3" Width="{ Binding ElementName=Column1, Path=Width }"/> 
      </Grid.ColumnDefinitions> 

     <Label Grid.Column="0" Background="Green" /> 
     <GridSplitter Grid.Column="0" Width="5" /> 
     <Label Grid.Column="1" Background="Yellow" /> 
     <Label Grid.Column="2" Background="Red" /> 
    </Grid> 
</Page> 

Như bạn có thể thấy, độ rộng cột bên phải được ràng buộc với chiều rộng của cột đầu tiên, vì vậy khi bạn trượt cột bên trái sử dụng splitter, cột bên phải cũng làm như vậy :) Nếu bạn trượt cột bên trái sang phải, cuối cùng nó sẽ trượt trên một nửa trang/cửa sổ và sang phía bên phải của cửa sổ, đẩy cột 2 sang bên phải và

Tôi muốn ngăn điều này bằng cách đặt MaxWidth của cột 1 thành một phần ba chiều rộng cửa sổ (hoặc thứ gì đó tương tự). Tôi có thể làm điều này trong mã phía sau khá dễ dàng, nhưng làm thế nào để làm điều đó trong "XAML Only"?

EDIT: David Schmitt đề xuất sử dụng SharedSizeGroup thay vì ràng buộc, đây là một gợi ý tuyệt vời. mẫu mã của tôi sẽ giống như thế này thì:

<Page xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:sys="clr-namespace:System;assembly=mscorlib" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" > 
     <Grid IsSharedSizeScope="True"> 
      <Grid.ColumnDefinitions> 
       <ColumnDefinition x:Name="Column1" SharedSizeGroup="ColWidth" Width="40"/> 
       <ColumnDefinition x:Name="Column2" MinWidth="50" Width="*" /> 
       <ColumnDefinition x:Name="Column3" SharedSizeGroup="ColWidth"/> 
      </Grid.ColumnDefinitions> 
      <Label Grid.Column="0" Background="Green" /> 
      <GridSplitter Grid.Column="0" Width="5" /> 
      <Label Grid.Column="1" Background="Yellow" /> 
      <Label Grid.Column="2" Background="Red" /> 
     </Grid> 
</Page> 

Trả lời

7

Tôi nghĩ rằng cách tiếp cận XAML chỉ là hơi mạch, nhưng đây là một cách để thực hiện.

<Page xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
     xmlns:sys="clr-namespace:System;assembly=mscorlib" 
     xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" > 

    <!-- This contains our real grid, and a reference grid for binding the layout--> 
    <Grid x:Name="Container"> 

     <!-- hidden because it's behind the grid below --> 
     <Grid x:Name="LayoutReference"> 
     <Grid.ColumnDefinitions> 
      <ColumnDefinition Width="*"/> 
      <ColumnDefinition Width="*"/> 
      <ColumnDefinition Width="*"/> 
     </Grid.ColumnDefinitions> 
     <!-- We need the border, because the column doesn't have an ActualWidth --> 
     <Border x:Name="ReferenceBorder" 
       Background="Black" /> 
     <Border Background="White" Grid.Column="1" /> 
     <Border Background="Black" Grid.Column="2" /> 
     </Grid> 

     <!-- I made this transparent, so we can see the reference --> 
     <Grid Opacity="0.9"> 
      <Grid.ColumnDefinitions> 
       <ColumnDefinition x:Name="Column1" 
           MaxWidth="{Binding ElementName=ReferenceBorder,Path=ActualWidth}"/> 
       <ColumnDefinition x:Name="Column2" 
           MinWidth="50" /> 
       <ColumnDefinition x:Name="Column3" 
           Width="{ Binding ElementName=Column1, Path=Width }"/> 
       </Grid.ColumnDefinitions> 

      <Label Grid.Column="0" Background="Green"/> 
      <GridSplitter Grid.Column="0" Width="5" /> 
      <Label Grid.Column="1" Background="Yellow" /> 
      <Label Grid.Column="2" Background="Red" /> 
     </Grid> 
    </Grid> 

</Page> 
+4

Vui lòng sử dụng SharedSizeGroup thay vì gắn với chiều rộng của cột khác! –

+0

Tôi đã thử xaml ở trên trong XamlPad và nó cư xử kiểu lạ, nhưng tôi thấy quan điểm của bạn! Cảm ơn. –

0

Quá lười biếng để thực sự viết nó lên bản thân mình, nhưng bạn sẽ có thể sử dụng một bộ chuyển đổi toán học và liên kết với các cửa sổ cha mẹ chiều rộng của bạn (hoặc theo tên, hoặc với một tìm kiếm tổ tiên RelativeSource).

//I know I borrowed this from someone, sorry I forgot to add a comment from whom 
public class ScaledValueConverter : IValueConverter 
{ 
    public Object Convert(Object value, Type targetType, Object parameter, System.Globalization.CultureInfo culture) 
    { 
    Double scalingFactor = 0; 
    if (parameter != null) 
    { 
     Double.TryParse((String)(parameter), out scalingFactor); 
    } 

    if (scalingFactor == 0.0d) 
    { 
     return Double.NaN; 
    } 

    return (Double)value * scalingFactor; 
    } 

    public Object ConvertBack(Object value, Type targetType, Object parameter, System.Globalization.CultureInfo culture) 
    { 
    throw new Exception("The method or operation is not implemented."); 
    } 
} 
Các vấn đề liên quan