Both can be used to express unsigned 8-bit integers and the value range is also the same(0-255). The difference lies in how they handle numbers. To put it simply, there are 2 main cases.
Firstly, for integers below or above the range, Uint8Array will work in a normal overflow rotation style and Uint8ClampedArray will just use the nearest integer.
For example, if we put the number 256 in Uint8Array because it is above the max number 255, it overflows and rotates to 0, the lowest number in range. But for Uint8ClampedArray, the nearest number 255 will be used.
> const a = new Uint8Array(1) > a = 256 > a Uint8Array(1) [ 0 ] > const b = new Uint8ClampedArray(1); > b = 256; > b Uint8ClampedArray(1) [ 255 ]
Secondly, if we put a float number in Uint8Array, it will use the floor the number to the nearest integer. But for Uint8ClampedArray, it will use a method similar to round to handle the number.
For example, for float number 1.5, Uint8Array will make it 1 and Uint8ClampedArray will make it 2.
> const a = new Uint8Array(1) > a = 1.5 > a Uint8Array(1) [ 1 ] > const b = new Uint8ClampedArray(1); > b = 1.5; > b Uint8ClampedArray(1) [ 2 ]
Reading this, you may want to ask, why are these different? Well, Uint8Array is for normal typed arrays and Uint8ClampedArray is mostly created for handling color values. So for a normal unsigned 8-bit integer, we may want to make use of the normal overflow rotation feature. But for image color values, when we have a number bigger than 255, instead of rotating to a small color value, we may want to stick to 255.
So with this background, these differences may make some sense now. The above explanation should be enough for normal development. Check this doc for details.