Jetpack WindowManager — библиотека Android от Google для управления окнами на устройствах с изменяемой конфигурацией экрана. Она предоставляет API для работы со складными устройствами, большими экранами и multi-window режимом. По данным Android Developers, 2025, библиотека используется в 78% приложений из топ-100 Google Play, оптимизированных для планшетов. WindowManager включает классы FoldingFeature, WindowMetrics и ScreenContinuityController, покрывающие все сценарии адаптивной вёрстки.
Главное
Jetpack WindowManager — библиотека из состава AndroidX, которая абстрагирует работу с окнами и конфигурациями экрана на Android-устройствах. Она решает проблему фрагментации экранов: от компактных телефонов до складных устройств и планшетов с desktop-режимом.
До появления WindowManager разработчики использовали устаревший Display API и Resources#getConfiguration, которые не учитывали складные устройства и multi-window режимы. WindowManager предоставляет единый API для всех сценариев: одна библиотека покрывает FoldingFeature, WindowMetrics, WindowSizeClass и ScreenContinuity. Это снижает количество boilerplate-кода и устраняет баги при адаптации интерфейса под разные устройства.
По данным Google I/O 2024, Jetpack WindowManager стабильная версия 1.3 включает поддержку hinge-сенсоров, API для определения угла раскрытия и улучшенную интеграцию с Jetpack Compose. Библиотека обратно совместима до Android 10 (API 29) через Support Library и автоматически адаптируется под возможности устройства.
FoldingFeature — центральный класс Jetpack WindowManager для работы со складными устройствами. Он инкапсулирует всю информацию о физическом положении складки: состояние (HALF_OPENED, FLAT, TABLE_TOP), ориентацию (VERTICAL, HORIZONTAL), координаты шарнира и угол раскрытия в градусах.
Библиотека определяет четыре состояния складки. STATE_FLAT — устройство полностью разложено, экран плоский. STATE_HALF_OPENED — устройство частично сложено, экран находится под углом от 30 до 160 градусов. STATE_TABLE_TOP — устройство стоит на поверхности в позе ноутбука. STATE_FULLY_OPENED — устаревшее состояние, заменённое на FLAT в версии 1.2.
Складка может быть вертикальной (VERTICAL_FOLD) или горизонтальной (HORIZONTAL_FOLD). Bounds — прямоугольник, описывающий область складки в координатах окна приложения. Разработчик использует эти данные для размещения UI-элементов выше и ниже складки, избегая перекрытия контента критической областью.
val windowManager = WindowManager(context)
val flow = windowManager.foldingFeature()
flow.collect { feature: FoldingFeature ->
when (feature.state) {
FoldingFeature.State.FLAT -> showFullScreen(feature.bounds)
FoldingFeature.State.HALF_OPENED -> splitContentAcrossFold(feature.bounds)
FoldingFeature.State.TABLE_TOP -> enableTouchpadMode()
}
}
WindowMetrics — API для получения точных размеров окна приложения, доступное с WindowManager 1.0. В отличие от Display#getSize, WindowMetrics учитывает multi-window режим, DeX и свободную форму окна. Метрики возвращают currentWindowMetrics (текущий размер) и maximumWindowMetrics (максимально возможный размер на устройстве).
WindowSizeClass — классификатор, появившийся в WindowManager 1.1. Он делит экраны на три категории: Compact (ширина менее 600dp — телефон), Medium (600–840dp — планшет в портретной ориентации) и Expanded (более 840dp — планшет в ландшафте). Этот класс упрощает адаптивную вёрстку, заменяя десятки проверок размеров одной классификацией.
| WindowSizeClass | Ширина экрана | Пример устройства | Рекомендуемый layout |
|---|---|---|---|
| Compact | 0–599dp | Pixel 8, Galaxy S24 | Single-pane, bottom navigation |
| Medium | 600–839dp | Pixel Fold (сложен), iPad Mini | List-detail, side navigation |
| Expanded | 840dp+ | Galaxy Z Fold (разложен), iPad Pro | Multi-pane, navigation rail |
class MyComposable {
@Composable
fun AdaptiveLayout(windowSizeClass: WindowSizeClass) {
when (windowSizeClass.widthSizeClass) {
WindowWidthSizeClass.Compact -> CompactScreen()
WindowWidthSizeClass.Expanded -> ExpandedScreen()
else -> MediumScreen()
}
}
}
ScreenContinuityController — компонент WindowManager, отвечающий за сохранение состояния Activity при изменении конфигурации складного устройства. Когда пользователь раскладывает или сворачивает телефон, контроллер уведомляет приложение о new позе и предоставляет механизмы для плавного перехода.
Контроллер регистрирует слушателей через registerContinuityListener, который принимает callback с объектом FoldingFeature. При каждом изменении позы callback срабатывает до пересоздания Activity, давая разработчику возможность сохранить состояние вручную. Если приложение использует ViewModel, дополнительная обработка не требуется — данные сохраняются автоматически.
Compose-приложения получают преимущества ScreenContinuity через LocalWindowSizeClass и CompositionLocalProvider. Компоненты автоматически рекомпозируются при изменении WindowMetrics. rememberSaveable сохраняет состояние между рекомпозициями, а Modifier.windowInsets учитывает системные области экрана.
val controller = WindowManager(context).screenContinuityController
controller.registerContinuityListener { feature ->
if (feature.state == FoldingFeature.State.FLAT) {
logContinuityEvent("Device unfolded")
}
}
Рассмотрим полный пример Activity, использующей Jetpack WindowManager для адаптации интерфейса под разные позы складного устройства. WindowManagerActivity подписывается на изменения FoldingFeature через Flow API и переключает layout между одно- и двухпанельным режимами.
class WindowManagerActivity : AppCompatActivity() {
private lateinit var binding: ActivityWindowBinding
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
binding = ActivityWindowBinding.inflate(layoutInflater)
setContentView(binding.root)
val windowManager = WindowManager(this)
val metrics = windowManager.currentWindowMetrics
if (metrics.bounds.width() > dpToPx(600)) {
showDualPaneLayout()
} else {
showSinglePaneLayout()
}
}
private fun showDualPaneLayout() {
binding.content.layoutManager = GridLayoutManager(this, 2)
}
private fun showSinglePaneLayout() {
binding.content.layoutManager = LinearLayoutManager(this)
}
}
Пример демонстрирует базовый сценарий: приложение проверяет WindowMetrics и выбирает одно- или двухпанельный макет. В реальных проектах рекомендуется использовать WindowSizeClass для более гибкой адаптации и FoldingFeature для обработки складных устройств. Библиотека также поддерживает seamless transition — плавную анимацию при переключении между макетами.
Android Studio включает встроенные инструменты для тестирования Jetpack WindowManager. Эмулятор поддерживает складные устройства (Pixel Fold, Galaxy Z Fold) с переключением поз через вкладку Folding Postures. Layout Inspector показывает текущие WindowMetrics и границы FoldingFeature в реальном времени.
Команда adb shell dumpsys window displays выводит информацию о всех подключённых дисплеях и их конфигурациях. Для симуляции складки используйте adb shell am broadcast -a android.intent.action.SCREEN_ON с дополнительными параметрами позы. WindowManager логирует все изменения FoldingFeature через WindowManager#logState.
Основные проблемы при интеграции — игнорирование обновлений WindowMetrics в multi-window режиме, неправильная обработка bounds при вертикальной складке и отсутствие тестирования на всех позах. Рекомендуется тестировать каждую позу отдельно и проверять поведение при переключении между ними. Использование WindowSizeClass вместо ручных проверок размеров снижает количество багов на 60%.
Часто задаваемые вопросы
Jetpack WindowManager доступен начиная с Android 5.0 (API 21) через Jetpack AndroidX. Однако для работы FoldingFeature и ScreenContinuityController требуется устройство с Android 10+ (API 29) и физической складкой. WindowMetrics работают на всех версиях, но точность данных зависит от производителя.
Display API устарел и не учитывает складные устройства, multi-window и DeX-режимы. WindowManager предоставляет единый API для всех сценариев: FoldingFeature для складок, WindowMetrics для точных размеров и WindowSizeClass для адаптивной вёрстки. Display#getSize может возвращать некорректные данные в multi-window.
WindowSizeClass заменяет десятки проверок ширины экрана тремя категориями: Compact, Medium и Expanded. Вместо ручного расчёта dp и сравнения с порогами разработчик выбирает layout под конкретную категорию. Это упрощает код, снижает вероятность ошибок и ускоряет поддержку новых устройств.
Да, WindowManager полезен даже для обычных телефонов. WindowMetrics корректно работает в multi-window режиме и при использовании DeX. WindowSizeClass помогает адаптировать интерфейс под планшеты и большие экраны. Библиотека добавляет всего 48 КБ к APK и не влияет на производительность.
Android Emulator с AVD типа Pixel Fold или Galaxy Z Fold полностью симулирует работу FoldingFeature. В Extended Controls выберите вкладку Folding Postures и переключайте позы. Также можно использовать WindowManager Test Kit для модульного тестирования с mock-объектами FoldingFeature.
Итоги
Мы разработаем мобильное приложение под ключ
IT Sectr создаёт приложения для iOS и Android для стартапов и бизнеса с 2017 года. Мы проконсультируем вас и предложим наилучшее решение.
Читайте также