package geom

// RectangleF is defined by two points, the minimum and maximum (floating point).
// Tries to use the same interface as the image.Rectangle but uses float64 instead of int.
type RectangleF struct {
	Min, Max PointF
}

// RectF is a shorthand function to create a rectangle.
func RectF(x0, y0, x1, y1 float64) RectangleF {
	if x0 > x1 {
		x0, x1 = x1, x0
	}
	if y0 > y1 {
		y0, y1 = y1, y0
	}
	return RectangleF{PtF(x0, y0), PtF(x1, y1)}
}

// Add translates rectangle r by point p.
func (r RectangleF) Add(p PointF) RectangleF {
	return RectangleF{
		PointF{r.Min.X + p.X, r.Min.Y + p.Y},
		PointF{r.Max.X + p.X, r.Max.Y + p.Y},
	}
}

// Inset returns the rectangle r inset by n. The resulting rectangle will never have
// a negative size.
func (r RectangleF) Inset(n float64) RectangleF {
	if r.Dx() < 2*n {
		r.Min.X = (r.Min.X + r.Max.X) / 2
		r.Max.X = r.Min.X
	} else {
		r.Min.X += n
		r.Max.X -= n
	}
	if r.Dy() < 2*n {
		r.Min.Y = (r.Min.Y + r.Max.Y) / 2
		r.Max.Y = r.Min.Y
	} else {
		r.Min.Y += n
		r.Max.Y -= n
	}
	return r
}

// Dx returns the width of r.
func (r RectangleF) Dx() float64 {
	return r.Max.X - r.Min.X
}

// Dy returns the height of r.
func (r RectangleF) Dy() float64 {
	return r.Max.Y - r.Min.Y
}

// Center returns the center of the rectangle.
func (r RectangleF) Center() PointF {
	return PointF{r.Min.X + .5*(r.Max.X-r.Min.X), r.Min.Y + .5*(r.Max.Y-r.Min.Y)}
}

// Size returns the size of the rectangle.
func (r RectangleF) Size() PointF {
	return PointF{r.Max.X - r.Min.X, r.Max.Y - r.Min.Y}
}