0

textures are now stored in a continuous array in memory, instead of a dict

This commit is contained in:
Aaron Griffith
2011-11-11 15:34:45 -05:00
parent bb55547b0d
commit afd3ad639b
2 changed files with 36 additions and 32 deletions

View File

@@ -22,9 +22,13 @@ static PyObject *chunk_mod = NULL;
static PyObject *blockmap = NULL; static PyObject *blockmap = NULL;
static PyObject *known_blocks = NULL; static PyObject *known_blocks = NULL;
static PyObject *transparent_blocks = NULL; static PyObject *transparent_blocks = NULL;
static unsigned int max_blockid = 0;
static unsigned int max_data = 0;
PyObject *init_chunk_render(PyObject *self, PyObject *args) { PyObject *init_chunk_render(PyObject *self, PyObject *args) {
PyObject *tmp = NULL;
/* this function only needs to be called once, anything more should be /* this function only needs to be called once, anything more should be
* ignored */ * ignored */
if (blockmap) { if (blockmap) {
@@ -53,6 +57,15 @@ PyObject *init_chunk_render(PyObject *self, PyObject *args) {
if (!transparent_blocks) if (!transparent_blocks)
return NULL; return NULL;
tmp = PyObject_GetAttrString(textures, "max_blockid");
if (!tmp)
return NULL;
max_blockid = PyInt_AsLong(tmp);
tmp = PyObject_GetAttrString(textures, "max_data");
if (!tmp)
return NULL;
max_data = PyInt_AsLong(tmp);
Py_RETURN_NONE; Py_RETURN_NONE;
} }
@@ -373,15 +386,13 @@ chunk_render(PyObject *self, PyObject *args) {
for (state.x = 15; state.x > -1; state.x--) { for (state.x = 15; state.x > -1; state.x--) {
for (state.y = 0; state.y < 16; state.y++) { for (state.y = 0; state.y < 16; state.y++) {
PyObject *blockid = NULL;
/* set up the render coordinates */ /* set up the render coordinates */
state.imgx = xoff + state.x*12 + state.y*12; state.imgx = xoff + state.x*12 + state.y*12;
/* 128*12 -- offset for z direction, 15*6 -- offset for x */ /* 128*12 -- offset for z direction, 15*6 -- offset for x */
state.imgy = yoff - state.x*6 + state.y*6 + 128*12 + 15*6; state.imgy = yoff - state.x*6 + state.y*6 + 128*12 + 15*6;
for (state.z = 0; state.z < 128; state.z++) { for (state.z = 0; state.z < 128; state.z++) {
PyObject *tmp;
unsigned char ancilData; unsigned char ancilData;
state.imgy -= 12; state.imgy -= 12;
@@ -399,14 +410,7 @@ chunk_render(PyObject *self, PyObject *args) {
if ((state.imgy >= imgsize1 + 24) || (state.imgy <= -24)) { if ((state.imgy >= imgsize1 + 24) || (state.imgy <= -24)) {
continue; continue;
} }
/* decref'd on replacement *and* at the end of the z for block */
if (blockid) {
Py_DECREF(blockid);
}
blockid = PyInt_FromLong(state.block);
/* check for occlusion */ /* check for occlusion */
if (render_mode_occluded(rendermode, state.x, state.y, state.z)) { if (render_mode_occluded(rendermode, state.x, state.y, state.z)) {
continue; continue;
@@ -431,15 +435,12 @@ chunk_render(PyObject *self, PyObject *args) {
state.block_pdata = 0; state.block_pdata = 0;
} }
tmp = PyTuple_New(2); /* make sure our block info is in-bounds */
if (state.block >= max_blockid || ancilData >= max_data)
continue;
Py_INCREF(blockid); /* because SetItem steals */ /* get the texture */
PyTuple_SetItem(tmp, 0, blockid); t = PyList_GET_ITEM(blockmap, max_data * state.block + ancilData);
PyTuple_SetItem(tmp, 1, PyInt_FromLong(ancilData));
/* this is a borrowed reference. no need to decref */
t = PyDict_GetItem(blockmap, tmp);
Py_DECREF(tmp);
/* if we found a proper texture, render it! */ /* if we found a proper texture, render it! */
if (t != NULL && t != Py_None) if (t != NULL && t != Py_None)
@@ -470,11 +471,6 @@ chunk_render(PyObject *self, PyObject *args) {
} }
} }
} }
if (blockid) {
Py_DECREF(blockid);
blockid = NULL;
}
} }
} }

View File

@@ -423,7 +423,7 @@ def tintTexture(im, c):
def generate_texture_tuple(img): def generate_texture_tuple(img):
""" This takes an image and returns the needed tuple for the """ This takes an image and returns the needed tuple for the
blockmap dictionary.""" blockmap array."""
if img is None: if img is None:
return None return None
return (img, generate_opaque_mask(img)) return (img, generate_opaque_mask(img))
@@ -543,10 +543,14 @@ def loadLightColor():
# placeholders that are generated in generate() # placeholders that are generated in generate()
texture_dimensions = None texture_dimensions = None
blockmap_generators = {} blockmap_generators = {}
blockmap = {} blockmap = []
biome_grass_texture = None biome_grass_texture = None
known_blocks = set() known_blocks = set()
used_datas = set()
max_blockid = 0
max_data = 0
transparent_blocks = set() transparent_blocks = set()
solid_blocks = set() solid_blocks = set()
fluid_blocks = set() fluid_blocks = set()
@@ -578,6 +582,7 @@ def material(blockid=[], data=[0], **kwargs):
except TypeError: except TypeError:
return func(blockid, data) return func(blockid, data)
used_datas.update(data)
for block in blockid: for block in blockid:
# set the property sets appropriately # set the property sets appropriately
known_blocks.update([block]) known_blocks.update([block])
@@ -658,23 +663,26 @@ def generate(path=None,texture_size=24,bgc = (26,26,26,0),north_direction='lower
# generate the blocks # generate the blocks
global blockmap, blockmap_generators global blockmap, blockmap_generators
blockmap = {} global max_blockid, max_data
max_blockid = max(known_blocks) + 1
max_data = max(used_datas) + 1
blockmap = [None] * max_blockid * max_data
for blockid, data in blockmap_generators: for blockid, data in blockmap_generators:
texgen = blockmap_generators[(blockid, data)] texgen = blockmap_generators[(blockid, data)]
tex = texgen(blockid, data, north_direction) tex = texgen(blockid, data, north_direction)
blockmap[(blockid, data)] = generate_texture_tuple(tex) blockmap[blockid * max_data + data] = generate_texture_tuple(tex)
if texture_size != 24: if texture_size != 24:
# rescale biome textures. # rescale biome textures.
biome_grass_texture = biome_grass_texture.resize(texture_dimensions, Image.ANTIALIAS) biome_grass_texture = biome_grass_texture.resize(texture_dimensions, Image.ANTIALIAS)
# rescale the special block images # rescale the special block images
for blockid, data in iter(blockmap): for i, tex in enumerate(blockmap):
block = blockmap[(blockid,data)] if tex != None:
if block != None: block = tex[0]
block = block[0]
scaled_block = block.resize(texture_dimensions, Image.ANTIALIAS) scaled_block = block.resize(texture_dimensions, Image.ANTIALIAS)
blockmap[(blockid,data)] = generate_texture_tuple(scaled_block, blockid) blockmap[i] = generate_texture_tuple(scaled_block)
## ##
## and finally: actual texture definitions ## and finally: actual texture definitions