New to three.js - Tips on how to improve my soda can

Hi! So I’ve recently started using three.js in my spare time and it’s really fun!
I’ve added some lights to my scene, casting shadows on a shadow plane and added OrbitControls to make it easier for me to look at my geometrys.

However, my point of goal right now is to create a soda can and I’m having a hard time to understand how I can form it by using only the CylinderGeometry class.

Is there any better ways of doing it?
I don’t want to start using the model loaders yet since modelling for me is another undiscovered territory.

I’m also wondering if I can get a darker side of the can where the spotlight doesn’t reach the texture.
I send you an image so you get a better understanding on my progress.

For the lighting you should use a MeshLambertMaterial, i suppose you’re using MeshBasicMaterial which doesn’t use lights.

If you’re trying to get a real can of coke, you should load a model of it instead primitives. There are a lot coke cans you can download, to create one yourself you need to use modelling software such as Blender (free). In case you want to go with a cylinder, i think the cylinder geometry generates groups for the tube and the caps already. In this case you could use a MultiMaterial passing 3 materials one for the tube and the next 2 for the caps.


Hi! :slight_smile:
Creating a can from a pure THREE.CylinderGeometry() is fun, but I’d recommend to have a look at THREE.LatheGeometry():
Disadvantage of this method is strange UV coordinates.


Hi and thanks for your reply! I tried out using the MeshLambertMaterial and like you said it responds to the lighting, thanks!

Regarding the model I added three materials (1 texture and two colored) and that worked great. Thank you :slight_smile:

Oh my god, that’s so nice of you. I did not know about the LatheGeometry but this is exactly what I need.

I will try out and see if I can get the texture to look good on it and get back if I get stuck again.

Again, thank you :smiley:

By the way, how did you come up with how to draw the path?
Also, is there a way to get the height out of a LatheBufferGeometry?

LatheGeometry is so underrated :laughing:

  1. I had a can of cola in front of me :smile: So, I’ve just imagined a path (THREE.Path()) I have to rotate around Y-axis to have an object, visually similar to the can.
  2. If I got you correctly about the height, then you can use .computeBoundingBox() method and then .boundingBox peoperty of your geometry. .boundinBox is the property of THREE.Box3() type (the other users will correct me, if I’m wrong). So, THREE.Box3() has .getSize() method. Using it, you can obtain the size of your geometry (width, height, depth). I’ve updated my jsfiddle, have a look at the browser console :slight_smile:
1 Like

:smile: It’s as underrated as .displacementMap :beers:

1 Like

Haha that’s awesome!

I got some progress with the can. Tried out the MeshLambertMaterial to get similar reflection as with your jsfiddle by adding a metallic texture for the envMap parameter.
I also added the height calculation so I can stack cans on top of eachother without hard typing the known height.

Regarding the logo on the can, do you think it’s possible to match the paths of the lathe mesh?
If not I will stick with a metallic can only :slight_smile:

Check the image to see my progress (nothing new really compared to yours though, hehe)

You can play with UV coordinates. :slight_smile:
I’ve updated the fiddle.

1 Like

Awesome, thanks!

I applied your UV changes and modified them a bit.
I also modified (without knowing what I’m doing) the texture and added a grey background on the top and bottom.
With this modification I could adjust the positioning better.
I tried to get the texture to look nice on the slopes but since that was above my league I ended up adding it only to the middle part of the can.

Since I wanted to learn more about the THREE.Path class I added more lines to get a more realistic top to the can. Not sure on how to get the lid to look good though but this is what I came up with:


1 Like

Terra incognita and spirit of discovery in one can :smile:
The result is really good :+1:

haha thank you!
By the way, since I’m using typescript I’ve found some missing type definitions for the DefinitelyTyped repository on github.

One major thing that is missing is the attributes parameters. For example, the .uv and .position that you added to your jsfiddle.

I will try to add those in a pull request later

EDIT: Oh, it might actually be latheGeo.attributes.count instead of .position.count

EDIT again: I ended up removing my ts-ignore for now and used the method getAttribute instead.

Just a tip, for the shape you can use BezierCurveTo to as well, although it can take some time to learn how to move the control points. That way you get the smooth curves on the edges of the can. It works just like the bezier curve for canvas drawing, and explains how to set the control points well.

Generally for curves I just park the first handle at the starting point and then pull the second control point along the same line that the last line end point had (which is the start point of this curve).

Also if you have a modern GPU you can safely use MeshStandardMaterial and even adjust metalness and such. For the coke can I believe the material should have a separate metal map as the area that has print on it has a little less metal reflection.