github.com/cellofellow/gopkg@v0.0.0-20140722061823-eec0544a62ad/image/webp/capi.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 webp 6 7 /* 8 #cgo CFLAGS: -I./libwebp/include -I./libwebp/src -DWEBP_EXPERIMENTAL_FEATURES 9 10 #include "webp.h" 11 */ 12 import "C" 13 import ( 14 "errors" 15 "unsafe" 16 ) 17 18 func webpGetInfo(data []byte) (width, height int, has_alpha bool, err error) { 19 if len(data) == 0 { 20 err = errors.New("webpGetInfo: bad arguments") 21 return 22 } 23 var c_width, c_height, c_has_alpha C.int 24 rv := C.webpGetInfo( 25 (*C.uint8_t)(unsafe.Pointer(&data[0])), C.size_t(len(data)), 26 &c_width, &c_height, &c_has_alpha, 27 ) 28 if rv == 0 { 29 err = errors.New("webpGetInfo: failed") 30 return 31 } 32 width, height = int(c_width), int(c_height) 33 has_alpha = (c_has_alpha != 0) 34 return 35 } 36 37 func webpDecodeGray(data []byte) (pix []byte, width, height int, err error) { 38 if len(data) == 0 { 39 err = errors.New("webpDecodeGray: bad arguments") 40 return 41 } 42 var c_width, c_height C.int 43 d := C.webpDecodeGray( 44 (*C.uint8_t)(unsafe.Pointer(&data[0])), C.size_t(len(data)), 45 &c_width, &c_height, 46 ) 47 if d == nil { 48 err = errors.New("webpDecodeGray: failed") 49 return 50 } 51 width, height = int(c_width), int(c_height) 52 pix = make([]byte, width*height*1) 53 copy(pix, ((*[1 << 30]byte)(unsafe.Pointer(d)))[0:len(pix):len(pix)]) 54 C.webpFree(unsafe.Pointer(d)) 55 return 56 } 57 58 func webpDecodeRGB(data []byte) (pix []byte, width, height int, err error) { 59 if len(data) == 0 { 60 err = errors.New("webpDecodeRGB: bad arguments") 61 return 62 } 63 var c_width, c_height C.int 64 d := C.webpDecodeRGB( 65 (*C.uint8_t)(unsafe.Pointer(&data[0])), C.size_t(len(data)), 66 &c_width, &c_height, 67 ) 68 if d == nil { 69 err = errors.New("webpDecodeRGB: failed") 70 return 71 } 72 width, height = int(c_width), int(c_height) 73 pix = make([]byte, width*height*3) 74 copy(pix, ((*[1 << 30]byte)(unsafe.Pointer(d)))[0:len(pix):len(pix)]) 75 C.webpFree(unsafe.Pointer(d)) 76 return 77 } 78 79 func webpDecodeRGBA(data []byte) (pix []byte, width, height int, err error) { 80 if len(data) == 0 { 81 err = errors.New("webpDecodeRGBA: bad arguments") 82 return 83 } 84 var c_width, c_height C.int 85 d := C.webpDecodeRGBA( 86 (*C.uint8_t)(unsafe.Pointer(&data[0])), C.size_t(len(data)), 87 &c_width, &c_height, 88 ) 89 if d == nil { 90 err = errors.New("webpDecodeRGBA: failed") 91 return 92 } 93 width, height = int(c_width), int(c_height) 94 pix = make([]byte, width*height*4) 95 copy(pix, ((*[1 << 30]byte)(unsafe.Pointer(d)))[0:len(pix):len(pix)]) 96 C.webpFree(unsafe.Pointer(d)) 97 return 98 } 99 100 func webpEncodeGray( 101 pix []byte, width, height, stride int, 102 quality_factor float32, 103 ) (output []byte, err error) { 104 if len(pix) == 0 || width <= 0 || height <= 0 || stride <= 0 || quality_factor < 0.0 { 105 err = errors.New("webpEncodeGray: bad arguments") 106 return 107 } 108 if stride < width*1 && len(pix) < height*stride { 109 err = errors.New("webpEncodeGray: bad arguments") 110 return 111 } 112 var d *C.uint8_t 113 d_size := C.webpEncodeGray( 114 (*C.uint8_t)(unsafe.Pointer(&pix[0])), C.int(width), C.int(height), 115 C.int(stride), C.float(quality_factor), 116 &d, 117 ) 118 if d_size == 0 { 119 err = errors.New("webpEncodeGray: failed") 120 return 121 } 122 output = make([]byte, int(d_size)) 123 copy(output, ((*[1 << 30]byte)(unsafe.Pointer(d)))[0:len(output):len(output)]) 124 C.webpFree(unsafe.Pointer(d)) 125 return 126 } 127 128 func webpEncodeRGB( 129 pix []byte, width, height, stride int, 130 quality_factor float32, 131 ) (output []byte, err error) { 132 if len(pix) == 0 || width <= 0 || height <= 0 || stride <= 0 || quality_factor < 0.0 { 133 err = errors.New("webpEncodeRGB: bad arguments") 134 return 135 } 136 if stride < width*3 && len(pix) < height*stride { 137 err = errors.New("webpEncodeRGB: bad arguments") 138 return 139 } 140 var d *C.uint8_t 141 d_size := C.webpEncodeRGB( 142 (*C.uint8_t)(unsafe.Pointer(&pix[0])), C.int(width), C.int(height), 143 C.int(stride), C.float(quality_factor), 144 &d, 145 ) 146 if d_size == 0 { 147 err = errors.New("webpEncodeRGB: failed") 148 return 149 } 150 output = make([]byte, int(d_size)) 151 copy(output, ((*[1 << 30]byte)(unsafe.Pointer(d)))[0:len(output):len(output)]) 152 C.webpFree(unsafe.Pointer(d)) 153 return 154 } 155 156 func webpEncodeRGBA( 157 pix []byte, width, height, stride int, 158 quality_factor float32, 159 ) (output []byte, err error) { 160 if len(pix) == 0 || width <= 0 || height <= 0 || stride <= 0 || quality_factor < 0.0 { 161 err = errors.New("webpEncodeRGBA: bad arguments") 162 return 163 } 164 if stride < width*4 && len(pix) < height*stride { 165 err = errors.New("webpEncodeRGBA: bad arguments") 166 return 167 } 168 var d *C.uint8_t 169 d_size := C.webpEncodeRGBA( 170 (*C.uint8_t)(unsafe.Pointer(&pix[0])), C.int(width), C.int(height), 171 C.int(stride), C.float(quality_factor), 172 &d, 173 ) 174 if d_size == 0 { 175 err = errors.New("webpEncodeRGBA: failed") 176 return 177 } 178 output = make([]byte, int(d_size)) 179 copy(output, ((*[1 << 30]byte)(unsafe.Pointer(d)))[0:len(output):len(output)]) 180 C.webpFree(unsafe.Pointer(d)) 181 return 182 } 183 184 func webpEncodeLosslessGray( 185 pix []byte, width, height, stride int, 186 ) (output []byte, err error) { 187 if len(pix) == 0 || width <= 0 || height <= 0 || stride <= 0 { 188 err = errors.New("webpEncodeLosslessGray: bad arguments") 189 return 190 } 191 if stride < width*1 && len(pix) < height*stride { 192 err = errors.New("webpEncodeLosslessGray: bad arguments") 193 return 194 } 195 var d *C.uint8_t 196 d_size := C.webpEncodeLosslessGray( 197 (*C.uint8_t)(unsafe.Pointer(&pix[0])), C.int(width), C.int(height), 198 C.int(stride), 199 &d, 200 ) 201 if d_size == 0 { 202 err = errors.New("webpEncodeLosslessGray: failed") 203 return 204 } 205 output = make([]byte, int(d_size)) 206 copy(output, ((*[1 << 30]byte)(unsafe.Pointer(d)))[0:len(output):len(output)]) 207 C.webpFree(unsafe.Pointer(d)) 208 return 209 } 210 211 func webpEncodeLosslessRGB( 212 pix []byte, width, height, stride int, 213 ) (output []byte, err error) { 214 if len(pix) == 0 || width <= 0 || height <= 0 || stride <= 0 { 215 err = errors.New("webpEncodeLosslessRGB: bad arguments") 216 return 217 } 218 if stride < width*3 && len(pix) < height*stride { 219 err = errors.New("webpEncodeLosslessRGB: bad arguments") 220 return 221 } 222 var d *C.uint8_t 223 d_size := C.webpEncodeLosslessRGB( 224 (*C.uint8_t)(unsafe.Pointer(&pix[0])), C.int(width), C.int(height), 225 C.int(stride), 226 &d, 227 ) 228 if d_size == 0 { 229 err = errors.New("webpEncodeLosslessRGB: failed") 230 return 231 } 232 output = make([]byte, int(d_size)) 233 copy(output, ((*[1 << 30]byte)(unsafe.Pointer(d)))[0:len(output):len(output)]) 234 C.webpFree(unsafe.Pointer(d)) 235 return 236 } 237 238 func webpEncodeLosslessRGBA( 239 pix []byte, width, height, stride int, 240 ) (output []byte, err error) { 241 if len(pix) == 0 || width <= 0 || height <= 0 || stride <= 0 { 242 err = errors.New("webpEncodeLosslessRGBA: bad arguments") 243 return 244 } 245 if stride < width*4 && len(pix) < height*stride { 246 err = errors.New("webpEncodeLosslessRGBA: bad arguments") 247 return 248 } 249 var d *C.uint8_t 250 d_size := C.webpEncodeLosslessRGBA( 251 (*C.uint8_t)(unsafe.Pointer(&pix[0])), C.int(width), C.int(height), 252 C.int(stride), 253 &d, 254 ) 255 if d_size == 0 { 256 err = errors.New("webpEncodeLosslessRGBA: failed") 257 return 258 } 259 output = make([]byte, int(d_size)) 260 copy(output, ((*[1 << 30]byte)(unsafe.Pointer(d)))[0:len(output):len(output)]) 261 C.webpFree(unsafe.Pointer(d)) 262 return 263 }