在图片框中画线并在缩放时重绘

本文关键字:缩放 | 更新日期: 2023-09-27 18:34:28

我以这种方式在图片框中画一条线:

horizontalstart = new Point(0, e.Y); //Start point of Horizontal line.
horizontalend = new Point(picbox_mpr.Width, e.Y); //End point of Horizontal line.
verticalstart = new Point(e.X, 0); //Start point of Vertical line
verticalend = new Point(e.X, picbox_mpr.Height); //End point of Vertical line.

然后在绘画事件中,我这样做:

e.Graphics.DrawLine(redline, horizontalstart, horizontalend); //Draw Horizontal line.
e.Graphics.DrawLine(redline, verticalstart, verticalend); //Draw Vertical line.

很简单,现在,我的图像可以缩放,这就是我挣扎的地方。

即使缩放图像,如何将线条保持在绘制的同一位置?

在图片框中画线并在缩放时重绘

存储一个十进制值,表示该坐标相对于图像宽度/高度的"百分比",而不是存储绝对整数坐标。 因此,如果 X 值为 10,宽度为 100,则存储 0.1。 假设图像被缩放,现在是 300 宽。 0.1 现在将转换为 0.1 * 300 = 30。 您可以将"百分比"X,Y 对存储在 PointF(( 而不是 Point(( 中。

这里有一个快速的例子:

public partial class Form1 : Form
{
    private List<Tuple<PointF, PointF>> Points = new List<Tuple<PointF, PointF>>();
    public Form1()
    {
        InitializeComponent();
        this.Shown += new EventHandler(Form1_Shown);
        this.pictureBox1.BackColor = Color.Red;
        this.pictureBox1.SizeChanged += new EventHandler(pictureBox1_SizeChanged);
        this.pictureBox1.Paint += new PaintEventHandler(pictureBox1_Paint);
    }
    void Form1_Shown(object sender, EventArgs e)
    {
        // convert absolute points:
        Point ptStart = new Point(100, 25);
        Point ptEnd = new Point(300, 75);
        // to percentages:
        PointF ptFstart = new PointF((float)ptStart.X / (float)pictureBox1.Width, (float)ptStart.Y / (float)pictureBox1.Height);
        PointF ptFend = new PointF((float)ptEnd.X / (float)pictureBox1.Width, (float)ptEnd.Y / (float)pictureBox1.Height);
        // add the percentage point to our list:
        Points.Add(new Tuple<PointF, PointF>(ptFstart, ptFend));
        pictureBox1.Refresh();
    }
    private void button1_Click(object sender, EventArgs e)
    {
        // increase the size of the picturebox 
        // watch how the line(s) change with the changed picturebox
        pictureBox1.Size = new Size(pictureBox1.Width + 50, pictureBox1.Height + 50);
    }
    void pictureBox1_SizeChanged(object sender, EventArgs e)
    {
        pictureBox1.Refresh();
    }
    void pictureBox1_Paint(object sender, PaintEventArgs e)
    {
        foreach (Tuple<PointF, PointF> tup in Points)
        {
            // convert the percentages back to absolute coord based on the current size:
            Point ptStart = new Point((int)(tup.Item1.X * pictureBox1.Width), (int)(tup.Item1.Y * pictureBox1.Height));
            Point ptEnd = new Point((int)(tup.Item2.X * pictureBox1.Width), (int)(tup.Item2.Y * pictureBox1.Height));
            e.Graphics.DrawLine(Pens.Black, ptStart, ptEnd);
        }
    }
}