github.com/cellofellow/gopkg@v0.0.0-20140722061823-eec0544a62ad/image/draw/draw.go (about) 1 // Copyright 2014 <chaishushan{AT}gmail.com>. All rights reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 // Package draw provides image composition functions. 6 package draw 7 8 import ( 9 "image" 10 "image/draw" 11 12 image_ext "github.com/chai2010/gopkg/image" 13 ) 14 15 // Draw aligns r.Min in dst with sp in src and then replaces the rectangle r in dst with src. 16 func Draw(dst draw.Image, r image.Rectangle, src image.Image, sp image.Point) { 17 r0 := r.Intersect(dst.Bounds()).Sub(r.Min) 18 r1 := image.Rect(sp.X, sp.Y, sp.X+r.Dx(), sp.Y+r.Dy()).Intersect(src.Bounds()).Sub(sp) 19 r = r0.Intersect(r1).Add(r.Min) 20 21 switch dst := dst.(type) { 22 case *image.Gray: 23 drawGray(dst, r, src, sp) 24 case *image.Gray16: 25 drawGray16(dst, r, src, sp) 26 case *image_ext.Gray32f: 27 drawGray32f(dst, r, src, sp) 28 case *image_ext.RGB: 29 drawRGB(dst, r, src, sp) 30 case *image_ext.RGB48: 31 drawRGB48(dst, r, src, sp) 32 case *image_ext.RGB96f: 33 drawRGB96f(dst, r, src, sp) 34 case *image.RGBA: 35 drawRGBA(dst, r, src, sp) 36 case *image.RGBA64: 37 drawRGBA64(dst, r, src, sp) 38 case *image_ext.RGBA128f: 39 drawRGBA128f(dst, r, src, sp) 40 default: 41 drawImage(dst, r, src, sp) 42 } 43 } 44 45 func drawGray(dst *image.Gray, r image.Rectangle, src image.Image, sp image.Point) { 46 switch src := src.(type) { 47 case *image.Gray: 48 for y := r.Min.Y; y < r.Max.Y; y++ { 49 off0 := dst.PixOffset(r.Min.X, y) 50 off1 := src.PixOffset(sp.X, y-r.Min.Y+sp.Y) 51 copy(dst.Pix[off0:][:r.Dx()], src.Pix[off1:]) 52 } 53 default: 54 drawImage(dst, r, src, sp) 55 } 56 } 57 58 func drawGray16(dst *image.Gray16, r image.Rectangle, src image.Image, sp image.Point) { 59 switch src := src.(type) { 60 case *image.Gray16: 61 for y := r.Min.Y; y < r.Max.Y; y++ { 62 off0 := dst.PixOffset(r.Min.X, y) 63 off1 := src.PixOffset(sp.X, y-r.Min.Y+sp.Y) 64 copy(dst.Pix[off0:][:r.Dx()*2], src.Pix[off1:]) 65 } 66 default: 67 drawImage(dst, r, src, sp) 68 } 69 } 70 71 func drawGray32f(dst *image_ext.Gray32f, r image.Rectangle, src image.Image, sp image.Point) { 72 switch src := src.(type) { 73 case *image_ext.Gray32f: 74 for y := r.Min.Y; y < r.Max.Y; y++ { 75 off0 := dst.PixOffset(r.Min.X, y) 76 off1 := src.PixOffset(sp.X, y-r.Min.Y+sp.Y) 77 copy(dst.Pix[off0:][:r.Dx()*4], src.Pix[off1:]) 78 } 79 default: 80 drawImage(dst, r, src, sp) 81 } 82 } 83 84 func drawRGB(dst *image_ext.RGB, r image.Rectangle, src image.Image, sp image.Point) { 85 switch src := src.(type) { 86 case *image_ext.RGB: 87 for y := r.Min.Y; y < r.Max.Y; y++ { 88 off0 := dst.PixOffset(r.Min.X, y) 89 off1 := src.PixOffset(sp.X, y-r.Min.Y+sp.Y) 90 copy(dst.Pix[off0:][:r.Dx()*3], src.Pix[off1:]) 91 } 92 default: 93 drawImage(dst, r, src, sp) 94 } 95 } 96 97 func drawRGB48(dst *image_ext.RGB48, r image.Rectangle, src image.Image, sp image.Point) { 98 switch src := src.(type) { 99 case *image_ext.RGB48: 100 for y := r.Min.Y; y < r.Max.Y; y++ { 101 off0 := dst.PixOffset(r.Min.X, y) 102 off1 := src.PixOffset(sp.X, y-r.Min.Y+sp.Y) 103 copy(dst.Pix[off0:][:r.Dx()*6], src.Pix[off1:]) 104 } 105 default: 106 drawImage(dst, r, src, sp) 107 } 108 } 109 110 func drawRGB96f(dst *image_ext.RGB96f, r image.Rectangle, src image.Image, sp image.Point) { 111 switch src := src.(type) { 112 case *image_ext.RGB96f: 113 for y := r.Min.Y; y < r.Max.Y; y++ { 114 off0 := dst.PixOffset(r.Min.X, y) 115 off1 := src.PixOffset(sp.X, y-r.Min.Y+sp.Y) 116 copy(dst.Pix[off0:][:r.Dx()*12], src.Pix[off1:]) 117 } 118 default: 119 drawImage(dst, r, src, sp) 120 } 121 } 122 123 func drawRGBA(dst *image.RGBA, r image.Rectangle, src image.Image, sp image.Point) { 124 switch src := src.(type) { 125 case *image.RGBA: 126 for y := r.Min.Y; y < r.Max.Y; y++ { 127 off0 := dst.PixOffset(r.Min.X, y) 128 off1 := src.PixOffset(sp.X, y-r.Min.Y+sp.Y) 129 copy(dst.Pix[off0:][:r.Dx()*4], src.Pix[off1:]) 130 } 131 default: 132 drawImage(dst, r, src, sp) 133 } 134 } 135 136 func drawRGBA64(dst *image.RGBA64, r image.Rectangle, src image.Image, sp image.Point) { 137 switch src := src.(type) { 138 case *image.RGBA64: 139 for y := r.Min.Y; y < r.Max.Y; y++ { 140 off0 := dst.PixOffset(r.Min.X, y) 141 off1 := src.PixOffset(sp.X, y-r.Min.Y+sp.Y) 142 copy(dst.Pix[off0:][:r.Dx()*8], src.Pix[off1:]) 143 } 144 default: 145 drawImage(dst, r, src, sp) 146 } 147 } 148 149 func drawRGBA128f(dst *image_ext.RGBA128f, r image.Rectangle, src image.Image, sp image.Point) { 150 switch src := src.(type) { 151 case *image_ext.RGBA128f: 152 for y := r.Min.Y; y < r.Max.Y; y++ { 153 off0 := dst.PixOffset(r.Min.X, y) 154 off1 := src.PixOffset(sp.X, y-r.Min.Y+sp.Y) 155 copy(dst.Pix[off0:][:r.Dx()*16], src.Pix[off1:]) 156 } 157 default: 158 drawImage(dst, r, src, sp) 159 } 160 } 161 162 func drawYCbCr(dst *yCbCr, r image.Rectangle, src image.Image, sp image.Point) { 163 drawImage(dst, r, src, sp) 164 } 165 166 func drawImage(dst draw.Image, r image.Rectangle, src image.Image, sp image.Point) { 167 for y := r.Min.Y; y < r.Max.Y; y++ { 168 for x := r.Min.X; x < r.Max.X; x++ { 169 dst.Set(x, y, src.At(x-r.Min.X+sp.X, y-r.Min.Y+sp.Y)) 170 } 171 } 172 }