AniUI

Safe Area

Styled SafeAreaView wrapper with theme-aware variants.

Installation#

npx @aniui/cli add safe-area
Safe area (top)
Content
Safe area (bottom)
Web preview — components render natively on iOS & Android
import { SafeArea } from "@/components/ui/safe-area";

export function MyScreen() {
  return (
    <SafeArea variant="default">
      {/* Screen content */}
    </SafeArea>
  );
}

Usage#

app/index.tsx
import { SafeArea } from "@/components/ui/safe-area";

export function MyScreen() {
  return (
    <SafeArea variant="default">
      {/* Screen content */}
    </SafeArea>
  );
}

Examples#

Edges and variants
// Only apply safe area to top and bottom
<SafeArea edges={["top", "bottom"]}>
  {/* Content */}
</SafeArea>

// Card background variant
<SafeArea variant="card">
  {/* Content */}
</SafeArea>

Props#

PropTypeDefault
variant
"default" | "card" | "transparent"
"default"
className
string
-
edges
("top" | "bottom" | "left" | "right")[]
-

Also accepts all SafeAreaView props from react-native-safe-area-context.

Accessibility#

  • SafeAreaView wrapper that respects device safe areas.
  • No additional accessibility concerns -- content within inherits standard behavior.

Source#

components/ui/safe-area.tsx
import React from "react";
import { View } from "react-native";
import { SafeAreaView } from "react-native-safe-area-context";
import { cva, type VariantProps } from "class-variance-authority";
import { cn } from "@/lib/utils";

const safeAreaVariants = cva("flex-1", {
  variants: {
    variant: {
      default: "bg-background",
      card: "bg-card",
      transparent: "bg-transparent",
    },
  },
  defaultVariants: { variant: "default" },
});

export interface SafeAreaProps
  extends React.ComponentPropsWithoutRef<typeof SafeAreaView>,
    VariantProps<typeof safeAreaVariants> {
  className?: string;
  children?: React.ReactNode;
}

export function SafeArea({ variant, className, children, style, ...props }: SafeAreaProps) {
  // Background + flex live on a plain View (className works reliably under both
  // NativeWind and Uniwind, and colors the full screen incl. the inset areas).
  // The SafeAreaView only applies the insets — className isn't applied to that
  // third-party component by the styling engines, so we keep flex inline there.
  return (
    <View className={cn(safeAreaVariants({ variant }), className)} style={{ flex: 1 }}>
      <SafeAreaView style={[{ flex: 1 }, style]} {...props}>
        {children}
      </SafeAreaView>
    </View>
  );
}