fixed transparent block lighting
This commit is contained in:
@@ -59,14 +59,27 @@ imaging_python_to_c(PyObject *obj)
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* img should be an Image object, type 'L'
|
* img should be an Image object, type 'L' or 'RGBA'
|
||||||
|
* for RGBA images, operates on the alpha only
|
||||||
* factor should be between 0 and 1, inclusive
|
* factor should be between 0 and 1, inclusive
|
||||||
*/
|
*/
|
||||||
PyObject *brightness(PyObject *img, double factor) {
|
PyObject *brightness(PyObject *img, float factor) {
|
||||||
Imaging imDest;
|
Imaging imDest;
|
||||||
|
|
||||||
imDest = imaging_python_to_c(img);
|
imDest = imaging_python_to_c(img);
|
||||||
assert(imDest);
|
if (!imDest)
|
||||||
|
return NULL;
|
||||||
|
|
||||||
|
if (strcmp(imDest->mode, "RGBA") != 0 && strcmp(imDest->mode, "L") != 0) {
|
||||||
|
PyErr_SetString(PyExc_ValueError,
|
||||||
|
"given image does not have mode \"RGBA\" or \"L\"");
|
||||||
|
return NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* how far into image the first alpha byte resides */
|
||||||
|
int offset = (imDest->pixelsize == 4 ? 3 : 0);
|
||||||
|
/* how many bytes to skip to get to the next alpha byte */
|
||||||
|
int stride = imDest->pixelsize;
|
||||||
|
|
||||||
int x, y;
|
int x, y;
|
||||||
|
|
||||||
@@ -74,18 +87,14 @@ PyObject *brightness(PyObject *img, double factor) {
|
|||||||
int ysize = imDest->ysize;
|
int ysize = imDest->ysize;
|
||||||
|
|
||||||
for (y = 0; y < ysize; y++) {
|
for (y = 0; y < ysize; y++) {
|
||||||
UINT8 *out = (UINT8 *)imDest->image[y];
|
UINT8 *out = (UINT8 *)imDest->image[y] + offset;
|
||||||
//UINT8 *outmask = (UINT8 *)imDest->image[y] + 3;
|
|
||||||
|
|
||||||
for (x = 0; x < xsize; x++) {
|
for (x = 0; x < xsize; x++) {
|
||||||
//printf("old out: %d\n", *out);
|
|
||||||
*out *= factor;
|
*out *= factor;
|
||||||
//printf("new out: %d\n", *out);
|
out += stride;
|
||||||
out++;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* the alpha_over function, in a form that can be called from C */
|
/* the alpha_over function, in a form that can be called from C */
|
||||||
|
|||||||
@@ -41,7 +41,7 @@ Imaging imaging_python_to_c(PyObject *obj);
|
|||||||
PyObject *alpha_over(PyObject *dest, PyObject *src, PyObject *mask, int dx,
|
PyObject *alpha_over(PyObject *dest, PyObject *src, PyObject *mask, int dx,
|
||||||
int dy, int xsize, int ysize);
|
int dy, int xsize, int ysize);
|
||||||
PyObject *alpha_over_wrap(PyObject *self, PyObject *args);
|
PyObject *alpha_over_wrap(PyObject *self, PyObject *args);
|
||||||
PyObject *brightness(PyObject *img, double factor);
|
PyObject *brightness(PyObject *img, float factor);
|
||||||
|
|
||||||
/* in iterate.c */
|
/* in iterate.c */
|
||||||
typedef struct {
|
typedef struct {
|
||||||
|
|||||||
@@ -133,7 +133,7 @@ get_lighting_coefficient(RenderModeLighting *self, RenderState *state,
|
|||||||
/* shades the drawn block with the given facemask/black_color, based on the
|
/* shades the drawn block with the given facemask/black_color, based on the
|
||||||
lighting results from (x, y, z) */
|
lighting results from (x, y, z) */
|
||||||
static inline void
|
static inline void
|
||||||
do_shading_for_face(RenderModeLighting *self, RenderState *state,
|
do_shading_with_mask(RenderModeLighting *self, RenderState *state,
|
||||||
int x, int y, int z, PyObject *facemask) {
|
int x, int y, int z, PyObject *facemask) {
|
||||||
/* first, check for occlusion if the block is in the local chunk */
|
/* first, check for occlusion if the block is in the local chunk */
|
||||||
if (x >= 0 && x < 16 && y >= 0 && y < 16 && z >= 0 && z < 128) {
|
if (x >= 0 && x < 16 && y >= 0 && y < 16 && z >= 0 && z < 128) {
|
||||||
@@ -220,10 +220,15 @@ rendermode_lighting_draw(void *data, RenderState *state, PyObject *src, PyObject
|
|||||||
RenderModeLighting* self = (RenderModeLighting *)data;
|
RenderModeLighting* self = (RenderModeLighting *)data;
|
||||||
int x = state->x, y = state->y, z = state->z;
|
int x = state->x, y = state->y, z = state->z;
|
||||||
|
|
||||||
// TODO whole-block shading for transparent blocks
|
if (is_transparent(state->block)) {
|
||||||
do_shading_for_face(self, state, x, y, z+1, self->facemasks[0]);
|
/* transparent: do shading on whole block */
|
||||||
do_shading_for_face(self, state, x-1, y, z, self->facemasks[1]);
|
do_shading_with_mask(self, state, x, y, z, mask);
|
||||||
do_shading_for_face(self, state, x, y+1, z, self->facemasks[2]);
|
} else {
|
||||||
|
/* opaque: do per-face shading */
|
||||||
|
do_shading_with_mask(self, state, x, y, z+1, self->facemasks[0]);
|
||||||
|
do_shading_with_mask(self, state, x-1, y, z, self->facemasks[1]);
|
||||||
|
do_shading_with_mask(self, state, x, y+1, z, self->facemasks[2]);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
RenderModeInterface rendermode_lighting = {
|
RenderModeInterface rendermode_lighting = {
|
||||||
|
|||||||
Reference in New Issue
Block a user