forked from Mirrorlandia_minetest/minetest
Added sprite extruder
This commit is contained in:
parent
4ed837bcfa
commit
36bcbca9ac
349
src/camera.cpp
349
src/camera.cpp
@ -63,6 +63,8 @@ Camera::Camera(scene::ISceneManager* smgr, MapDrawControl& draw_control):
|
||||
m_headnode = smgr->addEmptySceneNode(m_playernode);
|
||||
m_cameranode = smgr->addCameraSceneNode(smgr->getRootSceneNode());
|
||||
m_cameranode->bindTargetAndRotation(true);
|
||||
m_wieldnode = new ExtrudedSpriteSceneNode(smgr->getRootSceneNode(), smgr, -1, v3f(0, 120, 10), v3f(0, 0, 0), v3f(100, 100, 100));
|
||||
//m_wieldnode = new ExtrudedSpriteSceneNode(smgr->getRootSceneNode(), smgr, -1);
|
||||
|
||||
updateSettings();
|
||||
}
|
||||
@ -341,3 +343,350 @@ void Camera::updateSettings()
|
||||
m_wanted_frametime = 1.0 / wanted_fps;
|
||||
}
|
||||
|
||||
void Camera::wield(InventoryItem* item)
|
||||
{
|
||||
if (item != NULL)
|
||||
{
|
||||
dstream << "wield item: " << item->getName() << std::endl;
|
||||
m_wieldnode->setSprite(item->getImageRaw());
|
||||
m_wieldnode->setVisible(true);
|
||||
}
|
||||
else
|
||||
{
|
||||
dstream << "wield item: none" << std::endl;
|
||||
m_wieldnode->setVisible(false);
|
||||
}
|
||||
}
|
||||
|
||||
void Camera::setDigging(bool digging)
|
||||
{
|
||||
// TODO
|
||||
}
|
||||
|
||||
|
||||
ExtrudedSpriteSceneNode::ExtrudedSpriteSceneNode(
|
||||
scene::ISceneNode* parent,
|
||||
scene::ISceneManager* mgr,
|
||||
s32 id,
|
||||
const v3f& position,
|
||||
const v3f& rotation,
|
||||
const v3f& scale
|
||||
):
|
||||
ISceneNode(parent, mgr, id, position, rotation, scale)
|
||||
{
|
||||
m_meshnode = mgr->addMeshSceneNode(NULL, this, -1, v3f(0,0,0), v3f(0,0,0), v3f(1,1,1), true);
|
||||
m_thickness = 0.1;
|
||||
m_cubemesh = NULL;
|
||||
m_is_cube = false;
|
||||
}
|
||||
|
||||
ExtrudedSpriteSceneNode::~ExtrudedSpriteSceneNode()
|
||||
{
|
||||
removeChild(m_meshnode);
|
||||
if (m_cubemesh)
|
||||
m_cubemesh->drop();
|
||||
}
|
||||
|
||||
void ExtrudedSpriteSceneNode::setSprite(video::ITexture* texture)
|
||||
{
|
||||
if (texture == NULL)
|
||||
{
|
||||
m_meshnode->setVisible(false);
|
||||
return;
|
||||
}
|
||||
|
||||
io::path name = getExtrudedName(texture);
|
||||
scene::IMeshCache* cache = SceneManager->getMeshCache();
|
||||
scene::IAnimatedMesh* mesh = cache->getMeshByName(name);
|
||||
if (mesh != NULL)
|
||||
{
|
||||
// Extruded texture has been found in cache.
|
||||
m_meshnode->setMesh(mesh);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Texture was not yet extruded, do it now and save in cache
|
||||
mesh = extrude(texture);
|
||||
if (mesh == NULL)
|
||||
{
|
||||
dstream << "Warning: failed to extrude sprite" << std::endl;
|
||||
m_meshnode->setVisible(false);
|
||||
return;
|
||||
}
|
||||
cache->addMesh(name, mesh);
|
||||
m_meshnode->setMesh(mesh);
|
||||
mesh->drop();
|
||||
}
|
||||
|
||||
m_meshnode->setScale(v3f(1, 1, m_thickness));
|
||||
m_meshnode->getMaterial(0).setTexture(0, texture);
|
||||
m_meshnode->getMaterial(0).setFlag(video::EMF_LIGHTING, false);
|
||||
m_meshnode->getMaterial(0).setFlag(video::EMF_BILINEAR_FILTER, false);
|
||||
m_meshnode->getMaterial(0).MaterialType = video::EMT_TRANSPARENT_ALPHA_CHANNEL_REF;
|
||||
m_meshnode->setVisible(true);
|
||||
m_is_cube = false;
|
||||
}
|
||||
|
||||
void ExtrudedSpriteSceneNode::setCube(video::ITexture* texture)
|
||||
{
|
||||
if (texture == NULL)
|
||||
{
|
||||
m_meshnode->setVisible(false);
|
||||
return;
|
||||
}
|
||||
|
||||
if (m_cubemesh == NULL)
|
||||
m_cubemesh = SceneManager->getGeometryCreator()->createCubeMesh(v3f(1));
|
||||
|
||||
m_meshnode->setMesh(m_cubemesh);
|
||||
m_meshnode->setScale(v3f(1));
|
||||
m_meshnode->getMaterial(0).setTexture(0, texture);
|
||||
m_meshnode->getMaterial(0).setFlag(video::EMF_LIGHTING, false);
|
||||
m_meshnode->getMaterial(0).setFlag(video::EMF_BILINEAR_FILTER, false);
|
||||
m_meshnode->getMaterial(0).MaterialType = video::EMT_TRANSPARENT_ALPHA_CHANNEL_REF;
|
||||
m_meshnode->setVisible(true);
|
||||
m_is_cube = true;
|
||||
}
|
||||
|
||||
void ExtrudedSpriteSceneNode::removeSpriteFromCache(video::ITexture* texture)
|
||||
{
|
||||
scene::IMeshCache* cache = SceneManager->getMeshCache();
|
||||
scene::IAnimatedMesh* mesh = cache->getMeshByName(getExtrudedName(texture));
|
||||
if (mesh != NULL)
|
||||
cache->removeMesh(mesh);
|
||||
}
|
||||
|
||||
void ExtrudedSpriteSceneNode::setSpriteThickness(f32 thickness)
|
||||
{
|
||||
m_thickness = thickness;
|
||||
if (!m_is_cube)
|
||||
m_meshnode->setScale(v3f(1, 1, thickness));
|
||||
}
|
||||
|
||||
const core::aabbox3d<f32>& ExtrudedSpriteSceneNode::getBoundingBox() const
|
||||
{
|
||||
return m_meshnode->getBoundingBox();
|
||||
}
|
||||
|
||||
void ExtrudedSpriteSceneNode::OnRegisterSceneNode()
|
||||
{
|
||||
if (IsVisible)
|
||||
SceneManager->registerNodeForRendering(this);
|
||||
ISceneNode::OnRegisterSceneNode();
|
||||
}
|
||||
|
||||
void ExtrudedSpriteSceneNode::render()
|
||||
{
|
||||
// do nothing
|
||||
}
|
||||
|
||||
io::path ExtrudedSpriteSceneNode::getExtrudedName(video::ITexture* texture)
|
||||
{
|
||||
io::path path = texture->getName();
|
||||
path.append("/[extruded]");
|
||||
return path;
|
||||
}
|
||||
|
||||
scene::IAnimatedMesh* ExtrudedSpriteSceneNode::extrudeARGB(u32 width, u32 height, u8* data)
|
||||
{
|
||||
const s32 argb_wstep = 4 * width;
|
||||
const s32 alpha_threshold = 1;
|
||||
|
||||
scene::IMeshBuffer* buf = new scene::SMeshBuffer();
|
||||
video::SColor c(255,255,255,255);
|
||||
|
||||
// Front and back
|
||||
{
|
||||
video::S3DVertex vertices[8] =
|
||||
{
|
||||
video::S3DVertex(-0.5,-0.5,-0.5, 0,0,-1, c, 0,1),
|
||||
video::S3DVertex(-0.5,0.5,-0.5, 0,0,-1, c, 0,0),
|
||||
video::S3DVertex(0.5,0.5,-0.5, 0,0,-1, c, 1,0),
|
||||
video::S3DVertex(0.5,-0.5,-0.5, 0,0,-1, c, 1,1),
|
||||
video::S3DVertex(0.5,-0.5,0.5, 0,0,1, c, 1,1),
|
||||
video::S3DVertex(0.5,0.5,0.5, 0,0,1, c, 1,0),
|
||||
video::S3DVertex(-0.5,0.5,0.5, 0,0,1, c, 0,0),
|
||||
video::S3DVertex(-0.5,-0.5,0.5, 0,0,1, c, 0,1),
|
||||
};
|
||||
u16 indices[12] = {0,1,2,2,3,0,4,5,6,6,7,4};
|
||||
buf->append(vertices, 8, indices, 12);
|
||||
}
|
||||
|
||||
// "Interior"
|
||||
// (add faces where a solid pixel is next to a transparent one)
|
||||
u8* solidity = new u8[(width+2) * (height+2)];
|
||||
u32 wstep = width + 2;
|
||||
for (u32 y = 0; y < height + 2; ++y)
|
||||
{
|
||||
u8* scanline = solidity + y * wstep;
|
||||
if (y == 0 || y == height + 1)
|
||||
{
|
||||
for (u32 x = 0; x < width + 2; ++x)
|
||||
scanline[x] = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
scanline[0] = 0;
|
||||
u8* argb_scanline = data + (y - 1) * argb_wstep;
|
||||
for (u32 x = 0; x < width; ++x)
|
||||
scanline[x+1] = (argb_scanline[x*4+3] >= alpha_threshold);
|
||||
scanline[width + 1] = 0;
|
||||
}
|
||||
}
|
||||
|
||||
// without this, there would be occasional "holes" in the mesh
|
||||
f32 eps = 0.01;
|
||||
|
||||
for (u32 y = 0; y <= height; ++y)
|
||||
{
|
||||
u8* scanline = solidity + y * wstep + 1;
|
||||
for (u32 x = 0; x <= width; ++x)
|
||||
{
|
||||
if (scanline[x] && !scanline[x + wstep])
|
||||
{
|
||||
u32 xx = x + 1;
|
||||
while (scanline[xx] && !scanline[xx + wstep])
|
||||
++xx;
|
||||
f32 vx1 = (x - eps) / (f32) width - 0.5;
|
||||
f32 vx2 = (xx + eps) / (f32) width - 0.5;
|
||||
f32 vy = 0.5 - (y - eps) / (f32) height;
|
||||
f32 tx1 = x / (f32) width;
|
||||
f32 tx2 = xx / (f32) width;
|
||||
f32 ty = (y - 0.5) / (f32) height;
|
||||
video::S3DVertex vertices[8] =
|
||||
{
|
||||
video::S3DVertex(vx1,vy,-0.5, 0,-1,0, c, tx1,ty),
|
||||
video::S3DVertex(vx2,vy,-0.5, 0,-1,0, c, tx2,ty),
|
||||
video::S3DVertex(vx2,vy,0.5, 0,-1,0, c, tx2,ty),
|
||||
video::S3DVertex(vx1,vy,0.5, 0,-1,0, c, tx1,ty),
|
||||
};
|
||||
u16 indices[6] = {0,1,2,2,3,0};
|
||||
buf->append(vertices, 4, indices, 6);
|
||||
x = xx - 1;
|
||||
}
|
||||
if (!scanline[x] && scanline[x + wstep])
|
||||
{
|
||||
u32 xx = x + 1;
|
||||
while (!scanline[xx] && scanline[xx + wstep])
|
||||
++xx;
|
||||
f32 vx1 = (x - eps) / (f32) width - 0.5;
|
||||
f32 vx2 = (xx + eps) / (f32) width - 0.5;
|
||||
f32 vy = 0.5 - (y + eps) / (f32) height;
|
||||
f32 tx1 = x / (f32) width;
|
||||
f32 tx2 = xx / (f32) width;
|
||||
f32 ty = (y + 0.5) / (f32) height;
|
||||
video::S3DVertex vertices[8] =
|
||||
{
|
||||
video::S3DVertex(vx1,vy,-0.5, 0,1,0, c, tx1,ty),
|
||||
video::S3DVertex(vx1,vy,0.5, 0,1,0, c, tx1,ty),
|
||||
video::S3DVertex(vx2,vy,0.5, 0,1,0, c, tx2,ty),
|
||||
video::S3DVertex(vx2,vy,-0.5, 0,1,0, c, tx2,ty),
|
||||
};
|
||||
u16 indices[6] = {0,1,2,2,3,0};
|
||||
buf->append(vertices, 4, indices, 6);
|
||||
x = xx - 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (u32 x = 0; x <= width; ++x)
|
||||
{
|
||||
u8* scancol = solidity + x + wstep;
|
||||
for (u32 y = 0; y <= height; ++y)
|
||||
{
|
||||
if (scancol[y * wstep] && !scancol[y * wstep + 1])
|
||||
{
|
||||
u32 yy = y + 1;
|
||||
while (scancol[yy * wstep] && !scancol[yy * wstep + 1])
|
||||
++yy;
|
||||
f32 vx = (x - eps) / (f32) width - 0.5;
|
||||
f32 vy1 = 0.5 - (y - eps) / (f32) height;
|
||||
f32 vy2 = 0.5 - (yy + eps) / (f32) height;
|
||||
f32 tx = (x - 0.5) / (f32) width;
|
||||
f32 ty1 = y / (f32) height;
|
||||
f32 ty2 = yy / (f32) height;
|
||||
video::S3DVertex vertices[8] =
|
||||
{
|
||||
video::S3DVertex(vx,vy1,-0.5, 1,0,0, c, tx,ty1),
|
||||
video::S3DVertex(vx,vy1,0.5, 1,0,0, c, tx,ty1),
|
||||
video::S3DVertex(vx,vy2,0.5, 1,0,0, c, tx,ty2),
|
||||
video::S3DVertex(vx,vy2,-0.5, 1,0,0, c, tx,ty2),
|
||||
};
|
||||
u16 indices[6] = {0,1,2,2,3,0};
|
||||
buf->append(vertices, 4, indices, 6);
|
||||
y = yy - 1;
|
||||
}
|
||||
if (!scancol[y * wstep] && scancol[y * wstep + 1])
|
||||
{
|
||||
u32 yy = y + 1;
|
||||
while (!scancol[yy * wstep] && scancol[yy * wstep + 1])
|
||||
++yy;
|
||||
f32 vx = (x + eps) / (f32) width - 0.5;
|
||||
f32 vy1 = 0.5 - (y - eps) / (f32) height;
|
||||
f32 vy2 = 0.5 - (yy + eps) / (f32) height;
|
||||
f32 tx = (x + 0.5) / (f32) width;
|
||||
f32 ty1 = y / (f32) height;
|
||||
f32 ty2 = yy / (f32) height;
|
||||
video::S3DVertex vertices[8] =
|
||||
{
|
||||
video::S3DVertex(vx,vy1,-0.5, -1,0,0, c, tx,ty1),
|
||||
video::S3DVertex(vx,vy2,-0.5, -1,0,0, c, tx,ty2),
|
||||
video::S3DVertex(vx,vy2,0.5, -1,0,0, c, tx,ty2),
|
||||
video::S3DVertex(vx,vy1,0.5, -1,0,0, c, tx,ty1),
|
||||
};
|
||||
u16 indices[6] = {0,1,2,2,3,0};
|
||||
buf->append(vertices, 4, indices, 6);
|
||||
y = yy - 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Add to mesh
|
||||
scene::SMesh* mesh = new scene::SMesh();
|
||||
mesh->addMeshBuffer(buf);
|
||||
buf->drop();
|
||||
mesh->recalculateBoundingBox();
|
||||
scene::SAnimatedMesh* anim_mesh = new scene::SAnimatedMesh(mesh);
|
||||
mesh->drop();
|
||||
return anim_mesh;
|
||||
}
|
||||
|
||||
scene::IAnimatedMesh* ExtrudedSpriteSceneNode::extrude(video::ITexture* texture)
|
||||
{
|
||||
scene::IAnimatedMesh* mesh = NULL;
|
||||
core::dimension2d<u32> size = texture->getSize();
|
||||
video::ECOLOR_FORMAT format = texture->getColorFormat();
|
||||
if (format == video::ECF_A8R8G8B8)
|
||||
{
|
||||
// Texture is in the correct color format, we can pass it
|
||||
// to extrudeARGB right away.
|
||||
void* data = texture->lock(true);
|
||||
if (data == NULL)
|
||||
return NULL;
|
||||
mesh = extrudeARGB(size.Width, size.Height, (u8*) data);
|
||||
texture->unlock();
|
||||
}
|
||||
else
|
||||
{
|
||||
video::IVideoDriver* driver = SceneManager->getVideoDriver();
|
||||
|
||||
video::IImage* img1 = driver->createImageFromData(format, size, texture->lock(true));
|
||||
if (img1 == NULL)
|
||||
return NULL;
|
||||
|
||||
// img1 is in the texture's color format, convert to 8-bit ARGB
|
||||
video::IImage* img2 = driver->createImage(video::ECF_A8R8G8B8, size);
|
||||
if (img2 != NULL)
|
||||
{
|
||||
img1->copyTo(img2);
|
||||
img1->drop();
|
||||
|
||||
mesh = extrudeARGB(size.Width, size.Height, (u8*) img2->lock());
|
||||
img2->unlock();
|
||||
img2->drop();
|
||||
}
|
||||
img1->drop();
|
||||
}
|
||||
return mesh;
|
||||
}
|
||||
|
||||
|
66
src/camera.h
66
src/camera.h
@ -21,14 +21,17 @@ with this program; if not, write to the Free Software Foundation, Inc.,
|
||||
#define CAMERA_HEADER
|
||||
|
||||
#include "common_irrlicht.h"
|
||||
#include "inventory.h"
|
||||
#include "utility.h"
|
||||
|
||||
class LocalPlayer;
|
||||
class MapDrawControl;
|
||||
class ExtrudedSpriteSceneNode;
|
||||
|
||||
/*
|
||||
Client camera class, manages the player and camera scene nodes, the viewing distance
|
||||
and performs view bobbing etc.
|
||||
and performs view bobbing etc. It also displays the wielded tool in front of the
|
||||
first-person camera.
|
||||
*/
|
||||
class Camera
|
||||
{
|
||||
@ -59,6 +62,12 @@ public:
|
||||
return m_cameranode;
|
||||
}
|
||||
|
||||
// Get wielded item scene node.
|
||||
inline ExtrudedSpriteSceneNode* getWieldNode() const
|
||||
{
|
||||
return m_wieldnode;
|
||||
}
|
||||
|
||||
// Get the camera position (in absolute scene coordinates).
|
||||
// This has view bobbing applied.
|
||||
inline v3f getPosition() const
|
||||
@ -107,12 +116,19 @@ public:
|
||||
// Update settings from g_settings
|
||||
void updateSettings();
|
||||
|
||||
// Replace the wielded item mesh
|
||||
void wield(InventoryItem* item);
|
||||
|
||||
// Start or stop digging animation
|
||||
void setDigging(bool digging);
|
||||
|
||||
private:
|
||||
// Scene manager and nodes
|
||||
scene::ISceneManager* m_smgr;
|
||||
scene::ISceneNode* m_playernode;
|
||||
scene::ISceneNode* m_headnode;
|
||||
scene::ICameraSceneNode* m_cameranode;
|
||||
ExtrudedSpriteSceneNode* m_wieldnode;
|
||||
|
||||
// draw control
|
||||
MapDrawControl& m_draw_control;
|
||||
@ -151,5 +167,51 @@ private:
|
||||
f32 m_view_bobbing_speed;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
/*
|
||||
A scene node that displays a 2D mesh extruded into the third dimension,
|
||||
to add an illusion of depth.
|
||||
|
||||
Since this class was created to display the wielded tool of the local
|
||||
player, and only tools and items are rendered like this (but not solid
|
||||
content like stone and mud, which are shown as cubes), the option to
|
||||
draw a textured cube instead is provided.
|
||||
*/
|
||||
class ExtrudedSpriteSceneNode: public scene::ISceneNode
|
||||
{
|
||||
public:
|
||||
ExtrudedSpriteSceneNode(
|
||||
scene::ISceneNode* parent,
|
||||
scene::ISceneManager* mgr,
|
||||
s32 id = -1,
|
||||
const v3f& position = v3f(0,0,0),
|
||||
const v3f& rotation = v3f(0,0,0),
|
||||
const v3f& scale = v3f(0,0,0));
|
||||
~ExtrudedSpriteSceneNode();
|
||||
|
||||
void setSprite(video::ITexture* texture);
|
||||
void setCube(const TileSpec faces[6]);
|
||||
|
||||
f32 getSpriteThickness() const { return m_thickness; }
|
||||
void setSpriteThickness(f32 thickness);
|
||||
|
||||
void removeSpriteFromCache(video::ITexture* texture);
|
||||
|
||||
virtual const core::aabbox3d<f32>& getBoundingBox() const;
|
||||
virtual void OnRegisterSceneNode();
|
||||
virtual void render();
|
||||
|
||||
private:
|
||||
scene::IMeshSceneNode* m_meshnode;
|
||||
f32 m_thickness;
|
||||
scene::IMesh* m_cubemesh;
|
||||
bool m_is_cube;
|
||||
|
||||
// internal extrusion helper methods
|
||||
io::path getExtrudedName(video::ITexture* texture);
|
||||
scene::IAnimatedMesh* extrudeARGB(u32 width, u32 height, u8* data);
|
||||
scene::IAnimatedMesh* extrude(video::ITexture* texture);
|
||||
scene::IMesh* createCubeMesh();
|
||||
};
|
||||
|
||||
#endif
|
||||
|
@ -2004,14 +2004,6 @@ LocalPlayer* Client::getLocalPlayer()
|
||||
return m_env.getLocalPlayer();
|
||||
}
|
||||
|
||||
void Client::setPlayerWield(scene::ISceneNode *wield)
|
||||
{
|
||||
//JMutexAutoLock envlock(m_env_mutex); //bulk comment-out
|
||||
LocalPlayer *player = m_env.getLocalPlayer();
|
||||
assert(player != NULL);
|
||||
player->wield = wield;
|
||||
}
|
||||
|
||||
void Client::setPlayerControl(PlayerControl &control)
|
||||
{
|
||||
//JMutexAutoLock envlock(m_env_mutex); //bulk comment-out
|
||||
|
@ -210,7 +210,6 @@ public:
|
||||
|
||||
LocalPlayer* getLocalPlayer();
|
||||
|
||||
void setPlayerWield(scene::ISceneNode *wield);
|
||||
void setPlayerControl(PlayerControl &control);
|
||||
|
||||
void selectPlayerItem(u16 item);
|
||||
|
70
src/game.cpp
70
src/game.cpp
@ -819,44 +819,6 @@ void the_game(
|
||||
f32 camera_yaw = 0; // "right/left"
|
||||
f32 camera_pitch = 0; // "up/down"
|
||||
|
||||
/*
|
||||
Tool
|
||||
*/
|
||||
|
||||
v3f tool_wield_position(0.06*BS, -0.06*BS, 0.1*BS);
|
||||
v3f tool_wield_rotation(-25, 180, -25);
|
||||
float tool_wield_animation = 0.0;
|
||||
scene::IMeshSceneNode *tool_wield;
|
||||
{
|
||||
scene::SMesh *mesh = new scene::SMesh();
|
||||
scene::IMeshBuffer *buf = new scene::SMeshBuffer();
|
||||
video::SColor c(255,255,255,255);
|
||||
video::S3DVertex vertices[4] =
|
||||
{
|
||||
video::S3DVertex(-0.5,0,0, 0,0,0, c, 0,1),
|
||||
video::S3DVertex(0.5,0,0, 0,0,0, c, 1,1),
|
||||
video::S3DVertex(0.5,0.5,0, 0,0,0, c, 1,0),
|
||||
video::S3DVertex(-0.5,0.5,0, 0,0,0, c, 0,0),
|
||||
};
|
||||
u16 indices[] = {0,1,2,2,3,0};
|
||||
buf->append(vertices, 4, indices, 6);
|
||||
// Set material
|
||||
buf->getMaterial().setFlag(video::EMF_LIGHTING, false);
|
||||
buf->getMaterial().setFlag(video::EMF_BILINEAR_FILTER, false);
|
||||
buf->getMaterial().MaterialType = video::EMT_TRANSPARENT_ALPHA_CHANNEL_REF;
|
||||
// Add to mesh
|
||||
mesh->addMeshBuffer(buf);
|
||||
buf->drop();
|
||||
|
||||
tool_wield = smgr->addMeshSceneNode(mesh, camera.getHeadNode());
|
||||
mesh->drop();
|
||||
}
|
||||
tool_wield->setVisible(false);
|
||||
tool_wield->setPosition(tool_wield_position);
|
||||
tool_wield->setRotation(tool_wield_rotation);
|
||||
|
||||
client.setPlayerWield(tool_wield);
|
||||
|
||||
/*
|
||||
Clouds
|
||||
*/
|
||||
@ -1552,6 +1514,7 @@ void the_game(
|
||||
std::cout<<DTIME<<"Left-clicked object"<<std::endl;
|
||||
client.clickObject(0, selected_object->getBlock()->getPos(),
|
||||
selected_object->getId(), g_selected_item);
|
||||
camera.setDigging(true);
|
||||
}
|
||||
else if(input->getRightClicked())
|
||||
{
|
||||
@ -1619,6 +1582,7 @@ void the_game(
|
||||
std::cout<<DTIME<<"Left-clicked object"<<std::endl;
|
||||
client.clickActiveObject(0,
|
||||
selected_active_object->getId(), g_selected_item);
|
||||
camera.setDigging(true);
|
||||
}
|
||||
else if(input->getRightClicked())
|
||||
{
|
||||
@ -1792,6 +1756,8 @@ void the_game(
|
||||
}
|
||||
|
||||
dig_time += dtime;
|
||||
|
||||
camera.setDigging(true);
|
||||
}
|
||||
}
|
||||
|
||||
@ -1859,16 +1825,6 @@ void the_game(
|
||||
|
||||
nodepos_old = nodepos;
|
||||
}
|
||||
else{
|
||||
}
|
||||
|
||||
|
||||
if(input->getLeftState())
|
||||
// Tool animation loops 0.0 - 1.0
|
||||
tool_wield_animation = fmod(tool_wield_animation + dtime * 3.0, 1.0);
|
||||
else
|
||||
// Return tool to holding position if not digging
|
||||
tool_wield_animation /= 1.5;
|
||||
|
||||
} // selected_object == NULL
|
||||
|
||||
@ -1880,6 +1836,7 @@ void the_game(
|
||||
std::cout<<DTIME<<"Left button released (stopped digging)"
|
||||
<<std::endl;
|
||||
client.groundAction(2, v3s16(0,0,0), v3s16(0,0,0), 0);
|
||||
camera.setDigging(false);
|
||||
}
|
||||
if(input->getRightReleased())
|
||||
{
|
||||
@ -1985,16 +1942,6 @@ void the_game(
|
||||
);
|
||||
}
|
||||
|
||||
/*
|
||||
Animate tool
|
||||
*/
|
||||
{
|
||||
f32 tool_wield_sin = sin(tool_wield_animation * PI);
|
||||
tool_wield->setRotation(tool_wield_rotation - tool_wield_sin * 40.0);
|
||||
tool_wield->setPosition(tool_wield_position - tool_wield_sin * BS / 30.0);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
Update gui stuff (0ms)
|
||||
*/
|
||||
@ -2140,6 +2087,13 @@ void the_game(
|
||||
old_selected_item = g_selected_item;
|
||||
//std::cout<<"Updating local inventory"<<std::endl;
|
||||
client.getLocalInventory(local_inventory);
|
||||
|
||||
// Update wielded tool
|
||||
InventoryList *mlist = local_inventory.getList("main");
|
||||
InventoryItem *item = NULL;
|
||||
if(mlist != NULL)
|
||||
item = mlist->getItem(g_selected_item);
|
||||
camera.wield(item);
|
||||
}
|
||||
|
||||
/*
|
||||
|
@ -56,8 +56,6 @@ public:
|
||||
// Return the name of the image for this item
|
||||
virtual std::string getBasename() { return ""; }
|
||||
// Shall return an image of the item (or NULL)
|
||||
virtual video::ITexture * getImageRaw() { return NULL; }
|
||||
// Shall return an image to show in the GUI (or NULL)
|
||||
virtual video::ITexture * getImage() { return NULL; }
|
||||
#endif
|
||||
// Shall return a text to show in the GUI
|
||||
@ -156,7 +154,6 @@ public:
|
||||
video::ITexture * getImage()
|
||||
{
|
||||
return content_features(m_content).inventory_texture;
|
||||
return NULL;
|
||||
}
|
||||
#endif
|
||||
std::string getText()
|
||||
@ -388,14 +385,6 @@ public:
|
||||
return "cloud.png";
|
||||
}
|
||||
|
||||
video::ITexture * getImageRaw()
|
||||
{
|
||||
if(g_texturesource == NULL)
|
||||
return NULL;
|
||||
|
||||
return g_texturesource->getTextureRaw(getBasename());
|
||||
}
|
||||
|
||||
video::ITexture * getImage()
|
||||
{
|
||||
if(g_texturesource == NULL)
|
||||
|
@ -309,31 +309,12 @@ LocalPlayer::LocalPlayer():
|
||||
// Initialize hp to 0, so that no hearts will be shown if server
|
||||
// doesn't support health points
|
||||
hp = 0;
|
||||
|
||||
// No tool wielded initially
|
||||
wield = NULL;
|
||||
}
|
||||
|
||||
LocalPlayer::~LocalPlayer()
|
||||
{
|
||||
}
|
||||
|
||||
void LocalPlayer::wieldItem(u16 item)
|
||||
{
|
||||
m_selected_item = item;
|
||||
|
||||
if(wield) {
|
||||
InventoryItem* i = inventory.getList("main")->getItem(m_selected_item);
|
||||
|
||||
if(i && strcmp(i->getName(), "ToolItem") == 0) {
|
||||
wield->getMaterial(0).setTexture(0, i->getImageRaw());
|
||||
wield->setVisible(true);
|
||||
}
|
||||
else
|
||||
wield->setVisible(false);
|
||||
}
|
||||
}
|
||||
|
||||
void LocalPlayer::move(f32 dtime, Map &map, f32 pos_max_d,
|
||||
core::list<CollisionInfo> *collision_info)
|
||||
{
|
||||
|
@ -357,8 +357,6 @@ public:
|
||||
return true;
|
||||
}
|
||||
|
||||
void wieldItem(u16 item);
|
||||
|
||||
void move(f32 dtime, Map &map, f32 pos_max_d,
|
||||
core::list<CollisionInfo> *collision_info);
|
||||
void move(f32 dtime, Map &map, f32 pos_max_d);
|
||||
@ -367,8 +365,6 @@ public:
|
||||
|
||||
PlayerControl control;
|
||||
|
||||
scene::ISceneNode *wield;
|
||||
|
||||
private:
|
||||
// This is used for determining the sneaking range
|
||||
v3s16 m_sneak_node;
|
||||
|
Loading…
Reference in New Issue
Block a user