android – How to apply a color filter to a view with all children-ThrowExceptions

Exception or error:

How do I grey out a view uniformly which contains many different items – ImageViews, TextViews, background image. Do I have to grey out each thing individually? Or is there a way to apply the same color filter to all?

How to solve:

Unless somebody else has a better answer, my current method is greying out each item separatedly.

PorterDuffColorFilter greyFilter = new PorterDuffColorFilter(Color.GRAY, PorterDuff.Mode.MULTIPLY);

For more or nested children probably a loop with instanceof would be suitable but I don’t need it.

Edit: This filter isn’t actually grey, a better filter is here: Drawable => grayscale
Which can be used in the same way.


It’s easy to do that by defining a custom view group as follows:

public class MyViewContainer extends XXXLayout {
    //XXLayout could be LinearLayout, RelativeLayout or others
    private Paint m_paint;

    //define constructors here and call _Init() at the end of constructor function

    private void
        ColorMatrix cm = new ColorMatrix();
        m_paint = new Paint();
        m_paint.setColorFilter(new ColorMatrixColorFilter(cm));

    @Override protected void 
    dispatchDraw(Canvas canvas)
        canvas.saveLayer(null, m_paint, Canvas.ALL_SAVE_FLAG);

All children views of MyViewContainer will be shown in grey. 🙂


Sam Lu’s answer is a good start, but I had performance problems and decided to switch to hardware layers. With hardware layers, you can do it like this:

private final Paint grayscalePaint = new Paint();

ColorMatrix cm = new ColorMatrix();
grayscalePaint.setColorFilter(new ColorMatrixColorFilter(cm));

public void setGrayedOut(boolean grayedOut) {       
    if (grayedOut) {
        setLayerType(View.LAYER_TYPE_HARDWARE, grayscalePaint);
    } else {
        setLayerType(View.LAYER_TYPE_NONE, null);       

Be careful not to do the layers in dispatchDraw() itself as that will crash the app.


It depends entirely on the method you are using to “gray out” items. If you are doing so by calling setEnabled(false) on the parent ViewGroup, by default state flags (like disabled) do not trickle down to the child views. However, there are two simple ways you can customize this:

One option is to add the attribute android:duplicateParentState="true" to each child view in your XML. This will tell the children to get their state flags from the parent. This will mirror ALL flags however, including pressed, checked, etc…not just enabled.

Another option is to create a custom subclass of your ViewGroup and override setEnabled() to call all the child views as well, i.e.

public void setEnabled(boolean enabled) {

    for(int i=0; i < getChildCount(); i++) {


What I like to do is create a view which overlaps the view you are trying to tint and set its background to a transparent color. Then you can turn the tint on and off by setting that views visibility





Then in your controller:

m_DisabledBlackTintOverlay = (View) view.findViewById(;


Leave a Reply

Your email address will not be published. Required fields are marked *