简体   繁体   中英

Removing a rectangle from imagebox

I borrowed some code to draw a rectangle on an image, eg like a selection box. Right now, the code draws a rectangle any time you click and drag your mouse. If you simply left-click without dragging, nothing at all happens - the existing rectangle stays put. If you click and drag a new rectangle, the old rectangle disappears.

That's almost exactly like I want (I'm not wanting to permanently draw on the image... yet...), but with one change: I'd like for a single left-click to make the rectangle disappear as well.

The code is as follows:

public partial class ScreenSelection : Form
{
  private Point RectStartPoint;
  private Rectangle Rect = new Rectangle();
  private Brush selectionBrush = new SolidBrush(Color.FromArgb(128, 72, 145, 220));

  public ScreenSelection(DataTable buttonData)
  {
    InitializeComponent();
  }

  private void Canvas_MouseDown(object sender, MouseEventArgs e)
  {
    if (e.Button == MouseButtons.Left)
    {
      RectStartPoint = e.Location;
      Invalidate();
    }
  }

  private void Canvas_MouseMove(object sender, MouseEventArgs e)
  {
    if (e.Button != MouseButtons.Left)
      return;
    Point tempEndPoint = e.Location;
    Rect.Location = new Point(
        Math.Min(RectStartPoint.X, tempEndPoint.X),
        Math.Min(RectStartPoint.Y, tempEndPoint.Y));
    Rect.Size = new Size(
        Math.Abs(RectStartPoint.X - tempEndPoint.X),
        Math.Abs(RectStartPoint.Y - tempEndPoint.Y));
    Canvas.Invalidate();
  }

  private void Canvas_Paint(object sender, PaintEventArgs e)
  {
    // Draw the rectangle...
    if (Canvas.Image != null)
    {
      if (Rect != null && Rect.Width > 0 && Rect.Height > 0)
      {
        e.Graphics.FillRectangle(selectionBrush, Rect);
      }
    }
  }
}

I also have the user load a bitmap in as the image of the canvas, so once the user does that, canvas.image won't equal null.

so how can I make that rectangle disappear on a left click? I'm already doing an invalidate on the left-click, and that's clearly not getting rid of it.

I tried forcing the rectangle size on a left-click by doing:

        if (e.Button == MouseButtons.Left)
        {
            RectStartPoint = e.Location;
            Rect.Height = 0;
            Rect.Width = 0;
            Invalidate();
        }

and tried Rect.Size, Rect = Rectangle.Empty, Canvas.Refresh()...

How can I accomplish this?

Edit: I've also tried saving the graphics state and restoring it. That doesn't work... (no errors, just not getting rid of the rectangle)

Finally found a way to do it where I keep the drawing inside the paint event to improve performance / remove flicker...

It all had to do with fillRectangle s

here's the working code:

public partial class ScreenSelection : Form
{
    private Point RectStartPoint;
    private Rectangle Rect = new Rectangle();
    private Brush selectionBrush = new SolidBrush(Color.FromArgb(128, 72, 145, 220));
    private List<Rectangle> Rects = new List<Rectangle>();
    private bool RectStart = false;

    public ScreenSelection(DataTable buttonData)
    {
        InitializeComponent();
    }

   private void Canvas_MouseUp(object sender, MouseEventArgs e)
    {
        if (e.Button == MouseButtons.Left)
        {
            if (RectStartPoint == e.Location)
            {
                int i = Rects.Count;
                if (i > 0) { Rects.RemoveAt(i - 1); }
                Canvas.Refresh();
            }
        }
    }

    private void Canvas_MouseDown(object sender, MouseEventArgs e)
    {
        if (e.Button == MouseButtons.Left)
        {
            RectStartPoint = e.Location;
            int i = Rects.Count;
            if (i >= 1) { Rects.RemoveAt(i - 1); }
            RectStart = false;
            Canvas.Refresh();
        }
    }

    private void Canvas_MouseMove(object sender, MouseEventArgs e)
    {
        if (e.Button != MouseButtons.Left)
            return;

        Point tempEndPoint = e.Location;
        Rect.Location = new Point(
            Math.Min(RectStartPoint.X, tempEndPoint.X),
            Math.Min(RectStartPoint.Y, tempEndPoint.Y));
        Rect.Size = new Size(
            Math.Abs(RectStartPoint.X - tempEndPoint.X),
            Math.Abs(RectStartPoint.Y - tempEndPoint.Y));
        if (!RectStart)
        {
            Rects.Add(Rect);
            RectStart = true;
        }
        else
        {
            Rects[(Rects.Count - 1)] = Rect;
        }
        Canvas.Invalidate(); 
    }

    private void Canvas_Paint(object sender, PaintEventArgs e)
    {
        // Draw the rectangle...
        if (Canvas.Image != null)
        {
            if (Rects.Count > 0)
            {
                e.Graphics.FillRectangles(selectionBrush, Rects.ToArray());
            }
        }

    }
}

The bonus to this is that if I'm careful, I'll be able to also make some rectangles permanent while removing others.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM