Sweep Gradient : What it is and its examples Sweep Gradient : What it is and its examples android android

Sweep Gradient : What it is and its examples


The word gradient in this context (as in many graphics editors, including Photoshop) refers to a smooth transition between multiple colors, as opposed to using just a single color to fill an area.

The Android API provides 3 different gradients: LinearGradient, RadialGradient and SweepGradient.

These are all subclasses of Shader. You can set a Shader on a Paint object, and then draw any shape with that Paint. The shape will be filled with colors and transitions between them, according to the kind of the gradient.

For example:

output image of the code below

This image can be produced with this code:

Bitmap test = Bitmap.createBitmap(640, 200, Bitmap.Config.ARGB_8888);Canvas c = new Canvas(test);{ // draw a dark gray background    Paint backgroundPaint = new Paint();    backgroundPaint.setARGB(255, 24, 24, 24);    c.drawPaint(backgroundPaint);}Path heart = new Path();{ // prepare a heart shape    heart.moveTo(110, 175);    heart.lineTo(10, 75);    RectF leftCircle = new RectF(10, 25, 110, 125);    heart.arcTo(leftCircle, 180, 180);    RectF rightCircle = new RectF(110, 25, 210, 125);    heart.arcTo(rightCircle, 180, 180);    heart.close();}Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);paint.setTextSize(18f);int[] colors = {        0xFFFFFF88, // yellow        0xFF0088FF, // blue        0xFF000000, // black        0xFFFFFF88  // yellow};float[] positions = {0.0f, 0.33f, 0.66f, 1.0f};{ // draw the left heart    SweepGradient sweepGradient;    { // initialize the sweep gradient        sweepGradient = new SweepGradient(50, 50, colors, positions);        paint.setShader(sweepGradient);    }    c.drawPath(heart, paint);    c.drawText("SweepGradient", 50, 190, paint);}{ // draw the middle heart    LinearGradient linearGradient;    { // initialize a linear gradient        linearGradient = new LinearGradient(250, 0, 350, 150, colors, positions, Shader.TileMode.CLAMP);        paint.setShader(linearGradient);    }    heart.offset(210, 0); // move the heart shape to the middle    c.drawPath(heart, paint);    c.drawText("LinearGradient", 260, 190, paint);}{ // draw the right heart    RadialGradient radialGradient;    { // initialize a linear gradient        radialGradient = new RadialGradient(550, 50, 100, colors, positions, Shader.TileMode.CLAMP);        paint.setShader(radialGradient);    }    heart.offset(210, 0); // move the heart shape to the right    c.drawPath(heart, paint);    c.drawText("RadialGradient", 470, 190, paint);}{ // save the bitmap    String filename = Environment.getExternalStorageDirectory().getAbsolutePath() + File.separator + "test.png";    FileOutputStream out = null;    try {        out = new FileOutputStream(filename);        test.compress(Bitmap.CompressFormat.PNG, 90, out);    } catch (Exception e) {    } finally {        try {            out.close();        } catch (Exception e) {        }    }}
  • So the LinearGradient is Linear Gradient in Photoshop, RadialGradient is Radial Gradient, and SweepGradient is Angular Gradient, as described in your 3rd reference. I recommend trying these in an image editor first (all popular image editors have these tools), and you'll quickly get the idea of how they work.

  • You can use these gradients in an XML drawable too (like in your 4th reference), with a limitation of using 3 colors maximum.

  • In a SweepGradient, when providing positions, the 0.0 point is at 3 o'clock, going clockwise (with 0.25 being at 6 o'clock, 0.5 at 9 o'clock, 0.75 at 12 o'clock, and 1.0 back at 3 o'clock).

About your conclusions:

  • As you can see, any shape can be drawn with a SweepGradient, not just a ring. Even the labels are drawn with the gradients in the example above.
  • Yes, the clock's hand analogy is spot on.
  • In usage, SweepGradient is very similar to LinearGradient, except you don't need to provide a TileMode, because you cannot run outside of the bounds of your color list.
  • Yes, you need to provide the coordinates of the center point.

I hope this clears it up.


For xml drawable this can be specified with

android:type="sweep"

android:type can have values(case-sensitive): linear, radial or sweep