Merge pull request #47 from MarkTraceur/master

More better ladders
This commit is contained in:
Nils Dagsson Moskopp 2011-08-01 05:59:40 -07:00
commit f6bc662194
11 changed files with 164 additions and 4 deletions

BIN
data/item_ladder.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 581 B

BIN
data/ladder.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 691 B

@ -413,6 +413,22 @@ InventoryItem *craft_get_result(InventoryItem **items)
} }
} }
// Ladder
{
ItemSpec specs[9];
specs[0] = ItemSpec(ITEM_CRAFT, "Stick");
specs[2] = ItemSpec(ITEM_CRAFT, "Stick");
specs[3] = ItemSpec(ITEM_CRAFT, "Stick");
specs[4] = ItemSpec(ITEM_CRAFT, "Stick");
specs[5] = ItemSpec(ITEM_CRAFT, "Stick");
specs[6] = ItemSpec(ITEM_CRAFT, "Stick");
specs[8] = ItemSpec(ITEM_CRAFT, "Stick");
if(checkItemCombination(items, specs))
{
return new MaterialItem(CONTENT_LADDER, 1);
}
}
return NULL; return NULL;
} }

@ -1134,6 +1134,53 @@ void mapblock_mesh_generate_special(MeshMakeData *data,
u16 indices[] = {0,1,2,2,3,0}; u16 indices[] = {0,1,2,2,3,0};
collector.append(material_rail, vertices, 4, indices, 6); collector.append(material_rail, vertices, 4, indices, 6);
} }
else if (n.getContent() == CONTENT_LADDER) {
u8 l = decode_light(n.getLightBlend(data->m_daynight_ratio));
video::SColor c(255,l,l,l);
float d = (float)BS/16;
// Assume wall is at X+
video::S3DVertex vertices[4] =
{
video::S3DVertex(BS/2-d,-BS/2,-BS/2, 0,0,0, c, 0,1),
video::S3DVertex(BS/2-d,-BS/2,BS/2, 0,0,0, c, 1,1),
video::S3DVertex(BS/2-d,BS/2,BS/2, 0,0,0, c, 1,0),
video::S3DVertex(BS/2-d,BS/2,-BS/2, 0,0,0, c, 0,0),
};
v3s16 dir = unpackDir(n.param2);
for(s32 i=0; i<4; i++)
{
if(dir == v3s16(1,0,0))
vertices[i].Pos.rotateXZBy(0);
if(dir == v3s16(-1,0,0))
vertices[i].Pos.rotateXZBy(180);
if(dir == v3s16(0,0,1))
vertices[i].Pos.rotateXZBy(90);
if(dir == v3s16(0,0,-1))
vertices[i].Pos.rotateXZBy(-90);
if(dir == v3s16(0,-1,0))
vertices[i].Pos.rotateXYBy(-90);
if(dir == v3s16(0,1,0))
vertices[i].Pos.rotateXYBy(90);
vertices[i].Pos += intToFloat(p + blockpos_nodes, BS);
}
video::SMaterial material_ladder;
material_ladder.setFlag(video::EMF_LIGHTING, false);
material_ladder.setFlag(video::EMF_BACK_FACE_CULLING, false);
material_ladder.setFlag(video::EMF_BILINEAR_FILTER, false);
material_ladder.setFlag(video::EMF_FOG_ENABLE, true);
material_ladder.MaterialType = video::EMT_TRANSPARENT_ALPHA_CHANNEL_REF;
material_ladder.setTexture(0, g_texturesource->getTextureRaw("ladder.png"));
u16 indices[] = {0,1,2,2,3,0};
// Add to mesh collector
collector.append(material_ladder, vertices, 4, indices, 6);
}
} }
} }
#endif #endif

@ -303,6 +303,20 @@ void content_mapnode_init()
f->walkable = false; f->walkable = false;
setDirtLikeDiggingProperties(f->digging_properties, 0.75); setDirtLikeDiggingProperties(f->digging_properties, 0.75);
i = CONTENT_LADDER;
f = &content_features(i);
f->setInventoryTexture("item_ladder.png");
f->light_propagates = true;
f->param_type = CPT_LIGHT;
f->is_ground_content = true;
f->dug_item = std::string("MaterialItem ")+itos(i)+" 1";
f->wall_mounted = true;
f->solidness = 0;
f->air_equivalent = true;
f->walkable = false;
f->climbable = true;
setWoodLikeDiggingProperties(f->digging_properties, 0.5);
// Deprecated // Deprecated
i = CONTENT_COALSTONE; i = CONTENT_COALSTONE;
f = &content_features(i); f = &content_features(i);

@ -46,6 +46,7 @@ MapNode mapnode_translate_to_internal(MapNode n_from, u8 version);
#define CONTENT_FURNACE 16 #define CONTENT_FURNACE 16
#define CONTENT_FENCE 21 #define CONTENT_FENCE 21
#define CONTENT_RAIL 30 #define CONTENT_RAIL 30
#define CONTENT_LADDER 31
// 0x800...0xfff (2048...4095): higher 4 bytes of param2 are not usable // 0x800...0xfff (2048...4095): higher 4 bytes of param2 are not usable
#define CONTENT_GRASS 0x800 //1 #define CONTENT_GRASS 0x800 //1
@ -75,6 +76,5 @@ MapNode mapnode_translate_to_internal(MapNode n_from, u8 version);
#define CONTENT_NC 0x817 #define CONTENT_NC 0x817
#define CONTENT_NC_RB 0x818 #define CONTENT_NC_RB 0x818
#endif #endif

