[ReactNative] Component - 재사용성을 고려한 컴포넌트 구성

bi_sz·2023년 11월 1일
0

ReactNative

목록 보기
21/37
post-thumbnail

🔶Component🔶

코드를 작성하다보면 중복된 코드가 생겨납니다.
중복된 코드를 반복적으로 작성하게된다면 코드 양이 많아지게되고, 코드 양이 많아질수록 유지보수 난이도는 증가합니다.

한 번 작성된 코드를 재사용할 수 있도록 Component로 만들어주게 된다면 중복된 코드를 작성하지 않아도 됩니다.

하지만 너무 잦은 컴포넌트화는 예상하지 못한 변경점이 생기면서 버그로 이어질 수 있습니다.

🔹 Atomic design patten

작은단위부터 큰 단위까지의 컴포넌트를 조합해 만들어가는 것 입니다.

ATOMS -> MOLECULES -> ORGANISMS -> TEMPLATES -> PAGES

🔹 Dumb Component

보여주는 일에만 집중하는 Component 입니다.

state를 가지고 있지 않고, props를 통해 어떻게 보여줄지에 대해서만 집중한 Component 입니다.

가장 작은 단위의 ATOMS Component를 만들 때에는 state가 필요한 경우는 드물기 때문에 Dumb Component인 경우가 많습니다.

🔹 Smart Component

상태를 가지로 스스로 변하는 Component 입니다.

스스로 state를 가지고 있고, 어떠한 계산을 통해서 변하는 것 까지 가능한 Component 입니다.

🔸 Component 를 만드는 Timing

가장 작은 단위는 우선적으로 Component 로 만들어 재사용하고,
Molcule 이상의 단계들 중에서 3회이상 반복되면 Component 로 만들어주는 것이 좋습니다.


프로젝트 생성

> npx create-expo-app example_component

git repository 에도 연결해주었습니다.


Compononet Design 해보기

🔷 ATOM Component 🔷

앱을 구성하는 가장 작은 단위인 TypographyText, Button, ImageComponent 로 만들어주려 합니다.

이런 작은 단위의 구성요소들은 앱을 만들기 시작할 때 만들어두지 않으면, 추후에는 Component화가 어렵고, 화면마다 다른 Component를 사용하게 되는 경우가 많습니다.

🔻 Text

src폴더를 만들고 그 안에 components 폴더를 만들고, 그 안에 Typography.js 파일을 생성해주었습니다.

fontSizecolor를 조절할 수 있 는 간단한 컴포넌트입니다.

App.js에서 사용해주었습니다.

RNText 요소 안에 입력한 문구가 잘 표시됩니다.

Typography 컴포넌트에서 fontSize, colorprop으로 받을 수 있게 해두었으니, 원하는 색상과 크기로 변경하기 위해 prop을 넘겨주었습니다.

Text의 경우에는 중첩하여 사용할 수도 있습니다.

RNText를 중첩하여 사용하여, 텍스트 부분의 색상만 다르게 해주었습니다.

TypeCheck

fontSize prop에 숫자가 아닌 문자열이나 다른 값이 들어가게 된다면, 버전에 따라서 오류가 나거나, 아에 없는 값인것 처럼 적용이 안된 채로 동작하는 경우가 있습니다.

prop-types 를 사용해서 prop에 어떤 단위가 들어오는지 검증해보려 합니다.

> npm install prop-types

우선 라이브러리를 install 해주었습니다.

TypographypropTypes 를 세팅해주었습니다.

App.js 에서 fontSizeprop에 문자열을 넘겨주었습니다.

fontSizetypenumber여야하는데 string이라고 Warring을 띄워줍니다.

해당 기능은 JavaScript에서 type Check를 할 수 있다는 점을 알기 위해 사용해 보았습니다.


🔻 Image

LocalImage

src 폴더의 components 폴더 안에 LocalImage.js 파일을 생성해주었습니다.

이미지의 sourcestyleprops으로 받고, style 중에서 widthheight를 직관적으로 받아주었습니다.

App.js에서 사용해주었습니다.

expo에서 기본으로 제공해주는 assets폴더 안의 이미지 경로를 localAsset으로 주었고, widthheigh를 넘겨주었습니다.

