skip to Main Content
Project Description

Fast fourier transform height field based ocean simulations, popularized by Jerry  Tessendorf, have been present in the industry for many years.

We developed a CUDA  optimized version, capable of rendering a 512×512 ocean patch at 600 fps running on  Intel(R) Xeon(R) CPU E5-1620 v4 @ 3.50GHz with a NVIDIA GeForce GTX 1060.

Using CUDA optimization techniques such as streaming , dynamic shared memory, privatization and memory coalescing, we optimized the naive CUDA implimentation by more than 400%.

This Project was done in collaboration with Daryl Teo: https://www.linkedin.com/in/dteowm/

Details
3D Ocean Simulation
2 Team Members
C++, OpenGL, CUDA, GPGPU
3 week timeline
Algorithm Summary

There are four parts in the ocean simulation:

1

 

Generating Modified Phillips Spectrum

Generates a wave spectrum in frequencies space using complex number arithmetic, sine and cosine functions. The output is a frequency domain image which looks like: 

2

 

Inverse Fast Fourier Transform

Using an inverse fast fourier transform in cuFFT to convert the Modified Philips Spectrum from frequency domain to spatial domain, we obtain the following image:

3

 

Generating Wave Geometry

Applying the output from the previous step as a displacement on the ocean grid, we then achieve an ocean like planar geometry.

4

 

Generate Vertex & Face Normals

However, the vertex and face normals are incorrect, causing the ocean to look unrealistic. We fix this by calculating the vertex and face normals using tri-linear slope interpolation for each face.

 

With this step, we are done and have a realistic approximation of an ocean surface.

Optimization

Optimization was an iterative processes for us, starting out with the naive CPU version and slowly optimizing it into the fast CUDA based simulation it is now.

  • CPU Simulation
    • The initial simulation was done mainly on the CPU with only the rendering and shading done on the GPU. This build made use of the naive Fourier Transform method, not the IFFT.
      As such the time taken to render a 512×512 grid sized ocean was around 160ms, a whopping 6 frames per second.
  • First Iteration: Naive Port to CUDA
My Task

I was in charge of generating the Ocean Geometry. As such i took charge of the first 2 steps in the algorithm, computing the Modified Philips Spectrum and Applying the Inverse Fast Fourier Transform. Furthermore i was tasked with making the simulation look more realistic, so I created simple ocean shaders to simulate the light passing through crest of the waves where the water was not as thick and opaque. I also applied simple specular shaders to certain parts of the wave to help them “catch the light” at certain angles making it sparkle.

 

In Summary:

  • Generating Phillips Spectrum in Complex Number Frequency Space in CUDA.
  • Calculating the Displacement Map using Inverse Fast Fourier Transform in CUDA.
  • CUDA Optimizations.
    • Memory coalescing
    • Dynamic Shared memory
    • Streaming
    • Privatization
  • Ocean Shaders for simulated translucency and sparkling.
Back To Top