#include "irrlichttypes_extrabloated.h"
#include "mapnode.h"
#include "porting.h"
-#include "main.h" // For g_settings
#include "nodedef.h"
#include "content_mapnode.h" // For mapnode_translate_*_internal
#include "serialization.h" // For ser_ver_supported
param1 |= (a_light & 0x0f)<<4;
}
else
- assert(0);
+ assert("Invalid light bank" == NULL);
+}
+
+bool MapNode::isLightDayNightEq(INodeDefManager *nodemgr) const
+{
+ const ContentFeatures &f = nodemgr->get(*this);
+ bool isEqual;
+
+ if (f.param_type == CPT_LIGHT) {
+ u8 day = MYMAX(f.light_source, param1 & 0x0f);
+ u8 night = MYMAX(f.light_source, (param1 >> 4) & 0x0f);
+ isEqual = day == night;
+ } else {
+ isEqual = true;
+ }
+
+ return isEqual;
}
u8 MapNode::getLight(enum LightBank bank, INodeDefManager *nodemgr) const
return MYMAX(f.light_source, light);
}
+u8 MapNode::getLightNoChecks(enum LightBank bank, const ContentFeatures *f) const
+{
+ return MYMAX(f->light_source,
+ bank == LIGHTBANK_DAY ? param1 & 0x0f : (param1 >> 4) & 0x0f);
+}
+
bool MapNode::getLightBanks(u8 &lightday, u8 &lightnight, INodeDefManager *nodemgr) const
{
// Select the brightest of [light source, propagated light]
{
const ContentFeatures &f = nodemgr->get(*this);
if(f.param_type_2 == CPT2_FACEDIR)
- return getParam2() & 0x1F;
+ return (getParam2() & 0x1F) % 24;
return 0;
}
}
}
-void MapNode::rotateAlongYAxis(INodeDefManager *nodemgr, Rotation rot) {
+void MapNode::rotateAlongYAxis(INodeDefManager *nodemgr, Rotation rot)
+{
ContentParamType2 cpt2 = nodemgr->get(*this).param_type_2;
if (cpt2 == CPT2_FACEDIR) {
- u8 newrot = param2 & 3;
- param2 &= ~3;
- param2 |= (newrot + rot) & 3;
+ static const u8 rotate_facedir[24 * 4] = {
+ // Table value = rotated facedir
+ // Columns: 0, 90, 180, 270 degrees rotation around vertical axis
+ // Rotation is anticlockwise as seen from above (+Y)
+
+ 0, 1, 2, 3, // Initial facedir 0 to 3
+ 1, 2, 3, 0,
+ 2, 3, 0, 1,
+ 3, 0, 1, 2,
+
+ 4, 13, 10, 19, // 4 to 7
+ 5, 14, 11, 16,
+ 6, 15, 8, 17,
+ 7, 12, 9, 18,
+
+ 8, 17, 6, 15, // 8 to 11
+ 9, 18, 7, 12,
+ 10, 19, 4, 13,
+ 11, 16, 5, 14,
+
+ 12, 9, 18, 7, // 12 to 15
+ 13, 10, 19, 4,
+ 14, 11, 16, 5,
+ 15, 8, 17, 6,
+
+ 16, 5, 14, 11, // 16 to 19
+ 17, 6, 15, 8,
+ 18, 7, 12, 9,
+ 19, 4, 13, 10,
+
+ 20, 23, 22, 21, // 20 to 23
+ 21, 20, 23, 22,
+ 22, 21, 20, 23,
+ 23, 22, 21, 20
+ };
+ u8 facedir = (param2 & 31) % 24;
+ u8 index = facedir * 4 + rot;
+ param2 &= ~31;
+ param2 |= rotate_facedir[index];
} else if (cpt2 == CPT2_WALLMOUNTED) {
u8 wmountface = (param2 & 7);
if (wmountface <= 1)
return;
-
+
Rotation oldrot = wallmounted_to_rot[wmountface - 2];
param2 &= ~7;
param2 |= rot_to_wallmounted[(oldrot - rot) & 3];
facedir&=0x03;
for(std::vector<aabb3f>::const_iterator
i = fixed.begin();
- i != fixed.end(); i++)
+ i != fixed.end(); ++i)
{
aabb3f box = *i;
return setLevel(nodemgr, level);
}
-void MapNode::freezeMelt(INodeDefManager *ndef) {
- u8 level_was_max = this->getMaxLevel(ndef);
- u8 level_was = this->getLevel(ndef);
- this->setContent(ndef->getId(ndef->get(*this).freezemelt));
- u8 level_now_max = this->getMaxLevel(ndef);
- if (level_was_max && level_was_max != level_now_max) {
- u8 want = (float)level_now_max / level_was_max * level_was;
- if (!want)
- want = 1;
- if (want != level_was)
- this->setLevel(ndef, want);
- //errorstream<<"was="<<(int)level_was<<"/"<<(int)level_was_max<<" nowm="<<(int)want<<"/"<<(int)level_now_max<< " => "<<(int)this->getLevel(ndef)<< std::endl;
- }
- if (this->getMaxLevel(ndef) && !this->getLevel(ndef))
- this->addLevel(ndef);
-}
-
u32 MapNode::serializedLength(u8 version)
{
if(!ser_ver_supported(version))
throw VersionMismatchException("ERROR: MapNode format not supported");
-
+
if(version == 0)
return 1;
else if(version <= 9)
{
if(!ser_ver_supported(version))
throw VersionMismatchException("ERROR: MapNode format not supported");
-
+
// Can't do this anymore; we have 16-bit dynamically allocated node IDs
// in memory; conversion just won't work in this direction.
if(version < 24)
throw SerializationError("MapNode::serialize: serialization to "
"version < 24 not possible");
-
+
writeU16(dest+0, param0);
writeU8(dest+2, param1);
writeU8(dest+3, param2);
{
if(!ser_ver_supported(version))
throw VersionMismatchException("ERROR: MapNode format not supported");
-
+
if(version <= 21)
{
deSerialize_pre22(source, version);
if(!ser_ver_supported(version))
throw VersionMismatchException("ERROR: MapNode format not supported");
- assert(content_width == 2);
- assert(params_width == 2);
+ sanity_check(content_width == 2);
+ sanity_check(params_width == 2);
// Can't do this anymore; we have 16-bit dynamically allocated node IDs
// in memory; conversion just won't work in this direction.
if(!ser_ver_supported(version))
throw VersionMismatchException("ERROR: MapNode format not supported");
- assert(version >= 22);
- assert(content_width == 1 || content_width == 2);
- assert(params_width == 2);
+ if (version < 22
+ || (content_width != 1 && content_width != 2)
+ || params_width != 2)
+ FATAL_ERROR("Deserialize bulk node data error");
// Uncompress or read data
u32 len = nodecount * (content_width + params_width);
param2 &= 0x0f;
}
}
-
+
// Convert special values from old version to new
if(version <= 19)
{