@ -1511,6 +1511,8 @@ void ClientEnvironment::step(float dtime)
/* /*
Get the speed the player is going Get the speed the player is going
*/ */
bool is_climbing = lplayer->is_climbing;
f32 player_speed = 0.001; // just some small value f32 player_speed = 0.001; // just some small value
player_speed = lplayer->getSpeed().getLength(); player_speed = lplayer->getSpeed().getLength();
@ -1568,7 +1570,7 @@ void ClientEnvironment::step(float dtime)
v3f lplayerpos = lplayer->getPosition(); v3f lplayerpos = lplayer->getPosition();
// Apply physics // Apply physics
if(free_move == false) if(free_move == false && is_climbing == false)
{ {
// Gravity // Gravity
v3f speed = lplayer->getSpeed(); v3f speed = lplayer->getSpeed();

@ -538,6 +538,56 @@ void getPointedNode(Client *client, v3f player_position,
} }
} }
} }
else if(n.getContent() == CONTENT_LADDER)
{
v3s16 dir = unpackDir(n.param2);
v3f dir_f = v3f(dir.X, dir.Y, dir.Z);
dir_f *= BS/2 - BS/6 - BS/20;
v3f cpf = npf + dir_f;
f32 distance = (cpf - camera_position).getLength();
v3f vertices[4] =
{
v3f(BS*0.42,-BS/2,-BS/2),
v3f(BS*0.49, BS/2, BS/2),
};
for(s32 i=0; i<2; i++)
{
if(dir == v3s16(1,0,0))
vertices[i].rotateXZBy(0);
if(dir == v3s16(-1,0,0))
vertices[i].rotateXZBy(180);
if(dir == v3s16(0,0,1))
vertices[i].rotateXZBy(90);
if(dir == v3s16(0,0,-1))
vertices[i].rotateXZBy(-90);
if(dir == v3s16(0,-1,0))
vertices[i].rotateXYBy(-90);
if(dir == v3s16(0,1,0))
vertices[i].rotateXYBy(90);
vertices[i] += npf;
}
core::aabbox3d<f32> box;
box = core::aabbox3d<f32>(vertices[0]);
box.addInternalPoint(vertices[1]);
if(distance < mindistance)
{
if(box.intersectsWithLine(shootline))
{
nodefound = true;
nodepos = np;
neighbourpos = np;
mindistance = distance;
nodehilightbox = box;
}
}
}
else if(n.getContent() == CONTENT_RAIL) else if(n.getContent() == CONTENT_RAIL)
{ {
v3s16 dir = unpackDir(n.param0); v3s16 dir = unpackDir(n.param0);

@ -128,6 +128,8 @@ struct ContentFeatures
bool pointable; bool pointable;
// Player can dig these // Player can dig these
bool diggable; bool diggable;
// Player can climb these
bool climbable;
// Player can build on these // Player can build on these
bool buildable_to; bool buildable_to;
// Whether the node has no liquid, source liquid or flowing liquid // Whether the node has no liquid, source liquid or flowing liquid
@ -171,6 +173,7 @@ struct ContentFeatures
walkable = true; walkable = true;
pointable = true; pointable = true;
diggable = true; diggable = true;
climbable = false;
buildable_to = false; buildable_to = false;
liquid_type = LIQUID_NONE; liquid_type = LIQUID_NONE;
wall_mounted = false; wall_mounted = false;

@ -375,6 +375,21 @@ void LocalPlayer::move(f32 dtime, Map &map, f32 pos_max_d,
in_water_stable = false; in_water_stable = false;
} }
/*
Check if player is climbing
*/
try {
v3s16 pp = floatToInt(position + v3f(0,0.5*BS,0), BS);
v3s16 pp2 = floatToInt(position + v3f(0,-0.2*BS,0), BS);
is_climbing = ((content_features(map.getNode(pp).getContent()).climbable ||
content_features(map.getNode(pp2).getContent()).climbable) && !free_move);
}
catch(InvalidPositionException &e)
{
is_climbing = false;
}
/* /*
Collision uncertainty radius Collision uncertainty radius
Make it a bit larger than the maximum distance of movement Make it a bit larger than the maximum distance of movement
@ -723,7 +738,7 @@ void LocalPlayer::applyControl(float dtime)
bool fast_move = g_settings.getBool("fast_move"); bool fast_move = g_settings.getBool("fast_move");
bool continuous_forward = g_settings.getBool("continuous_forward"); bool continuous_forward = g_settings.getBool("continuous_forward");
if(free_move) if(free_move || is_climbing)
{ {
v3f speed = getSpeed(); v3f speed = getSpeed();
speed.Y = 0; speed.Y = 0;
@ -750,6 +765,12 @@ void LocalPlayer::applyControl(float dtime)
speed.Y = -walkspeed_max; speed.Y = -walkspeed_max;
setSpeed(speed); setSpeed(speed);
} }
else if(is_climbing)
{
v3f speed = getSpeed();
speed.Y = -3*BS;
setSpeed(speed);
}
else else
{ {
// If not free movement but fast is allowed, aux1 is // If not free movement but fast is allowed, aux1 is
@ -812,6 +833,12 @@ void LocalPlayer::applyControl(float dtime)
setSpeed(speed); setSpeed(speed);
swimming_up = true; swimming_up = true;
} }
else if(is_climbing)
{
v3f speed = getSpeed();
speed.Y = 3*BS;
setSpeed(speed);
}
} }
// The speed of the player (Y is ignored) // The speed of the player (Y is ignored)

@ -118,6 +118,7 @@ public:
bool in_water; bool in_water;
// This is more stable and defines the maximum speed of the player // This is more stable and defines the maximum speed of the player
bool in_water_stable; bool in_water_stable;
bool is_climbing;
bool swimming_up; bool swimming_up;
Inventory inventory; Inventory inventory;