本文へ移動
cccskills
無料GitHub で公開

edge-to-edge

RIPDPI's edge-to-edge and window-inset rules for Compose screens, scaffolds, sheets, and the single enableEdgeToEdge() call site. Use for insets, system bars, or edge-to-edge layout here.

インストール方法を見る

含まれるファイル(1)

  • SKILL.md6.9 KB

SKILL.md(原文)

インストールする前に、エージェントに与えられる指示の中身を確認できます。

Edge-to-Edge on RIPDPI

Read ripdpi.targetSdk and ripdpi.compileSdk from gradle.properties before auditing. When the live target is API 35 or newer, Android 15+ enforces edge-to-edge regardless of theme flags — any screen that wraps content without inset handling will clip under the status or navigation bars.

The single entry point

app/src/main/kotlin/com/poyka/ripdpi/activities/MainActivity.kt is the only call site; locate onCreate by symbol rather than retaining a line-number snapshot:

override fun onCreate(savedInstanceState: Bundle?) {
    val splashScreen = installSplashScreen()
    enableEdgeToEdge()
    super.onCreate(savedInstanceState)
    ...
}

Rule: installSplashScreen() must run before enableEdgeToEdge(), and both must run before super.onCreate(...). Read the active splashscreen version from gradle/libs.versions.toml; the splash overlay lifecycle must attach before the activity window switches to edge-to-edge mode.

Do not call enableEdgeToEdge() from a second activity, a Compose entry, or a @Composable effect. The activity owns the window.

Choosing the right inset source in Compose

For any composable that touches a screen edge, you must pick one inset source:

InsetWhen to useNotes
WindowInsets.safeDrawingDefault for most content surfaces. Union of system bars + display cutout + IME.What you want unless you have a specific reason otherwise.
WindowInsets.systemBarsOnly the status + navigation bars. Use when you explicitly want to draw under a display cutout.Rare in RIPDPI; status bar is the common case.
WindowInsets.navigationBarsBottom nav only. Use for a custom bottom bar that should sit above the system nav gesture area.See BottomNavBar.kt for the anchor.
WindowInsets.statusBarsTop system bar only. Rare — prefer safeDrawing so cutouts are handled.Use when you want to draw behind the status bar but respect the nav bar normally.
WindowInsets.imeKeyboard insets.Combine with others via union() for fields that must stay above the keyboard.

windowInsetsPadding vs safeDrawingPadding

Modifier.windowInsetsPadding(WindowInsets.navigationBars)   // only nav bar
Modifier.safeDrawingPadding()                               // safeDrawing shortcut

safeDrawingPadding() is the convenience modifier for windowInsetsPadding(WindowInsets.safeDrawing). Prefer it on root containers. Use windowInsetsPadding(...) with an explicit inset source only when you need a specific subset (e.g. a bottom bar that handles just the nav bar, so the status bar is handled by the content above it).

Do not stack padding modifiers that apply overlapping insets — safeDrawingPadding() + windowInsetsPadding(WindowInsets.statusBars) double-pads the top. One modifier per axis, and let the composable tree handle the rest via consumeWindowInsets.

Bottom sheets, dialogs, and the nav bar

RipDpiBottomSheet.kt and BottomNavBar.kt are the two bottom-edge anchor files. When authoring a new bottom sheet or modifying an existing one:

  1. The sheet container itself is responsible for bottom inset padding. Its parent must not consume the nav bar inset first, or the sheet will be paddless.
  2. Use WindowInsets.navigationBarsIgnoringVisibility for bottom sheets that must remain fixed even when the gesture nav pill transiently hides. This is the difference between a nav bar that briefly disappears during scroll and a sheet that jumps 24dp.
  3. For the IME interaction: WindowInsets.ime.union(WindowInsets.navigationBars) on the sheet container ensures fields remain visible above the keyboard on devices where the IME doesn't fully overlap the nav bar.

Scaffold caveats

Material 3 Scaffold handles insets for its own top bar, bottom bar, and FAB slots. Read the active Compose BOM from gradle/libs.versions.toml before making version-specific claims. If you put a custom bar outside a Scaffold slot and provide a topBar or bottomBar at the same time, you are inset-padding twice. Pick one:

  • Use Scaffold slots and let it handle insets → don't add padding modifiers to the slot content.
  • Don't use Scaffold slots and handle insets manually on your custom bars.

