]> git.lizzy.rs Git - minetest.git/blobdiff - src/camera.cpp
Remove no virtual dtor warnings, make MapgenParams contain actual NoiseParams
[minetest.git] / src / camera.cpp
index ca2a6eb53db8365a503aeb495b12ad7884225bb1..0dd0a767bce056cf37412ec169afc68dd674e62d 100644 (file)
@@ -1,6 +1,6 @@
 /*
-Minetest-c55
-Copyright (C) 2010-2011 celeron55, Perttu Ahola <celeron55@gmail.com>
+Minetest
+Copyright (C) 2010-2013 celeron55, Perttu Ahola <celeron55@gmail.com>
 
 This program is free software; you can redistribute it and/or modify
 it under the terms of the GNU Lesser General Public License as published by
@@ -67,9 +67,11 @@ Camera::Camera(scene::ISceneManager* smgr, MapDrawControl& draw_control,
        m_view_bobbing_anim(0),
        m_view_bobbing_state(0),
        m_view_bobbing_speed(0),
+       m_view_bobbing_fall(0),
 
        m_digging_anim(0),
-       m_digging_button(-1)
+       m_digging_button(-1),
+       m_dummymesh(createCubeMesh(v3f(1,1,1)))
 {
        //dstream<<__FUNCTION_NAME<<std::endl;
 
@@ -84,13 +86,14 @@ Camera::Camera(scene::ISceneManager* smgr, MapDrawControl& draw_control,
        // all other 3D scene nodes and before the GUI.
        m_wieldmgr = smgr->createNewSceneManager();
        m_wieldmgr->addCameraSceneNode();
-       m_wieldnode = m_wieldmgr->addMeshSceneNode(createCubeMesh(v3f(1,1,1)), NULL);  // need a dummy mesh
+       m_wieldnode = m_wieldmgr->addMeshSceneNode(m_dummymesh, NULL);  // need a dummy mesh
 }
 
 Camera::~Camera()
 {
-       m_wieldnode->setMesh(NULL);
        m_wieldmgr->drop();
+
+       delete m_dummymesh;
 }
 
 bool Camera::successfullyCreated(std::wstring& error_message)
@@ -132,6 +135,13 @@ inline f32 my_modf(f32 x)
 
 void Camera::step(f32 dtime)
 {
+       if(m_view_bobbing_fall > 0)
+       {
+               m_view_bobbing_fall -= 3 * dtime;
+               if(m_view_bobbing_fall <= 0)
+                       m_view_bobbing_fall = -1; // Mark the effect as finished
+       }
+
        if (m_view_bobbing_state != 0)
        {
                //f32 offset = dtime * m_view_bobbing_speed * 0.035;
@@ -218,6 +228,8 @@ void Camera::update(LocalPlayer* player, f32 frametime, v2u32 screensize,
        // Smooth the movement when walking up stairs
        v3f old_player_position = m_playernode->getPosition();
        v3f player_position = player->getPosition();
+       if (player->isAttached && player->parent)
+               player_position = player->parent->getPosition();
        //if(player->touching_ground && player_position.Y > old_player_position.Y)
        if(player->touching_ground &&
                        player_position.Y > old_player_position.Y)
@@ -233,9 +245,31 @@ void Camera::update(LocalPlayer* player, f32 frametime, v2u32 screensize,
        m_playernode->setRotation(v3f(0, -1 * player->getYaw(), 0));
        m_playernode->updateAbsolutePosition();
 
+       // Get camera tilt timer (hurt animation)
+       float cameratilt = fabs(fabs(player->hurt_tilt_timer-0.75)-0.75);
+
+       // Fall bobbing animation
+       float fall_bobbing = 0;
+       if(player->camera_impact >= 1)
+       {
+               if(m_view_bobbing_fall == -1) // Effect took place and has finished
+                       player->camera_impact = m_view_bobbing_fall = 0;
+               else if(m_view_bobbing_fall == 0) // Initialize effect
+                       m_view_bobbing_fall = 1;
+
+               // Convert 0 -> 1 to 0 -> 1 -> 0
+               fall_bobbing = m_view_bobbing_fall < 0.5 ? m_view_bobbing_fall * 2 : -(m_view_bobbing_fall - 0.5) * 2 + 1;
+               // Smoothen and invert the above
+               fall_bobbing = sin(fall_bobbing * 0.5 * M_PI) * -1;
+               // Amplify according to the intensity of the impact
+               fall_bobbing *= (1 - rangelim(50 / player->camera_impact, 0, 1)) * 5;
+
+               fall_bobbing *= g_settings->getFloat("fall_bobbing_amount");
+       }
+
        // Set head node transformation
-       m_headnode->setPosition(player->getEyeOffset());
-       m_headnode->setRotation(v3f(player->getPitch(), 0, 0));
+       m_headnode->setPosition(player->getEyeOffset()+v3f(0,cameratilt*-player->hurt_tilt_strength+fall_bobbing,0));
+       m_headnode->setRotation(v3f(player->getPitch(), 0, cameratilt*player->hurt_tilt_strength));
        m_headnode->updateAbsolutePosition();
 
        // Compute relative camera position and target
@@ -308,8 +342,7 @@ void Camera::update(LocalPlayer* player, f32 frametime, v2u32 screensize,
        m_fov_y = fov_degrees * M_PI / 180.0;
        // Increase vertical FOV on lower aspect ratios (<16:10)
        m_fov_y *= MYMAX(1.0, MYMIN(1.4, sqrt(16./10. / m_aspect)));
-       // WTF is this? It can't be right
-       m_fov_x = 2 * atan(0.5 * m_aspect * tan(m_fov_y));
+       m_fov_x = 2 * atan(m_aspect * tan(0.5 * m_fov_y));
        m_cameranode->setAspectRatio(m_aspect);
        m_cameranode->setFOV(m_fov_y);
 
@@ -544,7 +577,7 @@ void Camera::wield(const ItemStack &item)
 void Camera::drawWieldedTool()
 {
        // Set vertex colors of wield mesh according to light level
-       u8 li = decode_light(m_wieldlight);
+       u8 li = m_wieldlight;
        video::SColor color(255,li,li,li);
        setMeshColor(m_wieldnode->getMesh(), color);