SignalClusterView.java revision 6d035f15d5c8c67d97a4d5b6ed44f8cca0772e1f
1/*
2 * Copyright (C) 2011 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package com.android.systemui.statusbar;
18
19import android.content.Context;
20import android.util.AttributeSet;
21import android.util.Log;
22import android.view.View;
23import android.view.ViewGroup;
24import android.view.accessibility.AccessibilityEvent;
25import android.widget.ImageView;
26import android.widget.LinearLayout;
27
28import com.android.systemui.R;
29import com.android.systemui.statusbar.policy.NetworkControllerImpl;
30import com.android.systemui.statusbar.policy.SecurityController;
31
32// Intimately tied to the design of res/layout/signal_cluster_view.xml
33public class SignalClusterView
34        extends LinearLayout
35        implements NetworkControllerImpl.SignalCluster,
36        SecurityController.SecurityControllerCallback {
37
38    static final String TAG = "SignalClusterView";
39    static final boolean DEBUG = Log.isLoggable(TAG, Log.DEBUG);
40
41    NetworkControllerImpl mNC;
42    SecurityController mSC;
43
44    private boolean mVpnVisible = false;
45    private boolean mWifiVisible = false;
46    private int mWifiStrengthId = 0;
47    private boolean mMobileVisible = false;
48    private int mMobileStrengthId = 0, mMobileTypeId = 0;
49    private boolean mIsAirplaneMode = false;
50    private int mAirplaneIconId = 0;
51    private String mWifiDescription, mMobileDescription, mMobileTypeDescription;
52    private boolean mIsMobileTypeIconWide;
53
54    ViewGroup mWifiGroup, mMobileGroup;
55    ImageView mVpn, mWifi, mMobile, mMobileType, mAirplane;
56    View mWifiAirplaneSpacer;
57    View mWifiSignalSpacer;
58
59    private int mWideTypeIconStartPadding;
60    private int mEndPadding;
61    private int mEndPaddingNothingVisible;
62
63    public SignalClusterView(Context context) {
64        this(context, null);
65    }
66
67    public SignalClusterView(Context context, AttributeSet attrs) {
68        this(context, attrs, 0);
69    }
70
71    public SignalClusterView(Context context, AttributeSet attrs, int defStyle) {
72        super(context, attrs, defStyle);
73    }
74
75    public void setNetworkController(NetworkControllerImpl nc) {
76        if (DEBUG) Log.d(TAG, "NetworkController=" + nc);
77        mNC = nc;
78    }
79
80    public void setSecurityController(SecurityController sc) {
81        if (DEBUG) Log.d(TAG, "SecurityController=" + sc);
82        mSC = sc;
83        mSC.addCallback(this);
84        mVpnVisible = mSC.isVpnEnabled();
85    }
86
87    @Override
88    protected void onFinishInflate() {
89        super.onFinishInflate();
90        mWideTypeIconStartPadding = getContext().getResources().getDimensionPixelSize(
91                R.dimen.wide_type_icon_start_padding);
92        mEndPadding = getContext().getResources().getDimensionPixelSize(
93                R.dimen.signal_cluster_battery_padding);
94        mEndPaddingNothingVisible = getContext().getResources().getDimensionPixelSize(
95                R.dimen.no_signal_cluster_battery_padding);
96    }
97
98    @Override
99    protected void onAttachedToWindow() {
100        super.onAttachedToWindow();
101
102        mVpn            = (ImageView) findViewById(R.id.vpn);
103        mWifiGroup      = (ViewGroup) findViewById(R.id.wifi_combo);
104        mWifi           = (ImageView) findViewById(R.id.wifi_signal);
105        mMobileGroup    = (ViewGroup) findViewById(R.id.mobile_combo);
106        mMobile         = (ImageView) findViewById(R.id.mobile_signal);
107        mMobileType     = (ImageView) findViewById(R.id.mobile_type);
108        mAirplane       = (ImageView) findViewById(R.id.airplane);
109        mWifiAirplaneSpacer =         findViewById(R.id.wifi_airplane_spacer);
110        mWifiSignalSpacer =           findViewById(R.id.wifi_signal_spacer);
111
112        apply();
113    }
114
115    @Override
116    protected void onDetachedFromWindow() {
117        mVpn            = null;
118        mWifiGroup      = null;
119        mWifi           = null;
120        mMobileGroup    = null;
121        mMobile         = null;
122        mMobileType     = null;
123        mAirplane       = null;
124
125        super.onDetachedFromWindow();
126    }
127
128    // From SecurityController.
129    @Override
130    public void onStateChanged() {
131        post(new Runnable() {
132            @Override
133            public void run() {
134                mVpnVisible = mSC.isVpnEnabled();
135                apply();
136            }
137        });
138    }
139
140    @Override
141    public void setWifiIndicators(boolean visible, int strengthIcon, String contentDescription) {
142        mWifiVisible = visible;
143        mWifiStrengthId = strengthIcon;
144        mWifiDescription = contentDescription;
145
146        apply();
147    }
148
149    @Override
150    public void setMobileDataIndicators(boolean visible, int strengthIcon, int typeIcon,
151            String contentDescription, String typeContentDescription, boolean isTypeIconWide) {
152        mMobileVisible = visible;
153        mMobileStrengthId = strengthIcon;
154        mMobileTypeId = typeIcon;
155        mMobileDescription = contentDescription;
156        mMobileTypeDescription = typeContentDescription;
157        mIsMobileTypeIconWide = isTypeIconWide;
158
159        apply();
160    }
161
162    @Override
163    public void setIsAirplaneMode(boolean is, int airplaneIconId) {
164        mIsAirplaneMode = is;
165        mAirplaneIconId = airplaneIconId;
166
167        apply();
168    }
169
170    @Override
171    public boolean dispatchPopulateAccessibilityEvent(AccessibilityEvent event) {
172        // Standard group layout onPopulateAccessibilityEvent() implementations
173        // ignore content description, so populate manually
174        if (mWifiVisible && mWifiGroup != null && mWifiGroup.getContentDescription() != null)
175            event.getText().add(mWifiGroup.getContentDescription());
176        if (mMobileVisible && mMobileGroup != null && mMobileGroup.getContentDescription() != null)
177            event.getText().add(mMobileGroup.getContentDescription());
178        return super.dispatchPopulateAccessibilityEvent(event);
179    }
180
181    @Override
182    public void onRtlPropertiesChanged(int layoutDirection) {
183        super.onRtlPropertiesChanged(layoutDirection);
184
185        if (mWifi != null) {
186            mWifi.setImageDrawable(null);
187        }
188
189        if (mMobile != null) {
190            mMobile.setImageDrawable(null);
191        }
192
193        if (mMobileType != null) {
194            mMobileType.setImageDrawable(null);
195        }
196
197        if(mAirplane != null) {
198            mAirplane.setImageDrawable(null);
199        }
200
201        apply();
202    }
203
204    @Override
205    public boolean hasOverlappingRendering() {
206        return false;
207    }
208
209    // Run after each indicator change.
210    private void apply() {
211        if (mWifiGroup == null) return;
212
213        mVpn.setVisibility(mVpnVisible ? View.VISIBLE : View.GONE);
214        if (DEBUG) Log.d(TAG, String.format("vpn: %s", mVpnVisible ? "VISIBLE" : "GONE"));
215        if (mWifiVisible) {
216            mWifi.setImageResource(mWifiStrengthId);
217            mWifiGroup.setContentDescription(mWifiDescription);
218            mWifiGroup.setVisibility(View.VISIBLE);
219        } else {
220            mWifiGroup.setVisibility(View.GONE);
221        }
222
223        if (DEBUG) Log.d(TAG,
224                String.format("wifi: %s sig=%d",
225                    (mWifiVisible ? "VISIBLE" : "GONE"),
226                    mWifiStrengthId));
227
228        if (mMobileVisible && !mIsAirplaneMode) {
229            mMobile.setImageResource(mMobileStrengthId);
230            mMobileType.setImageResource(mMobileTypeId);
231            mMobileGroup.setContentDescription(mMobileTypeDescription + " " + mMobileDescription);
232            mMobileGroup.setVisibility(View.VISIBLE);
233        } else {
234            mMobileGroup.setVisibility(View.GONE);
235        }
236
237        if (mIsAirplaneMode) {
238            mAirplane.setImageResource(mAirplaneIconId);
239            mAirplane.setVisibility(View.VISIBLE);
240        } else {
241            mAirplane.setVisibility(View.GONE);
242        }
243
244        if (mIsAirplaneMode && mWifiVisible) {
245            mWifiAirplaneSpacer.setVisibility(View.VISIBLE);
246        } else {
247            mWifiAirplaneSpacer.setVisibility(View.GONE);
248        }
249
250        if (mMobileVisible && mMobileTypeId != 0 && mWifiVisible) {
251            mWifiSignalSpacer.setVisibility(View.VISIBLE);
252        } else {
253            mWifiSignalSpacer.setVisibility(View.GONE);
254        }
255
256        mMobile.setPaddingRelative(mIsMobileTypeIconWide ? mWideTypeIconStartPadding : 0, 0, 0, 0);
257
258        if (DEBUG) Log.d(TAG,
259                String.format("mobile: %s sig=%d typ=%d",
260                    (mMobileVisible ? "VISIBLE" : "GONE"),
261                    mMobileStrengthId, mMobileTypeId));
262
263        mMobileType.setVisibility(mMobileTypeId != 0 ? View.VISIBLE : View.GONE);
264
265        boolean anythingVisible = mWifiVisible || mIsAirplaneMode || mMobileVisible || mVpnVisible;
266        setPaddingRelative(0, 0, anythingVisible ? mEndPadding : mEndPaddingNothingVisible, 0);
267    }
268}
269
270