math/fixed: add Floor, Round and Ceil methods.

Change-Id: I7ed8c79a9098f45b38db947b5d99d021358e4e96
Reviewed-on: https://go-review.googlesource.com/21700
Reviewed-by: David Crawshaw <crawshaw@golang.org>
diff --git a/math/fixed/fixed.go b/math/fixed/fixed.go
index 2f25d0e..fe27934 100644
--- a/math/fixed/fixed.go
+++ b/math/fixed/fixed.go
@@ -41,6 +41,15 @@
 	return "-33554432:00" // The minimum value is -(1<<25).
 }
 
+// Floor returns the greatest integer value less than or equal to x.
+func (x Int26_6) Floor() Int26_6 { return (x + 0x00) &^ 0x3f }
+
+// Round returns the nearest integer value to x. Ties are rounded up.
+func (x Int26_6) Round() Int26_6 { return (x + 0x20) &^ 0x3f }
+
+// Ceil returns the least integer value greater than or equal to x.
+func (x Int26_6) Ceil() Int26_6 { return (x + 0x3f) &^ 0x3f }
+
 // Int52_12 is a signed 52.12 fixed-point number.
 //
 // The integer part ranges from -2251799813685248 to 2251799813685247,
@@ -65,6 +74,15 @@
 	return "-2251799813685248:0000" // The minimum value is -(1<<51).
 }
 
+// Floor returns the greatest integer value less than or equal to x.
+func (x Int52_12) Floor() Int52_12 { return (x + 0x000) &^ 0xfff }
+
+// Round returns the nearest integer value to x. Ties are rounded up.
+func (x Int52_12) Round() Int52_12 { return (x + 0x800) &^ 0xfff }
+
+// Ceil returns the least integer value greater than or equal to x.
+func (x Int52_12) Ceil() Int52_12 { return (x + 0xfff) &^ 0xfff }
+
 // P returns the integer values x and y as a Point26_6.
 //
 // For example, passing the integer values (2, -3) yields Point26_6{128, -192}.
diff --git a/math/fixed/fixed_test.go b/math/fixed/fixed_test.go
index e252de7..464a449 100644
--- a/math/fixed/fixed_test.go
+++ b/math/fixed/fixed_test.go
@@ -9,17 +9,33 @@
 )
 
 func TestInt26_6(t *testing.T) {
-	got := Int26_6(1<<6 + 1<<4).String()
-	want := "1:16"
-	if got != want {
-		t.Fatalf("got %q, want %q", got, want)
+	x := Int26_6(1<<6 + 1<<4)
+	if got, want := x.String(), "1:16"; got != want {
+		t.Errorf("String: got %q, want %q", got, want)
+	}
+	if got, want := x.Floor(), Int26_6(1<<6); got != want {
+		t.Errorf("Floor: got %v, want %v", got, want)
+	}
+	if got, want := x.Round(), Int26_6(1<<6); got != want {
+		t.Errorf("Round: got %v, want %v", got, want)
+	}
+	if got, want := x.Ceil(), Int26_6(2<<6); got != want {
+		t.Errorf("Ceil: got %v, want %v", got, want)
 	}
 }
 
 func TestInt52_12(t *testing.T) {
-	got := Int52_12(1<<12 + 1<<10).String()
-	want := "1:1024"
-	if got != want {
-		t.Fatalf("got %q, want %q", got, want)
+	x := Int52_12(1<<12 + 1<<10)
+	if got, want := x.String(), "1:1024"; got != want {
+		t.Errorf("String: got %q, want %q", got, want)
+	}
+	if got, want := x.Floor(), Int52_12(1<<12); got != want {
+		t.Errorf("Floor: got %v, want %v", got, want)
+	}
+	if got, want := x.Round(), Int52_12(1<<12); got != want {
+		t.Errorf("Round: got %v, want %v", got, want)
+	}
+	if got, want := x.Ceil(), Int52_12(2<<12); got != want {
+		t.Errorf("Ceil: got %v, want %v", got, want)
 	}
 }