Grid
In Babylon.js, the Grid layout is a flexible UI system that lets you organize 2D controls (like buttons, text, and shapes) in a structured table of rows and columns. It works much like CSS Grid, providing proportional or fixed sizing for responsive, layered interfaces and it is ideal for HUDs, menus, and overlays in 3D scenes.
Reactylon builds on this by introducing a declarative, JSX-based syntax for Babylon Grid, allowing you to write complex layouts using grid
, row
and column
components.
Basic
The following layout visually divides the interface horizontally into two equal parts, using a single row
with two equally sized column
.
<advancedDynamicTexture kind='createFullscreenUI' createFullscreenUI={{ name: 'grid-layout' }} >
<grid name='grid'>
<row height={1} >
<column width={0.5}>
<rectangle thickness={0} background='#FFD54F'>
<textBlock name='column-1-text' text={`Row 1\nColumn 1`} />
</rectangle>
</column>
<column width={0.5}>
<rectangle thickness={0} background='#E53935'>
<textBlock name='column-1-text' text={`Row 1\nColumn 2`} />
</rectangle>
</column>
</row>
</grid>
</advancedDynamicTexture>
Advanced
The following layout defines a nested grid structure, illustrating a visually rich and complex UI composed of multiple row
and column
, some embedded within others.
<advancedDynamicTexture kind='createFullscreenUI' createFullscreenUI={{ name: 'grid-layout' }} >
<grid name='grid'>
<row height={0.5}>
<column width={0.5}>
<row height={1}>
<column width={0.5}>
<rectangle thickness={0} background='#FFD54F'>
<textBlock fontSize={14} text={`Row 1 \nColumn 1 \nRow 1 \nColumn 1`} />
</rectangle>
</column>
<column width={0.5}>
<rectangle thickness={0} background='#FF7043'>
<textBlock fontSize={14} text={`Row 1 \nColumn 1 \nRow 1 \nColumn 2`} />
</rectangle>
</column>
</row>
</column>
<column width={0.5}>
<row height={0.5}>
<column width={1}>
<rectangle thickness={0} background='#42A5F5'>
<textBlock fontSize={14} text={`Row 1 \nColumn 2 \nRow 1 \nColumn 1`} />
</rectangle>
</column>
</row>
<row height={0.5}>
<column width={0.3}>
<rectangle thickness={0} background='#8BC34A'>
<textBlock fontSize={14} text={`Row 1 \nColumn 2 \nRow 2 \nColumn 1`} />
</rectangle>
</column>
<column width={0.3}>
<rectangle thickness={0} background='#E53935'>
<textBlock fontSize={14} text={`Row 1 \nColumn 2 \nRow 2 \nColumn 2`} />
</rectangle>
</column>
<column width={0.3}>
<rectangle thickness={0} background='#B39DDB'>
<textBlock fontSize={14} text={`Row 1 \nColumn 2 \nRow 2 \nColumn 3`} />
</rectangle>
</column>
</row>
</column>
</row>
<row height={0.5}>
<column width={1}>
<rectangle thickness={0} background='#90A4AE'>
<textBlock fontSize={14} text={`Row 2 \nColumn 1`} />
</rectangle>
</column>
</row>
</grid>
</advancedDynamicTexture>
Dynamic
The following layout replicates the previous nested grid structure but removes all internal labels. Each colored cell is now interactive: clicking on one will remove it from the layout. This demonstrates the power of dynamic grid composition and automatic recalculation of structure when elements are added or removed.
The code behind this example is intentionally exaggerated to push the boundaries of what a nested layout can do. It’s unlikely you’ll see a real-world use case exactly like this. Are you brave enough to see the code? Click on “Open in StackBlitz” to dive in!
Caveats
The Babylon.js Grid layout doesn’t natively support inserting rows or columns at arbitrary positions. You can only append them to the end, and there is no built-in API to insert elements in the middle of an existing grid layout.
However, Reactylon offers a seamless solution to handle this scenario through the key
prop, enabling full control over grid rebuilding and conditional layout updates. Example:
<row height={0.5} key={isFirstColumnVisible} >
{isFirstColumnVisible ? (
<column width={1}>
<rectangle name='green' thickness={0} background='#8BC34A' />
</column>
) : null}
<column width={1}>
<rectangle name='red' thickness={0} background='#E53935' />
</column>
</row>
In most cases, you won’t need key
- Reactylon manages grid updates seamlessly. Use it only when you need dynamic insertion or reordering of rows/columns (e.g. conditional rendering in the middle of the grid), or when the entire grid structure changes significantly, to enforce a clean rebuild without unintended side effects.
Learn More
To learn more about the underlying Grid layout, please refer to Babylon.js documentation: https://doc.babylonjs.com/features/featuresDeepDive/gui/gui/#grid.