@Vermut756

Не понимаю, как в суппорт-либе v7 перехватить нажатие home/up, если у меня свой тулбар с ActionBarDrawerToggle?

Дано: AppCompatActivity. Со своим тулбаром с DrawerLayout и кнопкой-гамбургером. И фрагмент в этой активити, Во фрагменте в какой-то момент юзер открывает всплывающий интерфейс.

Требуется: реализовать закрытие интерфейса двумя способами - железный back и кнопка home/up.
То есть при открытии гамбургер меняется на стрелочку назад. А при ее нажатии всплывающий интерфейс прячется, и снова возвращается гамбургер, который снова может открывать DrawerLayout.

С железным backом сразу заметил проблему. onBackPressed работает только в активити. А тут фрагмент, чтобы в него передать - надо городить что-то вроде своего листенера, а это не так просто из-за довольно сложного лайфцикла. Нужно хорошо подумать, чтобы не привело к подводным камням.
Поэтому решил back пока отложить. Занялся стрелочкой, это вроде проще: уже делал через onOptionsItemSelected и android.R.id.home, а это должно работать и во фрагменте. Как же я ошибался(((

Нет, во фрагменте-то оно работает. Но не работает по другой причине - из-за гамбургера с DrawerLayout, которые сделаны через создание ActionBarDrawerToggle, а он все меняет, и onOptionsItemSelected вообще не вызывается при нажатии home/up, даже после того, как я вызвал setDisplayHomeAsUpEnabled(true).
Покопав форумы и исходный код, нашел решение:
toolbar.setNavigationOnClickListener(new OnClickListener() {
			@Override
			public void onClick(View arg0) {
				// TODO Auto-generated method stub
			}
});


Но это опять головная боль, ведь сразу же возникает вопрос - а где ставить обратно старый листенер?
Да и как его ставить? Точнее, как сохранить старый листенер в буфер?
Никакого метода getNavigationOnClickListener() я не нашел. Решил реализовать с помощью toolbar.getChildAt и поиска того Child, который ImageButton, это и есть та кнопка. Но это уже не совсем чистый хак, а еще и оказалось, что ни ImageButton, ни View тоже не имеют метода getOnClickListener! Это так заложено еще в самом Android, и обойти это можно только через - о ужас- рефлексию... Занавес.

Получается, мне нужно сначала toolbar.setNavigationOnClickListener, затем заново создавать ActionBarDrawerToggle - потому что другого способа вернуть старый обработчик просто не существует - и где все это делать?
Логика подсказывает, что в Activity, объявив 2 соответствующих метода, но обращаться к ним из фрагмента, это опять головная боль, ведь getActivity может и null возвращать, может получиться и так, что фрагмент пересоздастся, всплывающий интерфейс пропадет, но все это произойдет не при нажатии стрелочки, а когда Android захочет очистить память, ну или еще как-то, поэтому вместо гамбургера навсегда останется стрелочка...

Нет слов. Одни эмоции. Ненависть. Тонны ненависти к тем, кто писал суппорт либу и мерзопакостный ActionBarDrawerToggle. Почему они сломали столь удобный onItemSelected, доступный и во фрагментах, и не дали ничего адекватного взамен? Почему???

У меня уже голова пухнет, а мне еще железный back делать....
С onBackPressed тоже "хорошо", почему его нет во фрагментах, даже версии суппорт v4, а еще более новой версии базового класса для фрагмента просто не существует??? Что им, сложно было?
  • Вопрос задан
  • 221 просмотр
Решения вопроса 1
zagayevskiy
@zagayevskiy Куратор тега Java
Android developer at Yandex
Курите жизненный цикл фрагментов и взаимодействуте через активити. На дровер навесьте листенер, который будет звать onBackPressed у активити, а она уже прокидывает во фрагменты (через свой базовый класс BaseFragment или типа того, от которого наследуйте все фрагменты).
Ответ написан
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы