Chỉ định android:onClick
kết quả thuộc tính trong Button
ví dụ gọi setOnClickListener
nội bộ. Do đó hoàn toàn không có sự khác biệt.
Để hiểu rõ hơn, chúng ta hãy xem cách onClick
thuộc tính XML được xử lý bởi khung công tác.
Khi tệp bố cục bị thổi phồng, tất cả các Chế độ xem được chỉ định trong đó sẽ được khởi tạo. Trong trường hợp cụ thể này, Button
thể hiện được tạo bằng cách sử dụng hàm public Button (Context context, AttributeSet attrs, int defStyle)
tạo. Tất cả các thuộc tính trong thẻ XML được đọc từ gói tài nguyên và được chuyển AttributeSet
cho hàm tạo.
Button
lớp được kế thừa từ View
lớp dẫn đến hàm View
tạo được gọi, trong đó đảm nhiệm việc thiết lập trình xử lý gọi lại nhấp qua setOnClickListener
.
Thuộc tính onClick được xác định trong attrs.xml , được gọi trong View.java là R.styleable.View_onClick
.
Đây là mã của View.java
hầu hết các công việc cho bạn bằng cách gọi setOnClickListener
bằng chính nó.
case R.styleable.View_onClick:
if (context.isRestricted()) {
throw new IllegalStateException("The android:onClick attribute cannot "
+ "be used within a restricted context");
}
final String handlerName = a.getString(attr);
if (handlerName != null) {
setOnClickListener(new OnClickListener() {
private Method mHandler;
public void onClick(View v) {
if (mHandler == null) {
try {
mHandler = getContext().getClass().getMethod(handlerName,
View.class);
} catch (NoSuchMethodException e) {
int id = getId();
String idText = id == NO_ID ? "" : " with id '"
+ getContext().getResources().getResourceEntryName(
id) + "'";
throw new IllegalStateException("Could not find a method " +
handlerName + "(View) in the activity "
+ getContext().getClass() + " for onClick handler"
+ " on view " + View.this.getClass() + idText, e);
}
}
try {
mHandler.invoke(getContext(), View.this);
} catch (IllegalAccessException e) {
throw new IllegalStateException("Could not execute non "
+ "public method of the activity", e);
} catch (InvocationTargetException e) {
throw new IllegalStateException("Could not execute "
+ "method of the activity", e);
}
}
});
}
break;
Như bạn có thể thấy, setOnClickListener
được gọi để đăng ký gọi lại, như chúng tôi làm trong mã của chúng tôi. Chỉ khác là nó sử dụng Java Reflection
để gọi phương thức gọi lại được xác định trong Hoạt động của chúng tôi.
Dưới đây là lý do cho các vấn đề được đề cập trong các câu trả lời khác:
- Phương thức gọi lại phải công khai : Vì
Java Class getMethod
được sử dụng, nên chỉ các chức năng với công cụ xác định truy cập công cộng được tìm kiếm. Nếu không hãy sẵn sàng để xử lý IllegalAccessException
ngoại lệ.
- Trong khi sử dụng Nút với onClick in Fragment, cuộc gọi lại phải được xác định trong Activity :
getContext().getClass().getMethod()
cuộc gọi giới hạn tìm kiếm phương thức trong bối cảnh hiện tại, đó là Activity trong trường hợp Fragment. Do đó phương thức được tìm kiếm trong lớp Activity chứ không phải lớp Fragment.
- Phương thức gọi lại nên chấp nhận Xem tham số : Vì
Java Class getMethod
các tìm kiếm cho phương thức chấp nhận View.class
làm tham số.