Layout
When you are handling the overall layout of a page, this component might be helpfull.
Overview#
Layout: The layout wrapper, in whichHeaderSiderContentFooterorLayoutitself can be nested, and can be placed in any parent container.Header: The top layout with default style, in which any element can be nested, and must be placed inLayout.Sider: The sidebar with default style and basic functions, in which any element can be nested, and must be placed inLayout.Content: The content layout with default style, in which any element can be nested, and must be placed inLayout.Footer: The bottom layout with default style, in which any element can be nested, and must be placed inLayout.
Base on
flex layout, please pay attention to the compatibility.
Examples
import { Layout } from 'antd';
const { Header, Footer, Sider, Content } = Layout;
ReactDOM.render(
<div>
<Layout>
<Header>Header</Header>
<Content>Content</Content>
<Footer>Footer</Footer>
</Layout>
<Layout>
<Header>Header</Header>
<Layout>
<Sider>Sider</Sider>
<Content>Content</Content>
</Layout>
<Footer>Footer</Footer>
</Layout>
<Layout>
<Header>Header</Header>
<Layout>
<Content>Content</Content>
<Sider>Sider</Sider>
</Layout>
<Footer>Footer</Footer>
</Layout>
<Layout>
<Sider>Sider</Sider>
<Layout>
<Header>Header</Header>
<Content>Content</Content>
<Footer>Footer</Footer>
</Layout>
</Layout>
</div>
, mountNode);import { Layout, Menu, Breadcrumb } from 'antd';
const { Header, Content, Footer } = Layout;
ReactDOM.render(
<Layout className="layout">
<Header>
<div className="logo" />
<Menu
theme="dark"
mode="horizontal"
defaultSelectedKeys={['2']}
style={{ lineHeight: '64px' }}
>
<Menu.Item key="1">nav 1</Menu.Item>
<Menu.Item key="2">nav 2</Menu.Item>
<Menu.Item key="3">nav 3</Menu.Item>
</Menu>
</Header>
<Content style={{ padding: '0 50px' }}>
<Breadcrumb style={{ margin: '12px 0' }}>
<Breadcrumb.Item>Home</Breadcrumb.Item>
<Breadcrumb.Item>List</Breadcrumb.Item>
<Breadcrumb.Item>App</Breadcrumb.Item>
</Breadcrumb>
<div style={{ background: '#fff', padding: 24, minHeight: 280 }}>Content</div>
</Content>
<Footer style={{ textAlign: 'center' }}>
Ant Design ©2016 Created by Ant UED
</Footer>
</Layout>
, mountNode);#components-layout-demo-top .logo {
width: 120px;
height: 31px;
background: #333;
border-radius: 6px;
margin: 16px 24px 16px 0;
float: left;
}import { Layout, Menu, Breadcrumb, Icon } from 'antd';
const { SubMenu } = Menu;
const { Header, Content, Sider } = Layout;
ReactDOM.render(
<Layout>
<Header className="header">
<div className="logo" />
<Menu
theme="dark"
mode="horizontal"
defaultSelectedKeys={['2']}
style={{ lineHeight: '64px' }}
>
<Menu.Item key="1">nav 1</Menu.Item>
<Menu.Item key="2">nav 2</Menu.Item>
<Menu.Item key="3">nav 3</Menu.Item>
</Menu>
</Header>
<Layout>
<Sider width={200} style={{ background: '#fff' }}>
<Menu
mode="inline"
defaultSelectedKeys={['1']}
defaultOpenKeys={['sub1']}
style={{ height: '100%' }}
>
<SubMenu key="sub1" title={<span><Icon type="user" />subnav 1</span>}>
<Menu.Item key="1">option1</Menu.Item>
<Menu.Item key="2">option2</Menu.Item>
<Menu.Item key="3">option3</Menu.Item>
<Menu.Item key="4">option4</Menu.Item>
</SubMenu>
<SubMenu key="sub2" title={<span><Icon type="laptop" />subnav 2</span>}>
<Menu.Item key="5">option5</Menu.Item>
<Menu.Item key="6">option6</Menu.Item>
<Menu.Item key="7">option7</Menu.Item>
<Menu.Item key="8">option8</Menu.Item>
</SubMenu>
<SubMenu key="sub3" title={<span><Icon type="notification" />subnav 3</span>}>
<Menu.Item key="9">option9</Menu.Item>
<Menu.Item key="10">option10</Menu.Item>
<Menu.Item key="11">option11</Menu.Item>
<Menu.Item key="12">option12</Menu.Item>
</SubMenu>
</Menu>
</Sider>
<Layout style={{ padding: '0 24px 24px' }}>
<Breadcrumb style={{ margin: '12px 0' }}>
<Breadcrumb.Item>Home</Breadcrumb.Item>
<Breadcrumb.Item>List</Breadcrumb.Item>
<Breadcrumb.Item>App</Breadcrumb.Item>
</Breadcrumb>
<Content style={{ background: '#fff', padding: 24, margin: 0, minHeight: 280 }}>
Content
</Content>
</Layout>
</Layout>
</Layout>
, mountNode);#components-layout-demo-top-side-2 .logo {
width: 120px;
height: 31px;
background: #333;
border-radius: 6px;
margin: 16px 28px 16px 0;
float: left;
}import { Layout, Menu, Breadcrumb, Icon } from 'antd';
const { SubMenu } = Menu;
const { Header, Content, Footer, Sider } = Layout;
ReactDOM.render(
<Layout>
<Header className="header">
<div className="logo" />
<Menu
theme="dark"
mode="horizontal"
defaultSelectedKeys={['2']}
style={{ lineHeight: '64px' }}
>
<Menu.Item key="1">nav 1</Menu.Item>
<Menu.Item key="2">nav 2</Menu.Item>
<Menu.Item key="3">nav 3</Menu.Item>
</Menu>
</Header>
<Content style={{ padding: '0 50px' }}>
<Breadcrumb style={{ margin: '12px 0' }}>
<Breadcrumb.Item>Home</Breadcrumb.Item>
<Breadcrumb.Item>List</Breadcrumb.Item>
<Breadcrumb.Item>App</Breadcrumb.Item>
</Breadcrumb>
<Layout style={{ padding: '24px 0', background: '#fff' }}>
<Sider width={200} style={{ background: '#fff' }}>
<Menu
mode="inline"
defaultSelectedKeys={['1']}
defaultOpenKeys={['sub1']}
style={{ height: '100%' }}
>
<SubMenu key="sub1" title={<span><Icon type="user" />subnav 1</span>}>
<Menu.Item key="1">option1</Menu.Item>
<Menu.Item key="2">option2</Menu.Item>
<Menu.Item key="3">option3</Menu.Item>
<Menu.Item key="4">option4</Menu.Item>
</SubMenu>
<SubMenu key="sub2" title={<span><Icon type="laptop" />subnav 2</span>}>
<Menu.Item key="5">option5</Menu.Item>
<Menu.Item key="6">option6</Menu.Item>
<Menu.Item key="7">option7</Menu.Item>
<Menu.Item key="8">option8</Menu.Item>
</SubMenu>
<SubMenu key="sub3" title={<span><Icon type="notification" />subnav 3</span>}>
<Menu.Item key="9">option9</Menu.Item>
<Menu.Item key="10">option10</Menu.Item>
<Menu.Item key="11">option11</Menu.Item>
<Menu.Item key="12">option12</Menu.Item>
</SubMenu>
</Menu>
</Sider>
<Content style={{ padding: '0 24px', minHeight: 280 }}>
Content
</Content>
</Layout>
</Content>
<Footer style={{ textAlign: 'center' }}>
Ant Design ©2016 Created by Ant UED
</Footer>
</Layout>
, mountNode);#components-layout-demo-top-side .logo {
width: 120px;
height: 31px;
background: #333;
border-radius: 6px;
margin: 16px 28px 16px 0;
float: left;
}import { Layout, Menu, Breadcrumb, Icon } from 'antd';
const { Header, Content, Footer, Sider } = Layout;
const SubMenu = Menu.SubMenu;
class SiderDemo extends React.Component {
state = {
collapsed: false,
mode: 'inline',
};
onCollapse = (collapsed) => {
console.log(collapsed);
this.setState({
collapsed,
mode: collapsed ? 'vertical' : 'inline',
});
}
render() {
return (
<Layout>
<Sider
collapsible
collapsed={this.state.collapsed}
onCollapse={this.onCollapse}
>
<div className="logo" />
<Menu theme="dark" mode={this.state.mode} defaultSelectedKeys={['6']}>
<SubMenu
key="sub1"
title={<span><Icon type="user" /><span className="nav-text">User</span></span>}
>
<Menu.Item key="1">Tom</Menu.Item>
<Menu.Item key="2">Bill</Menu.Item>
<Menu.Item key="3">Alex</Menu.Item>
</SubMenu>
<SubMenu
key="sub2"
title={<span><Icon type="team" /><span className="nav-text">Team</span></span>}
>
<Menu.Item key="4">Team 1</Menu.Item>
<Menu.Item key="5">Team 2</Menu.Item>
</SubMenu>
<Menu.Item key="6">
<span>
<Icon type="file" />
<span className="nav-text">File</span>
</span>
</Menu.Item>
</Menu>
</Sider>
<Layout>
<Header style={{ background: '#fff', padding: 0 }} />
<Content style={{ margin: '0 16px' }}>
<Breadcrumb style={{ margin: '12px 0' }}>
<Breadcrumb.Item>User</Breadcrumb.Item>
<Breadcrumb.Item>Bill</Breadcrumb.Item>
</Breadcrumb>
<div style={{ padding: 24, background: '#fff', minHeight: 360 }}>
Bill is a cat.
</div>
</Content>
<Footer style={{ textAlign: 'center' }}>
Ant Design ©2016 Created by Ant UED
</Footer>
</Layout>
</Layout>
);
}
}
ReactDOM.render(<SiderDemo />, mountNode);#components-layout-demo-side .logo {
height: 32px;
background: #333;
border-radius: 6px;
margin: 16px;
}
#components-layout-demo-side .ant-layout-sider-collapsed .anticon {
font-size: 16px;
margin-left: 8px;
}
#components-layout-demo-side .ant-layout-sider-collapsed .nav-text {
display: none;
}
#components-layout-demo-side .ant-layout-sider-collapsed .ant-menu-submenu-vertical > .ant-menu-submenu-title:after {
display: none;
}import { Layout, Menu, Icon } from 'antd';
const { Header, Sider, Content } = Layout;
class SiderDemo extends React.Component {
state = {
collapsed: false,
};
toggle = () => {
this.setState({
collapsed: !this.state.collapsed,
});
}
render() {
return (
<Layout>
<Sider
trigger={null}
collapsible
collapsed={this.state.collapsed}
>
<div className="logo" />
<Menu theme="dark" mode="inline" defaultSelectedKeys={['1']}>
<Menu.Item key="1">
<Icon type="user" />
<span className="nav-text">nav 1</span>
</Menu.Item>
<Menu.Item key="2">
<Icon type="video-camera" />
<span className="nav-text">nav 2</span>
</Menu.Item>
<Menu.Item key="3">
<Icon type="upload" />
<span className="nav-text">nav 3</span>
</Menu.Item>
</Menu>
</Sider>
<Layout>
<Header style={{ background: '#fff', padding: 0 }}>
<Icon
className="trigger"
type={this.state.collapsed ? 'menu-unfold' : 'menu-fold'}
onClick={this.toggle}
/>
</Header>
<Content style={{ margin: '24px 16px', padding: 24, background: '#fff', minHeight: 280 }}>
Content
</Content>
</Layout>
</Layout>
);
}
}
ReactDOM.render(<SiderDemo />, mountNode);#components-layout-demo-custom-trigger .trigger {
font-size: 18px;
line-height: 64px;
padding: 0 16px;
cursor: pointer;
transition: color .3s;
}
#components-layout-demo-custom-trigger .trigger:hover {
color: #108ee9;
}
#components-layout-demo-custom-trigger .logo {
height: 32px;
background: #333;
border-radius: 6px;
margin: 16px;
}
#components-layout-demo-custom-trigger .ant-layout-sider-collapsed .anticon {
font-size: 16px;
}
#components-layout-demo-custom-trigger .ant-layout-sider-collapsed .nav-text {
display: none;
}import { Layout, Menu, Icon } from 'antd';
const { Header, Content, Footer, Sider } = Layout;
ReactDOM.render(<Layout>
<Sider
breakpoint="lg"
collapsedWidth="0"
onCollapse={(collapsed, type) => { console.log(collapsed, type); }}
>
<div className="logo" />
<Menu theme="dark" mode="inline" defaultSelectedKeys={['4']}>
<Menu.Item key="1">
<Icon type="user" />
<span className="nav-text">nav 1</span>
</Menu.Item>
<Menu.Item key="2">
<Icon type="video-camera" />
<span className="nav-text">nav 2</span>
</Menu.Item>
<Menu.Item key="3">
<Icon type="upload" />
<span className="nav-text">nav 3</span>
</Menu.Item>
<Menu.Item key="4">
<Icon type="user" />
<span className="nav-text">nav 4</span>
</Menu.Item>
</Menu>
</Sider>
<Layout>
<Header style={{ background: '#fff', padding: 0 }} />
<Content style={{ margin: '24px 16px 0' }}>
<div style={{ padding: 24, background: '#fff', minHeight: 360 }}>
content
</div>
</Content>
<Footer style={{ textAlign: 'center' }}>
Ant Design ©2016 Created by Ant UED
</Footer>
</Layout>
</Layout>, mountNode);#components-layout-demo-responsive .logo {
height: 32px;
background: #333;
border-radius: 6px;
margin: 16px;
}import { Layout, Menu, Breadcrumb } from 'antd';
const { Header, Content, Footer } = Layout;
ReactDOM.render(
<Layout>
<Header className="header">
<div className="logo" />
<Menu
theme="dark"
mode="horizontal"
defaultSelectedKeys={['2']}
style={{ lineHeight: '64px' }}
>
<Menu.Item key="1">nav 1</Menu.Item>
<Menu.Item key="2">nav 2</Menu.Item>
<Menu.Item key="3">nav 3</Menu.Item>
</Menu>
</Header>
<Content className="content">
<Breadcrumb style={{ margin: '12px 0' }}>
<Breadcrumb.Item>Home</Breadcrumb.Item>
<Breadcrumb.Item>List</Breadcrumb.Item>
<Breadcrumb.Item>App</Breadcrumb.Item>
</Breadcrumb>
<div style={{ background: '#fff', padding: 24, minHeight: 280 }}>Content</div>
</Content>
<Footer style={{ textAlign: 'center' }}>
Ant Design ©2016 Created by Ant UED
</Footer>
</Layout>
, mountNode);#components-layout-demo-fixed .logo {
width: 120px;
height: 31px;
background: #333;
border-radius: 6px;
margin: 16px 24px 16px 0;
float: left;
}
#components-layout-demo-fixed .header {
position: fixed;
width: 100%;
}
#components-layout-demo-fixed .content {
padding: 0 50px;
margin-top: 64px;
}API#
<Layout>
<Header>header</Header>
<Layout>
<Sider>left sidebar</Sider>
<Content>main content</Content>
<Sider>right sidebar</Sider>
</Layout>
<Footer>footer</Footer>
</Layout>Layout#
The wrapper.
| Property | Description | Type | Default |
|---|---|---|---|
| style | to custom the styles | object | - |
| className | container className | string | - |
API of
Layout.HeaderLayout.FooterLayout.Contentis the same withLayout.
Layout.Sider#
The sidebar.
| Property | Description | Type | Default |
|---|---|---|---|
| collapsible | whether can be collapsed | boolean | false |
| defaultCollapsed | to set the initial status | boolean | false |
| collapsed | to set the current status | boolean | - |
| onCollapse | the callback function, can be executed by clicking the trigger or activating the responsive layout | (collapsed, type) => {} | - |
| trigger | specify the customized trigger, set to null to hide the trigger | string|ReactNode | - |
| width | width of the sidebar | number|string | 200 |
| collapsedWidth | width of the collapsed sidebar, by setting to 0 a special trigger will appear | number | 64 |
| breakpoint | breakpoint of the responsive layout | Enum { 'xs', 'sm', 'md', 'lg', 'xl' } | - |
| style | to custom the styles | object | - |
| className | container className | string | - |
Note: If you want to wrap the
Sider, do not forget to add this setting to the customized component:__ANT_LAYOUT_SIDER = true. e.g.
const CustomizedSider = (props) => <Sider {...props} />
CustomizedSider.__ANT_LAYOUT_SIDER = true;
...
<CustomizedSider>Sider Content</CustomizedSider>