From 9752aaf91ec321dbc94ad55535975e78f663da34 Mon Sep 17 00:00:00 2001 From: Evan Moon Date: Mon, 21 Dec 2020 15:33:05 +0900 Subject: [PATCH] =?UTF-8?q?feat(ui-kit):=20Row=20=EC=BB=B4=ED=8F=AC?= =?UTF-8?q?=EB=84=8C=ED=8A=B8=20=EC=B6=94=EA=B0=80=20=EB=B0=8F=20=EA=B7=B8?= =?UTF-8?q?=EB=A6=AC=EB=93=9C=20=EC=9D=B8=ED=84=B0=ED=8E=98=EC=9D=B4?= =?UTF-8?q?=EC=8A=A4=20=ED=99=95=EC=A0=95=20(#27)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * feat(ui-kit): Row 컴포넌트 추가 * chore: PR Template 수정 * feat(ui-kit): add variable width story * feat(ui-kit): remove unused row component * feat(ui-kit): Row컴포넌트의 direction 스토리 추가 --- .github/pull_request_template.md | 24 ++---- .../src/components/Column/index.stories.tsx | 19 ----- ui-kit/src/components/Column/index.tsx | 57 -------------- ui-kit/src/components/Column/types.ts | 1 - ui-kit/src/components/Grid/Column.tsx | 38 ++++++++++ ui-kit/src/components/Grid/Row.tsx | 34 +++++++++ ui-kit/src/components/Grid/index.ts | 2 + ui-kit/src/components/Grid/types.ts | 5 ++ ui-kit/src/components/Row/index.tsx | 11 --- ui-kit/src/components/Row/style.scss | 0 ui-kit/src/components/index.ts | 2 +- ui-kit/src/sass/components/_Column.scss | 75 +++---------------- ui-kit/src/sass/components/_Row.scss | 39 ++++++++++ ui-kit/src/sass/components/_index.scss | 1 + ui-kit/src/sass/utils/_breakpoints.scss | 13 ++++ ui-kit/src/sass/utils/_grid.scss | 2 + ui-kit/src/sass/utils/_index.scss | 2 + ui-kit/src/stories/Grid.stories.tsx | 67 +++++++++++++++++ ui-kit/tsconfig.json | 1 + 19 files changed, 222 insertions(+), 171 deletions(-) delete mode 100644 ui-kit/src/components/Column/index.stories.tsx delete mode 100644 ui-kit/src/components/Column/index.tsx delete mode 100644 ui-kit/src/components/Column/types.ts create mode 100644 ui-kit/src/components/Grid/Column.tsx create mode 100644 ui-kit/src/components/Grid/Row.tsx create mode 100644 ui-kit/src/components/Grid/index.ts create mode 100644 ui-kit/src/components/Grid/types.ts delete mode 100644 ui-kit/src/components/Row/index.tsx delete mode 100644 ui-kit/src/components/Row/style.scss create mode 100644 ui-kit/src/sass/components/_Row.scss create mode 100644 ui-kit/src/sass/utils/_breakpoints.scss create mode 100644 ui-kit/src/sass/utils/_grid.scss create mode 100644 ui-kit/src/stories/Grid.stories.tsx diff --git a/.github/pull_request_template.md b/.github/pull_request_template.md index c8a6fa5a..31e222df 100644 --- a/.github/pull_request_template.md +++ b/.github/pull_request_template.md @@ -1,22 +1,10 @@ - -# 이 Pull Request가 BREAKING CHANGE를 포함하고 있나요? -BREAKING CHANGE가 포함된 PR이라면 Base를 Beta로 잡아주셔야 합니다 ! -확인 후 이 내용은 지워주셔도 됩니다. - +> 이 PR이 BREAKING_CHANGE를 포함하고 있다면 반드시 명시해주세요! -## 주요 변경사항 - +## 변경사항 +어떤 사항이 변경되었는지 자세히 적어주세요! -## 링크 -- 디자인 시안 링크: -- 슬랙 링크: +## 디자인 시안 링크 +디자인 시안 링크를 첨부해주세요! -## 시급한 정도 - ---- -⚠︎ 긴급 : 선 어프루브 후 리뷰를 부탁드립니다. (리뷰는 추후 반영) -🏃‍♂️ 보통 : 최대한 빠르게 리뷰 부탁드립니다. -🐢 천천히 : 급하지 않습니다. +## 집중적으로 리뷰 받고 싶은 부분이 있나요? -## 중점적으로 봐주었으면 하는 부분 - diff --git a/ui-kit/src/components/Column/index.stories.tsx b/ui-kit/src/components/Column/index.stories.tsx deleted file mode 100644 index 5077ecbc..00000000 --- a/ui-kit/src/components/Column/index.stories.tsx +++ /dev/null @@ -1,19 +0,0 @@ -import React from 'react'; -import Column from './index'; -import { Meta } from '@storybook/react/types-6-0'; - -export default { - title: 'Lubycon UI Kit/Column', - component: Column, -} as Meta; - -export const Default = () => ( -
- - Column - - - Column - -
-); diff --git a/ui-kit/src/components/Column/index.tsx b/ui-kit/src/components/Column/index.tsx deleted file mode 100644 index c3bbff69..00000000 --- a/ui-kit/src/components/Column/index.tsx +++ /dev/null @@ -1,57 +0,0 @@ -import React, { HTMLAttributes, useState } from 'react'; - -import { DEFAULT_ELEMENT } from './types'; -import { OverridableProps } from 'types/OverridableProps'; -import classNames from 'classnames'; - -type NumberAttribute = 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12; -type ColumnSize = boolean | 'auto' | NumberAttribute; - -interface ColumnBaseProps extends HTMLAttributes { - xs?: ColumnSize; - sm?: ColumnSize; - md?: ColumnSize; - lg?: ColumnSize; - xl?: ColumnSize; -} -type ColumnProps = OverridableProps< - T, - ColumnBaseProps ->; - -type ColumnResponsive = 'xl' | 'lg' | 'md' | 'sm' | 'xs'; -const sizes: ColumnResponsive[] = ['xl', 'lg', 'md', 'sm', 'xs']; - -const Column = ( - { as, ...props }: ColumnProps, - ref: React.Ref -) => { - const [spans, setSpans] = useState([]); - - sizes.forEach(function (size) { - const { [size]: propValue } = props; - - if (!propValue) { - return; - } - - const { span } = propValue; - const infix = size !== 'xs' ? `-${size}` : ''; - - if (span) { - const currentSpan = span ? `column${infix}-${span}` : `column${infix}`; - setSpans((prevSpans) => [...prevSpans, currentSpan]); - } - }); - - if (spans.length === 0) { - spans.push('column'); - } - - const target = as ?? DEFAULT_ELEMENT; - const Component = target; - - return ; -}; - -export default React.forwardRef(Column) as typeof Column; diff --git a/ui-kit/src/components/Column/types.ts b/ui-kit/src/components/Column/types.ts deleted file mode 100644 index b8ec9e05..00000000 --- a/ui-kit/src/components/Column/types.ts +++ /dev/null @@ -1 +0,0 @@ -export const DEFAULT_ELEMENT = 'div' as const; diff --git a/ui-kit/src/components/Grid/Column.tsx b/ui-kit/src/components/Grid/Column.tsx new file mode 100644 index 00000000..58935d4c --- /dev/null +++ b/ui-kit/src/components/Grid/Column.tsx @@ -0,0 +1,38 @@ +import React, { ElementType, useMemo } from 'react'; +import { ColumnSize, ColumnResponsive, DEFAULT_ELEMENT } from './types'; +import { OverridableProps } from 'types/OverridableProps'; +import classNames from 'classnames'; + +const sizes: ColumnResponsive[] = ['xl', 'lg', 'md', 'sm', 'xs']; + +type ColumnBaseProps = { + [key in ColumnResponsive]?: ColumnSize; +}; + +type ColumnProps = OverridableProps< + T, + ColumnBaseProps +>; + +const Column = ( + { as, ...props }: ColumnProps, + ref: React.Ref +) => { + const spanClasses = useMemo( + () => + sizes.map((size) => { + const { [size]: sizeValue } = props; + return sizeValue ? `lubycon-grid-column--${size}__${sizeValue}` : ''; + }), + [] + ); + + const target = as ?? DEFAULT_ELEMENT; + const Component = target; + + return ( + + ); +}; + +export default React.forwardRef(Column) as typeof Column; diff --git a/ui-kit/src/components/Grid/Row.tsx b/ui-kit/src/components/Grid/Row.tsx new file mode 100644 index 00000000..77c647fc --- /dev/null +++ b/ui-kit/src/components/Grid/Row.tsx @@ -0,0 +1,34 @@ +import React, { ElementType, Ref, forwardRef } from 'react'; +import { DEFAULT_ELEMENT } from './types'; +import classnames from 'classnames'; +import { OverridableProps } from 'src/types/OverridableProps'; + +type BaseAlign = 'flex-start' | 'center' | 'flex-end'; +interface RowBaseProps { + direction?: 'column' | 'row' | 'row-reverse' | 'column-reverse'; + justify?: BaseAlign | 'space-between' | 'space-around' | 'space-evenly'; + alignItems?: BaseAlign | 'stretch' | 'baseline'; +} +type RowProps = OverridableProps; + +const Row = ( + { as, direction = 'row', justify = 'flex-start', alignItems = 'flex-start', ...props }: RowProps, + ref: Ref +) => { + const Component = as ?? DEFAULT_ELEMENT; + + return ( + + ); +}; + +export default forwardRef(Row) as typeof Row; diff --git a/ui-kit/src/components/Grid/index.ts b/ui-kit/src/components/Grid/index.ts new file mode 100644 index 00000000..54468411 --- /dev/null +++ b/ui-kit/src/components/Grid/index.ts @@ -0,0 +1,2 @@ +export { default as Row } from './Row'; +export { default as Column } from './Column'; diff --git a/ui-kit/src/components/Grid/types.ts b/ui-kit/src/components/Grid/types.ts new file mode 100644 index 00000000..975e2928 --- /dev/null +++ b/ui-kit/src/components/Grid/types.ts @@ -0,0 +1,5 @@ +export const DEFAULT_ELEMENT = 'div' as const; + +type ColumnNumberSize = 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12; +export type ColumnSize = boolean | 'auto' | ColumnNumberSize; +export type ColumnResponsive = 'xl' | 'lg' | 'md' | 'sm' | 'xs'; diff --git a/ui-kit/src/components/Row/index.tsx b/ui-kit/src/components/Row/index.tsx deleted file mode 100644 index d3024d4a..00000000 --- a/ui-kit/src/components/Row/index.tsx +++ /dev/null @@ -1,11 +0,0 @@ -import React, { HTMLAttributes } from 'react'; - -interface RowProps extends HTMLAttributes { - gutters: boolean; -} - -type RowColsVal = 1 | 2 | 3 | 4 | 5 | 6; - -export default function Row({ gutters = false, ...props }: RowProps): JSX.Element { - return
{props.children}
; -} diff --git a/ui-kit/src/components/Row/style.scss b/ui-kit/src/components/Row/style.scss deleted file mode 100644 index e69de29b..00000000 diff --git a/ui-kit/src/components/index.ts b/ui-kit/src/components/index.ts index f34fe57f..ed6daaa8 100644 --- a/ui-kit/src/components/index.ts +++ b/ui-kit/src/components/index.ts @@ -1,3 +1,3 @@ export { default as Button } from './Button'; export { default as Text } from './Text'; -export { default as Column } from './Column'; +export { Row, Column } from './Grid'; diff --git a/ui-kit/src/sass/components/_Column.scss b/ui-kit/src/sass/components/_Column.scss index da8a90e8..f98c7a80 100644 --- a/ui-kit/src/sass/components/_Column.scss +++ b/ui-kit/src/sass/components/_Column.scss @@ -1,70 +1,17 @@ -$grid-breakpoints: ( - xs: 0, - sm: 576px, - md: 768px, - lg: 992px, - xl: 1200px, -) !default; - -@function breakpoint-min($name, $breakpoints: $grid-breakpoints) { - $min: map-get($breakpoints, $name); - @return if($min != 0, $min, null); -} - -@function breakpoint-infix($name, $breakpoints: $grid-breakpoints) { - @return if(breakpoint-min($name, $breakpoints) == null, '', '-#{$name}'); -} - -@mixin media-breakpoint-up($name, $breakpoints: $grid-breakpoints) { - $min: breakpoint-min($name, $breakpoints); - @if $min { - @media (min-width: $min) { - @content; - } - } @else { - @content; - } +.lubycon-grid-column { + position: relative; + width: 100%; + padding-right: ($gutter / 2); + padding-left: ($gutter / 2); } -@mixin make-column($size, $columns: $grid-columns) { - flex: 0 0 auto; - width: percentage($size / $columns); -} - -@mixin generate-grid-columns($columns: 12, $gutter: 12px, $breakpoints: $grid-breakpoints) { - %grid-column { - position: relative; - width: 100%; - padding-right: ($gutter / 2); - padding-left: ($gutter / 2); - } - - @each $breakpoint in map-keys($breakpoints) { - $infix: breakpoint-infix($breakpoint, $breakpoints); - - @for $i from 1 through $columns { - .column#{$infix}-#{$i} { - @extend %grid-column; - } - } - .column#{$infix} { - @extend %grid-column; - } - - @include media-breakpoint-up($breakpoint, $breakpoints) { - .column#{$infix} { - flex-basis: 0; - flex-grow: 1; - max-width: 100%; - } - - @for $i from 1 through $columns { - .column#{$infix}-#{$i} { - @include make-column($i, $columns); - } +@each $breakpoint, $size in $breakpoints { + @for $i from 1 through $max-columns { + .lubycon-grid-column--#{$breakpoint}__#{$i} { + @include media-breakpoint($size) { + flex: 0 0 auto; + width: percentage($i / $max-columns); } } } } - -@include generate-grid-columns(); diff --git a/ui-kit/src/sass/components/_Row.scss b/ui-kit/src/sass/components/_Row.scss new file mode 100644 index 00000000..b47b26af --- /dev/null +++ b/ui-kit/src/sass/components/_Row.scss @@ -0,0 +1,39 @@ +@mixin direction($direction) { + &--direction__#{$direction} { + flex-direction: $direction; + } +} +@mixin justify($align) { + &--justify__#{$align} { + justify-content: $align; + } +} +@mixin alignItems($align) { + &--align-items__#{$align} { + align-items: $align; + } +} + +.lubycon-grid-row { + display: flex; + width: 100%; + margin: #{-$gutter / 2}; + + @include direction(row); + @include direction(column); + @include direction(row-reverse); + @include direction(column-reverse); + + @include justify(flex-start); + @include justify(center); + @include justify(flex-end); + @include justify(space-between); + @include justify(space-around); + @include justify(space-evenly); + + @include alignItems(flex-start); + @include alignItems(center); + @include alignItems(flex-end); + @include alignItems(stretch); + @include alignItems(baseline); +} diff --git a/ui-kit/src/sass/components/_index.scss b/ui-kit/src/sass/components/_index.scss index 3f35d98b..b8fdd9d2 100644 --- a/ui-kit/src/sass/components/_index.scss +++ b/ui-kit/src/sass/components/_index.scss @@ -1,4 +1,5 @@ @import './Button'; @import './Text'; @import './Radio'; +@import './Row'; @import './Column'; diff --git a/ui-kit/src/sass/utils/_breakpoints.scss b/ui-kit/src/sass/utils/_breakpoints.scss new file mode 100644 index 00000000..00fcd4cc --- /dev/null +++ b/ui-kit/src/sass/utils/_breakpoints.scss @@ -0,0 +1,13 @@ +$breakpoints: ( + xs: 0, + sm: 576px, + md: 768px, + lg: 992px, + xl: 1200px, +) !default; + +@mixin media-breakpoint($size) { + @media (min-width: $size) { + @content; + } +} diff --git a/ui-kit/src/sass/utils/_grid.scss b/ui-kit/src/sass/utils/_grid.scss new file mode 100644 index 00000000..bda37c22 --- /dev/null +++ b/ui-kit/src/sass/utils/_grid.scss @@ -0,0 +1,2 @@ +$max-columns: 12; +$gutter: 12px; diff --git a/ui-kit/src/sass/utils/_index.scss b/ui-kit/src/sass/utils/_index.scss index 60452a26..9fa07d19 100644 --- a/ui-kit/src/sass/utils/_index.scss +++ b/ui-kit/src/sass/utils/_index.scss @@ -1,3 +1,5 @@ +@import './breakpoints'; +@import './grid'; @import './font'; @import './font-weights'; @import './typography'; diff --git a/ui-kit/src/stories/Grid.stories.tsx b/ui-kit/src/stories/Grid.stories.tsx new file mode 100644 index 00000000..e899aec6 --- /dev/null +++ b/ui-kit/src/stories/Grid.stories.tsx @@ -0,0 +1,67 @@ +import React, { CSSProperties } from 'react'; +import { Column, Row } from 'components/Grid'; +import Text from 'components/Text'; +import { Meta } from '@storybook/react/types-6-0'; +import { colors } from 'src/constants/colors'; + +export default { + title: 'Lubycon UI Kit/Grid', + subcomponents: { Column, Row }, +} as Meta; + +const columns = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12]; +const columnStyle: CSSProperties = { + border: `1px solid ${colors.blue50}`, + backgroundColor: colors.blue40, + height: 100, + color: colors.gray10, + display: 'flex', + justifyContent: 'center', + alignItems: 'center', +}; + +export const Default = () => ( + + {columns.map((column) => ( + + + Column{column} + + + ))} + +); + +export const Direction = () => ( + + {columns.map((column) => ( + + + Column{column} + + + ))} + +); + +export const Responsive = () => ( + + + lg=8 md=4, xs=2 + + auto + + lg=1, md=5, xs=8 + + +); + +export const VariableWidth = () => ( + + + width: 40px + + Column + Column + +); diff --git a/ui-kit/tsconfig.json b/ui-kit/tsconfig.json index a94a6da4..18f35951 100644 --- a/ui-kit/tsconfig.json +++ b/ui-kit/tsconfig.json @@ -6,6 +6,7 @@ "src/*": ["./src/*"], "components/*": ["./src/components/*"], "types/*": ["./src/types/*"], + "constants/*": ["./src/constants/*"], } } } \ No newline at end of file