I overriden Border control and in my overriden OnRender I do:

protected override void OnRender(System.Windows.Media.DrawingContext dc)
        {
            this.SnapsToDevicePixels = true;
            this.VisualEdgeMode = EdgeMode.Aliased;
            var myPen = new Pen(new SolidColorBrush(Colors.LightGray), 1);
            dc.DrawLine(myPen, new Point(1, 1), new Point(1, RenderSize.Height - 1));
            return;

Which give me this result: enter image description here

Question:

Is anybody can tell me why my code draw a line that start at (0,1) while it is suppose to start at (1, 1) like written in code ?

My DPI are 96, 96.

For ref, this is my xaml:

<Window xmlns:MyControls="clr-namespace:MyControls;assembly=MyControls"  x:Class="TestControls.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        Title="MainWindow" Height="350" Width="525">
    <Grid>
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto"></RowDefinition>
            <RowDefinition></RowDefinition>
            <RowDefinition></RowDefinition>
        </Grid.RowDefinitions>

        <Grid.ColumnDefinitions>
            <ColumnDefinition Width="Auto"></ColumnDefinition>
            <ColumnDefinition></ColumnDefinition>
            <ColumnDefinition></ColumnDefinition>
        </Grid.ColumnDefinitions>


        <MyControls:Border3D BorderThickness="3" BorderBrush="Aqua">
            <Rectangle Width="74" Height="3" HorizontalAlignment="Left">
                <Rectangle.Fill>
                    <SolidColorBrush Color="#40FF0000">

                    </SolidColorBrush>
                </Rectangle.Fill>
            </Rectangle>
        </MyControls:Border3D>

        <Rectangle  Grid.Row="1" Grid.Column="0" Width="80" Grid.ColumnSpan="2" HorizontalAlignment="Left">
            <Rectangle.Fill>
                <SolidColorBrush Color="LightGray"></SolidColorBrush>
            </Rectangle.Fill>
        </Rectangle>

    </Grid>
</Window>
有帮助吗?

解决方案

Keep in mind that (0, 0) is not the center of the upper left pixel. Instead it is the upper left corner of that pixel. In order to draw a line with a stroke thickness of 1 in the middle of the second pixel column (with index 1) you would have to draw from (1.5, 1) to (1.5, RenderSize.Height - 1):

dc.DrawLine(myPen, new Point(1.5, 1), new Point(1.5, RenderSize.Height - 1));

Setting SnapsToDevicePixels = true made your line snap to the left by half a pixel.


If you would use PenLineCap.Square for both the StartLineCap and EndLineCap properties of the line's Pen, you could draw from exactly one pixel center to the other:

var myPen = new Pen(Brushes.LightGray, 1);
myPen.StartLineCap = PenLineCap.Square;
myPen.EndLineCap = PenLineCap.Square;
dc.DrawLine(myPen, new Point(1.5, 1.5), new Point(1.5, RenderSize.Height - 1.5));
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top