Mixing produces the classic "my bottom bar sits 48dp too high" regression.

Splash screen handoff

The splashscreen library keeps the splash visible until setKeepOnScreenCondition { ... } returns false. In MainActivity.onCreate, locate the current condition and verify that it follows viewModel.startupState.value.isReady; do not rely on a stored line number. The splash overlay sits on top of the activity window, so edge-to-edge enforcement on MainActivityContent does not affect what the user sees during splash.

Gotcha: if you ever migrate away from installSplashScreen() to a custom splash composable, you must add inset handling to the custom composable yourself — it no longer has the splash library's overlay to hide behind.

Verification

After any edge-to-edge change:

  1. Visually verify on API 35 and API 30 emulators (Android 15 and Android 11). API 35 shows enforcement; API 30 shows the pre-enforcement behavior and confirms your rule doesn't break older OS versions.
  2. Toggle gesture vs 3-button nav in the emulator (Settings → System → Gestures). Content must not clip under either nav style.
  3. For any screen that takes keyboard input, open the IME and confirm the focused field stays visible. Run the existing Maestro flow maestro/03-advanced-settings-edit-save.yaml as a spot check for form-field insets.
  4. Roborazzi screenshots at app/src/test must be re-recorded if inset padding on a visible surface changed: ./gradlew recordScreenshots then review the diff.

Out of scope

  • Custom status-bar / nav-bar colors. The design system (docs/design-system.md) owns theming; edge-to-edge is about inset math, not color.
  • Pre-API-30 behavior beyond the emulator spot check. minSdk = 27 means the app runs on older OSes, but R-era inset APIs are the baseline; earlier system-ui-visibility flags are not used and must not be introduced.
  • Window manager layout params (FLAG_LAYOUT_NO_LIMITS, SOFT_INPUT_ADJUST_*). These are legacy and must not be added; modern edge-to-edge uses the Compose inset system exclusively.

External reference

Run android skills edge-to-edge for Google's generic edge-to-edge skill covering API surface background, cross-version inset compat, and the View-system equivalents. Use it alongside this RIPDPI-specific skill for context on why the API shape looks the way it does. This skill is the project-specific authority for where and how to apply insets in RIPDPI's Compose tree.

レビュー

まだレビューはありません。使ってみた感想をお寄せください。

同じリポジトリのスキル

概要と使いどころ

RIPDPI's own Compose conventions: ViewModel pattern, Route/Screen split, DataStore->StateFlow, RipDpiThemeTokens. Use for how this app does Compose, not generic Compose API questions (see compose).

日本語の概要は準備中です。原文の説明を表示しています。

po4yka/RIPDPI792026年10月13日 更新

ADB-based RIPDPI device/emulator debugging: build/install/launch, logcat filtering, fixture port-forwarding, instrumented tests, crash/ANR triage. Use when debugging on a real device or emulator.

日本語の概要は準備中です。原文の説明を表示しています。

po4yka/RIPDPI792026年10月13日 更新

RIPDPI Appium launch-contract reference: start routes and permission/service/data presets. Use when a test launches to the wrong screen or a new automation route is added. General flakiness: appium-test-debug.

日本語の概要は準備中です。原文の説明を表示しています。

po4yka/RIPDPI792026年10月13日 更新

RIPDPI Appium test authoring: page objects, resource-id locators, assertions, wait tiers. Use when writing a new Appium test or page object, or adding coverage for a new screen.

日本語の概要は準備中です。原文の説明を表示しています。

po4yka/RIPDPI792026年10月13日 更新

RIPDPI Appium failure triage: flaky tests, locator/session/wait issues, screenshot and element-tree debugging. Use when an Appium test fails or is flaky.

日本語の概要は準備中です。原文の説明を表示しています。

po4yka/RIPDPI792026年10月13日 更新

Add or modify a GitHub Actions job. Use when editing a file under .github/workflows/. Not for running a workflow locally (local-ci-act) or release signing (release-signing).

日本語の概要は準備中です。原文の説明を表示しています。

po4yka/RIPDPI792026年10月13日 更新

po4yka のスキルをすべて見る

このスキルの問題を報告する