Introduced Layout component
Summary: This diff introduces a Layout component. Layout is now quite randomly build up by using panels, sidebars, flex columns, flexrow and view components. They all have slight different scrolling, overflow, and grow behavior. Which causes issues with areas not being srcollable, double scrollbars or simply the wrong area scrolling. Too make things worse to design, many components by default display hidden content, and show scrollbars automatically rather than deliberately. To work towards a consist, and especially simple layout model, over time I want to build a consistent outside-in layout model, where always parents reserve space for children, and children fill the available space and device it even further. Note that this approaches better how 'applications' typically organize their layout, which is opposite from the classic 'document', where the contents is allowed to grow and is used to push things down / aside where they want. However, such a model fits an application with toolbars, sidebars and scroll regions badly, and currently those two philosophies are mixed throughout the application. This component is a very small first step to organizing our layout consistently. By using a new component there is less risk to break existing layouts. The `Layout` component takes up all available space, both horizontally and vertically, and gives the first child what it needs based on its own size (typically, a toolbar or (resizable) sidebar), and all the remaining space to the second child. By default the space is distributed vertically, but it can also be distributed horizontally. It can provide scrollbars as well if needed so that the main content doesn't need to provide that by itself. Examples: ``` <Layout scrollable> <Toolbar /> <LargePicture /> </Layout> <Layout horizontal> <ResizableSidebar /> <SomeContentTable /> </Layout> ``` Reviewed By: jknoxville Differential Revision: D21178245 fbshipit-source-id: c2d2f167d1572278e51a5b66e1cbf13c42c3b898
This commit is contained in:
committed by
Facebook GitHub Bot
parent
8936ec540c
commit
4665bcf218
73
desktop/app/src/ui/components/Layout.tsx
Normal file
73
desktop/app/src/ui/components/Layout.tsx
Normal file
@@ -0,0 +1,73 @@
|
|||||||
|
/**
|
||||||
|
* Copyright (c) Facebook, Inc. and its affiliates.
|
||||||
|
*
|
||||||
|
* This source code is licensed under the MIT license found in the
|
||||||
|
* LICENSE file in the root directory of this source tree.
|
||||||
|
*
|
||||||
|
* @format
|
||||||
|
*/
|
||||||
|
|
||||||
|
import React from 'react';
|
||||||
|
import styled from '@emotion/styled';
|
||||||
|
|
||||||
|
type Props = {
|
||||||
|
scrollable?: boolean;
|
||||||
|
horizontal?: boolean;
|
||||||
|
};
|
||||||
|
|
||||||
|
const FixedContainer = styled('div')({
|
||||||
|
flex: 'none',
|
||||||
|
height: 'auto',
|
||||||
|
overflow: 'none',
|
||||||
|
});
|
||||||
|
FixedContainer.displayName = 'Layout:FixedContainer';
|
||||||
|
|
||||||
|
const ScrollContainer = styled('div')<Props>(({scrollable}) => ({
|
||||||
|
overflow: scrollable ? 'auto' : 'hidden',
|
||||||
|
flex: 'auto',
|
||||||
|
display: 'flex',
|
||||||
|
}));
|
||||||
|
ScrollContainer.displayName = 'Layout:ScrollContainer';
|
||||||
|
|
||||||
|
const Container = styled('div')<Props>(({horizontal}) => ({
|
||||||
|
display: 'flex',
|
||||||
|
flex: 'auto',
|
||||||
|
flexDirection: horizontal ? 'row' : 'column',
|
||||||
|
height: '100%',
|
||||||
|
width: '100%',
|
||||||
|
overflow: 'hidden',
|
||||||
|
}));
|
||||||
|
Container.displayName = 'Layout:Container';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The Layout component divides all available screenspace over two components:
|
||||||
|
* A fixed top (or left) component, and all remaining space to a bottom component.
|
||||||
|
*
|
||||||
|
* The main area will be scrollable by default, but if multiple containers are nested,
|
||||||
|
* scrolling can be disabled by using `scrollable={false}`
|
||||||
|
*/
|
||||||
|
const Layout: React.FC<
|
||||||
|
{
|
||||||
|
children: [React.ReactNode, React.ReactNode];
|
||||||
|
} & Props
|
||||||
|
> = ({children, ...props}) => {
|
||||||
|
if (children.length > 2) {
|
||||||
|
throw new Error('VerticalContainer expects exactly 2 children');
|
||||||
|
}
|
||||||
|
const top = children[0];
|
||||||
|
const main = children[1];
|
||||||
|
return (
|
||||||
|
<Container {...props}>
|
||||||
|
<FixedContainer>{top}</FixedContainer>
|
||||||
|
<ScrollContainer {...props}>{main}</ScrollContainer>
|
||||||
|
</Container>
|
||||||
|
);
|
||||||
|
};
|
||||||
|
|
||||||
|
Layout.displayName = 'Layout';
|
||||||
|
Layout.defaultProps = {
|
||||||
|
scrollable: false,
|
||||||
|
horizontal: false,
|
||||||
|
};
|
||||||
|
|
||||||
|
export default Layout;
|
||||||
@@ -173,3 +173,4 @@ export {default as CenteredView} from './components/CenteredView';
|
|||||||
export {default as Info} from './components/Info';
|
export {default as Info} from './components/Info';
|
||||||
export {default as Bordered} from './components/Bordered';
|
export {default as Bordered} from './components/Bordered';
|
||||||
export {default as AlternatingRows} from './components/AlternatingRows';
|
export {default as AlternatingRows} from './components/AlternatingRows';
|
||||||
|
export {default as Layout} from './components/Layout';
|
||||||
|
|||||||
Reference in New Issue
Block a user