Browse Source

Add area customization

The props for styling areas of layouts have been added, with sensible
low-specificity default styles added.
master
TheoryOfNekomata 2 years ago
parent
commit
3cfc87a5da
11 changed files with 251 additions and 116 deletions
  1. +12
    -0
      example/layouts/basic/index.tsx
  2. +42
    -0
      example/layouts/left-sidebar-with-menu/index.tsx
  3. +16
    -0
      example/layouts/left-sidebar/index.tsx
  4. +1
    -0
      example/package.json
  5. +1
    -1
      package.json
  6. +3
    -0
      src/layouts/Basic/index.tsx
  7. +3
    -0
      src/layouts/BasicNarrow/index.tsx
  8. +16
    -5
      src/layouts/LeftSidebar/index.tsx
  9. +106
    -80
      src/layouts/LeftSidebarWithMenu/index.tsx
  10. +14
    -2
      src/layouts/RightSidebarStatic/index.tsx
  11. +37
    -28
      src/widgets/TopBar/index.tsx

+ 12
- 0
example/layouts/basic/index.tsx View File

@@ -1,15 +1,27 @@
import * as React from 'react'
import * as ReactDOM from 'react-dom';
import ReactMarkdown from 'react-markdown'
import styled from 'styled-components';
import Brand from '../../components/Brand';
import { Basic } from '../../..';

const TopBar = styled('div')({
backgroundColor: 'black',
color: 'white',
boxShadow: '0 0 0.25rem rgba(0,0,0,0.25)',
'a': {
color: 'inherit',
textDecoration: 'none',
}
})

