]> git.lizzy.rs Git - minetest-m13.git/blob - src/mapnode.h
9b8ea4e05c2b9a0cec6d1bb8ad50715d30a44e64
[minetest-m13.git] / src / mapnode.h
1 /*
2 Minetest-m13
3 Copyright (C) 2010-2011 celeron55, Perttu Ahola <celeron55@gmail.com>
4
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2 of the License, or
8 (at your option) any later version.
9
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13 GNU General Public License for more details.
14
15 You should have received a copy of the GNU General Public License along
16 with this program; if not, write to the Free Software Foundation, Inc.,
17 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 */
19
20 #ifndef MAPNODE_HEADER
21 #define MAPNODE_HEADER
22
23 #include "irrlichttypes.h"
24 #include "light.h"
25
26 class INodeDefManager;
27
28 /*
29         Naming scheme:
30         - Material = irrlicht's Material class
31         - Content = (content_t) content of a node
32         - Tile = TileSpec at some side of a node of some content type
33
34         Content ranges:
35           0x000...0x07f: param2 is fully usable
36           0x800...0xfff: param2 lower 4 bits are free
37 */
38 typedef u16 content_t;
39 #define MAX_CONTENT 0xfff
40
41 /*
42         Ignored node.
43
44         Anything that stores MapNodes doesn't have to preserve parameters
45         associated with this material.
46         
47         Doesn't create faces with anything and is considered being
48         out-of-map in the game map.
49 */
50 #define CONTENT_IGNORE 127
51 #define CONTENT_IGNORE_DEFAULT_PARAM 0
52
53 /*
54         The common material through which the player can walk and which
55         is transparent to light
56 */
57 #define CONTENT_AIR 126
58
59 enum LightBank
60 {
61         LIGHTBANK_DAY,
62         LIGHTBANK_NIGHT
63 };
64
65 /*
66         Masks for MapNode.param2 of flowing liquids
67  */
68 #define LIQUID_LEVEL_MASK 0x07
69 #define LIQUID_FLOW_DOWN_MASK 0x08
70
71 /* maximum amount of liquid in a block */
72 #define LIQUID_LEVEL_MAX LIQUID_LEVEL_MASK
73 #define LIQUID_LEVEL_SOURCE (LIQUID_LEVEL_MAX+1)
74
75 /*
76         This is the stuff what the whole world consists of.
77 */
78
79
80 struct MapNode
81 {
82         /*
83                 Main content
84                 0x00-0x7f: Short content type
85                 0x80-0xff: Long content type (param2>>4 makes up low bytes)
86         */
87         u8 param0;
88
89         /*
90                 Misc parameter. Initialized to 0.
91                 - For light_propagates() blocks, this is light intensity,
92                   stored logarithmically from 0 to LIGHT_MAX.
93                   Sunlight is LIGHT_SUN, which is LIGHT_MAX+1.
94                   - Contains 2 values, day- and night lighting. Each takes 4 bits.
95                 - Uhh... well, most blocks have light or nothing in here.
96         */
97         u8 param1;
98         
99         /*
100                 The second parameter. Initialized to 0.
101                 E.g. direction for torches and flowing water.
102                 If param0 >= 0x80, bits 0xf0 of this is extended content type data
103         */
104         u8 param2;
105
106         MapNode(const MapNode & n)
107         {
108                 *this = n;
109         }
110         
111         MapNode(content_t content=CONTENT_AIR, u8 a_param1=0, u8 a_param2=0)
112         {
113                 param1 = a_param1;
114                 param2 = a_param2;
115                 // Set content (param0 and (param2&0xf0)) after other params
116                 // because this needs to override part of param2
117                 setContent(content);
118         }
119         
120         // Create directly from a nodename
121         // If name is unknown, sets CONTENT_IGNORE
122         MapNode(INodeDefManager *ndef, const std::string &name,
123                         u8 a_param1=0, u8 a_param2=0);
124
125         bool operator==(const MapNode &other)
126         {
127                 return (param0 == other.param0
128                                 && param1 == other.param1
129                                 && param2 == other.param2);
130         }
131         
132         // To be used everywhere
133         content_t getContent() const
134         {
135                 if(param0 < 0x80)
136                         return param0;
137                 else
138                         return (param0<<4) + (param2>>4);
139         }
140         void setContent(content_t c)
141         {
142                 if(c < 0x80)
143                 {
144                         if(param0 >= 0x80)
145                                 param2 &= ~(0xf0);
146                         param0 = c;
147                 }
148                 else
149                 {
150                         param0 = c>>4;
151                         param2 &= ~(0xf0);
152                         param2 |= (c&0x0f)<<4;
153                 }
154         }
155         u8 getParam1() const
156         {
157                 return param1;
158         }
159         void setParam1(u8 p)
160         {
161                 param1 = p;
162         }
163         u8 getParam2() const
164         {
165                 if(param0 < 0x80)
166                         return param2;
167                 else
168                         return param2 & 0x0f;
169         }
170         void setParam2(u8 p)
171         {
172                 if(param0 < 0x80)
173                         param2 = p;
174                 else{
175                         param2 &= 0xf0;
176                         param2 |= (p&0x0f);
177                 }
178         }
179         
180         void setLight(enum LightBank bank, u8 a_light, INodeDefManager *nodemgr);
181         u8 getLight(enum LightBank bank, INodeDefManager *nodemgr) const;
182         bool getLightBanks(u8 &lightday, u8 &lightnight, INodeDefManager *nodemgr) const;
183         
184         // 0 <= daylight_factor <= 1000
185         // 0 <= return value <= LIGHT_SUN
186         u8 getLightBlend(u32 daylight_factor, INodeDefManager *nodemgr) const
187         {
188                 u8 lightday = 0;
189                 u8 lightnight = 0;
190                 getLightBanks(lightday, lightnight, nodemgr);
191                 return blend_light(daylight_factor, lightday, lightnight);
192         }
193
194         u8 getFaceDir(INodeDefManager *nodemgr) const;
195         u8 getWallMounted(INodeDefManager *nodemgr) const;
196         v3s16 getWallMountedDir(INodeDefManager *nodemgr) const;
197
198         /*
199                 Serialization functions
200         */
201
202         static u32 serializedLength(u8 version);
203         void serialize(u8 *dest, u8 version);
204         void deSerialize(u8 *source, u8 version);
205         
206         // Serializes or deserializes a list of nodes in bulk format (first the
207         // content of all nodes, then the param1 of all nodes, then the param2
208         // of all nodes).
209         //   version = serialization version. Must be >= 22
210         //   content_width = the number of bytes of content per node
211         //   params_width = the number of bytes of params per node
212         //   compressed = true to zlib-compress output
213         static void serializeBulk(std::ostream &os, int version,
214                         const MapNode *nodes, u32 nodecount,
215                         u8 content_width, u8 params_width, bool compressed);
216         static void deSerializeBulk(std::istream &is, int version,
217                         MapNode *nodes, u32 nodecount,
218                         u8 content_width, u8 params_width, bool compressed);
219
220 private:
221         // Deprecated serialization methods
222         void serialize_pre22(u8 *dest, u8 version);
223         void deSerialize_pre22(u8 *source, u8 version);
224 };
225
226
227 /*
228         MapNode helpers for mesh making stuff
229 */
230
231 #ifndef SERVER
232
233 /*
234         Nodes make a face if contents differ and solidness differs.
235         Return value:
236                 0: No face
237                 1: Face uses m1's content
238                 2: Face uses m2's content
239         equivalent: Whether the blocks share the same face (eg. water and glass)
240 */
241 u8 face_contents(content_t m1, content_t m2, bool *equivalent,
242                 INodeDefManager *nodemgr);
243
244 /*
245         Gets lighting value at face of node
246         
247         Parameters must consist of air and !air.
248         Order doesn't matter.
249
250         If either of the nodes doesn't exist, light is 0.
251         
252         parameters:
253                 daynight_ratio: 0...1000
254                 n: getNode(p) (uses only the lighting value)
255                 n2: getNode(p + face_dir) (uses only the lighting value)
256                 face_dir: axis oriented unit vector from p to p2
257         
258         returns encoded light value.
259 */
260 u8 getFaceLight(u32 daynight_ratio, MapNode n, MapNode n2,
261                 v3s16 face_dir, INodeDefManager *nodemgr);
262
263 #endif
264
265
266 #endif
267