Please change this below lines of code below to the path off your own water and box textures.
water->setMaterialTexture(0, driver->getTexture("water.jpg"));
cube->setMaterialTexture(0, driver->getTexture("wood.jpeg"));
Code: Select all
#include <irrlicht.h>
#include <cmath>
using namespace irr;
using namespace core;
using namespace scene;
using namespace video;
using namespace io;
using namespace gui;
int main()
{
// Create device
IrrlichtDevice *device = createDevice(EDT_OPENGL, dimension2d<u32>(800, 600), 16, false, false, false, 0);
if (!device)
return 1;
device->setWindowCaption(L"Irrlicht Engine - Water with floating box scene ");
IVideoDriver *driver = device->getVideoDriver();
ISceneManager *smgr = device->getSceneManager();
IGUIEnvironment *guienv = device->getGUIEnvironment();
// Add camera
smgr->addCameraSceneNode(0, vector3df(0, 100, -200), vector3df(0, 0, 0));
// Add light
smgr->addLightSceneNode(0, vector3df(50, 50, 50), SColorf(1.0f, 1.0f, 1.0f), 500.0f);
// Create custom water surface mesh
IMesh* waterMesh = smgr->addHillPlaneMesh("myHill",
dimension2d<f32>(20, 20), dimension2d<u32>(40, 40), 0, 0.0f, dimension2d<f32>(1.0f, 1.0f));
ISceneNode* water = smgr->addWaterSurfaceSceneNode(waterMesh, 3.0f, 600.0f, 30.0f);
water->setMaterialFlag(EMF_LIGHTING, false);
water->setMaterialTexture(0, driver->getTexture("water.jpg"));
water->setMaterialType(EMT_TRANSPARENT_ADD_COLOR);
// Add rectangular cube
ISceneNode *cube = smgr->addCubeSceneNode(40.0f);
if (cube)
{
cube->setPosition(vector3df(0, 5.0f, 0)); // Initially half submerged
cube->setMaterialTexture(0, driver->getTexture("wood.jpeg"));
cube->setMaterialFlag(EMF_LIGHTING, false);
}
// Physics variables
f32 cubeMass = 1.0f; // mass of the cube
f32 gravity = -9.81f; // gravity constant
f32 cubeVelocity = 0.0f; // initial velocity of the cube
f32 damping = 0.99f; // damping factor to simulate resistance
u32 then = device->getTimer()->getTime();
// Main loop
while (device->run())
{
// Render the scene
driver->beginScene(true, true, SColor(255, 100, 101, 140));
smgr->drawAll();
guienv->drawAll();
const u32 now = device->getTimer()->getTime();
const f32 deltaTime = (f32)(now - then) / 1000.f; // Time in seconds
then = now;
// Get the cube's current position
vector3df cubePos = cube->getPosition();
// Calculate the wave height at the cube's position
f32 waveHeight = 3.0f * sinf(cubePos.X * 0.05f + now / 1000.0f) * cosf(cubePos.Z * 0.05f + now / 1000.0f);
// Calculate the wave height at slightly different positions to determine slope
f32 waveHeightX1 = 3.0f * sinf((cubePos.X + 1) * 0.05f + now / 1000.0f) * cosf(cubePos.Z * 0.05f + now / 1000.0f);
f32 waveHeightX2 = 3.0f * sinf((cubePos.X - 1) * 0.05f + now / 1000.0f) * cosf(cubePos.Z * 0.05f + now / 1000.0f);
f32 waveHeightZ1 = 3.0f * sinf(cubePos.X * 0.05f + now / 1000.0f) * cosf((cubePos.Z + 1) * 0.05f + now / 1000.0f);
f32 waveHeightZ2 = 3.0f * sinf(cubePos.X * 0.05f + now / 1000.0f) * cosf((cubePos.Z - 1) * 0.05f + now / 1000.0f);
// Calculate the slopes in the X and Z directions
f32 slopeX = (waveHeightX1 - waveHeightX2) / 2.0f;
f32 slopeZ = (waveHeightZ1 - waveHeightZ2) / 2.0f;
// Calculate the rotation angles based on the slopes
f32 tiltAngleX = atan(slopeZ) * 180.0f / 3.14159265f; // Rotate around the X-axis
f32 tiltAngleZ = atan(slopeX) * 180.0f / 3.14159265f; // Rotate around the Z-axis
// Apply the rotations to the cube
cube->setRotation(vector3df(tiltAngleX, 0, tiltAngleZ));
// Calculate the buoyancy force based on the wave height
f32 submergedVolume = (cubePos.Y < waveHeight) ? (waveHeight - cubePos.Y) * 40.0f * 40.0f : 0.0f;
f32 buoyancy = submergedVolume * 10.0f / cubeMass;
// Update the velocity with gravity and buoyancy
cubeVelocity += (gravity + buoyancy) * deltaTime;
cubeVelocity *= damping; // apply damping
// Update the cube's position
cubePos.Y += cubeVelocity * deltaTime;
cube->setPosition(cubePos);
driver->endScene();
}
device->drop();
return 0;
}