Creating a lava lamp in React (Web)

I’ve been working with Next.JS (a React framework) for the last few months and I decided make something more interesting than a simple webpage. I wanted to create a lava lamp using only SVG paths. (It might not look like a proper lava lamp, but it will probably melt your CPU/GPU because it’s not the most optimized piece of software).

Basic idea

  1. Procedurally generated shapes by using only few generated points
  2. Creating smoothened SVG path from points.
  3. Adding shadow and gradient to the shapes.
  4. Create multiple stages while slightly moving points around (hence creating a morphing shape)
  5. Applying shape morphing
  6. Multiply the same logic and enjoying the result

1. Generating shape

This one is quite easy, I wanted a hump in the middle of the screen, so I looked for function that resulted in the desired shape. I ended up using a frequency curve but I found other that could be useful in the future. (Except hyperbola, because I’d have to update the whole plot render to handle two shapes on one layer.)

Visualization of selected functions

It’s only a short for loop to get our array of x:y coordinates (from -5 to 5 in my case). At this point, we don’t have to worry about getting the SVG path definition yet.

2. Creating smoothened SVG path

I found this wonderful article from François Romain about exactly what I needed. Based on the knowledge in this article, it’s fairly easy to implement a solid path smoothing.

3. Adding shadows and gradients

Adding linear gradients are simple but shadow looks a little tricky to me. But hey, it works and looks better than without it.

4. Adding noise

To achieve the morphing effect, I simply created 5 different versions of the initial shape coordinate array (see point 1) by changing every single point slightly in a given radius. We can do this by using Pythagoras theorem (a²+b²=c²)

5. Morphing

My main issue with this part was that many SVG animation tool is not available in React or poorly implemented. Thankfully I don’t have to deal with different number of points in the different stages but that can be an issue while doing SVG animations using automatic interpolation.

I started off by trying to use Paper.js because it has a smoothing and morphing example not too far from my goal but unfortunately I couldn’t get it working in React.

So, after a little research, I found an article about react-spring on CSS tricks. It perfect, they basically done it for me. I just had to add the previously generated stages to the output value and changing the x valued using a setInterval. The CSS tricks example has only 2 stages, so instead of using “active” I used “stage” because I had n stage instead of just A and B. Be careful though, while we have multiple stages (eg 5) the range of x is still from 0 to 1 so will need to use float values otherwise the animation will be jumpy.

6. Laying back

12 hours later, my creation is alive! Check it out on https://onet.dev

Choosing the unknown

Love podcasts or audiobooks? Learn on the go with our new app.

Recommended from Medium

Beginner`s guide to NPM

React GET API call to dynamically display data

JAMstack News — Issue #5

LightningJ Paywall — Bringing Micropayments to Microservices.

11-year-old girl shot, killed in 'hunting accident'

Stop using the number input field incorrectly — not all numbers are alike

Advanced console.log Tips & Tricks

NodeJS? Have you still not found what it is all about?

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store
József Koller

József Koller

Choosing the unknown

More from Medium

ReactJS Girls Online #3 in Review

PJ’s Pooch Attires — An app built with React

PJ’s Pooch Attires Homepage with sliders that showcase store ‘all time favorite products” for customers to enjoy.

Google reCaptcha V3 on a form that posts to NextJs API Route.

8 Famous Projects Using React.JS: Feature Overview