diff --git a/overviewer_core/rendermodes.py b/overviewer_core/rendermodes.py
index 4b81681..739e085 100644
--- a/overviewer_core/rendermodes.py
+++ b/overviewer_core/rendermodes.py
@@ -59,6 +59,40 @@ class EdgeLines(RenderPrimitive):
"opacity": ("darkness of the edge lines, from 0.0 to 1.0", 0.15),
}
+class Cave(RenderPrimitive):
+ name = "cave"
+ options = {
+ "only_lit": ("only render lit caves", False),
+ }
+
+class DepthTinting(RenderPrimitive):
+ name = "depth-tinting"
+
+ @property
+ def depth_colors(self):
+ depth_colors = getattr(self, "_depth_colors", [])
+ if depth_colors:
+ return depth_colors
+ r = 255
+ g = 0
+ b = 0
+ for z in range(128):
+ depth_colors.append(r)
+ depth_colors.append(g)
+ depth_colors.append(b)
+
+ if z < 32:
+ g += 7
+ elif z < 64:
+ r -= 7
+ elif z < 96:
+ b += 7
+ else:
+ g -= 7
+
+ self._depth_colors = depth_colors
+ return depth_colors
+
# Render 3 blending masks for lighting
# first is top (+Z), second is left (-X), third is right (+Y)
def generate_facemasks():
@@ -90,26 +124,3 @@ def generate_facemasks():
return (top, left, right)
facemasks = generate_facemasks()
-
-# Render 128 different color images for color coded depth blending in cave mode
-def generate_depthcolors():
- depth_colors = []
- r = 255
- g = 0
- b = 0
- for z in range(128):
- depth_colors.append(r)
- depth_colors.append(g)
- depth_colors.append(b)
-
- if z < 32:
- g += 7
- elif z < 64:
- r -= 7
- elif z < 96:
- b += 7
- else:
- g -= 7
-
- return depth_colors
-depth_colors = generate_depthcolors()
diff --git a/overviewer_core/src/rendermode-cave.c b/overviewer_core/src/primitives/cave.c
similarity index 64%
rename from overviewer_core/src/rendermode-cave.c
rename to overviewer_core/src/primitives/cave.c
index 9807ed2..f4d6605 100644
--- a/overviewer_core/src/rendermode-cave.c
+++ b/overviewer_core/src/primitives/cave.c
@@ -15,15 +15,32 @@
* with the Overviewer. If not, see .
*/
-#include "overviewer.h"
+#include "../overviewer.h"
#include
+typedef struct {
+ /* data used to know where the surface is */
+ PyObject *skylight;
+ PyObject *left_skylight;
+ PyObject *right_skylight;
+ PyObject *up_left_skylight;
+ PyObject *up_right_skylight;
+
+ /* data used to know where the lit caves are */
+ PyObject *blocklight;
+ PyObject *left_blocklight;
+ PyObject *right_blocklight;
+ PyObject *up_left_blocklight;
+ PyObject *up_right_blocklight;
+
+ int only_lit;
+} RenderPrimitiveCave;
+
static inline int
touches_light(unsigned int x, unsigned int y, unsigned int z,
PyObject *light, PyObject *left_light, PyObject *right_light,
PyObject *up_left_light, PyObject *up_right_light) {
-
if (getArrayByte3D(light, x, y, z+1) != 0) {
return 1;
}
@@ -79,10 +96,11 @@ touches_light(unsigned int x, unsigned int y, unsigned int z,
return 0;
}
-static inline int
-rendermode_cave_adjacent_occluded(void *data, RenderState *state, int x, int y, int z) {
- /* check for occlusion of edge blocks, using adjacent block data */
-
+static int
+cave_occluded(void *data, RenderState *state, int x, int y, int z) {
+ /* check for normal occlusion */
+ /* use ajacent chunks, if not you get blocks spreaded in chunk edges */
+
if (z != 127) {
if ( (x == 0) && (y != 15) ) {
if (state->left_blocks != Py_None) {
@@ -133,26 +151,11 @@ rendermode_cave_adjacent_occluded(void *data, RenderState *state, int x, int y,
}
static int
-rendermode_cave_occluded(void *data, RenderState *state, int x, int y, int z) {
- /* first, check to see if it's "normally" occluded */
- if (rendermode_lighting.occluded(data, state, x, y, z))
- return 1;
-
- /* check for normal occlusion */
- /* use ajacent chunks, if not you get blocks spreaded in chunk edges */
- return rendermode_cave_adjacent_occluded(data, state, x, y, z);
-}
-
-static int
-rendermode_cave_hidden(void *data, RenderState *state, int x, int y, int z) {
- RenderModeCave* self;
+cave_hidden(void *data, RenderState *state, int x, int y, int z) {
+ RenderPrimitiveCave* self;
int dz = 0;
- self = (RenderModeCave *)data;
+ self = (RenderPrimitiveCave *)data;
- /* first, check to see if it's "normally" hidden */
- if (rendermode_lighting.hidden(data, state, x, y, z))
- return 1;
-
/* check if the block is touching skylight */
if (z != 127) {
@@ -190,51 +193,25 @@ rendermode_cave_hidden(void *data, RenderState *state, int x, int y, int z) {
/* unfortunate side-effect of lit cave mode: we need to count occluded
* blocks as hidden for the lighting to look right, since technically our
* hiding depends on occlusion as well
- *
- * We leave out this check otherwise because it's fairly expensive.
*/
- if (self->lighting) {
- if ( (x != 0) && (y != 15) && (z != 127) &&
- !is_transparent(getArrayByte3D(state->blocks, x-1, y, z)) &&
- !is_transparent(getArrayByte3D(state->blocks, x, y, z+1)) &&
- !is_transparent(getArrayByte3D(state->blocks, x, y+1, z))) {
- return 1;
- }
-
- return rendermode_cave_adjacent_occluded(data, state, x, y, z);
+ if ( (x != 0) && (y != 15) && (z != 127) &&
+ !is_transparent(getArrayByte3D(state->blocks, x-1, y, z)) &&
+ !is_transparent(getArrayByte3D(state->blocks, x, y, z+1)) &&
+ !is_transparent(getArrayByte3D(state->blocks, x, y+1, z))) {
+ return 1;
}
- return 0;
+ return cave_occluded(data, state, x, y, z);
}
static int
-rendermode_cave_start(void *data, RenderState *state, PyObject *options) {
- RenderModeCave* self;
+cave_start(void *data, RenderState *state, PyObject *support) {
+ RenderPrimitiveCave* self;
int ret;
- self = (RenderModeCave *)data;
+ self = (RenderPrimitiveCave *)data;
- /* first, chain up */
- ret = rendermode_lighting.start(data, state, options);
- if (ret != 0)
- return ret;
-
- self->depth_tinting = 1;
- if (!render_mode_parse_option(options, "depth_tinting", "i", &(self->depth_tinting)))
+ if (!render_mode_parse_option(support, "only_lit", "i", &(self->only_lit)))
return 1;
-
- self->only_lit = 0;
- if (!render_mode_parse_option(options, "only_lit", "i", &(self->only_lit)))
- return 1;
-
- self->lighting = 0;
- if (!render_mode_parse_option(options, "lighting", "i", &(self->lighting)))
- return 1;
-
- if (self->lighting)
- {
- /* we can't skip lighting the sides in cave mode, it looks too weird */
- self->parent.skip_sides = 0;
- }
/* if there's skylight we are in the surface! */
self->skylight = get_chunk_data(state, CURRENT, SKYLIGHT);
@@ -251,16 +228,13 @@ rendermode_cave_start(void *data, RenderState *state, PyObject *options) {
self->up_right_blocklight = get_chunk_data(state, UP_RIGHT, BLOCKLIGHT);
}
- /* colors for tinting */
- self->depth_colors = PyObject_GetAttrString(state->support, "depth_colors");
-
return 0;
}
static void
-rendermode_cave_finish(void *data, RenderState *state) {
- RenderModeCave* self;
- self = (RenderModeCave *)data;
+cave_finish(void *data, RenderState *state) {
+ RenderPrimitiveCave* self;
+ self = (RenderPrimitiveCave *)data;
Py_DECREF(self->skylight);
Py_DECREF(self->left_skylight);
@@ -275,55 +249,13 @@ rendermode_cave_finish(void *data, RenderState *state) {
Py_DECREF(self->up_left_blocklight);
Py_DECREF(self->up_right_blocklight);
}
-
- Py_DECREF(self->depth_colors);
-
- rendermode_lighting.finish(data, state);
}
-static void
-rendermode_cave_draw(void *data, RenderState *state, PyObject *src, PyObject *mask, PyObject *mask_light) {
- RenderModeCave* self;
- int z, r, g, b;
- self = (RenderModeCave *)data;
-
- z = state->z;
- r = 0, g = 0, b = 0;
-
- /* draw the normal block */
- if (self->lighting) {
- rendermode_lighting.draw(data, state, src, mask, mask_light);
- } else {
- rendermode_normal.draw(data, state, src, mask, mask_light);
- }
-
- if (self->depth_tinting) {
- /* get the colors and tint and tint */
- r = PyInt_AsLong(PyList_GetItem(self->depth_colors, 0 + z*3));
- g = PyInt_AsLong(PyList_GetItem(self->depth_colors, 1 + z*3));
- b = PyInt_AsLong(PyList_GetItem(self->depth_colors, 2 + z*3));
-
- tint_with_mask(state->img, r, g, b, 255, mask, state->imgx, state->imgy, 0, 0);
- }
-
-}
-
-const RenderModeOption rendermode_cave_options[] = {
- {"depth_tinting", "tint caves based on how deep they are (default: True)"},
- {"only_lit", "only render lit caves (default: False)"},
- {"lighting", "render caves with lighting enabled (default: False)"},
- {NULL, NULL}
-};
-
-RenderModeInterface rendermode_cave = {
- "cave", "Cave",
- "render only caves",
- rendermode_cave_options,
- &rendermode_lighting,
- sizeof(RenderModeCave),
- rendermode_cave_start,
- rendermode_cave_finish,
- rendermode_cave_occluded,
- rendermode_cave_hidden,
- rendermode_cave_draw,
+RenderPrimitiveInterface primitive_cave = {
+ "cave", sizeof(RenderPrimitiveCave),
+ cave_start,
+ cave_finish,
+ cave_occluded,
+ cave_hidden,
+ NULL,
};
diff --git a/overviewer_core/src/primitives/depth-tinting.c b/overviewer_core/src/primitives/depth-tinting.c
new file mode 100644
index 0000000..80d5226
--- /dev/null
+++ b/overviewer_core/src/primitives/depth-tinting.c
@@ -0,0 +1,70 @@
+/*
+ * This file is part of the Minecraft Overviewer.
+ *
+ * Minecraft Overviewer is free software: you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License as published
+ * by the Free Software Foundation, either version 3 of the License, or (at
+ * your option) any later version.
+ *
+ * Minecraft Overviewer is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
+ * Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License along
+ * with the Overviewer. If not, see .
+ */
+
+#include "../overviewer.h"
+#include
+
+typedef struct {
+ /* list of colors used for tinting */
+ PyObject *depth_colors;
+} RenderPrimitiveDepthTinting;
+
+static int
+depth_tinting_start(void *data, RenderState *state, PyObject *support) {
+ RenderPrimitiveDepthTinting* self;
+ self = (RenderPrimitiveDepthTinting *)data;
+
+ self->depth_colors = PyObject_GetAttrString(support, "depth_colors");
+ if (self->depth_colors == NULL)
+ return 1;
+
+ return 0;
+}
+
+static void
+depth_tinting_finish(void *data, RenderState *state) {
+ RenderPrimitiveDepthTinting* self;
+ self = (RenderPrimitiveDepthTinting *)data;
+
+ Py_DECREF(self->depth_colors);
+}
+
+static void
+depth_tinting_draw(void *data, RenderState *state, PyObject *src, PyObject *mask, PyObject *mask_light) {
+ RenderPrimitiveDepthTinting* self;
+ int z, r, g, b;
+ self = (RenderPrimitiveDepthTinting *)data;
+
+ z = state->z;
+ r = 0, g = 0, b = 0;
+
+ /* get the colors and tint and tint */
+ r = PyInt_AsLong(PyList_GetItem(self->depth_colors, 0 + z*3));
+ g = PyInt_AsLong(PyList_GetItem(self->depth_colors, 1 + z*3));
+ b = PyInt_AsLong(PyList_GetItem(self->depth_colors, 2 + z*3));
+
+ tint_with_mask(state->img, r, g, b, 255, mask, state->imgx, state->imgy, 0, 0);
+}
+
+RenderPrimitiveInterface primitive_depth_tinting = {
+ "depth-tinting", sizeof(RenderPrimitiveDepthTinting),
+ depth_tinting_start,
+ depth_tinting_finish,
+ NULL,
+ NULL,
+ depth_tinting_draw,
+};
diff --git a/overviewer_core/src/rendermodes.h b/overviewer_core/src/rendermodes.h
index d10acff..3d835ec 100644
--- a/overviewer_core/src/rendermodes.h
+++ b/overviewer_core/src/rendermodes.h
@@ -174,34 +174,6 @@ typedef struct {
} RenderModeSpawn;
extern RenderModeInterface rendermode_spawn;
-/* CAVE */
-typedef struct {
- /* render blocks with lighting mode */
- RenderModeLighting parent;
-
- /* data used to know where the surface is */
- PyObject *skylight;
- PyObject *left_skylight;
- PyObject *right_skylight;
- PyObject *up_left_skylight;
- PyObject *up_right_skylight;
-
- /* data used to know where the surface is */
- PyObject *blocklight;
- PyObject *left_blocklight;
- PyObject *right_blocklight;
- PyObject *up_left_blocklight;
- PyObject *up_right_blocklight;
-
- /* colors used for tinting */
- PyObject *depth_colors;
-
- int depth_tinting;
- int only_lit;
- int lighting;
-} RenderModeCave;
-extern RenderModeInterface rendermode_cave;
-
/* MINERAL */
typedef struct {
/* inherits from overlay */