#include "util/u_math.h"
-
+/**
+ * Helper union for packing pixel values.
+ * Will often contain values in formats which are too complex to be described
+ * in simple terms, hence might just effectively contain a number of bytes.
+ * Must be big enough to hold data for all formats (currently 256 bits).
+ */
union util_color {
ubyte ub;
ushort us;
uint ui;
float f[4];
+ double d[4];
};
/**
#include "util/u_format.h"
#include "util/u_rect.h"
+#include "util/u_pack_color.h"
/**
unsigned dst_y,
unsigned width,
unsigned height,
- uint32_t value)
+ union util_color *uc)
{
unsigned i, j;
unsigned width_size;
dst_y /= blockheight;
width = (width + blockwidth - 1)/blockwidth;
height = (height + blockheight - 1)/blockheight;
-
+
dst += dst_x * blocksize;
dst += dst_y * dst_stride;
width_size = width * blocksize;
-
+
switch (blocksize) {
case 1:
if(dst_stride == width_size)
- memset(dst, (ubyte) value, height * width_size);
+ memset(dst, uc->ub, height * width_size);
else {
- for (i = 0; i < height; i++) {
- memset(dst, (ubyte) value, width_size);
- dst += dst_stride;
- }
+ for (i = 0; i < height; i++) {
+ memset(dst, uc->ub, width_size);
+ dst += dst_stride;
+ }
}
break;
case 2:
for (i = 0; i < height; i++) {
- uint16_t *row = (uint16_t *)dst;
- for (j = 0; j < width; j++)
- *row++ = (uint16_t) value;
- dst += dst_stride;
+ uint16_t *row = (uint16_t *)dst;
+ for (j = 0; j < width; j++)
+ *row++ = uc->us;
+ dst += dst_stride;
}
break;
case 4:
for (i = 0; i < height; i++) {
- uint32_t *row = (uint32_t *)dst;
- for (j = 0; j < width; j++)
- *row++ = value;
- dst += dst_stride;
+ uint32_t *row = (uint32_t *)dst;
+ for (j = 0; j < width; j++)
+ *row++ = uc->ui;
+ dst += dst_stride;
+ }
+ break;
+ case 8:
+ case 12:
+ case 16:
+ case 24:
+ case 32:
+ for (i = 0; i < height; i++) {
+ ubyte *row = dst;
+ for (j = 0; j < width; j++) {
+ memcpy(row, uc, blocksize);
+ row += blocksize;
+ }
+ dst += dst_stride;
}
break;
default:
- assert(0);
- break;
+ assert(0);
+ break;
}
}
#include "pipe/p_format.h"
+#include "util/u_pack_color.h"
extern void
extern void
util_fill_rect(ubyte * dst, enum pipe_format format,
unsigned dst_stride, unsigned dst_x, unsigned dst_y,
- unsigned width, unsigned height, uint32_t value);
+ unsigned width, unsigned height, union util_color *uc);
#endif /* U_RECT_H */
assert(dst->texture);
if (!dst->texture)
return;
- util_pack_color(rgba, dst->texture->format, &uc);
+
dst_trans = pipe_get_transfer(pipe,
dst->texture,
dst->face,
if (dst_map) {
assert(dst_trans->stride > 0);
- switch (util_format_get_blocksize(dst->texture->format)) {
- case 1:
- case 2:
- case 4:
- util_pack_color(rgba, dst->texture->format, &uc);
- util_fill_rect(dst_map, dst->texture->format,
- dst_trans->stride,
- 0, 0, width, height, uc.ui);
- break;
- case 8:
- {
- /* expand the 4-byte clear value to an 8-byte value */
- /* should probably not convert back from ubyte but not
- sure what this code really achieved since it doesn't even
- check for format type... */
- ushort *row = (ushort *) dst_map;
- ushort val0 = UBYTE_TO_USHORT((uc.ui >> 0) & 0xff);
- ushort val1 = UBYTE_TO_USHORT((uc.ui >> 8) & 0xff);
- ushort val2 = UBYTE_TO_USHORT((uc.ui >> 16) & 0xff);
- ushort val3 = UBYTE_TO_USHORT((uc.ui >> 24) & 0xff);
- unsigned i, j;
- val0 = (val0 << 8) | val0;
- val1 = (val1 << 8) | val1;
- val2 = (val2 << 8) | val2;
- val3 = (val3 << 8) | val3;
- for (i = 0; i < height; i++) {
- for (j = 0; j < width; j++) {
- row[j*4+0] = val0;
- row[j*4+1] = val1;
- row[j*4+2] = val2;
- row[j*4+3] = val3;
- }
- row += dst_trans->stride/2;
- }
- }
- break;
- default:
- assert(0);
- break;
- }
+ util_pack_color(rgba, dst->texture->format, &uc);
+ util_fill_rect(dst_map, dst->texture->format,
+ dst_trans->stride,
+ 0, 0, width, height, &uc);
}
pipe->transfer_unmap(pipe, dst_trans);