Question

I want to do this animation - Water level rises in sea engulfing a small mountain having pits. When water recedes some of it stays in the pockets and again when water level rises it all becomes one. This animation continues indefinitely. Now i have tried doing this by using two approaches,

1) Drawing and clearing the water in pool with the flow of water in sea. ctx.bezierCurveTo(x1,y1,x2,y2,end_x,end_y); I changed first and second control points with the flow of water to make the base change from little flat to spherical and vice-versa. But wasn't smooth and also second pit has irregular base so impossible.

2) I made the required pockets filled with water and played with opacity so that pocket water mixes with sea water when submerged. Again this approach doesn't give smooth look.

Here's what it should look like:

https://s3.postimg.org/7f430a1ir/Picture1.jpg

The base image is background of canvas, i just have to control water flow.

Please suggest what to do.

Was it helpful?

Solution

You can use compositing to have your sea water seamlessly intrude on your mountain

In particular "source-out" compositing allows you to draw new content only where it doesn't overlap any existing content.

Therefore "source-out" compositing will allow you to draw new sea-water only where it doesn't overlap the existing mountain.

When the water is rising:

  1. clear canvas
  2. set globalCompositeOperation="source-over" // the default, new drawings will overdraw
  3. draw your mountain
  4. set globalCompositeOperation="source-out" // new sea water will not overdraw existing mountains
  5. draw the rising sea water
  6. increase the height of the sea water
  7. repeat with #1 until your sea water is at desired height

When the water is falling:

  1. clear canvas
  2. set globalCompositeOperation="source-over" // the default, new drawings will overdraw
  3. draw your mountain
  4. set globalCompositeOperation="source-out" // new sea water will not overdraw existing mountains
  5. draw the retained sea water only in the pit of your mountain
  6. draw the falling sea water
  7. decrease the height of the sea water
  8. repeat with #1 until your sea water is at desired height

OTHER TIPS

After much thinking found a 2-step approach.

Step-1 >>

1) Draw water in sea (Destination) 2) Set ctx.globalCompositeOperation="destination-out"; 3) Draw pool water (Source)

This will remove part of source overlapping with dest. thus creating sea water with a hollow space(transparency) in place of pool. Now this image with the hole becomes the dest. image on which i have to draw only pool water so that the consistency of water is maintained.

Step-2 >>

1) Set ctx.globalCompositeOperation="destination-atop"; 2) Draw pool water (Source)

This will draw dest. only where dest. and source overlap i.e. when dest. image with hole(transparency in place of pool) and pool overlap sea water is created in hollow area. Point to be noted - pool water is like a subset of sea water so i don't have to worry about pool water(Source) to be created as it is with "destination-atop".

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top