0

Biome tinting uses now uses the Biome Extractor data files.

See:
http://www.minecraftforum.net/viewtopic.php?f=25&t=80902&view=unread
This commit is contained in:
Andrew Chin
2010-11-14 15:07:26 -05:00
parent 210e65730f
commit dc80c88e94
2 changed files with 63 additions and 23 deletions

View File

@@ -14,10 +14,12 @@
# with the Overviewer. If not, see <http://www.gnu.org/licenses/>.
import numpy
from PIL import Image, ImageDraw, ImageEnhance
from PIL import Image, ImageDraw, ImageEnhance, ImageOps
import os.path
import hashlib
import logging
import time
import math
import nbt
import textures
@@ -473,6 +475,7 @@ class ChunkRenderer(object):
For cave mode, all blocks that have any direct sunlight are not
rendered, and blocks are drawn with a color tint depending on their
depth."""
blocks = self.blocks
if cave:
@@ -494,6 +497,11 @@ class ChunkRenderer(object):
tileEntities = get_tileentity_data(self.level)
biomeColorData = textures.prepareBiomeData(self.world.worlddir,
self.chunkX, self.chunkY)
# in the 8x8 block of biome data, what chunk is this?l
startX = (self.chunkX - int(math.floor(self.chunkX/8)*8))
startY = (self.chunkY - int(math.floor(self.chunkY/8)*8))
# Each block is 24x24
# The next block on the X axis adds 12px to x and subtracts 6px from y in the image
@@ -528,8 +536,22 @@ class ChunkRenderer(object):
if not t:
continue
if blockid in (2,18): # grass or leaves, tint according to biome
t = textures.tintForBiome(t, (16*self.chunkX) + x,y+(16*self.chunkY))
if blockid == 2: #grass
index = biomeColorData[ ((startY*16)+y) * 128 + (startX*16) + x]
c = textures.grasscolor[index]
# only tint the top texture
t = textures.prepareGrassTexture(c)
elif blockid == 18: # leaves
index = biomeColorData[ ((startY*16)+y) * 128 + (startX*16) + x]
c = textures.foliagecolor[index]
#i = textures.tintTexture(t,c)
i = ImageOps.colorize(ImageOps.grayscale(t[0]), (0,0,0), c)
i.putalpha(t[1])
t = (i, t[1])
# Check if this block is occluded
if cave and (
@@ -648,8 +670,6 @@ class ChunkRenderer(object):
# list above.
self.queue.put(['removePOI', (self.chunkX, self.chunkY)])
return img
# Render 3 blending masks for lighting

View File

@@ -538,30 +538,50 @@ def tintTexture(im, c):
i.putalpha(im.split()[3]); # copy the alpha band back in. assuming RGBA
return i
## prepare grasscolor.png
grassSide1 = transform_image_side(terrain_images[3])
grassSide2 = transform_image_side(terrain_images[3]).transpose(Image.FLIP_LEFT_RIGHT)
def prepareGrassTexture(color):
top = transform_image(tintTexture(terrain_images[0],color))
img = Image.new("RGBA", (24,24), (38,92,255,0))
img.paste(grassSide1, (0,6), grassSide1)
img.paste(grassSide2, (12,6), grassSide2)
img.paste(top, (0,0), top)
return (img.convert("RGB"), img.split()[3])
# TODO be more intelligent about where to find these files
grasscolor = list(Image.open("grasscolor.png").getdata())
foliagecolor = list(Image.open("foliagecolor.png").getdata())
currentBiomeFile = None
currentBiomeData = None
def prepareBiomeData(worlddir, chunkX, chunkY):
'''Opens the worlddir and reads in the biome color information
from the .biome files. See also:
http://www.minecraftforum.net/viewtopic.php?f=25&t=80902
'''
t = sys.modules[__name__]
if not os.path.exists(os.path.join(worlddir, "EXTRACTEDBIOMES")):
raise Exception("EXTRACTEDBIOMES not found")
biomeFile = "%d.%d.biome" % (
int(math.floor(chunkX/8)*8),
int(math.floor(chunkY/8)*8)
)
if biomeFile == t.currentBiomeFile:
return currentBiomeData
def tintForBiome(im, x, y):
result = gmc.submit_job("GetBiome", "%d,%d" % (x,y))
temp, moisture = map(lambda x: float(x),result.result.split("/"))
t.currentBiomeFile = biomeFile
#print result.result
moisture *= temp
i = int((1.0 - temp) * 255)
j = int((1.0 - moisture) * 255)
#print "tintInfo for %d,%d is %f,%f coord %d, %d" % (x,y, temp, moisture, i, j)
#print "resulting color: %r" % (grasscolor.getpixel((i,j))[:-1],)
#t = tintTexture(im[0], grasscolor.getpixel((i, j))[:-1])
#im[0] = t
#c = grasscolor.getpixel((j,i))[:-1]
c = grasscolor[(j << 8 | i)]
#print "grass color: %r" % (c,)
i = ImageOps.colorize(ImageOps.grayscale(im[0]), (0,0,0), c)
i.putalpha(im[1])
return (i, im[1])
f = open(os.path.join(worlddir, "EXTRACTEDBIOMES", biomeFile))
rawdata = f.read()
f.close()
data = numpy.frombuffer(rawdata, dtype=numpy.dtype(">u2"))
t.currentBiomeData = data
return data
# This set holds block ids that require special pre-computing. These are typically
# things that require ancillary data to render properly (i.e. ladder plus orientation)