Home | History | Annotate | Download | only in notification
      1 /*
      2  * Copyright (C) 2018 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file
      5  * except in compliance with the License. You may obtain a copy of the License at
      6  *
      7  *      http://www.apache.org/licenses/LICENSE-2.0
      8  *
      9  * Unless required by applicable law or agreed to in writing, software distributed under the
     10  * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
     11  * KIND, either express or implied. See the License for the specific language governing
     12  * permissions and limitations under the License.
     13  */
     14 
     15 package com.android.settingslib.notification;
     16 
     17 import android.content.Context;
     18 import android.util.AttributeSet;
     19 import android.view.View;
     20 import android.view.ViewGroup;
     21 import android.widget.LinearLayout;
     22 
     23 /**
     24  * Specialized layout for zen mode that allows the radio buttons to reside within
     25  * a RadioGroup, but also makes sure that all the heights of the radio buttons align
     26  * with the corresponding content in the second child of this view.
     27  */
     28 public class ZenRadioLayout extends LinearLayout {
     29 
     30     public ZenRadioLayout(Context context, AttributeSet attrs) {
     31         super(context, attrs);
     32     }
     33 
     34     /**
     35      * Run 2 measurement passes, 1 that figures out the size of the content, and another
     36      * that sets the size of the radio buttons to the heights of the corresponding content.
     37      */
     38     @Override
     39     protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
     40         super.onMeasure(widthMeasureSpec, heightMeasureSpec);
     41 
     42         ViewGroup radioGroup = (ViewGroup) getChildAt(0);
     43         ViewGroup radioContent = (ViewGroup) getChildAt(1);
     44         int size = radioGroup.getChildCount();
     45         if (size != radioContent.getChildCount()) {
     46             throw new IllegalStateException("Expected matching children");
     47         }
     48         boolean hasChanges = false;
     49         View lastView = null;
     50         for (int i = 0; i < size; i++) {
     51             View radio = radioGroup.getChildAt(i);
     52             View content = radioContent.getChildAt(i);
     53             if (lastView != null) {
     54                 radio.setAccessibilityTraversalAfter(lastView.getId());
     55             }
     56             View contentClick = findFirstClickable(content);
     57             if (contentClick != null) contentClick.setAccessibilityTraversalAfter(radio.getId());
     58             lastView = findLastClickable(content);
     59             if (radio.getLayoutParams().height != content.getMeasuredHeight()) {
     60                 hasChanges = true;
     61                 radio.getLayoutParams().height = content.getMeasuredHeight();
     62             }
     63         }
     64         // Measure again if any heights changed.
     65         if (hasChanges) {
     66             super.onMeasure(widthMeasureSpec, heightMeasureSpec);
     67         }
     68     }
     69 
     70     private View findFirstClickable(View content) {
     71         if (content.isClickable()) return content;
     72         if (content instanceof ViewGroup) {
     73             ViewGroup group = (ViewGroup) content;
     74             for (int i = 0; i < group.getChildCount(); i++) {
     75                 View v = findFirstClickable(group.getChildAt(i));
     76                 if (v != null) return v;
     77             }
     78         }
     79         return null;
     80     }
     81 
     82     private View findLastClickable(View content) {
     83         if (content.isClickable()) return content;
     84         if (content instanceof ViewGroup) {
     85             ViewGroup group = (ViewGroup) content;
     86             for (int i = group.getChildCount() - 1; i >= 0; i--) {
     87                 View v = findLastClickable(group.getChildAt(i));
     88                 if (v != null) return v;
     89             }
     90         }
     91         return null;
     92     }
     93 }
     94