将可点击文本添加到DrawingGroup

时间:2009-07-30 19:58:30

标签: wpf xaml

让(最终)使用XAML创建棒球钻石控件。 (以下代码)。我现在需要能够在主要位置(1B,2B,SS,3B等)创建“可点击”文本。文本也需要旋转(因为我在角落里绘制了整个控件,然后在最后旋转它。

有人可以协助我向DrawingGroup添加文字吗? (如果它是可点击的,那就是。)

任何其他评论赞赏,我是WPF的新手,所以我甚至不知道我是否正确地这样做。我的第一次尝试是用代码绘制的,但我想挑战自己在XAML中完全定义它。

<Window x:Class="Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Window1" Height="528.303" Width="582.133">
<Grid Background="#C0E49C">
    <Image HorizontalAlignment="Stretch" VerticalAlignment="bottom"> 
        <Image.Source>
            <DrawingImage>
                <DrawingImage.Drawing>
                    <DrawingGroup>
                        <DrawingGroup.Transform>
                                <TransformGroup>
                                    <RotateTransform CenterX="0" CenterY="0" Angle="-135" />
                                <TranslateTransform X="0" Y="-4" />
                            </TransformGroup>
                        </DrawingGroup.Transform>
                    <GeometryDrawing Brush="#FFC080" >
                        <GeometryDrawing.Pen>
                            <Pen Brush="Black" Thickness="1"/>
                        </GeometryDrawing.Pen> 
                    <GeometryDrawing.Geometry>
                        <GeometryGroup>
                           <PathGeometry>
                            <PathGeometry.Figures>
                                <PathFigureCollection>
                                    <PathFigure StartPoint="0,0">
                                        <PathFigure.Segments>
                                            <PathSegmentCollection>
                                                <LineSegment Point="500,0" />
                                                <BezierSegment Point1="606,350"
                                                       Point2="350,606"
                                                       Point3="0,500"
                                                       />
                                                <LineSegment Point="0,0" />
                                            </PathSegmentCollection>
                                        </PathFigure.Segments>
                                    </PathFigure>
                                </PathFigureCollection>                                   
                            </PathGeometry.Figures>
                         </PathGeometry>
                        <RectangleGeometry Rect="8,8,333,333" />
                        <EllipseGeometry Center="174.5,174.5" RadiusX="50" RadiusY="50" />

                      </GeometryGroup>
            </GeometryDrawing.Geometry>
        </GeometryDrawing>

    </DrawingGroup>
</DrawingImage.Drawing>
</DrawingImage>
</Image.Source>
</Image>
</Grid>
</Window>

1 个答案:

答案 0 :(得分:2)

向DrawingGroup添加文本的唯一方法是GlyphRunDrawing。这是一个非常低级的课程。我不会向普通用户推荐它。

有一个更好的方法:你将棒球钻石设置为背景图像,为什么不简单地将文字放在图像的顶部?

将根级网格更改为Viewbox。将网格放在Viewbox中。

其次,在项目中添加一个名为“SelectableTextblock”的新类文件。这是该类的代码隐藏:

public class SelectableTextBlock : TextBlock
{
    public bool IsSelected
    {
        get { return (bool)this.GetValue(IsSelectedProperty); }
        set { this.SetValue(IsSelectedProperty, value); }
    }

    public static readonly DependencyProperty IsSelectedProperty =
        DependencyProperty.Register("IsSelected", typeof(bool), typeof(SelectableTextBlock), new PropertyMetadata(false, IsSelectedPropertyChanged));

    static void IsSelectedPropertyChanged(DependencyObject obj, DependencyPropertyChangedEventArgs e)
    {
        SelectableTextBlock textBlock = obj as SelectableTextBlock;
        textBlock.Background = (bool)e.NewValue ? new SolidColorBrush(Color.FromArgb(200, 255, 255, 255)) : Brushes.Transparent;
    }

    protected override void OnMouseDown(MouseButtonEventArgs e)
    {
        IsSelected = !IsSelected;
        base.OnMouseDown(e);
    }
}

很简单,这只是声明了一个可以选择或不选择的DependencyProperty。它充当切换:当您单击它时,您选择文本;再次单击它,它将被取消选中。

现在,在XAML中声明本地命名空间,然后为钻石中的每个位置添加一个SelectableTextBlock:

<local:SelectableTextBlock>
  1st Base
</local:SelectableTextBlock>

以下是最终结果:

<Window x:Class="TestWpfApplication.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:TestWpfApplication"
Title="Window1"
Background="#C0E49C">
<Viewbox>
 <Grid>
  <Image HorizontalAlignment="Stretch" VerticalAlignment="bottom">
   <Image.Source>
    <DrawingImage>
     <DrawingImage.Drawing>
      <DrawingGroup>
       <DrawingGroup.Transform>
        <TransformGroup>
         <RotateTransform CenterX="0" CenterY="0" Angle="-135" />
         <TranslateTransform X="0" Y="-4" />
        </TransformGroup>
       </DrawingGroup.Transform>
       <GeometryDrawing Brush="#FFC080" >
        <GeometryDrawing.Pen>
         <Pen Brush="Black" Thickness="1"/>
        </GeometryDrawing.Pen>
        <GeometryDrawing.Geometry>
         <GeometryGroup>
         <PathGeometry>
          <PathGeometry.Figures>
           <PathFigureCollection>
            <PathFigure StartPoint="0,0">
             <PathFigure.Segments>
              <PathSegmentCollection>
               <LineSegment Point="500,0" />
               <BezierSegment Point1="606,350"
                              Point2="350,606"
                              Point3="0,500" />
               <LineSegment Point="0,0" />
              </PathSegmentCollection>
             </PathFigure.Segments>
            </PathFigure>
           </PathFigureCollection>
          </PathGeometry.Figures>
         </PathGeometry>
         <RectangleGeometry Rect="8,8,333,333" />
         <EllipseGeometry Center="174.5,174.5" RadiusX="50" RadiusY="50" />
        </GeometryGroup>
       </GeometryDrawing.Geometry>
      </GeometryDrawing>
     </DrawingGroup>
    </DrawingImage.Drawing>
   </DrawingImage>
  </Image.Source>
 </Image>
 <local:SelectableTextBlock Margin="480, 60, 0, 0"
                            HorizontalAlignment="Center"
                            VerticalAlignment="Center">
  1st Base
 </local:SelectableTextBlock>
</Grid>