이미지가 표시된 모습입니다.


RemoteImage

src폴더의 components 폴더 안에 RemoteImage.js 파일을 만들어주었습니다.

uristyle을 받아줍니다.

App.js에서 이미지 주소와 크기를 넣어주었습니다.

이미지가 잘 출력된 모습입니다.


🔻 Icons

src폴더의 components 폴더 안에 Icons.js 파일을 만들어주었습니다.

name, size, color props을 받아옵니다.

App.js에서 사용해주었습니다.

노란색 home 아이콘이 나타난 모습입니다.

https://icons.expo.fyi/Index

아이콘의 종류나 name 등의 정보는 해당 사이트에서 확인할 수 있습니다.


🔻 Badge

src폴더의 components 폴더 안에 Badge.js 파일을 만들어주었습니다.

View 로 감싸주고 style을 지정해주었습니다.
좌측상단에 고정되도록 해주었습니다.

App.js에서 사용해주었습니다.

TypographyIconBadge를 적용해보았습니다.

TextIcon 우측위에 Badge가 표시된 모습입니다.


🔻 Button

src폴더의 components 폴더 안에 Button.js 파일을 만들어주었습니다.

눌렀을때 동작할 함수인 onPress와 터치영역인 htiSlopprops으로 받아줍니다.

App.js에서 사용해줍니다.

버튼을 눌렀을 때 로고가 잘 찍히는 모습입니다.

Icon으로도 버튼을 만들어주었습니다.

![](https://velog.velcdn.com/images/bi-sz/pos![](https://velog.velcdn.com/images/bi-sz/post/8e0e78de-f55b-4c93-ae61-eceda5a20dc1/image.png)
t/afb6614f-0fef-4bd6-b5a4-c72e6ae0faea/image.png)

분홍색 아이콘이 보이고, 이 아이콘은 버튼으로 동작합니다.

눌렀을 때 로고가 잘 찍히는 모습입니다.


🔻 Divider

구분선입니다.

src폴더의 components 폴더 안에 Divider.js 파일을 만들어주었습니다.

View로 감싸주고 style을 지정해주었습니다.

App.js에서 사용해주었습니다.

구분선이 잘 표시된 모습입니다.


🔻 Spacer

여백을 주는 컴포넌트입니다.

src폴더의 components 폴더 안에 Spacer.js 파일을 만들어주었습니다.

App.js에서 중간중간 추가해주었습니다.

Spacer 컴포넌트를 추가한 부분에 공간이 생긴 모습입니다.


🔷 MOLCULE Component 🔷

🔻 TabIcon

src폴더의 components 폴더 안에 TabIcon.js 파일을 만들어주었습니다.

이전에 만들어두었던 ATOM ComponentBadgeIcon을 사용해주었습니다.

App.js에서 사용해주었습니다.

익숙한 아이콘이네요. 해당 어플의 알람 여부 혹은 개수를 알려주던 아이콘의 모습입니다.

TabIcon 컴포넌트에서 조건을 추가하였습니다.

visibleBadge가 있으면 Badge를 보여주고, 아니면 IconReturn되도록 수정해주었습니다.

App.js에서 두 가지 경우 모두 사용해보겠습니다.

visibleBadge 의 여부에 따라 Badge가 있는 Icon과, Badge가 없는 Icon이 보여집니다.


🔻 Header

Compound Component Pattern

Header 의 경우는 요구사항에 따라 변경되는 경우가 많기 때문에 유연하게 대응해야합니다.

Component 자체에 SubComponent API를 제공해서 SubComponent가 어떤 형태인지 제공해줍니다.

일반적으로는 Componentprops를 통해서 어떻게 보여줄지를 작성하지만, Compound Component Pattern 을 적용하게되면 새로운 Component가 추가됐을때 기존 코드를 보고 옵션에 대한 분기처리를 할 필요가 없어집니다.

SafeAreaContext

상단바, 혹은 하단바 영역을 제외한 영역에 화면이 그려지도록 도와주는 라이브러리입니다.

npm install react-native-safe-area-context

라이브러리를 install 해주었습니다.

src 폴더의 components 폴더 안에 HeaderWithoutCompound.js 파일을 생성해주었습니다.

