Home | History | Annotate | Download | only in launcher3
      1 package com.android.launcher3;
      2 
      3 import android.content.Context;
      4 import android.content.res.TypedArray;
      5 import android.graphics.Rect;
      6 import android.util.AttributeSet;
      7 import android.view.View;
      8 import android.view.ViewDebug;
      9 import android.view.ViewGroup;
     10 import android.widget.FrameLayout;
     11 
     12 public class InsettableFrameLayout extends FrameLayout implements
     13     ViewGroup.OnHierarchyChangeListener, Insettable {
     14 
     15     @ViewDebug.ExportedProperty(category = "launcher")
     16     protected Rect mInsets = new Rect();
     17 
     18     public Rect getInsets() {
     19         return mInsets;
     20     }
     21 
     22     public InsettableFrameLayout(Context context, AttributeSet attrs) {
     23         super(context, attrs);
     24         setOnHierarchyChangeListener(this);
     25     }
     26 
     27     public void setFrameLayoutChildInsets(View child, Rect newInsets, Rect oldInsets) {
     28         final LayoutParams lp = (LayoutParams) child.getLayoutParams();
     29 
     30         if (child instanceof Insettable) {
     31             ((Insettable) child).setInsets(newInsets);
     32         } else if (!lp.ignoreInsets) {
     33             lp.topMargin += (newInsets.top - oldInsets.top);
     34             lp.leftMargin += (newInsets.left - oldInsets.left);
     35             lp.rightMargin += (newInsets.right - oldInsets.right);
     36             lp.bottomMargin += (newInsets.bottom - oldInsets.bottom);
     37         }
     38         child.setLayoutParams(lp);
     39     }
     40 
     41     @Override
     42     public void setInsets(Rect insets) {
     43         // If the insets haven't changed, this is a no-op. Avoid unnecessary layout caused by
     44         // modifying child layout params.
     45         if (insets.equals(mInsets)) return;
     46 
     47         final int n = getChildCount();
     48         for (int i = 0; i < n; i++) {
     49             final View child = getChildAt(i);
     50             setFrameLayoutChildInsets(child, insets, mInsets);
     51         }
     52         mInsets.set(insets);
     53     }
     54 
     55     @Override
     56     public LayoutParams generateLayoutParams(AttributeSet attrs) {
     57         return new InsettableFrameLayout.LayoutParams(getContext(), attrs);
     58     }
     59 
     60     @Override
     61     protected LayoutParams generateDefaultLayoutParams() {
     62         return new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
     63     }
     64 
     65     // Override to allow type-checking of LayoutParams.
     66     @Override
     67     protected boolean checkLayoutParams(ViewGroup.LayoutParams p) {
     68         return p instanceof InsettableFrameLayout.LayoutParams;
     69     }
     70 
     71     @Override
     72     protected LayoutParams generateLayoutParams(ViewGroup.LayoutParams p) {
     73         return new LayoutParams(p);
     74     }
     75 
     76     public static class LayoutParams extends FrameLayout.LayoutParams {
     77         boolean ignoreInsets = false;
     78 
     79         public LayoutParams(Context c, AttributeSet attrs) {
     80             super(c, attrs);
     81             TypedArray a = c.obtainStyledAttributes(attrs,
     82                     R.styleable.InsettableFrameLayout_Layout);
     83             ignoreInsets = a.getBoolean(
     84                     R.styleable.InsettableFrameLayout_Layout_layout_ignoreInsets, false);
     85             a.recycle();
     86         }
     87 
     88         public LayoutParams(int width, int height) {
     89             super(width, height);
     90         }
     91 
     92         public LayoutParams(ViewGroup.LayoutParams lp) {
     93             super(lp);
     94         }
     95     }
     96 
     97     @Override
     98     public void onChildViewAdded(View parent, View child) {
     99         setFrameLayoutChildInsets(child, mInsets, new Rect());
    100     }
    101 
    102     @Override
    103     public void onChildViewRemoved(View parent, View child) {
    104     }
    105 
    106 }
    107