{"record":{"id":"6cc3ff1ef09e43a8","repo":"material-components/material-components-android","slug":"offset-must-be-greater-than-or-equal-to-0","errorCode":null,"errorMessage":"offset must be greater than or equal to 0","messagePattern":"offset must be greater than or equal to 0","errorType":"exception","errorClass":"IllegalArgumentException","httpStatus":null,"severity":"error","filePath":"lib/java/com/google/android/material/bottomsheet/BottomSheetBehavior.java","lineNumber":1201,"sourceCode":"   */\n  @FloatRange(from = 0.0f, to = 1.0f)\n  public float getHalfExpandedRatio() {\n    return halfExpandedRatio;\n  }\n\n  /**\n   * Determines the top offset of the BottomSheet in the {@link #STATE_EXPANDED} state when\n   * fitsToContent is false. The default value is 0, which results in the sheet matching the\n   * parent's top.\n   *\n   * @param offset an integer value greater than equal to 0, representing the {@link\n   *     #STATE_EXPANDED} offset. Value must not exceed the offset in the half expanded state.\n   * @attr ref\n   *     com.google.android.material.R.styleable#BottomSheetBehavior_Layout_behavior_expandedOffset\n   */\n  public void setExpandedOffset(int offset) {\n    if (offset < 0) {\n      throw new IllegalArgumentException(\"offset must be greater than or equal to 0\");\n    }\n    this.expandedOffset = offset;\n    updateDrawableForTargetState(state, /* animate= */ true);\n  }\n\n  /**\n   * Returns the current expanded offset. If {@code fitToContents} is true, it will automatically\n   * pick the offset depending on the height of the content.\n   *\n   * @attr ref\n   *     com.google.android.material.R.styleable#BottomSheetBehavior_Layout_behavior_expandedOffset\n   */\n  public int getExpandedOffset() {\n    return fitToContents\n        ? fitToContentsOffset\n        : Math.max(expandedOffset, paddingTopSystemWindowInsets ? 0 : insetTop);\n  }\n","sourceCodeStart":1183,"sourceCodeEnd":1219,"githubUrl":"https://github.com/material-components/material-components-android/blob/ac7e18efeefb331850c561faf9ab8bf81d27ba68/lib/java/com/google/android/material/bottomsheet/BottomSheetBehavior.java#L1183-L1219","documentation":"BottomSheetBehavior.setExpandedOffset(int) sets the top offset in pixels of the sheet in STATE_EXPANDED when fitToContents is false. Offsets are measured downward from the parent top, so only values >= 0 are valid; a negative offset throws IllegalArgumentException.","triggerScenarios":"Calling setExpandedOffset(-1) or any negative pixel value; computing the offset from status bar / window inset arithmetic that evaluates negative on edge-case devices; reading the offset from a dimension that resolves negative.","commonSituations":"Subtracting insets (getStatusBarHeight(), WindowInsets) in the wrong order so the result goes below zero; treating the offset as 'distance upward from the bottom' rather than 'distance downward from the top'; copying a negative value from old layout XML after a refactor.","solutions":["Pass 0 (default, sheet matches parent top) or a positive pixel offset.","Fix inset math: offset = Math.max(0, desiredTopInsetPx) rather than allowing negative intermediates.","Note the value must also not exceed the half-expanded offset — keep the two settings consistent."],"exampleFix":"// before\nint offset = topInset - peekHeight; // can be negative\nbehavior.setExpandedOffset(offset);\n\n// after\nbehavior.setExpandedOffset(Math.max(0, topInset));","handlingStrategy":"validation","validationCode":"int offset = Math.max(0, computedExpandedOffset);\nbehavior.setExpandedOffset(offset);","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Do inset arithmetic with clamping at the boundary.","Keep expandedOffset <= half-expanded offset to stay consistent."],"tags":["bottomsheet","illegal-argument","validation","insets"],"backgroundTag":null,"analyzedSha":"ac7e18efeefb331850c561faf9ab8bf81d27ba68","analyzedAt":"2026-08-14T15:35:35.735Z","schemaVersion":2},"datasetVersion":"2026-08-15T17:31:12.345Z"}