necolas/react-native-web · error · Error

The <Image> component cannot contain children. If you want t

Error message

The <Image> component cannot contain children. If you want to render content on top of the image, consider using the <ImageBackground> component or absolute positioning.

What it means

HTML/CSS cannot reliably render nested content inside an <img>-backed element the way native UIImageView+subviews can, so react-native-web forbids children on <Image>. The library provides <ImageBackground> (which renders a wrapper with the image as a child layer) for overlaying content. The check only runs in development (NODE_ENV !== 'production').

Source

Thrown at packages/react-native-web/src/exports/Image/index.js:199

    accessibilityLabel,
    blurRadius,
    defaultSource,
    draggable,
    onError,
    onLayout,
    onLoad,
    onLoadEnd,
    onLoadStart,
    pointerEvents,
    source,
    style,
    ...rest
  } = props;
  const ariaLabel = _ariaLabel || accessibilityLabel;

  if (process.env.NODE_ENV !== 'production') {
    if (props.children) {
      throw new Error(
        'The <Image> component cannot contain children. If you want to render content on top of the image, consider using the <ImageBackground> component or absolute positioning.'
      );
    }
  }

  const [state, updateState] = React.useState(() => {
    const uri = resolveAssetUri(source);
    if (uri != null) {
      const isLoaded = ImageLoader.has(uri);
      if (isLoaded) {
        return LOADED;
      }
    }
    return IDLE;
  });

  const [layout, updateLayout] = React.useState({});
  const hasTextAncestor = React.useContext(TextAncestorContext);

View on GitHub (pinned to a9de220ba9)

Solutions

  1. Replace <Image> with <ImageBackground> when children are needed.
  2. Or position the overlay outside the Image with absolute positioning inside a wrapper View.
  3. If no children are intended, remove the stray JSX inside <Image>.

Example fix

// before
<Image source={img}><Text>Hi</Text></Image>
// after
<ImageBackground source={img}>
  <Text>Hi</Text>
</ImageBackground>
Defensive patterns

Strategy: validation

Validate before calling

function assertNoImageChildren(props) {
  if (process.env.NODE_ENV !== 'production' && props.children != null) {
    throw new Error('Use <ImageBackground> instead of <Image> with children.');
  }
}

Type guard

const needsImageBackground = (children) => children != null;

Try / catch

try { return <Image {...props} />; } catch (e) { if (/cannot contain children/.test(e.message)) return <ImageBackground {...props} />; throw e; }

Prevention

When it happens

Trigger: Rendering any children inside <Image> in a non-production build, e.g. <Image source={...}><Text>label</Text></Image>.

Common situations: Migrating code from React Native where placing children in Image was tolerated or common before RN deprecated it; adding badges/overlays on top of avatars; following old RN tutorials.

Related errors


AI-assisted analysis of necolas/react-native-web@a9de220ba9 (2026-09-01). Data as JSON: /api/errors/4021d6a5a3debca2. Report an issue: GitHub.