Когда мы имеет дело с множеством кнопок в приложении, то нужно позаботиться об обработке событий. В данной статье мы рассмотрим работу с OnClickListener, варианты создания разных обработчиков событий и возможные пути идентификации конкретной кнопки. Так же мы рассмотрим преимущества и недостатки этих подходов, в некоторых случая они очень существенны, а в некоторых нет.
setOnClickListener метод. В параметре передается класс реализующий OnClickListener интерфейс, который имеет единственный метод onClick(View v). Установку обработчика для кнопок следует выполнять в onCreate() методе Activity.
Анонимный класс
Самый простой способ создания обработчика это использование анонимного класса.
mButton.setOnClickListener(new OnClickListener() {
@Override
public void onClick(View v) {
// ...
}
});
Преимуществом такого подхода является простота и не требует создания дополнительных переменных. Очень хорошо подходит, если у вас только одна кнопка. Недостатками является внутренняя реализация, обработчик нельзя задать в другом месте и при наличии нескольких кнопок, такой подход становиться массивным. Так же недостатком является то, что обработчик будет использоваться только данной кнопкой.
Поле типа OnClickListener
Вместо анонимного класса мы может определить поле с типа OnClickListener и сразу же его инициализировать:
private OnClickListener mButtonClickListener = new OnClickListener() {
@Override
public void onClick(View v) {
// ...
}
};
Здесь мы получает одновременное определение и реализацию. Далее созданное поле можно передать кнопке в качестве обработчика:
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mButton.setOnClickListener(mButtonClickListener);
}
По сравнению с анонимными классом, использовать поле типа OnClickListener более удобнее. Преимуществом является легкая установка обработчика сразу нескольким кнопкам и одновременное определение с реализацией. Реализация может располагаться в любом месте. Недостатком является создание поля, а именно экземпляра класса и при этом, он может иметь другие методы, но они будут не видны из вне.
Вложенный класс
При таком подходе создается вложенный класс реализующий OnClickListener интерфейс:
private class ButtonClickListener implements OnClickListener {
@Override
public void onClick(View v) {
// ...
}
}
После создание класса обработчика, его можно установить для каждой кнопки следующим образом:
private ButtonClickListener mButtonClickListener;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mButtonClickListener = new ButtonClickListener();
mButton.setOnClickListener(mButtonClickListener);
}
Преимуществом является простая установка в setOnClickListener методе и то, что класс может иметь другие методы, к которым можно обращается. Недостатком является обязательное определение класса и отведение отдельного поля для хранения созданного экземпляра.
Activity с реализацией OnClickListener
Activity может сама реализовывать интерфейс OnClickListener, тогда при установки обработчика передается this. Сначала нужно сообщить, что Activity будет реализовывать интерфейс:
public class MainActivity extends Activity implements OnClickListener {
@Override
public void onClick(View v) {
// ...
}
}
Чтобы установить обработчик, нужно передать this нашей Activity в качестве параметра:
mButton.setOnClickListener(this);
Если с кнопкой в дальнейшем не производиться никаких действий, то можно не создавать ее экземпляр и установка обработчика будет следующей:
findViewById(R.id.about).setOnClickListener(this);
Если нужно установить обработчик во внутреннем классе, то нужно передать в качестве параметра MainActivity.this.
findViewById(R.id.about).setOnClickListener(MainActivity.this);
Такой подход обработки нажатий более простой, удобный и наиболее предпочтительный, а так же не создает дополнительных полей или классов.
Использование одного обработчика
Было бы не разумно создавать для каждой кнопки свой обработчик, а постараться использовать уже созданный. Для определения конкретной нажатой кнопки, можно использовать getId() метод. Этот метод будет возвращать идентификатор нажатой кнопки, а мы сможем выполнить дальнейшею логику соответственно кнопки:
@Override
public void onClick(View v) {
switch(v.getId()) {
case R.id.home:
// ...
break;
case R.id.message:
// ...
break;
case R.id.email:
// ...
break;
}
}
Вы можете использовать фигурные скобки для лучшего разделения кода:
@Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.about: {
// ...
break;
}
case R.id.abs__action_bar: {
// ...
break;
}
case R.id.abs__action_bar_container: {
// ...
break;
}
}
}
Рассмотренные подходы обработки нажатий можно применять не только для кнопок, но и для других элементов, например таких как ListView и GridView.
Если я не ошибаюсь первый и второй случай мы создаем обработчик при помощи анонимного класса. Просто в первом случае это написано более кратко. Или я не прав?
ОтветитьУдалить