00001
00002
00003
00004
00005
00006
00007
00008
00009 #include "PixelTool.h"
00010
00011 #include "LogicException.h"
00012
00013 #include <assert.h>
00014
00015
00016
00017
00018
00019
00020 bool
00021 PixelTool::colorEquals(const SDL_Color &color1, const SDL_Color &color2)
00022 {
00023 return color1.r == color2.r
00024 && color1.g == color2.g
00025 && color1.b == color2.b;
00026 }
00027
00028 Uint32
00029 PixelTool::convertColor(SDL_PixelFormat *format, const SDL_Color &color)
00030 {
00031 return SDL_MapRGB(format, color.r, color.g, color.b);
00032 }
00033
00034
00035
00036
00037
00038
00039 SDL_Color
00040 PixelTool::getColor(SDL_Surface *surface, int x, int y)
00041 {
00042 SDL_Color color;
00043 SDL_GetRGBA(getPixel(surface, x, y), surface->format,
00044 &color.r, &color.g, &color.b, &color.unused);
00045 return color;
00046 }
00047
00048
00049
00050
00051
00052
00053 void
00054 PixelTool::putColor(SDL_Surface *surface, int x, int y,
00055 const SDL_Color &color)
00056 {
00057 Uint32 pixel = SDL_MapRGBA(surface->format,
00058 color.r, color.g, color.b, color.unused);
00059 putPixel(surface, x, y, pixel);
00060 }
00061
00062
00063
00064
00065
00066
00067 Uint32
00068 PixelTool::getPixel(SDL_Surface *surface, int x, int y)
00069 {
00070 assert((0 <= x && x < surface->w) && (0 <= y && y < surface->h));
00071
00072 int bpp = surface->format->BytesPerPixel;
00073 Uint8 *p = static_cast<Uint8*>(surface->pixels) + y * surface->pitch
00074 + x * bpp;
00075
00076 return unpackPixel(bpp, p);
00077 }
00078
00079
00080
00081
00082
00083 void
00084 PixelTool::putPixel(SDL_Surface *surface, int x, int y, Uint32 pixel)
00085 {
00086 if ((0 <= x && x < surface->w) && (0 <= y && y < surface->h)) {
00087 int bpp = surface->format->BytesPerPixel;
00088 Uint8 *p = static_cast<Uint8*>(surface->pixels) + y * surface->pitch
00089 + x * bpp;
00090
00091 packPixel(bpp, p, pixel);
00092 }
00093 }
00094
00095
00096
00097
00098
00099
00100
00101
00102 Uint32
00103 PixelTool::unpackPixel(Uint8 bpp, Uint8 *p)
00104 {
00105 switch(bpp) {
00106 case 1:
00107 return *p;
00108 case 2:
00109 return *reinterpret_cast<Uint16*>(p);
00110 case 3:
00111 if (SDL_BYTEORDER == SDL_BIG_ENDIAN) {
00112 return p[0] << 16 | p[1] << 8 | p[2];
00113 }
00114 else {
00115 return p[0] | p[1] << 8 | p[2] << 16;
00116 }
00117 case 4:
00118 return *reinterpret_cast<Uint32*>(p);
00119 default:
00120 throw LogicException(ExInfo("unknown color depth")
00121 .addInfo("bpp", bpp));
00122 }
00123 }
00124
00125
00126
00127
00128
00129
00130
00131
00132 void
00133 PixelTool::packPixel(Uint8 bpp, Uint8 *p, Uint32 pixel)
00134 {
00135 assert(p != NULL);
00136
00137 switch(bpp) {
00138 case 1:
00139 *p = pixel;
00140 break;
00141 case 2:
00142 *reinterpret_cast<Uint16*>(p) = pixel;
00143 break;
00144 case 3:
00145 if (SDL_BYTEORDER == SDL_BIG_ENDIAN) {
00146 p[0] = (pixel >> 16) & 0xff;
00147 p[1] = (pixel >> 8) & 0xff;
00148 p[2] = pixel & 0xff;
00149 } else {
00150 p[0] = pixel & 0xff;
00151 p[1] = (pixel >> 8) & 0xff;
00152 p[2] = (pixel >> 16) & 0xff;
00153 }
00154 break;
00155 case 4:
00156 *reinterpret_cast<Uint32*>(p) = pixel;
00157 break;
00158 default:
00159 throw LogicException(ExInfo("unknown color depth")
00160 .addInfo("bpp", bpp));
00161 }
00162 }
00163