Added the ability to specify multiple crop zones.
This commit is contained in:
@@ -709,8 +709,8 @@ values. The valid configuration keys are listed below.
|
|||||||
.. _crop:
|
.. _crop:
|
||||||
|
|
||||||
``crop``
|
``crop``
|
||||||
You can use this to render a small subset of your map, instead of the entire
|
You can use this to render one or more small subsets of your map, instead
|
||||||
thing. The format is (min x, min z, max x, max z).
|
of the entire thing. The format is [(min x, min z, max x, max z)].
|
||||||
|
|
||||||
The coordinates are block coordinates. The same you get with the debug menu
|
The coordinates are block coordinates. The same you get with the debug menu
|
||||||
in-game and the coordinates shown when you view a map.
|
in-game and the coordinates shown when you view a map.
|
||||||
@@ -723,6 +723,14 @@ values. The valid configuration keys are listed below.
|
|||||||
'crop': (-500, -500, 500, 500),
|
'crop': (-500, -500, 500, 500),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Example that renders two 500 by 500 squares of land:
|
||||||
|
|
||||||
|
renders['myrender'] = {
|
||||||
|
'world': 'myworld',
|
||||||
|
'title': "Multi cropped Example",
|
||||||
|
'crop': [(-500, -500, 0, 0), (0, 0, 500, 500)]
|
||||||
|
}
|
||||||
|
|
||||||
This option performs a similar function to the old ``--regionlist`` option
|
This option performs a similar function to the old ``--regionlist`` option
|
||||||
(which no longer exists). It is useful for example if someone has wandered
|
(which no longer exists). It is useful for example if someone has wandered
|
||||||
really far off and made your map too large. You can set the crop for the
|
really far off and made your map too large. You can set the crop for the
|
||||||
|
|||||||
@@ -488,16 +488,20 @@ dir but you forgot to put quotes around the directory, since it contains spaces.
|
|||||||
# regionset cache pulls from the same underlying cache object.
|
# regionset cache pulls from the same underlying cache object.
|
||||||
rset = world.CachedRegionSet(rset, caches)
|
rset = world.CachedRegionSet(rset, caches)
|
||||||
|
|
||||||
# If a crop is requested, wrap the regionset here
|
|
||||||
if "crop" in render:
|
|
||||||
rset = world.CroppedRegionSet(rset, *render['crop'])
|
|
||||||
|
|
||||||
# If this is to be a rotated regionset, wrap it in a RotatedRegionSet
|
# If this is to be a rotated regionset, wrap it in a RotatedRegionSet
|
||||||
# object
|
# object
|
||||||
if (render['northdirection'] > 0):
|
if (render['northdirection'] > 0):
|
||||||
rset = world.RotatedRegionSet(rset, render['northdirection'])
|
rset = world.RotatedRegionSet(rset, render['northdirection'])
|
||||||
logging.debug("Using RegionSet %r", rset)
|
logging.debug("Using RegionSet %r", rset)
|
||||||
|
|
||||||
|
# If a crop is requested, wrap the regionset here
|
||||||
|
if "crop" in render:
|
||||||
|
rsets = []
|
||||||
|
for zone in render['crop']:
|
||||||
|
rsets.append(world.CroppedRegionSet(rset, *zone))
|
||||||
|
else:
|
||||||
|
rsets = [rset]
|
||||||
|
|
||||||
###############################
|
###############################
|
||||||
# Do the final prep and create the TileSet object
|
# Do the final prep and create the TileSet object
|
||||||
|
|
||||||
@@ -508,8 +512,9 @@ dir but you forgot to put quotes around the directory, since it contains spaces.
|
|||||||
render['name'] = render_name # perhaps a hack. This is stored here for the asset manager
|
render['name'] = render_name # perhaps a hack. This is stored here for the asset manager
|
||||||
tileSetOpts = util.dict_subset(render, ["name", "imgformat", "renderchecks", "rerenderprob", "bgcolor", "defaultzoom", "imgquality", "optimizeimg", "rendermode", "worldname_orig", "title", "dimension", "changelist", "showspawn", "overlay", "base", "poititle", "maxzoom", "showlocationmarker", "minzoom"])
|
tileSetOpts = util.dict_subset(render, ["name", "imgformat", "renderchecks", "rerenderprob", "bgcolor", "defaultzoom", "imgquality", "optimizeimg", "rendermode", "worldname_orig", "title", "dimension", "changelist", "showspawn", "overlay", "base", "poititle", "maxzoom", "showlocationmarker", "minzoom"])
|
||||||
tileSetOpts.update({"spawn": w.find_true_spawn()}) # TODO find a better way to do this
|
tileSetOpts.update({"spawn": w.find_true_spawn()}) # TODO find a better way to do this
|
||||||
tset = tileset.TileSet(w, rset, assetMrg, tex, tileSetOpts, tileset_dir)
|
for rset in rsets:
|
||||||
tilesets.append(tset)
|
tset = tileset.TileSet(w, rset, assetMrg, tex, tileSetOpts, tileset_dir)
|
||||||
|
tilesets.append(tset)
|
||||||
|
|
||||||
# Do tileset preprocessing here, before we start dispatching jobs
|
# Do tileset preprocessing here, before we start dispatching jobs
|
||||||
logging.info("Preprocessing...")
|
logging.info("Preprocessing...")
|
||||||
|
|||||||
@@ -19,6 +19,7 @@ import tempfile
|
|||||||
import shutil
|
import shutil
|
||||||
import logging
|
import logging
|
||||||
import stat
|
import stat
|
||||||
|
import errno
|
||||||
|
|
||||||
default_caps = {"chmod_works": True, "rename_works": True}
|
default_caps = {"chmod_works": True, "rename_works": True}
|
||||||
|
|
||||||
@@ -150,6 +151,20 @@ class FileReplacer(object):
|
|||||||
else:
|
else:
|
||||||
# copy permission bits, if needed
|
# copy permission bits, if needed
|
||||||
if self.caps.get("chmod_works") and os.path.exists(self.destname):
|
if self.caps.get("chmod_works") and os.path.exists(self.destname):
|
||||||
shutil.copymode(self.destname, self.tmpname)
|
try:
|
||||||
|
shutil.copymode(self.destname, self.tmpname)
|
||||||
|
except OSError, e:
|
||||||
|
# Ignore errno ENOENT: file does not exist. Due to a race
|
||||||
|
# condition, two processes could conceivably try and update
|
||||||
|
# the same temp file at the same time
|
||||||
|
if e.errno != errno.ENOENT:
|
||||||
|
raise
|
||||||
# atomic rename into place
|
# atomic rename into place
|
||||||
os.rename(self.tmpname, self.destname)
|
try:
|
||||||
|
os.rename(self.tmpname, self.destname)
|
||||||
|
except OSError, e:
|
||||||
|
# Ignore errno ENOENT: file does not exist. Due to a race
|
||||||
|
# condition, two processes could conceivably try and update
|
||||||
|
# the same temp file at the same time
|
||||||
|
if e.errno != errno.ENOENT:
|
||||||
|
raise
|
||||||
|
|||||||
@@ -225,15 +225,23 @@ def validateOutputDir(d):
|
|||||||
return expand_path(d)
|
return expand_path(d)
|
||||||
|
|
||||||
def validateCrop(value):
|
def validateCrop(value):
|
||||||
if len(value) != 4:
|
if not isinstance(value, list):
|
||||||
raise ValidationException("The value for the 'crop' setting must be a tuple of length 4")
|
value = [value]
|
||||||
a, b, c, d = tuple(int(x) for x in value)
|
|
||||||
|
cropZones = []
|
||||||
if a >= c:
|
for zone in value:
|
||||||
a, c = c, a
|
if len(zone) != 4:
|
||||||
if b >= d:
|
raise ValidationException("The value for the 'crop' setting must be an array of tuples of length 4")
|
||||||
b, d = d, b
|
a, b, c, d = tuple(int(x) for x in zone)
|
||||||
return (a, b, c, d)
|
|
||||||
|
if a >= c:
|
||||||
|
a, c = c, a
|
||||||
|
if b >= d:
|
||||||
|
b, d = d, b
|
||||||
|
|
||||||
|
cropZones.append((a, b, c, d))
|
||||||
|
|
||||||
|
return cropZones
|
||||||
|
|
||||||
def validateObserver(observer):
|
def validateObserver(observer):
|
||||||
if all(map(lambda m: hasattr(observer, m), ['start', 'add', 'update', 'finish'])):
|
if all(map(lambda m: hasattr(observer, m), ['start', 'add', 'update', 'finish'])):
|
||||||
|
|||||||
@@ -947,7 +947,14 @@ class TileSet(object):
|
|||||||
if self.options['optimizeimg']:
|
if self.options['optimizeimg']:
|
||||||
optimize_image(tmppath, imgformat, self.options['optimizeimg'])
|
optimize_image(tmppath, imgformat, self.options['optimizeimg'])
|
||||||
|
|
||||||
os.utime(tmppath, (max_mtime, max_mtime))
|
try:
|
||||||
|
os.utime(tmppath, (max_mtime, max_mtime))
|
||||||
|
except OSError, e:
|
||||||
|
# Ignore errno ENOENT: file does not exist. Due to a race
|
||||||
|
# condition, two processes could conceivably try and update
|
||||||
|
# the same temp file at the same time
|
||||||
|
if e.errno != errno.ENOENT:
|
||||||
|
raise
|
||||||
|
|
||||||
def _render_rendertile(self, tile):
|
def _render_rendertile(self, tile):
|
||||||
"""Renders the given render-tile.
|
"""Renders the given render-tile.
|
||||||
|
|||||||
Reference in New Issue
Block a user