Cicerone ("чи-че-ро́-не" - устар. гид) - легкая библиотека для простой реализации навигации в андроид приложении.
Разработана для использования в MVP архитектуре (попробуйте Moxy), но легко встраивается в любые решения.
- не завязана на Fragment'ы
- не фреймворк
- короткие вызовы навигации (никаких билдеров)
- lifecycle-безопасна!
- простое расширение функционала
- приспособлена для Unit тестов
Добавьте в build.gradle зависимость:
dependencies {
//Cicerone
compile 'ru.terrakok.cicerone:cicerone:X.X.X'
}
И инициализируйте библиотеку, например, так:
public class SampleApplication extends MvpApplication {
public static SampleApplication INSTANCE;
private Cicerone<Router> cicerone;
@Override
public void onCreate() {
super.onCreate();
INSTANCE = this;
initCicerone();
}
private void initCicerone() {
cicerone = Cicerone.create();
}
public NavigatorHolder getNavigatorHolder() {
return cicerone.getNavigatorHolder();
}
public Router getRouter() {
return cicerone.getRouter();
}
}
Presenter вызывает у Router метод навигации.
public class SamplePresenter extends Presenter<SampleView> {
private Router router;
public SamplePresenter() {
router = SampleApplication.INSTANCE.getRouter();
}
public void onBackCommandClick() {
router.exit();
}
public void onForwardCommandClick() {
router.navigateTo("Some screen");
}
}
Router - класс, который реализует вызванный метод навигации набором Command и отправляет их в CommandBuffer. CommandBuffer проверяет есть ли "активный" Navigator. Если да, то на нем вызываются необходимые команды для осуществления запрошенного перехода. Если нет, то команды добавляются в очередь, которая будет применена, как только появится "активный" Navigator.
protected void executeCommand(Command command) {
if (navigator != null) {
navigator.applyCommand(command);
} else {
pendingCommands.add(command);
}
}
Navigator - (например) анонимный класс внутри Activity, который реализует команды навигации. Activity предоставляет свой Navigator для CommandBuffer в методе onResume и очищает в onPause
Внимание: В FragmentActivity следует использовать onResumeFragments(). (подробнее)
@Override
protected void onResume() {
super.onResume();
SampleApplication.INSTANCE.getNavigatorHolder().setNavigator(navigator);
}
@Override
protected void onPause() {
super.onPause();
SampleApplication.INSTANCE.getNavigatorHolder().removeNavigator();
}
private Navigator navigator = new Navigator() {
@Override
public void applyCommand(Command command) {
//implements commands logic
}
};
Навигатор не обязан быть в Activity. Он может быть и внутри Fragment'а, который переключает внутри себя View.
Для большинства задач предоставленных в библиотеке команд должно хватить, но их всегда можно дополнить собственными!
- Forward - переход на новый экран
- Back - возврат на предыдущий экран
- BackTo - возврат к конкретному экрану в цепочке, либо на корневой, если указанный экран не найден
- Replace - замена текущего экрана на новый
- SystemMessage - показ системного сообщения (Alert, Toast, Snack и тд)
Библиотека предоставляет готовые навигаторы для Activity. Чтобы их использовать, достаточно указать контейнер и передать FragmentManager.
private Navigator navigator = new SupportFragmentNavigator(
getSupportFragmentManager(), R.id.main_container) {
@Override
protected Fragment createFragment(String screenKey, Object data) {
return SampleFragment.getNewInstance((int) data);
}
@Override
protected void showSystemMessage(String message) {
Toast.makeText(MainActivity.this, message, Toast.LENGTH_SHORT).show();
}
@Override
protected void exit() {
finish();
}
};
Работу библиотеки, готовых навигаторов и другое можно посмотреть в sample приложении.
- идея и реализация - Константин Цховребов (@terrakok)
- архитектурные советы, документация и публикация - Василий Чирвон (@Jeevuz)
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.