Decoration: Handle facedir and wallmounted param2types with schematic rotation
authorkwolekr <kwolekr@minetest.net>
Mon, 8 Jul 2013 19:19:22 +0000 (15:19 -0400)
committerkwolekr <kwolekr@minetest.net>
Mon, 8 Jul 2013 19:19:48 +0000 (15:19 -0400)
src/mapgen.cpp
src/mapgen.h
src/mapnode.cpp
src/mapnode.h

index fe1cfb3a45be59504ea5bd8a9fd4bb54a38ff5e2..6bc487331730929d81a6fc328b4f1d56397f1a19 100644 (file)
@@ -237,6 +237,8 @@ Decoration::~Decoration() {
 
 
 void Decoration::resolveNodeNames(INodeDefManager *ndef) {
+       this->ndef = ndef;
+       
        if (c_place_on == CONTENT_IGNORE)
                c_place_on = ndef->getId(place_on_name);
 }
@@ -553,7 +555,7 @@ std::string DecoSchematic::getName() {
 
 
 void DecoSchematic::blitToVManip(v3s16 p, ManualMapVoxelManipulator *vm,
-                                                               int rot, bool force_placement) {
+                                                               Rotation rot, bool force_placement) {
        int xstride = 1;
        int ystride = size.X;
        int zstride = size.X * size.Y;
@@ -594,7 +596,7 @@ void DecoSchematic::blitToVManip(v3s16 p, ManualMapVoxelManipulator *vm,
                        u32 vi = vm->m_area.index(p.X + x, p.Y + y, p.Z + z);
                        if (!vm->m_area.contains(vi))
                                continue;
-                               
+                       
                        if (schematic[i].getContent() == CONTENT_IGNORE)
                                continue;
 
@@ -609,6 +611,9 @@ void DecoSchematic::blitToVManip(v3s16 p, ManualMapVoxelManipulator *vm,
                        
                        vm->m_data[vi] = schematic[i];
                        vm->m_data[vi].param1 = 0;
+                       
+                       if (rot)
+                               vm->m_data[vi].rotateAlongYAxis(ndef, rot);
                }
        }
 }
index 2287445ee542290706bc5dc8d1dba8c728f8a1f2..b167978d7e5f045fcbff40084bbff5bf3e036122 100644 (file)
@@ -23,6 +23,7 @@ with this program; if not, write to the Free Software Foundation, Inc.,
 #include "irrlichttypes_extrabloated.h"
 #include "util/container.h" // UniqueQueue
 #include "gamedef.h"
+#include "nodedef.h"
 #include "mapnode.h"
 #include "noise.h"
 #include "settings.h"
@@ -63,7 +64,6 @@ class EmergeManager;
 class MapBlock;
 class ManualMapVoxelManipulator;
 class VoxelManipulator;
-class INodeDefManager;
 struct BlockMakeData;
 class VoxelArea;
 class Map;
@@ -216,6 +216,8 @@ struct CutoffData {
 
 class Decoration {
 public:
+       INodeDefManager *ndef;
+       
        int mapseed;
        std::string place_on_name;
        content_t c_place_on;
@@ -262,14 +264,6 @@ public:
 
 #define MTSCHEM_FILE_SIGNATURE 0x4d54534d // 'MTSM'
 
-enum Rotation {
-       ROTATE_0,
-       ROTATE_90,
-       ROTATE_180,
-       ROTATE_270,
-       ROTATE_RAND,
-};
-
 class DecoSchematic : public Decoration {
 public:
        std::string filename;
@@ -291,7 +285,7 @@ public:
        virtual std::string getName();
        
        void blitToVManip(v3s16 p, ManualMapVoxelManipulator *vm,
-                                       int rot, bool force_placement);
+                                       Rotation rot, bool force_placement);
        
        bool loadSchematicFile();
        void saveSchematicFile(INodeDefManager *ndef);
index bba845fcce95678dffae5f033d96d554a911d681..388818c426b0366c6b200b2521805afcd8a56e9f 100644 (file)
@@ -28,6 +28,14 @@ with this program; if not, write to the Free Software Foundation, Inc.,
 #include <string>
 #include <sstream>
 
+static const Rotation wallmounted_to_rot[] = {
+       ROTATE_0, ROTATE_180, ROTATE_90, ROTATE_270
+};
+static const u8 rot_to_wallmounted[] = {
+       2, 4, 3, 5
+};
+
+
 /*
        MapNode
 */
@@ -132,6 +140,24 @@ v3s16 MapNode::getWallMountedDir(INodeDefManager *nodemgr) const
        }
 }
 
+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;
+       } 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];
+       }
+}
+
 static std::vector<aabb3f> transformNodeBox(const MapNode &n,
                const NodeBox &nodebox, INodeDefManager *nodemgr)
 {
index 1c8c5c49c0d55596c8c313cefd84c8e2f3fd211d..60211b87cae1ec7d450811e9d3292e82e5d56a44 100644 (file)
@@ -61,6 +61,17 @@ enum LightBank
        LIGHTBANK_NIGHT
 };
 
+/*
+       Simple rotation enum.
+*/
+enum Rotation {
+       ROTATE_0,
+       ROTATE_90,
+       ROTATE_180,
+       ROTATE_270,
+       ROTATE_RAND,
+};
+
 /*
        Masks for MapNode.param2 of flowing liquids
  */
@@ -181,6 +192,8 @@ struct MapNode
        u8 getFaceDir(INodeDefManager *nodemgr) const;
        u8 getWallMounted(INodeDefManager *nodemgr) const;
        v3s16 getWallMountedDir(INodeDefManager *nodemgr) const;
+       
+       void rotateAlongYAxis(INodeDefManager *nodemgr, Rotation rot);
 
        /*
                Gets list of node boxes (used for rendering (NDT_NODEBOX)