const Page = () => {
return (
<Basic.Layout
brand={
<Brand />
}
topBarComponent={TopBar}
topBarCenter={
<form
style={{


+ 42
- 0
example/layouts/left-sidebar-with-menu/index.tsx View File

@@ -3,6 +3,46 @@ import * as ReactDOM from 'react-dom';
import ReactMarkdown from 'react-markdown';
import Brand from '../../components/Brand';
import { LeftSidebarWithMenu } from '../../..';
import styled from 'styled-components';

const SidebarMenuComponent = styled('div')({
'::after': {
content: "''",
position: 'absolute',
top: 0,
right: 0,
height: '100%',
width: '0.0625rem',
backgroundColor: 'currentcolor',
opacity: 0.25,
pointerEvents: 'none',
}
})

const SidebarMainComponent = styled('div')({
'::before': {
content: "''",
position: 'absolute',
top: 0,
left: 0,
height: '100%',
width: '0.0625rem',
backgroundColor: 'currentcolor',
opacity: 0.25,
pointerEvents: 'none',
},
'::after': {
content: "''",
position: 'absolute',
top: 0,
right: 0,
height: '100%',
width: '0.0625rem',
backgroundColor: 'currentcolor',
opacity: 0.25,
pointerEvents: 'none',
}
})

const Page = () => {
const [sidebarMainOpen, setSidebarMainOpen] = React.useState(location.hash === '#sidebar')
@@ -23,6 +63,8 @@ const Page = () => {
return (
<LeftSidebarWithMenu.Layout
moreItemsOpen={moreItemsOpen}
sidebarMainComponent={SidebarMainComponent}
sidebarMenuComponent={SidebarMenuComponent}
sidebarMenuItems={[
{
id: 'foo',


+ 16
- 0
example/layouts/left-sidebar/index.tsx View File

@@ -1,9 +1,24 @@
import * as React from 'react'
import * as ReactDOM from 'react-dom';
import ReactMarkdown from 'react-markdown';
import styled from 'styled-components';
import Brand from '../../components/Brand';
import { LeftSidebar } from '../../..';

const SidebarMainComponent = styled('div')({
'::after': {
content: "''",
position: 'absolute',
top: 0,
right: 0,
height: '100%',
width: '0.0625rem',
backgroundColor: 'currentcolor',
opacity: 0.5,
pointerEvents: 'none',
}
})

const Page = () => {
const [sidebarMainOpen, setSidebarMainOpen] = React.useState(location.hash === '#sidebar')

@@ -78,6 +93,7 @@ const Page = () => {
</a>
</>
}
sidebarMainComponent={SidebarMainComponent}
>
<LeftSidebar.ContentContainer>
<ReactMarkdown


+ 1
- 0
example/package.json View File

@@ -11,6 +11,7 @@
"alias": {
"react": "../node_modules/react",
"react-dom": "../node_modules/react-dom/profiling",
"styled-components": "../node_modules/styled-components",
"scheduler/tracing": "../node_modules/scheduler/tracing-profiling"
},
"devDependencies": {


+ 1
- 1
package.json View File

@@ -1,5 +1,5 @@
{
"version": "0.2.1",
"version": "0.2.2",
"license": "MIT",
"main": "dist/index.js",
"typings": "dist/index.d.ts",


+ 3
- 0
src/layouts/Basic/index.tsx View File

@@ -23,12 +23,14 @@ type Props = {
brand?: React.ReactNode,
userLink?: React.ReactNode,
topBarCenter?: React.ReactChild,
topBarComponent?: React.ElementType,
}

export const Layout: React.FC<Props> = ({
brand,
userLink,
topBarCenter,
topBarComponent = 'div',
children,
}) => {
return (
@@ -44,6 +46,7 @@ export const Layout: React.FC<Props> = ({
<TopBar
brand={brand}
userLink={userLink}
baseComponent={topBarComponent}
>
{topBarCenter}
</TopBar>


+ 3
- 0
src/layouts/BasicNarrow/index.tsx View File

@@ -23,12 +23,14 @@ type Props = {
brand?: React.ReactNode,
userLink?: React.ReactNode,
topBarCenter?: React.ReactChild,
topBarComponent?: React.ElementType,
}

export const Layout: React.FC<Props> = ({
brand,
userLink,
topBarCenter,
topBarComponent = 'div',
children,
}) => {
return (
@@ -45,6 +47,7 @@ export const Layout: React.FC<Props> = ({
span="narrow"
brand={brand}
userLink={userLink}
baseComponent={topBarComponent}
>
{topBarCenter}
</TopBar>


+ 16
- 5
src/layouts/LeftSidebar/index.tsx View File

@@ -42,8 +42,12 @@ const SidebarBase = styled('div')({
left: '-100%',
width: '100%',
height: '100%',
overflow: 'hidden',
backgroundColor: 'var(--color-bg, white)',
'> *': {
display: 'block',
width: '100%',
height: '100%',
backgroundColor: 'white',
},
[minWidthFactor(3)]: {
width: `calc(50% - ${configVar('base-width')} * 0.5)`,
left: 0,
@@ -86,6 +90,8 @@ type Props = {
menuLink?: React.ReactNode,
userLink?: React.ReactNode,
topBarCenter?: React.ReactChild,
topBarComponent?: React.ElementType,
sidebarMainComponent?: React.ElementType,
}

export const Layout: React.FC<Props> = ({
@@ -96,6 +102,8 @@ export const Layout: React.FC<Props> = ({
userLink,
topBarCenter,
children,
topBarComponent: TopBarComponent = 'div',
sidebarMainComponent: SidebarMainComponent = 'div',
}) => {
const LeftSidebarComponent = sidebarMainOpen ? OpenSidebarBase : SidebarBase

@@ -113,13 +121,16 @@ export const Layout: React.FC<Props> = ({
brand={brand}
menuLink={menuLink}
userLink={userLink}
baseComponent={TopBarComponent}
>
{topBarCenter}
</TopBar>
<LeftSidebarComponent>
<SidebarOverflow>
{sidebarMain}
</SidebarOverflow>
<SidebarMainComponent>
<SidebarOverflow>
{sidebarMain}
</SidebarOverflow>
</SidebarMainComponent>
</LeftSidebarComponent>
<ContentBase>
{children}


+ 106
- 80
src/layouts/LeftSidebarWithMenu/index.tsx View File

@@ -31,7 +31,6 @@ const SidebarBase = styled('div')({
overflow: 'hidden',
display: 'contents',
left: `calc(${configVar('base-width')} * -1)`,
backgroundColor: 'var(--color-bg, white)',
[minWidthFactor(3)]: {
position: 'fixed',
top: 0,
@@ -49,15 +48,8 @@ const SidebarMain = styled('div')({
right: '100%',
width: '100%',
height: '100%',
overflow: 'auto',
// overflow: 'overlay',
paddingTop: 'inherit',
paddingBottom: 'var(--size-menu, 4rem)',
scrollbarWidth: 'none',
'::-webkit-scrollbar': {
display: 'none',
},
backgroundColor: 'var(--color-bg, white)',
[minWidthFactor(3)]: {
position: 'absolute',
right: 0,
@@ -65,6 +57,23 @@ const SidebarMain = styled('div')({
marginLeft: 'auto',
paddingBottom: 0,
},
'> *': {
display: 'block',
width: '100%',
height: '100%',
backgroundColor: 'white',
},
})

const SidebarMainOverflow = styled('div')({
width: '100%',
height: '100%',
overflow: 'auto',
// overflow: 'overlay',
scrollbarWidth: 'none',
'::-webkit-scrollbar': {
display: 'none',
},
})

const OpenSidebarMain = styled(SidebarMain)({
@@ -85,7 +94,12 @@ const SidebarMenu = styled('div')({
width: '100%',
height: 'var(--size-menu, 4rem)',
zIndex: 1,
backgroundColor: 'var(--color-bg, white)',
'> *': {
display: 'block',
width: '100%',
height: '100%',
backgroundColor: 'white',
},
[minWidthFactor(3)]: {
top: 0,
marginLeft: 'auto',
@@ -130,7 +144,6 @@ const MoreItems = styled('div')({
paddingBottom: 'var(--size-menu, 4rem)',
zIndex: -1,
boxSizing: 'border-box',
backgroundColor: 'var(--color-bg, white)',
[minWidthFactor(3)]: {
display: 'contents',
},
@@ -306,6 +319,9 @@ type Props = {
moreLinkComponent: React.ElementType,
linkComponent: React.ElementType,
topBarCenter?: React.ReactChild,
topBarComponent?: React.ElementType,
sidebarMainComponent?: React.ElementType,
sidebarMenuComponent?: React.ElementType,
}

export const Layout: React.FC<Props> = ({
@@ -321,6 +337,9 @@ export const Layout: React.FC<Props> = ({
linkComponent: LinkComponent,
topBarCenter,
children,
topBarComponent: TopBarComponent = 'div',
sidebarMainComponent: SidebarMainWrapperComponent = 'div',
sidebarMenuComponent: SidebarMenuComponent = 'div',
}) => {
const SidebarMainComponent = sidebarMainOpen ? OpenSidebarMain : SidebarMain
const MoreItemsComponent = moreItemsOpen ? OpenMoreItems : MoreItems
@@ -363,6 +382,7 @@ export const Layout: React.FC<Props> = ({
brand={brand}
menuLink={sidebarMain ? menuLink : undefined}
userLink={userLink}
baseComponent={TopBarComponent}
>
{topBarCenter}
</TopBar>
@@ -370,70 +390,11 @@ export const Layout: React.FC<Props> = ({
}
<SidebarBase>
<SidebarMenu>
<SidebarMenuSize>
<SidebarMenuGroup>
{visiblePrimarySidebarMenuItems.map((item) => {
return (
<SidebarMenuItem
key={item.id}
>
<LinkComponent
{...item}
/>
</SidebarMenuItem>
)
})}
</SidebarMenuGroup>
<MoreItemsComponent>
<MoreItemsScroll>
<MorePrimarySidebarMenuGroup>
{morePrimarySidebarMenuItems.map((item) => {
return (
<MoreSidebarMenuItem
key={item.id}
>
<MoreLinkComponent
{...item}
/>
</MoreSidebarMenuItem>
)
})}
</MorePrimarySidebarMenuGroup>
<MoreSecondarySidebarMenuGroup>
{moreSecondarySidebarMenuItems.map((item) => {
return (
<MoreSidebarMenuItem
key={item.id}
>
<MoreLinkComponent
{...item}
/>
</MoreSidebarMenuItem>
)
})}
</MoreSecondarySidebarMenuGroup>
</MoreItemsScroll>
</MoreItemsComponent>
{
(
morePrimarySidebarMenuItems.length > 0
|| moreSecondarySidebarMenuItems.length > 0
)
&& (
<MoreToggleSidebarMenuItem>
<SidebarMenuItem>
<LinkComponent
{...moreLinkMenuItem}
/>
</SidebarMenuItem>
</MoreToggleSidebarMenuItem>
)
}
{
visibleSecondarySidebarMenuItems.length > 0
&& (
<SidebarMenuGroup>
{visibleSecondarySidebarMenuItems.map((item) => (
<SidebarMenuComponent>
<SidebarMenuSize>
<SidebarMenuGroup>
{visiblePrimarySidebarMenuItems.map((item) => {
return (
<SidebarMenuItem
key={item.id}
>
@@ -441,17 +402,82 @@ export const Layout: React.FC<Props> = ({
{...item}
/>
</SidebarMenuItem>
))}
</SidebarMenuGroup>
)
}
</SidebarMenuSize>
)
})}
</SidebarMenuGroup>
<MoreItemsComponent>
<MoreItemsScroll>
<MorePrimarySidebarMenuGroup>
{morePrimarySidebarMenuItems.map((item) => {
return (
<MoreSidebarMenuItem
key={item.id}
>
<MoreLinkComponent
{...item}
/>
</MoreSidebarMenuItem>
)
})}
</MorePrimarySidebarMenuGroup>
<MoreSecondarySidebarMenuGroup>
{moreSecondarySidebarMenuItems.map((item) => {
return (
<MoreSidebarMenuItem
key={item.id}
>
<MoreLinkComponent
{...item}
/>
</MoreSidebarMenuItem>
)
})}
</MoreSecondarySidebarMenuGroup>
</MoreItemsScroll>
</MoreItemsComponent>
{
(
morePrimarySidebarMenuItems.length > 0
|| moreSecondarySidebarMenuItems.length > 0
)
&& (
<MoreToggleSidebarMenuItem>
<SidebarMenuItem>
<LinkComponent
{...moreLinkMenuItem}
/>
</SidebarMenuItem>
</MoreToggleSidebarMenuItem>
)
}
{
visibleSecondarySidebarMenuItems.length > 0
&& (
<SidebarMenuGroup>
{visibleSecondarySidebarMenuItems.map((item) => (
<SidebarMenuItem
key={item.id}
>
<LinkComponent
{...item}
/>
</SidebarMenuItem>
))}
</SidebarMenuGroup>
)
}
</SidebarMenuSize>
</SidebarMenuComponent>
</SidebarMenu>
{
(sidebarMain as unknown)
&& (
<SidebarMainComponent>
{sidebarMain}
<SidebarMainWrapperComponent>
<SidebarMainOverflow>
{sidebarMain}
</SidebarMainOverflow>
</SidebarMainWrapperComponent>
</SidebarMainComponent>
)
}


+ 14
- 2
src/layouts/RightSidebarStatic/index.tsx View File

@@ -25,7 +25,12 @@ const SidebarBase = styled('div')({
marginTop: -1,
boxSizing: 'border-box',
},
backgroundColor: 'var(--color-bg, white)',
'> *': {
display: 'block',
width: '100%',
height: '100%',
backgroundColor: 'white',
},
[minWidthFactor(3)]: {
position: 'absolute',
top: 0,
@@ -63,6 +68,8 @@ type Props = {
sidebarMain: React.ReactChild,
userLink?: React.ReactNode,
topBarCenter?: React.ReactChild,
topBarComponent?: React.ElementType,
sidebarMainComponent?: React.ElementType,
}

export const Layout: React.FC<Props> = ({
@@ -71,6 +78,8 @@ export const Layout: React.FC<Props> = ({
userLink,
topBarCenter,
children,
topBarComponent: TopBarComponent = 'div',
sidebarMainComponent: SidebarMainComponent = 'div',
}) => {
return (
<>
@@ -86,6 +95,7 @@ export const Layout: React.FC<Props> = ({
span="wide"
brand={brand}
userLink={userLink}
baseComponent={TopBarComponent}
>
{topBarCenter}
</TopBar>
@@ -95,7 +105,9 @@ export const Layout: React.FC<Props> = ({
{children}
</ContentBase>
<SidebarBase>
{sidebarMain}
<SidebarMainComponent>
{sidebarMain}
</SidebarMainComponent>
</SidebarBase>
</>
)


+ 37
- 28
src/widgets/TopBar/index.tsx View File

@@ -10,7 +10,12 @@ const Base = styled('div')({
width: '100%',
height: 'var(--height-topbar, 4rem)',
zIndex: 2,
backgroundColor: 'var(--color-bg, white)',
'> *': {
display: 'block',
width: '100%',
height: '100%',
backgroundColor: 'white',
},
'~ *': {
paddingTop: 'var(--height-topbar, 4rem)',
},
@@ -97,6 +102,7 @@ type Props = {
brand?: React.ReactNode,
menuLink?: React.ReactNode,
userLink?: React.ReactNode,
baseComponent?: React.ElementType,
}

const TopBar: React.FC<Props> = ({
@@ -105,41 +111,44 @@ const TopBar: React.FC<Props> = ({
menuLink,
userLink,
children,
baseComponent: BaseComponent = 'div',
}) => {
const { [span as keyof typeof CONTAINER_COMPONENTS]: ContainerComponent = Container } = CONTAINER_COMPONENTS
return (
<Base>
<ContainerComponent>
{
Boolean(brand as unknown)
&& (
<BrandContainer>
{brand}
</BrandContainer>
)
}
<CenterContainer>
{children}
</CenterContainer>
<ActionContainer>
{
Boolean(menuLink as unknown)
&& (
<MenuLinkContainer>
{menuLink}
</MenuLinkContainer>
)
}
<BaseComponent>
<ContainerComponent>
{
Boolean(userLink as unknown)
Boolean(brand as unknown)
&& (
<LinkContainer>
{userLink}
</LinkContainer>
<BrandContainer>
{brand}
</BrandContainer>
)
}
</ActionContainer>
</ContainerComponent>
<CenterContainer>
{children}
</CenterContainer>
<ActionContainer>
{
Boolean(menuLink as unknown)
&& (
<MenuLinkContainer>
{menuLink}
</MenuLinkContainer>
)
}
{
Boolean(userLink as unknown)
&& (
<LinkContainer>
{userLink}
</LinkContainer>
)
}
</ActionContainer>
</ContainerComponent>
</BaseComponent>
</Base>
)
}


Loading…
Cancel
Save