return으로 SafeAreaContext.Cunsumer를 사용해주었고, insets 이라는 것을 이용해줍니다.

RN에서 제공해주는 Dimensions를 이용해주었습니다.

widthDimesions, height는 일반적으로는 56 정도로 사용합니다.
현업에서는 height는 보통 지정해준다고 합니다.

title이 들어갈 Typography 부분, leftIcon, rightIconSpacer 로 여백을 주었습니다!

App.js 에서 HeaderWithoutCompound를 사용해주었고, title을 작성해주었습니다.

Component를 이래서 사용하나봅니다..

그 동안은 Header 부분을 App.js에 대충 작성했던거 같은데 차이점이 확 드러나네요.

이렇게 작성해둔 Header에 대해 수정사항이 생긴다면 title 혹은 Icon 리소스를 변경해야한다면 Header에서 Button의 추가,제거등의 분기가 이루어지려면 자체 스택을 고쳐야합니다.

Header의 수정으로 인하여 영향받는 모든 화면을 재검수해야합니다.

수정으로 인한 오류를 모두 잡아내지 못한다면 버그가 되게됩니다. 모든 화면에서 헤더가 잘 표시되는지 테스트해야하는 상황이 생깁니다.

이런상황을 대비해서 Compound Component Pattern을 통해 관리할 수 있습니다.


🔸 Compound Component Pattern 적용한 Header

Header

src폴더의 components 폴더 안에 Header 폴더를 하나 더 만들었고 그 안에 Header.js 파일을 추가해주었습니다.

Header 에 적용할 Component들을 구분하기 위해 따로 폴더를 추가해주었습니다.

기본적인 Headerroot가 될 코드를 작성해주었습니다.

처음 작성할땐 어지러웠는데 한 번 더 보니까 이젠 그래도 구조를 알겠네요.

HeaderTitle

Header폴더 안에 HeaderTitle.js 컴포넌트를 만들어주었습니다.

title이 들어갈 Typograghyreturn 해줍니다!

HeaderButton

Header폴더 안에 HeaderButton.js 컴포넌트를 만들어주었습니다.

마찬가지로 Icon Buttonreturn 해줍니다.

rootHeader 컴포넌트에 넣어줍니다!

App.js 에서 기존 HeaderWithoutCompound 대신 새로 만든 Header 컴포넌트를 적용해주었습니다.

HeaderHeader.Icon, Header.TitleIconTitleprop을 넘겨줍니다.

Header가 나타났는데 space-between을 주어서 그런 것 같습니다. 이것을 해치지 않기 위해서 컴포넌트를 하나 더 추가하겠습니다.

HeaderGroup

Header폴더 안에 HeaderGroup.js 컴포넌트를 만들어주었습니다.

Header 컴포넌트에도 추가해주었습니다.

App.js에서 HeaderGroup으로 묶어주었습니다.
close Icon도 추가해주었습니다.

Header가 완성된 모습입니다.


🔶 정리 🔶

Compound Component Pattern 적용한 Header를 보니 직관성이 좋아 Header가 어떻게 작성되어있는지 한 눈에 들어옵니다.

전체 코드가 길어진 감이 있고 전체 파일의 길이가 길어졌지만, 각각의 Component로 나눠서 구현을 해 두었기 때문에 어떠한 요구사항이 들어왔을 때 수정이 용이하며, 버그의 위험도도 낮아집니다.

이번 게시글에서 작성한 많고 많은 Component들을 작성하면서 솔직히 지겨웠는데요,,

이전에 만든 프로젝트를 진행하면서도 이미 알고있던 내용들 반복하는 것 같아서 타자연습을 엄청 열심히한 느낌이고 영타가 빨라진 장점만 느끼고 있었습니다.

Header Compononet를 작성하면서 미리 만들어 둔 Component들을 사용하니까 훨씬 빠르고 아 이래서 ATOM Component 를 프로젝트를 시작하면서 미리 만들어두는구나를 느꼈습니다.

이번 게시글에서 작성한 컴포넌트들은 이후 다른 프로젝트를 진행하면서도 유용하게 사용할 것 같습니다.

옵션을 추가하거나 상태를 추가하여 언제든지 확장할 수 있겠네요.

0개의 댓글