# Is there a better way to draw gradient colored ellipse?

**URL:** https://discourse.processing.org/t/is-there-a-better-way-to-draw-gradient-colored-ellipse/22220
**Category:** Coding Questions
**Created:** [June 28, 2020, 3:23pm UTC](https://discourse.processing.org/t/is-there-a-better-way-to-draw-gradient-colored-ellipse/22220 "2020-06-28T15:23:01Z")
**Posts on this page:** 1
**Showing post:** 4

<div class="post-metadata">

### Author: ![hamoid](https://yyz2.discourse-cdn.com/flex036/user_avatar/discourse.processing.org/hamoid/32/58_2.png) [@hamoid](https://discourse.processing.org/u/hamoid)
#### Post date: [June 29, 2020, 3:07pm UTC](https://discourse.processing.org/t/is-there-a-better-way-to-draw-gradient-colored-ellipse/22220/4 "2020-06-29T15:07:37Z")

</div>

Welcome to the forum! 🙂

> [@nh3](#):
>
> I was wondering if there would be some more efficient way to do this

There is a more efficient way, but efficient ways are not always easy. By programming the GPU you can create gradients, but it’s a different language called GLSL. If you’re starting with Processing then you can look at this in a year or two 🙂

The reason it’s faster it’s because there are no loops. The GPU calculates all the pixel colors in parallel. I’ll leave it here just in case someone needs faster gradients:

 ![2020-06-29-164634_800x800_scrot](https://canada1.discourse-cdn.com/flex036/uploads/processingfoundation1/original/2X/a/a6845df61fcc20c6ebb0934761d709a3358784f6.jpeg)

```auto
PShader gradient;
void setup() {
  size(800, 800, P2D);

  gradient = new PShader(this, new String[] {
      "uniform mat4 transformMatrix;", 
      "attribute vec4 position;", 
      "attribute vec4 color;", 
      "varying vec4 va_color;", 
      "varying vec2 va_pos;",
      "void main() {", 
      " gl_Position = transformMatrix * position;", 
      " va_color = color;",
      " va_pos = position.xy;",
      "}"
    }, new String[] {
      "uniform vec2 center;",
      "uniform vec3 centerColor;",
      "uniform float radius;",
      "uniform bool linear;",
      "varying vec4 va_color;", 
      "varying vec2 va_pos;",
      "void main() {",
      " float d = (linear ? distance(center.y, va_pos.y) : distance(center, va_pos))/radius;",
      " vec3 c = mix(centerColor / 255.0, va_color.rgb, min(d*d, 1.0));",
      " gl_FragColor = vec4(c, va_color.a);", 
      "}"
    });
}

void draw() {
  float x = random(width);
  float y = random(height);
  float radius = random(20, 200);

  shader(gradient); // activate the shader. Next shapes are affected by it.
  gradient.set("center", x, y); // set the center of the gradient
  gradient.set("radius", radius); // set the radius of the gradient
  gradient.set("linear", false); // two modes: linear and radial
  gradient.set("centerColor", random(255), random(255), random(255)); // use 3 floats here!
  fill(random(255), random(255), random(255)); // the outer color
  noStroke();
  circle(x, y, radius * 2); // you can draw any shape, not just circles
  resetShader(); // deactivate the shader. Next shapes use default rendering
  // ...draw something else here
}

```

The “linear” mode I implemented is just a vertical gradient. You can change `.y` to `.x` to make it horizontal. To allow any angle it needs some work. Instead of `center` and `radius` we should define `startPos` and `endPos` for the shader.

Note that `center` and `radius` do not need to match the shape you draw. You can draw a radial gradient in a square. Or set the center of the gradient in the top-left corner of the window and the shape on the center. You can experiment 🙂

Another note: centerColor must be 3 floats. It won’t work if you use integers. Fortunately `random()` produces floats.

One place to learn about shaders is the [https://thebookofshaders.com/](https://thebookofshaders.com/) (oops, link was wrong! fixed)

ps. Forgot to mention that the gradient is exponential. You can replace `d*d` with `d` to distribute the colors uniformly instead. Or with `pow(d, 3.0)` for a more extreme exponential distribution.

---

_[View the full topic](https://discourse.processing.org/t/is-there-a-better-way-to-draw-gradient-colored-ellipse/22220)._
