【发布时间】:2015-03-08 21:46:54
【问题描述】:
我正在编写一个实现 Checkable 接口的按钮。我重写了方法:performClick,但它没有被调用。根据文档中提到的:
从类中复制的描述:android.view.View 如果已定义,则调用此视图的 OnClickListener。执行与点击相关的所有正常操作:报告可访问性事件、播放声音等。
我认为当我点击屏幕上的按钮时系统应该会自动调用它。但什么也没发生。还是我必须自己调用?
我有以下代码:
public class MyButton extends Button implements Checkable {
private static final String TAG = "MyButton";
private boolean mChecked;
private boolean mBroadcasting;
private OnCheckedChangeListener mOnCheckedChangeListener;
private OnCheckedChangeListener mOnCheckedChangeWidgetListener;
private static final int[] CHECKED_STATE_SET = {
android.R.attr.state_checked
};
public MyButton(Context context) {
this(context, null);
}
public MyButton(Context context, AttributeSet attrs) {
this(context, attrs, 0);
}
public MyButton(Context context, AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
Log.i(TAG, "begin to paint lines");
Paint paint = getPaint();
paint.setColor(android.graphics.Color.BLACK);
canvas.drawLine(0, 0, this.getWidth(), 0, paint);
canvas.drawLine(0, 0, 0, this.getHeight(), paint);
canvas.drawLine(this.getWidth(), 0, this.getWidth(), this.getHeight(), paint);
canvas.drawLine(0, this.getHeight(), this.getWidth(), this.getHeight(), paint);
}
@Override
public void onInitializeAccessibilityEvent(AccessibilityEvent event) {
super.onInitializeAccessibilityEvent(event);
event.setClassName(MyButton.class.getName());
}
@Override
public void onInitializeAccessibilityNodeInfo(AccessibilityNodeInfo info) {
super.onInitializeAccessibilityNodeInfo(info);
info.setClassName(MyButton.class.getName());
}
@Override
public boolean performClick() {
toggle();
Log.i(TAG, "the view was clicked");
return super.performClick();
}
@Override
public void setChecked(boolean checked) {
if (mChecked != checked) {
mChecked = checked;
refreshDrawableState();
// Avoid infinite recursions if setChecked() is called from a listener
if (mBroadcasting) {
return;
}
mBroadcasting = true;
if (mOnCheckedChangeListener != null) {
mOnCheckedChangeListener.onCheckedChanged(this, mChecked);
}
if (mOnCheckedChangeWidgetListener != null) {
mOnCheckedChangeWidgetListener.onCheckedChanged(this, mChecked);
}
mBroadcasting = false;
}
}
@Override
public boolean isChecked() {
return mChecked;
}
@Override
public void toggle() {
setChecked(!mChecked);
Log.i(TAG, "the view was toggled");
}
@Override
protected int[] onCreateDrawableState(int extraSpace) {
int[] drawableState = super.onCreateDrawableState(extraSpace);
if (isChecked()) {
mergeDrawableStates(drawableState, CHECKED_STATE_SET);
}
return drawableState;
}
public OnCheckedChangeListener getOnCheckedChangeListener() {
return mOnCheckedChangeListener;
}
public void setOnCheckedChangeListener(OnCheckedChangeListener mOnCheckedChangeListener) {
this.mOnCheckedChangeListener = mOnCheckedChangeListener;
}
public OnCheckedChangeListener getOnCheckedChangeWidgetListener() {
return mOnCheckedChangeWidgetListener;
}
public void setOnCheckedChangeWidgetListener(OnCheckedChangeListener mOnCheckedChangeWidgetListener) {
this.mOnCheckedChangeWidgetListener = mOnCheckedChangeWidgetListener;
}
/**
* Interface definition for a callback to be invoked when the checked state
* of a compound button changed.
*/
public static interface OnCheckedChangeListener {
/**
* Called when the checked state of a compound button has changed.
*
* @param buttonView The compound button view whose state has changed.
* @param isChecked The new checked state of buttonView.
*/
void onCheckedChanged(MyButton buttonView, boolean isChecked);
}
}
布局中的MyButton:
<com.example.demo.view.MyButton
android:id="@+id/mybtn"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:background="@drawable/checkable_button"
android:textColor="@drawable/button_text"
android:text="checkable" />
先谢谢你了。
第一个答案是正确的。
解释:
public MyButton(Context context, AttributeSet attrs) 这个是 叫。然后它调用 MyButton(context, attrs, 0)。这是哪里 defStyleAttr 被设置为 0,而默认情况下它将是 com.android.internal.R.attr.buttonStyle.
【问题讨论】: