I have recently created easy-to-use softbodies (blob-like shapes)!
The code has customizable parameters and can easily be changed as you like!
Here’s a step-by-step guide on how to make a working softbody!
Objects:
Center
The center will serve as the center of the blob where the shape is built around.
Point
(Variables: vx, vy, Index, oldX, oldY)
The points are what is holding the shape together and what the shape is formed by, this is what most of the math will be acting upon.
BlobFiller
(Shape painter)
The shape painter will fill in and outline (optional) your blob for a nice looking aesthetic.
Scene variables:
(The variables with descriptions may be customized as you like.)
Index
Angle
Points - The amount of points in the polygon.
Radius - The width of a line drawn from the side of the shape to the center.
Events:
Just a clarification for the last event, the number can be changed to make the blob seem more like a liquid or a rubber or jelly-like substance.
I’ll do you a solid and give you the entire thing, but don’t forget to remove everything that’s in the event when you first create it.
const Radius = runtimeScene.getVariables().get("Radius").getAsNumber();
const points = runtimeScene.getObjects("Point");
const center = runtimeScene.getObjects("Center")[0];
if (!center || points.length !== points.length) return;
const targetArea = 3.14159265359 * Radius ** 2;
let area = 0;
for (let i = 0; i < points.length; i++) {
const A = points[i];
const B = points[(i + 1) % points.length];
area += A.getX() * B.getY() - B.getX() * A.getY();
}
const currentArea = Math.abs(area / 2);
const strengthMultiplier = 10;
// Change strengthMultiplier if you feel as if the blob is growing too much or too little on impact with an object.
const areaDiffFactor = ((targetArea - currentArea) / targetArea) * strengthMultiplier;
const cx = center.getX();
const cy = center.getY();
for (const point of points) {
const dx = point.getX() - cx;
const dy = point.getY() - cy;
const length = Math.sqrt(dx * dx + dy * dy);
if (length === 0) continue;
const unitX = dx / length;
const unitY = dy / length;
const moveX = unitX * areaDiffFactor;
const moveY = unitY * areaDiffFactor;
point.setX(point.getX() + moveX);
point.setY(point.getY() + moveY);
}
Now for the finishing touch.
All done!
Don’t forget to tell me if anything isn’t working, or if you have any feedback or suggestions, feel free to let me know!
Edit: I forgot to mention that if you don’t want the blob to follow your cursor you can add physics to the point/center objects to add gravity and collisions.