aboutsummaryrefslogtreecommitdiff
path: root/src/mapblock.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/mapblock.cpp')
-rw-r--r--src/mapblock.cpp123
1 files changed, 95 insertions, 28 deletions
diff --git a/src/mapblock.cpp b/src/mapblock.cpp
index ca2145cef..b85183a40 100644
--- a/src/mapblock.cpp
+++ b/src/mapblock.cpp
@@ -27,7 +27,7 @@ with this program; if not, write to the Free Software Foundation, Inc.,
#include "gamedef.h"
#include "log.h"
#include "nameidmapping.h"
-#include "content_mapnode.h" // For legacy name-id mapping
+#include "content_mapnode.h" // For legacy name-id mapping
#include "content_nodemeta.h" // For legacy deserialization
#include "serialization.h"
#ifndef SERVER
@@ -61,7 +61,6 @@ static const char *modified_reason_strings[] = {
"unknown",
};
-
/*
MapBlock
*/
@@ -85,6 +84,63 @@ MapBlock::~MapBlock()
#endif
}
+bool MapBlock::onObjectsActivation()
+{
+ // Ignore if no stored objects (to not set changed flag)
+ if (m_static_objects.getAllStored().empty())
+ return false;
+
+ verbosestream << "MapBlock::onObjectsActivation(): "
+ << "activating objects of block " << PP(getPos()) << " ("
+ << m_static_objects.getStoredSize() << " objects)" << std::endl;
+
+ if (m_static_objects.getStoredSize() > g_settings->getU16("max_objects_per_block")) {
+ errorstream << "suspiciously large amount of objects detected: "
+ << m_static_objects.getStoredSize() << " in "
+ << PP(getPos()) << "; removing all of them." << std::endl;
+ // Clear stored list
+ m_static_objects.clearStored();
+ raiseModified(MOD_STATE_WRITE_NEEDED, MOD_REASON_TOO_MANY_OBJECTS);
+ return false;
+ }
+
+ return true;
+}
+
+bool MapBlock::saveStaticObject(u16 id, const StaticObject &obj, u32 reason)
+{
+ if (m_static_objects.getStoredSize() >= g_settings->getU16("max_objects_per_block")) {
+ warningstream << "MapBlock::saveStaticObject(): Trying to store id = " << id
+ << " statically but block " << PP(getPos()) << " already contains "
+ << m_static_objects.getStoredSize() << " objects."
+ << std::endl;
+ return false;
+ }
+
+ m_static_objects.insert(id, obj);
+ if (reason != MOD_REASON_UNKNOWN) // Do not mark as modified if requested
+ raiseModified(MOD_STATE_WRITE_NEEDED, reason);
+
+ return true;
+}
+
+// This method is only for Server, don't call it on client
+void MapBlock::step(float dtime, const std::function<bool(v3s16, MapNode, f32)> &on_timer_cb)
+{
+ // Run script callbacks for elapsed node_timers
+ std::vector<NodeTimer> elapsed_timers = m_node_timers.step(dtime);
+ if (!elapsed_timers.empty()) {
+ MapNode n;
+ v3s16 p;
+ for (const NodeTimer &elapsed_timer : elapsed_timers) {
+ n = getNodeNoEx(elapsed_timer.position);
+ p = elapsed_timer.position + getPosRelative();
+ if (on_timer_cb(p, n, elapsed_timer.elapsed))
+ setNodeTimer(NodeTimer(elapsed_timer.timeout, 0, elapsed_timer.position));
+ }
+ }
+}
+
bool MapBlock::isValidPositionParent(v3s16 p)
{
if (isValidPosition(p)) {
@@ -392,9 +448,8 @@ void MapBlock::serialize(std::ostream &os_compressed, u8 version, bool disk, int
/*
Data that goes to disk, but not the network
*/
- if(disk)
- {
- if(version <= 24){
+ if (disk) {
+ if (version <= 24) {
// Node timers
m_node_timers.serialize(os, version);
}
@@ -402,7 +457,7 @@ void MapBlock::serialize(std::ostream &os_compressed, u8 version, bool disk, int
// Static objects
m_static_objects.serialize(os);
- if(version < 29){
+ if (version < 29) {
// Timestamp
writeU32(os, getTimestamp());
@@ -410,7 +465,7 @@ void MapBlock::serialize(std::ostream &os_compressed, u8 version, bool disk, int
nimap.serialize(os);
}
- if(version >= 25){
+ if (version >= 25) {
// Node timers
m_node_timers.serialize(os, version);
}
@@ -522,16 +577,15 @@ void MapBlock::deSerialize(std::istream &in_compressed, u8 version, bool disk)
/*
Data that is only on disk
*/
- if(disk)
- {
+ if (disk) {
// Node timers
- if(version == 23){
+ if (version == 23) {
// Read unused zero
readU8(is);
}
- if(version == 24){
- TRACESTREAM(<<"MapBlock::deSerialize "<<PP(getPos())
- <<": Node timers (ver==24)"<<std::endl);
+ if (version == 24) {
+ TRACESTREAM(<< "MapBlock::deSerialize " << PP(getPos())
+ << ": Node timers (ver==24)" << std::endl);
m_node_timers.deSerialize(is, version);
}
@@ -540,7 +594,7 @@ void MapBlock::deSerialize(std::istream &in_compressed, u8 version, bool disk)
<<": Static objects"<<std::endl);
m_static_objects.deSerialize(is);
- if(version < 29) {
+ if (version < 29) {
// Timestamp
TRACESTREAM(<<"MapBlock::deSerialize "<<PP(getPos())
<<": Timestamp"<<std::endl);
@@ -581,6 +635,26 @@ void MapBlock::deSerializeNetworkSpecific(std::istream &is)
}
}
+bool MapBlock::storeActiveObject(u16 id)
+{
+ if (m_static_objects.storeActiveObject(id)) {
+ raiseModified(MOD_STATE_WRITE_NEEDED,
+ MOD_REASON_REMOVE_OBJECTS_DEACTIVATE);
+ return true;
+ }
+
+ return false;
+}
+
+u32 MapBlock::clearObjects()
+{
+ u32 size = m_static_objects.size();
+ if (size > 0) {
+ m_static_objects.clear();
+ raiseModified(MOD_STATE_WRITE_NEEDED, MOD_REASON_CLEAR_ALL_OBJECTS);
+ }
+ return size;
+}
/*
Legacy serialization
*/
@@ -656,7 +730,7 @@ void MapBlock::deSerialize_pre22(std::istream &is, u8 version, bool disk)
is.read((char*)&flags, 1);
is_underground = (flags & 0x01) != 0;
m_day_night_differs = (flags & 0x02) != 0;
- if(version >= 18)
+ if (version >= 18)
m_generated = (flags & 0x08) == 0;
// Uncompress data
@@ -747,12 +821,10 @@ void MapBlock::deSerialize_pre22(std::istream &is, u8 version, bool disk)
correctBlockNodeIds(&nimap, data, m_gamedef);
}
-
// Legacy data changes
// This code has to convert from pre-22 to post-22 format.
const NodeDefManager *nodedef = m_gamedef->ndef();
- for(u32 i=0; i<nodecount; i++)
- {
+ for (u32 i = 0; i < nodecount; i++) {
const ContentFeatures &f = nodedef->get(data[i].getContent());
// Mineral
if(nodedef->getId("default:stone") == data[i].getContent()
@@ -768,21 +840,17 @@ void MapBlock::deSerialize_pre22(std::istream &is, u8 version, bool disk)
data[i].setParam1(0);
}
// facedir_simple
- if(f.legacy_facedir_simple)
- {
+ if (f.legacy_facedir_simple) {
data[i].setParam2(data[i].getParam1());
data[i].setParam1(0);
}
// wall_mounted
- if(f.legacy_wallmounted)
- {
+ if (f.legacy_wallmounted) {
u8 wallmounted_new_to_old[8] = {0x04, 0x08, 0x01, 0x02, 0x10, 0x20, 0, 0};
u8 dir_old_format = data[i].getParam2();
u8 dir_new_format = 0;
- for(u8 j=0; j<8; j++)
- {
- if((dir_old_format & wallmounted_new_to_old[j]) != 0)
- {
+ for (u8 j = 0; j < 8; j++) {
+ if ((dir_old_format & wallmounted_new_to_old[j]) != 0) {
dir_new_format = j;
break;
}
@@ -790,7 +858,6 @@ void MapBlock::deSerialize_pre22(std::istream &is, u8 version, bool disk)
data[i].setParam2(dir_new_format);
}
}
-
}
/*
@@ -798,7 +865,7 @@ void MapBlock::deSerialize_pre22(std::istream &is, u8 version, bool disk)
*/
std::string analyze_block(MapBlock *block)
{
- if(block == NULL)
+ if (block == NULL)
return "NULL";
std::ostringstream desc;