2010-02-10 79 views
14

我重新發布這個問題,因爲我沒有得到太多最後一次迴應,希望有點重新措辭可能幫助的......WPF畫布縮放/變換到適合

我基本上什麼試圖做的是創建一個數據綁定畫布,該畫布會自動縮放其內容以「填充」可用空間。有點像縮放以適應操作。不幸的是,我的WPF技能還不是很強大,我正在努力研究如何做到最後一部分。我已經遵循了一些數據綁定的例子來獲得畫布的界限,但不知道是否它的錯誤和阻礙了我。

我得在這取決於我嘗試解決該解決方案的方式,瞬間兩個基本問題,或者:

  • 我不知道如何通過使 畫布上重新大規模自動 XAML如果有可能使用 變換。
  • 我似乎無法通過 參考後面的 代碼的畫布,我猜是因爲它的一個ItemsControl的部分 ?

的我想要實現的,我有。我想嘗試,並獲得B中的例子:

刪除過期鏈接到IMG

的代碼我「M目前使用是非常簡單的,只創建4個點與給定的座標,和另一視圖模型來在這些包裹起來。

public class PointCollectionViewModel 
{ 
    private List<PointViewModel> viewModels; 
    public PointCollectionViewModel() 
    { 
     this.viewModels = new List<PointViewModel>(); 
     this.viewModels.Add(new PointViewModel(new Point(1, 1))); 
     this.viewModels.Add(new PointViewModel(new Point(9, 9))); 
     this.viewModels.Add(new PointViewModel(new Point(1, 9))); 
     this.viewModels.Add(new PointViewModel(new Point(9, 1))); 
    } 

    public List<PointViewModel> Models 
    { 
     get { return this.viewModels; } 
    } 
} 

public class PointViewModel 
{ 
    private Point point; 
    public PointViewModel(Point point) 
    { 
     this.point = point; 
    } 

    public Double X { get { return point.X; } } 
    public Double Y { get { return point.Y; } } 
} 

然後PointCollectionViewModel用作DATACON帳篷我AutoResizingCanvas,它具有以下XAML來實現綁定:

<UserControl x:Class="WpfCanvasTransform.AutoResizingCanvas" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation" 
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" 
    xmlns:local="clr-namespace:WpfCanvasTransform" 
    x:Name="parent"> 
    <ItemsControl x:Name="itemsControl" ItemsSource="{Binding Path=Models}"> 
    <ItemsControl.ItemsPanel> 
     <ItemsPanelTemplate> 
     <Canvas x:Name="canvas" Background="DarkSeaGreen" HorizontalAlignment="Stretch" VerticalAlignment="Stretch"> 
      <Canvas.LayoutTransform> 
      <ScaleTransform ScaleY="-1" /> 
      </Canvas.LayoutTransform> 

     </Canvas> 
     </ItemsPanelTemplate> 
    </ItemsControl.ItemsPanel> 
    <ItemsControl.ItemTemplate> 
     <DataTemplate DataType="{x:Type local:PointViewModel}"> 
     <Ellipse Width="3" Height="3" Fill="Red"/> 
     </DataTemplate> 
    </ItemsControl.ItemTemplate> 
    <ItemsControl.ItemContainerStyle> 
     <Style> 
     <Setter Property="Canvas.Top" Value="{Binding Path=Y}"/> 
     <Setter Property="Canvas.Left" Value="{Binding Path=X}"/> 
     </Style> 
    </ItemsControl.ItemContainerStyle> 
    </ItemsControl> 
</UserControl> 

回答

17

當你的Canvas似乎並不具有固定的寬度和高度,我將包括它變成一個Viewbox

<ItemsControl.ItemsPanel> 
    <ItemsPanelTemplate> 
     <Viewbox Stretch="Uniform"> 
      <Canvas x:Name="canvas" Background="DarkSeaGreen"> 
       <Canvas.LayoutTransform> 
       <ScaleTransform ScaleY="-1" /> 
       </Canvas.LayoutTransform> 
      </Canvas> 
     </Viewbox> 
    </ItemsPanelTemplate> 
</ItemsControl.ItemsPanel> 

或者,將您的整個UserControl放入ViewBox

+3

@Mart:非常有趣,它看起來像接近我想要的。如果我像你所建議的那樣更改我的代碼,我會得到一個InvalidOperationException異常「ItemsPanelTemplate的VisualTree必須包含一個面板,'System.Windows.Controls.Viewbox'不是面板。」 – Ian 2010-02-10 17:28:20

+0

@Mart:如果我將我的AutoResizingCanvas用戶控件包裝在視圖框中,按照您的其他建議,我的點會進行縮放,但它們會出現在奇怪的位置,並且我會丟失背景顏色。見截圖:http://img62.imageshack.us/img62/4481/imagejc.jpg – Ian 2010-02-10 17:30:27

+2

你的問題來自Canvas沒有維度的事實。其父容器使其佔用整個可用空間。 如果您知道您的點X和Y的界限,請將它們設置爲「畫布寬度」和「高度」。通過這種方式在UserControl或ItemsControl周圍放置一個Viewbox實際上可以擴展它。 – Mart 2010-02-11 09:05:17