1/*
2 * Copyright (C) 2016 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.setupwizardlib.items;
18
19import android.annotation.SuppressLint;
20import android.content.Context;
21import android.content.res.TypedArray;
22import android.util.AttributeSet;
23import android.view.ContextThemeWrapper;
24import android.view.LayoutInflater;
25import android.view.View;
26import android.view.ViewGroup;
27import android.widget.Button;
28
29import com.android.setupwizardlib.R;
30
31/**
32 * Description of a button inside {@link com.android.setupwizardlib.items.ButtonBarItem}. This item
33 * will not be bound by the adapter, and must be a child of {@code ButtonBarItem}.
34 */
35public class ButtonItem extends AbstractItem implements View.OnClickListener {
36
37    public interface OnClickListener {
38        void onClick(ButtonItem item);
39    }
40
41    private boolean mEnabled = true;
42    private CharSequence mText;
43    private int mTheme = R.style.SuwButtonItem;
44    private OnClickListener mListener;
45
46    private Button mButton;
47
48    public ButtonItem() {
49        super();
50    }
51
52    public ButtonItem(Context context, AttributeSet attrs) {
53        super(context, attrs);
54        TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.SuwButtonItem);
55        mEnabled = a.getBoolean(R.styleable.SuwButtonItem_android_enabled, true);
56        mText = a.getText(R.styleable.SuwButtonItem_android_text);
57        mTheme = a.getResourceId(R.styleable.SuwButtonItem_android_theme, R.style.SuwButtonItem);
58        a.recycle();
59    }
60
61    public void setOnClickListener(OnClickListener listener) {
62        mListener = listener;
63    }
64
65    public void setText(CharSequence text) {
66        mText = text;
67    }
68
69    public CharSequence getText() {
70        return mText;
71    }
72
73    /**
74     * The theme to use for this button. This can be used to create button of a particular style
75     * (e.g. a colored or borderless button). Typically {@code android:buttonStyle} will be set in
76     * the theme to change the style applied by the button.
77     *
78     * @param theme Resource ID of the theme
79     */
80    public void setTheme(int theme) {
81        mTheme = theme;
82        mButton = null;
83    }
84
85    /**
86     * @return Resource ID of the theme used by this button.
87     */
88    public int getTheme() {
89        return mTheme;
90    }
91
92    public void setEnabled(boolean enabled) {
93        mEnabled = enabled;
94    }
95
96    @Override
97    public int getCount() {
98        return 0;
99    }
100
101    @Override
102    public boolean isEnabled() {
103        return mEnabled;
104    }
105
106    @Override
107    public int getLayoutResource() {
108        return 0;
109    }
110
111    /**
112     * Do not use this since ButtonItem is not directly part of a list.
113     */
114    @Override
115    public final void onBindView(View view) {
116        throw new UnsupportedOperationException("Cannot bind to ButtonItem's view");
117    }
118
119    /**
120     * Create a button according to this button item.
121     *
122     * @param parent The parent of the button, used to retrieve the theme and context for this
123     *               button.
124     * @return A button that can be added to the parent.
125     */
126    protected Button createButton(ViewGroup parent) {
127        if (mButton == null) {
128            Context context = parent.getContext();
129            if (mTheme != 0) {
130                context = new ContextThemeWrapper(context, mTheme);
131            }
132            mButton = createButton(context);
133            mButton.setOnClickListener(this);
134        } else {
135            if (mButton.getParent() instanceof ViewGroup) {
136                // A view cannot be added to a different parent if one already exists. Remove this
137                // button from its parent before returning.
138                ((ViewGroup) mButton.getParent()).removeView(mButton);
139            }
140        }
141        mButton.setEnabled(mEnabled);
142        mButton.setText(mText);
143        mButton.setId(getViewId());
144        return mButton;
145    }
146
147    @Override
148    public void onClick(View v) {
149        if (mListener != null) {
150            mListener.onClick(this);
151        }
152    }
153
154    @SuppressLint("InflateParams")  // This is used similar to Button(Context), so it's OK to not
155                                    // specify the parent.
156    private Button createButton(Context context) {
157        // Inflate a single button from XML, so that when using support lib, it will take advantage
158        // of the injected layout inflater and give us AppCompatButton instead.
159        return (Button) LayoutInflater.from(context).inflate(R.layout.suw_button, null, false);
160    }
161}
162