// NewDrawableSize returns a new draw.Image with the same type as p and the given bounds. // If p is not a draw.Image, another type is used. func NewDrawableSize(p image.Image, r image.Rectangle) draw.Image { switch p := p.(type) { case *image.RGBA: return image.NewRGBA(r) case *image.RGBA64: return image.NewRGBA64(r) case *image.NRGBA: return image.NewNRGBA(r) case *image.NRGBA64: return image.NewNRGBA64(r) case *image.Alpha: return image.NewAlpha(r) case *image.Alpha16: return image.NewAlpha16(r) case *image.Gray: return image.NewGray(r) case *image.Gray16: return image.NewGray16(r) case *image.Paletted: pl := make(color.Palette, len(p.Palette)) copy(pl, p.Palette) return image.NewPaletted(r, pl) case *image.CMYK: return image.NewCMYK(r) default: return image.NewRGBA(r) } }
func NewImageOfTypeRect(src image.Image, bounds image.Rectangle) image.Image { switch i := src.(type) { case *image.Alpha: return image.NewAlpha(bounds) case *image.Alpha16: return image.NewAlpha16(bounds) case *image.Gray: return image.NewGray(bounds) case *image.Gray16: return image.NewGray16(bounds) case *image.NRGBA: return image.NewNRGBA(bounds) case *image.NRGBA64: return image.NewNRGBA64(bounds) case *image.Paletted: return image.NewPaletted(bounds, i.Palette) case *image.RGBA: return image.NewRGBA(bounds) case *image.RGBA64: return image.NewRGBA64(bounds) case *image.YCbCr: return image.NewYCbCr(bounds, i.SubsampleRatio) } panic("Unknown image type") }
func createRandomImage(maxPaletteSize int) image.Image { r := image.Rectangle{Min: image.Point{0, 0}, Max: image.Point{gen.Rand(32) + 1, gen.Rand(32) + 1}} var img Image switch gen.Rand(10) { case 0: img = image.NewAlpha(r) case 1: img = image.NewAlpha16(r) case 2: img = image.NewCMYK(r) case 3: img = image.NewGray(r) case 4: img = image.NewGray16(r) case 5: img = image.NewNRGBA(r) case 6: img = image.NewNRGBA64(r) case 7: img = image.NewPaletted(r, randPalette(maxPaletteSize)) case 8: img = image.NewRGBA(r) case 9: img = image.NewRGBA64(r) default: panic("bad") } fill := gen.Rand(19) var palette []color.Color if fill == 17 { palette = randPalette(maxPaletteSize) } for y := 0; y < r.Max.Y; y++ { for x := 0; x < r.Max.X; x++ { switch { case fill <= 15: img.Set(x, y, color.RGBA64{ ^uint16(0) * uint16((fill>>0)&1), ^uint16(0) * uint16((fill>>1)&1), ^uint16(0) * uint16((fill>>2)&1), ^uint16(0) * uint16((fill>>3)&1), }) case fill == 16: img.Set(x, y, randColor()) case fill == 17: img.Set(x, y, palette[gen.Rand(len(palette))]) case fill == 18: if gen.Rand(3) != 0 { img.Set(x, y, color.RGBA64{}) } else { img.Set(x, y, randColor()) } default: panic("bad") } } } return img.(image.Image) }
// ConvertToAlpha16 returns an *image.Alpha16 instance by asserting the given // ImageReader has that type or, if it does not, using Copy to concurrently // set the color.Color values of a new *image.Alpha16 instance with the same // bounds. func ConvertToAlpha16(src ImageReader) *image.Alpha16 { if dst, ok := src.(*image.Alpha16); ok { return dst } dst := image.NewAlpha16(src.Bounds()) Copy(dst, src) return dst }
func newImage(m image.Image, width, height int) draw.Image { switch m.(type) { case *image.RGBA: return image.NewRGBA(image.Rect(0, 0, width, height)) case *image.Gray: return image.NewGray(image.Rect(0, 0, width, height)) case *image.Gray16: return image.NewGray16(image.Rect(0, 0, width, height)) case *image.NRGBA: return image.NewNRGBA(image.Rect(0, 0, width, height)) case *image.RGBA64: return image.NewRGBA64(image.Rect(0, 0, width, height)) case *image.Alpha: return image.NewAlpha(image.Rect(0, 0, width, height)) case *image.Alpha16: return image.NewAlpha16(image.Rect(0, 0, width, height)) } return image.NewRGBA(image.Rect(0, 0, width, height)) }
func newDrawImage(r image.Rectangle, m color.Model) draw.Image { switch m { case color.RGBA64Model: return image.NewRGBA64(r) case color.NRGBAModel: return image.NewNRGBA(r) case color.NRGBA64Model: return image.NewNRGBA64(r) case color.AlphaModel: return image.NewAlpha(r) case color.Alpha16Model: return image.NewAlpha16(r) case color.GrayModel: return image.NewGray(r) case color.Gray16Model: return image.NewGray16(r) default: return image.NewRGBA(r) } }
// Pow2Image returns the given image, scaled to the smallest power-of-two // dimensions larger or equal to the input dimensions. // It preserves the image format and contents. // // This is useful if an image is to be used as an OpenGL texture. // These often require image data to have power-of-two dimensions. func Pow2Image(src image.Image) image.Image { sb := src.Bounds() w, h := uint32(sb.Dx()), uint32(sb.Dy()) if IsPow2(w) && IsPow2(h) { return src // Nothing to do. } rect := image.Rect(0, 0, int(Pow2(w)), int(Pow2(h))) switch src := src.(type) { case *image.Alpha: return copyImg(src, image.NewAlpha(rect)) case *image.Alpha16: return copyImg(src, image.NewAlpha16(rect)) case *image.Gray: return copyImg(src, image.NewGray(rect)) case *image.Gray16: return copyImg(src, image.NewGray16(rect)) case *image.NRGBA: return copyImg(src, image.NewNRGBA(rect)) case *image.NRGBA64: return copyImg(src, image.NewNRGBA64(rect)) case *image.Paletted: return copyImg(src, image.NewPaletted(rect, src.Palette)) case *image.RGBA: return copyImg(src, image.NewRGBA(rect)) case *image.RGBA64: return copyImg(src, image.NewRGBA64(rect)) } panic(fmt.Sprintf("Unsupported image format: %T", src)) }
func newDrawImage(r image.Rectangle, m color.Model) draw.Image { // TODO: 各カラーモデルごとに画像を初期化し返す。 // なお、指定されたカラーモデルがimage/colorパッケージに定義されていない場合は、 // RGBAの画像を作って返す。 switch m { case color.RGBA64Model: return image.NewRGBA64(r) case color.NRGBAModel: return image.NewNRGBA(r) case color.NRGBA64Model: return image.NewNRGBA64(r) case color.AlphaModel: return image.NewAlpha(r) case color.Alpha16Model: return image.NewAlpha16(r) case color.GrayModel: return image.NewGray(r) case color.Gray16Model: return image.NewGray16(r) default: return image.NewRGBA(r) } }
// NewDrawableSize returns a new draw.Image with the same type as p and the given bounds. // If p is not a draw.Image, another type is used. func NewDrawableSize(p image.Image, r image.Rectangle) draw.Image { switch p.(type) { case *image.RGBA: return image.NewRGBA(r) case *image.RGBA64: return image.NewRGBA64(r) case *image.NRGBA: return image.NewNRGBA(r) case *image.NRGBA64: return image.NewNRGBA64(r) case *image.Alpha: return image.NewAlpha(r) case *image.Alpha16: return image.NewAlpha16(r) case *image.Gray: return image.NewGray(r) case *image.Gray16: return image.NewGray16(r) case *image.CMYK: return image.NewCMYK(r) default: return image.NewRGBA(r) } }
func BenchmarkNewSetFuncAlpha16(b *testing.B) { benchmarkNewSetFunc(b, image.NewAlpha16(image.Rect(0, 0, 1, 1))) }
func TestNewDrawable(t *testing.T) { r := image.Rect(0, 0, 1, 1) for _, newImage := range []func(image.Rectangle) image.Image{ func(r image.Rectangle) image.Image { return image.NewRGBA(r) }, func(r image.Rectangle) image.Image { return image.NewRGBA64(r) }, func(r image.Rectangle) image.Image { return image.NewNRGBA(r) }, func(r image.Rectangle) image.Image { return image.NewNRGBA64(r) }, func(r image.Rectangle) image.Image { return image.NewAlpha(r) }, func(r image.Rectangle) image.Image { return image.NewAlpha16(r) }, func(r image.Rectangle) image.Image { return image.NewGray(r) }, func(r image.Rectangle) image.Image { return image.NewGray16(r) }, func(r image.Rectangle) image.Image { return image.NewCMYK(r) }, func(r image.Rectangle) image.Image { return image.NewPaletted(r, color.Palette{ color.RGBA{0, 0, 0, 255}, color.RGBA{255, 0, 0, 255}, color.RGBA{0, 255, 0, 255}, color.RGBA{0, 0, 255, 255}, color.RGBA{255, 255, 255, 255}, }) }, func(r image.Rectangle) image.Image { return image.NewYCbCr(r, image.YCbCrSubsampleRatio444) }, func(r image.Rectangle) image.Image { return image.NewYCbCr(r, image.YCbCrSubsampleRatio422) }, func(r image.Rectangle) image.Image { return image.NewYCbCr(r, image.YCbCrSubsampleRatio420) }, func(r image.Rectangle) image.Image { return image.NewYCbCr(r, image.YCbCrSubsampleRatio440) }, func(r image.Rectangle) image.Image { return image.NewYCbCr(r, image.YCbCrSubsampleRatio411) }, func(r image.Rectangle) image.Image { return image.NewYCbCr(r, image.YCbCrSubsampleRatio410) }, func(r image.Rectangle) image.Image { return image.NewNYCbCrA(r, image.YCbCrSubsampleRatio444) }, func(r image.Rectangle) image.Image { return image.NewNYCbCrA(r, image.YCbCrSubsampleRatio422) }, func(r image.Rectangle) image.Image { return image.NewNYCbCrA(r, image.YCbCrSubsampleRatio420) }, func(r image.Rectangle) image.Image { return image.NewNYCbCrA(r, image.YCbCrSubsampleRatio440) }, func(r image.Rectangle) image.Image { return image.NewNYCbCrA(r, image.YCbCrSubsampleRatio411) }, func(r image.Rectangle) image.Image { return image.NewNYCbCrA(r, image.YCbCrSubsampleRatio410) }, func(r image.Rectangle) image.Image { return image.NewUniform(color.RGBA{}) }, func(r image.Rectangle) image.Image { return &testImageDefault{image.NewRGBA(r)} }, } { p := newImage(r) t.Run(fmt.Sprintf("%T", p), func(t *testing.T) { NewDrawable(p) }) } }
// Copies an image to a new image of the same kind: func CloneKind(src image.Image) image.Image { srcBounds := src.Bounds().Canon() zeroedBounds := srcBounds.Sub(srcBounds.Min) switch si := src.(type) { case *image.RGBA: out := image.NewRGBA(zeroedBounds) for y := srcBounds.Min.Y; y < srcBounds.Max.Y; y++ { for x := srcBounds.Min.X; x < srcBounds.Max.X; x++ { out.SetRGBA(x-srcBounds.Min.X, y-srcBounds.Min.Y, si.At(x, y).(color.RGBA)) } } return out case *image.YCbCr: out := image.NewYCbCr(zeroedBounds, si.SubsampleRatio) for y := srcBounds.Min.Y; y < srcBounds.Max.Y; y++ { for x := srcBounds.Min.X; x < srcBounds.Max.X; x++ { ycbcr := si.At(x, y).(color.YCbCr) yoffs := out.YOffset(x-srcBounds.Min.X, y-srcBounds.Min.Y) coffs := out.COffset(x-srcBounds.Min.X, y-srcBounds.Min.Y) out.Y[yoffs] = ycbcr.Y out.Cb[coffs] = ycbcr.Cb out.Cr[coffs] = ycbcr.Cr } } return out case *image.Paletted: out := image.NewPaletted(zeroedBounds, si.Palette) for y := srcBounds.Min.Y; y < srcBounds.Max.Y; y++ { for x := srcBounds.Min.X; x < srcBounds.Max.X; x++ { out.SetColorIndex(x-srcBounds.Min.X, y-srcBounds.Min.Y, si.ColorIndexAt(x, y)) } } return out case *image.RGBA64: out := image.NewRGBA64(zeroedBounds) for y := srcBounds.Min.Y; y < srcBounds.Max.Y; y++ { for x := srcBounds.Min.X; x < srcBounds.Max.X; x++ { out.SetRGBA64(x-srcBounds.Min.X, y-srcBounds.Min.Y, si.At(x, y).(color.RGBA64)) } } return out case *image.NRGBA: out := image.NewNRGBA(zeroedBounds) for y := srcBounds.Min.Y; y < srcBounds.Max.Y; y++ { for x := srcBounds.Min.X; x < srcBounds.Max.X; x++ { out.SetNRGBA(x-srcBounds.Min.X, y-srcBounds.Min.Y, si.At(x, y).(color.NRGBA)) } } return out case *image.NRGBA64: out := image.NewNRGBA64(zeroedBounds) for y := srcBounds.Min.Y; y < srcBounds.Max.Y; y++ { for x := srcBounds.Min.X; x < srcBounds.Max.X; x++ { out.SetNRGBA64(x-srcBounds.Min.X, y-srcBounds.Min.Y, si.At(x, y).(color.NRGBA64)) } } return out case *image.Alpha: out := image.NewAlpha(zeroedBounds) for y := srcBounds.Min.Y; y < srcBounds.Max.Y; y++ { for x := srcBounds.Min.X; x < srcBounds.Max.X; x++ { out.SetAlpha(x-srcBounds.Min.X, y-srcBounds.Min.Y, si.At(x, y).(color.Alpha)) } } return out case *image.Alpha16: out := image.NewAlpha16(zeroedBounds) for y := srcBounds.Min.Y; y < srcBounds.Max.Y; y++ { for x := srcBounds.Min.X; x < srcBounds.Max.X; x++ { out.SetAlpha16(x-srcBounds.Min.X, y-srcBounds.Min.Y, si.At(x, y).(color.Alpha16)) } } return out case *image.Gray: out := image.NewGray(zeroedBounds) for y := srcBounds.Min.Y; y < srcBounds.Max.Y; y++ { for x := srcBounds.Min.X; x < srcBounds.Max.X; x++ { out.SetGray(x-srcBounds.Min.X, y-srcBounds.Min.Y, si.At(x, y).(color.Gray)) } } return out case *image.Gray16: out := image.NewGray16(zeroedBounds) for y := srcBounds.Min.Y; y < srcBounds.Max.Y; y++ { for x := srcBounds.Min.X; x < srcBounds.Max.X; x++ { out.SetGray16(x-srcBounds.Min.X, y-srcBounds.Min.Y, si.At(x, y).(color.Gray16)) } } return out default: panic(fmt.Errorf("Unhandled image format type: %s", reflect.TypeOf(src).Name())) } }
return image.NewRGBA(r) }, func(r image.Rectangle) image.Image { return image.NewRGBA64(r) }, func(r image.Rectangle) image.Image { return image.NewNRGBA(r) }, func(r image.Rectangle) image.Image { return image.NewNRGBA64(r) }, func(r image.Rectangle) image.Image { return image.NewAlpha(r) }, func(r image.Rectangle) image.Image { return image.NewAlpha16(r) }, func(r image.Rectangle) image.Image { return image.NewGray(r) }, func(r image.Rectangle) image.Image { return image.NewGray16(r) }, func(r image.Rectangle) image.Image { return image.NewCMYK(r) }, func(r image.Rectangle) image.Image { return image.NewPaletted(r, testPalette) }, func(r image.Rectangle) image.Image { return image.NewYCbCr(r, image.YCbCrSubsampleRatio444)