6

In the following example whenever Grid size is changed, the clipping region size remains as it is expressed in absolute coordinates.

<Grid Clip="M10,10 L10,150 L150,150 L150,10 Z">
    <Rectangle Fill="Red"/>
</Grid>

Is is possible somehow to clip the region such that the clipping geometry is scaled along with the clipped object?

Code behind solutions are not accepted, because this is to be used in the control template. Also, the region in the example is a simple shape for clarity sake. The actual used region is a complex and asymmetric shape.

EDIT:

It looks like I have to be more specific. This is the snipped that is part of custom control template for ProgressBar. When scaling the outer grid, the PART_Indicator rectangle does not scale its clipping region. The correct composition is when grid is sized 200x200.

<Grid>
    <Path Name="PART_Track" 
          Data="M100,0 A100,100 0 1 0 100,200 A100,100 0 1 0 100,0 Z"
          Fill="AliceBlue" Stretch="Fill"/>

    <Rectangle Clip="M100,0 A100,100 0 1 0 100,200 A100,100 0 1 0 100,0 Z"
               Stretch="Fill"
               Name="PART_Indicator" Fill="Red" 
               Height="100" VerticalAlignment="Top"/>

    <Path Name="Border" Data="M100,0 A100,100 0 1 0 100,200 A100,100 0 1 0 100,0 Z"
          Stretch="Fill" StrokeThickness="3" Stroke="Black"/>
</Grid>

UPDATE: Rick provided excellent suggestion, though it took time for me to understand how to use it. Here is the final code.

<Viewbox StretchDirection="Both" Stretch="Fill" >
    <Grid>
        <Path Name="PART_Track" 
              Data="M100,0 A100,100 0 1 0 100,200 A100,100 0 1 0 100,0 Z"
              Fill="AliceBlue" Stretch="Fill"/>

        <Border Clip="M100,0 A100,100 0 1 0 100,200 A100,100 0 1 0 100,0 Z"
                Height="200" VerticalAlignment="Bottom">
            <Rectangle Name="PART_Indicator" Fill="Red" VerticalAlignment="Bottom" 
                       Height="40"/>
        </Border>

        <Path Name="Border"
              Data="M100,0 A100,100 0 1 0 100,200 A100,100 0 1 0 100,0 Z"
              StrokeThickness="3"
              Stretch="Fill" Stroke="Black"/>
    </Grid>
</Viewbox>
AlexK
  • 228
  • 2
  • 7
  • This does beg the question: what's the initial scale? A grid can start out being any size based on screen, etc. but a geometry has a fixed size. An initial scale needs to be established. At that point, I'd write a custom panel inheriting from grid, adding a dep. prop. for initial scale, and hook calls to arrange; no "code behind", but a custom control. – J Trana May 10 '11 at 21:32
  • Yes, I realized that,about the scale, now. Replaced Grid with Rectangle with Stretch=Fill in attempt to achieve the same effect as Path Stretch=Fill does. Did not help though. The solution I am looking for is to use in control templates, not how to write custom controls. – AlexK May 10 '11 at 23:01

2 Answers2

4

Put the Grid inside of a Viewbox and change the size of the Viewbox instead of the Grid.

<Viewbox>
    <Grid Clip="M10,10 L10,150 L150,150 L150,10 Z" Width="200" Height="200">
        <Rectangle Fill="Red"/>
    </Grid>
</Viewbox>
Rick Sladkey
  • 33,988
  • 6
  • 71
  • 95
  • Viewbox does not seem to scale grid. In fact it does not show it at all. Snooping shows that Viewbox.RenderSize == 0,0. Also, not sure how resizing Viewbox helps? – AlexK May 10 '11 at 21:33
  • You seem to have some size in mind for the grid when you clip it. Set the `Grid.Width` and `Grid.Height` to that size. Then the viewbox will know how big it is. – Rick Sladkey May 10 '11 at 21:37
1

An alternative approach to this is to define the clipping path using element rather than attribute syntax, and then use the same transformation on the clip as you apply to the element as a whole, e.g.:

<Grid.Clip>
    <PathGeometry FillRule="Nonzero" Transform="{Binding Path=MatrixTransform, RelativeSource={RelativeSource TemplatedParent}, Mode=OneWay}">
        <PathFigure StartPoint="715, 96.3333" IsClosed="True" IsFilled="True">
            <PolyLineSegment IsStroked="False">
                <PolyLineSegment.Points>
                    <Point X="1255.2526" Y="540" />
                    <Point X="426.3333" Y="1342.3333" />
                     <Point X="64.66666" Y="7356.6666" />
                </PolyLineSegment.Points>
            </PolyLineSegment>
       </PathFigure>
   </PathGeometry>
</Grid.Clip>
Stephen Hewlett
  • 2,415
  • 1
  • 18
  • 31