bitmap.go 8.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288
  1. // albitmap
  2. package al
  3. /*
  4. #include <stdlib.h>
  5. #include <allegro5/allegro.h>
  6. #include "helpers.h"
  7. */
  8. import "C"
  9. import "runtime"
  10. import "unsafe"
  11. // Type that wraps a Bitmap
  12. type Bitmap struct {
  13. handle *C.ALLEGRO_BITMAP
  14. }
  15. // returns low level handle for the bitmap
  16. func (bmp *Bitmap) toC() * C.ALLEGRO_BITMAP {
  17. return bmp.handle
  18. }
  19. // Destroys a bitmap. Use this only when really needed!
  20. func (bmp *Bitmap) Destroy() {
  21. if bmp.handle != nil {
  22. C.al_destroy_bitmap(bmp.handle)
  23. }
  24. bmp.handle = nil
  25. }
  26. // Alias for destoy to make this implement a Closer interface
  27. func (bmp *Bitmap) Close() {
  28. bmp.Destroy()
  29. }
  30. // Wraps a C Allegro bitmap in a Bitmap. Sets no finalizer.
  31. func wrapBitmapRaw(handle *C.ALLEGRO_BITMAP) *Bitmap {
  32. if handle == nil {
  33. return nil
  34. }
  35. return &Bitmap{handle}
  36. }
  37. // Wraps a C Allegro Bitmap in a Bitmap. Sets a finalizer that calls Destroy.
  38. func wrapBitmap(handle *C.ALLEGRO_BITMAP) *Bitmap {
  39. bmp := wrapBitmapRaw(handle)
  40. if bmp != nil {
  41. runtime.SetFinalizer(bmp, func(me *Bitmap) { me.Destroy() })
  42. }
  43. return bmp
  44. }
  45. const (
  46. MEMORY_BITMAP = C.ALLEGRO_MEMORY_BITMAP
  47. FORCE_LOCKING = C.ALLEGRO_FORCE_LOCKING
  48. NO_PRESERVE_TEXTURE = C.ALLEGRO_NO_PRESERVE_TEXTURE
  49. MIN_LINEAR = C.ALLEGRO_MIN_LINEAR
  50. MAG_LINEAR = C.ALLEGRO_MAG_LINEAR
  51. MIPMAP = C.ALLEGRO_MIPMAP
  52. VIDEO_BITMAP = C.ALLEGRO_VIDEO_BITMAP
  53. CONVERT_BITMAP = C.ALLEGRO_CONVERT_BITMAP
  54. )
  55. // Sets the format for new bitmaps that are created using CreateBitmap
  56. func SetNewBitmapFormat(format int) {
  57. C.al_set_new_bitmap_format(C.int(format))
  58. }
  59. // Sets the flags for new bitmaps that are created using CreateBitmap
  60. func SetNewBitmapFlags(flags int) {
  61. C.al_set_new_bitmap_flags(C.int(flags))
  62. }
  63. // Adds a flags to the flags that will be used for new bitmaps that are created
  64. // using CreateBitmap
  65. func AddNewBitmapFlag(flags int) {
  66. C.al_add_new_bitmap_flag(C.int(flags))
  67. }
  68. // Gets the format for new bitmaps that are created using CreateBitmap
  69. func NewBitmapFormat() int {
  70. return int(C.al_get_new_bitmap_format())
  71. }
  72. // Gets the flags for new bitmaps that are created using CreateBitmap
  73. func NewBitmapFlags() int {
  74. return int(C.al_get_new_bitmap_flags())
  75. }
  76. // Gets the width of the bitmap.
  77. func (bmp *Bitmap) Width() int {
  78. return int(C.al_get_bitmap_width(bmp.handle))
  79. }
  80. // Gets the height of the bitmap.
  81. func (bmp *Bitmap) Height() int {
  82. return int(C.al_get_bitmap_height(bmp.handle))
  83. }
  84. // Gets the width of the bitmap as a float32.
  85. func (bmp *Bitmap) Widthf() float32 {
  86. return float32(bmp.Width())
  87. }
  88. // Gets the height of the bitmap as a float32.
  89. func (bmp *Bitmap) Heightf() float32 {
  90. return float32(bmp.Height())
  91. }
  92. // Gets the format of the bitmap.
  93. func (bmp *Bitmap) Format() int {
  94. return int(C.al_get_bitmap_format(bmp.handle))
  95. }
  96. // Gets the flags of the bitmap.
  97. func (bmp *Bitmap) Flags() int {
  98. return int(C.al_get_bitmap_flags(bmp.handle))
  99. }
  100. // Creates a new RAW bitmap. It will not be automatically destroyed!
  101. func CreateBitmapRaw(w, h int) *Bitmap {
  102. return wrapBitmapRaw(C.al_create_bitmap(C.int(w), C.int(h)))
  103. }
  104. // Creates a new bitmap. It has a finalizer in place that will let it be automatically
  105. // destroyed.
  106. func CreateBitmap(w, h int) *Bitmap {
  107. return wrapBitmap(C.al_create_bitmap(C.int(w), C.int(h)))
  108. }
  109. // Puts a pixel to the currently active bitmap
  110. func PutPixel(x, y int, color Color) {
  111. C.al_put_pixel(C.int(x), C.int(y), color.toC())
  112. }
  113. // Blends a pixel to the currently active bitmap
  114. func PutBlendedPixel(x, y int, color Color) {
  115. C.al_put_blended_pixel(C.int(x), C.int(y), color.toC())
  116. }
  117. // Gets a pixel from the bitmap
  118. func (bmp *Bitmap) Pixel(x, y int) (color Color) {
  119. return wrapColor(C.al_get_pixel(bmp.handle, C.int(x), C.int(y)))
  120. }
  121. // Converts pixels of the mask color to transparent pixels (with an alpha channel)
  122. // for the given bitmap. Useful for, say "magic pink" backgrounds.
  123. func (bmp *Bitmap) ConvertMaskToAlpha(mask_color Color) {
  124. C.al_convert_mask_to_alpha(bmp.handle, mask_color.toC())
  125. }
  126. // Sets the clipping rectangle for the currently active bitmap. Anything drawn outside
  127. // this rectangle will be cut off or "clipped".
  128. func SetClippingRectangle(x, y, w, h int) {
  129. C.al_set_clipping_rectangle(C.int(x), C.int(y), C.int(w), C.int(h))
  130. }
  131. // Resets the clipping rectangle for the currently active bitmap to the full size.
  132. func ResetClippingRectangle() {
  133. C.al_reset_clipping_rectangle()
  134. }
  135. // Gets the clipping rectangle for the currently active bitmap.
  136. func ClippingRectangle() (x, y, w, h int) {
  137. var cx, cy, cw, ch C.int
  138. C.al_get_clipping_rectangle(&cx, &cy, &cw, &ch)
  139. return int(cx), int(cy), int(cw), int(ch)
  140. }
  141. // Creates a RAW sub bitmap of the given bitmap that must be manually destoyed with
  142. // Destroy()
  143. func (bmp *Bitmap) CreateSubBitmapRaw(x, y, w, h int) *Bitmap {
  144. return wrapBitmapRaw(C.al_create_sub_bitmap(bmp.handle,
  145. C.int(x), C.int(y), C.int(w), C.int(h)))
  146. }
  147. // Creates a sub bitmap of the given bitmap that will automatically be destoyed
  148. // through a finalizer. However, you must ensure that this destroy happens before the
  149. // parent bitmap is disposed of. You may need to call Destroy manyally anyway.
  150. func (bmp *Bitmap) CreateSubBitmap(x, y, w, h int) *Bitmap {
  151. return wrapBitmap(C.al_create_sub_bitmap(bmp.handle,
  152. C.int(x), C.int(y), C.int(w), C.int(h)))
  153. }
  154. // Returns whether or not the bitmap is a sub bitmap
  155. func (bmp *Bitmap) IsSubBitmap() bool {
  156. return cb2b(C.al_is_sub_bitmap(bmp.handle))
  157. }
  158. // Returns the parent bitmap of this sub bitmap, or nil if there is no parent.
  159. // This is a raw bitmap that has no finaliser set on it since likely
  160. /// this function will only be used for inspection.
  161. func (bmp *Bitmap) Parent() *Bitmap {
  162. return wrapBitmapRaw(C.al_get_parent_bitmap(bmp.handle))
  163. }
  164. // Gets the Returns the X position within the parent of a sub bitmap
  165. func (bmp *Bitmap) SubX() int {
  166. return int(C.al_get_bitmap_x(bmp.handle))
  167. }
  168. // Gets the Returns the Y position within the parent of a sub bitmap
  169. func (bmp *Bitmap) SubY() int {
  170. return int(C.al_get_bitmap_y(bmp.handle))
  171. }
  172. // Changes the parent, size and position of a sub bitmap
  173. func (bmp *Bitmap) Reparent(parent * Bitmap, x, y, w, h int) {
  174. C.al_reparent_bitmap(bmp.handle, parent.handle, C.int(x), C.int(y), C.int(w), C.int(h))
  175. }
  176. // Returns a raw clone of the bitmap, that will not be automatically
  177. // destroyed.
  178. func (bmp *Bitmap) CloneRaw() *Bitmap {
  179. return wrapBitmapRaw(C.al_clone_bitmap(bmp.handle))
  180. }
  181. // Returns a clone of the bitmap, that will automatically be
  182. // destroyed.
  183. func (bmp *Bitmap) Clone() *Bitmap {
  184. return wrapBitmap(C.al_clone_bitmap(bmp.handle))
  185. }
  186. // Converts the bitmap to the current screen format, to ensure the blitting goes fast
  187. func (bmp *Bitmap) Convert() {
  188. C.al_convert_bitmap(bmp.handle)
  189. }
  190. // Converts all known unconverted memory bitmaps to the current screen format,
  191. // to ensure the blitting goes fast.
  192. func ConvertMemoryBitmaps() {
  193. C.al_convert_memory_bitmaps()
  194. }
  195. const (
  196. LOCK_READWRITE = C.ALLEGRO_LOCK_READWRITE
  197. LOCK_READONLY = C.ALLEGRO_LOCK_READONLY
  198. LOCK_WRITEONLY = C.ALLEGRO_LOCK_WRITEONLY
  199. )
  200. type LockedRegion = C.ALLEGRO_LOCKED_REGION
  201. // TODO: Provide better access to the data member if needed
  202. func (lk * LockedRegion) dataPointer() unsafe.Pointer {
  203. return unsafe.Pointer(lk.data)
  204. }
  205. func (lk * LockedRegion) Format() int {
  206. return int(lk.format)
  207. }
  208. func (lk * LockedRegion) Pitch() int {
  209. return int(lk.pitch)
  210. }
  211. func (lk * LockedRegion) PixelSize() int {
  212. return int(lk.pixel_size)
  213. }
  214. func (bmp * Bitmap) Lock(format, flags int) *LockedRegion {
  215. return (*LockedRegion)(C.al_lock_bitmap(bmp.handle, C.int(format), C.int(flags)))
  216. }
  217. func (bmp * Bitmap) LockRegion(x, y, width, height, format, flags int) *LockedRegion {
  218. return (*LockedRegion)(C.al_lock_bitmap_region(bmp.handle,
  219. C.int(x), C.int(y), C.int(width), C.int(height), C.int(format), C.int(flags)))
  220. }
  221. func (bmp * Bitmap) LockBlocked(flags int) *LockedRegion {
  222. return (*LockedRegion)(C.al_lock_bitmap_blocked(bmp.handle, C.int(flags)))
  223. }
  224. func (bmp * Bitmap) LockRegionBlocked(x, y, width, height, flags int) *LockedRegion {
  225. return (*LockedRegion)(C.al_lock_bitmap_region_blocked(bmp.handle,
  226. C.int(x), C.int(y), C.int(width), C.int(height), C.int(flags)))
  227. }
  228. func (bmp * Bitmap) Unlock(){
  229. C.al_unlock_bitmap(bmp.handle)
  230. }
  231. func (bmp * Bitmap) Locked() bool {
  232. return bool(C.al_is_bitmap_locked(bmp.handle))
  233. }