mjeongriver
article thumbnail
Published 2023. 1. 13. 17:49
day65-react TIL/React

1. 리액트

- 리액트는 자바스크립트 라이브러리 입니다.

- 구조가 MVC, MVVM과 같은 다른 프레임워크등과는 다르게 오직 View만 처리하는 라이브러리 입니다.

 

- SPA란?

- Single Page Application의 줄임말 입니다.

- index.html하나만 로드하고 실행시키는 구조입니다.

- 어떻게?

 

- 번들러(Webpack)가 이 모든것을 해줍니다.

Webpack이란 어플리케이션을 동작시키는데 필요한 자원(JS파일들, CSS, Image 등)을 하나로 묶어서 조합하여 경량화 하여 결과물을 만들어 주는 도구입니다.

- 번들러는 node.JS를 통해 직접 설정 할 수 있지만, 리액트 프로젝트를 생성시 자동으로 포함됩니다.

 

- DOM (Document Object Model) 이란?

- HTML을 이해하기 쉽도록 트리 구조로 만들어진 태그(객체)들 입니다

 

- 리액트의 Virtual DOM 이란?

- HTML에서 DOM을 조작하여 처리할 때, DOM핸들링 자체는 빠릅니다. 하지만, 웹 브라우저가 DOM의 변화를 감지하고, CSS를 적용하고, 처리하는 과정에서 시간이 많이 소요됩니다.

- 리액트의 Virtual DOM은, 이를 추상화시킨 자바스크립트 객체를 이용해서, 바뀐 부분만 부분적으로 리렌더링 하여 사용 하는 방법입니다.

 

 

1] 환경 설정하기

1) node.js 다운 설치

2) 에디터 vscode 설치

3) create-react-app으로 프로젝트 생성하기

- npm create react-app 프로젝트명

4) 프로젝트 시동하기

- npm start

 

2] 다운이 완료되면 terminal에서 new terminal - node -v 입력(안되면 껐다가 켜볼 것) - npm - npm create react-app react-basic - open folder해서 react-basic으로 변경해줄 것(이게 더 편함) - 다시 터미널 열어서 npm start 입력 - 창 나갈 때는 ctrl+c, 다시 키려면 npm start

(app.js에 <p>태그 안 내용 변경 후 npm start 하면 창 내용이 변경됨)

 

module: 필요한 모듈이 들어있음

public: 화면 최상단에 그려지는 부분에서 원래 문법, 공용으로 사용할 파일이 들어있음

src: 소스 코드 탭(가장 핵심이 되는 파일이 app.js, app.css참고해서 그려짐)

 

3] 리액트 코드 살펴보기

1) index.js

index.html에 id가 root인 값을 얻습니다

React.StricMode는 옛날 기능을 사용할때 경고를 출력하는 기능입니다(클래스형 컴포넌트)

root의 render함수는 App컴포넌트를 화면에 그립니다

 

2) App.js

- return (JSX) 문장을 반환합니다.

- export default App 로 모듈을 빼냅니다.

- Index.js 파일에서 <App/> 로 사용됩니다.

 

- JSX란? JS의 확장 문법으로 (HTML에 JS코드를 녹여낸 형태) 입니다.

- 코드를 수정하게 될 때 자동으로 화면이 리렌더링 됩니다. (웹팩 로더가 동작)

- Webpack Loader는 직접 설정(커스터마이징)도 가능하고, create react-app 생성시 자동으로 해줍니다.

Webpack Loader는 다양한 종류가 있습니다.
1. css로더 - css로드
2. file로더 - 폰트,이미지, 파일 등 로드
3. babel로더 - ES6문법을 화면에서 사용할 ES5문법으로 다운그레이드 하여 변환해 줍니다.

- JSX의 문법

1) JSX의 주석 alt + shift + a

2) JSX문법 - 반드시 하나의 태그를 return 해야 합니다.

3) div를 사용하기싫다면 Fragment컴포넌트를 이용하면 됩니다.

4) 함수안에서 만들어진 변수는  중괄호 {name} 로 참조할 수 있다.

5) if문 대신 3항연산자를 이용한다.

6) 화면에 보여주고싶은게 없다면 null을 이용합니다.

7) undefind을 반환하는 상황을 만들면 안 됩니다. 

8) DOM요소에 스타일을 직접 넣을때는 반드시 객체형 객체로 묶고 속성은 카멜 표기법을 사용합니다.

9) class대신 className을 사용합니다.

10) 홀로 사용하는 태그는 닫는태그를 반드시 작성합니다.

 

* app.js

import logo from './logo.svg';
import './App.css';
import { Fragment } from 'react';

function App() {

  const name = "홍길동"; //변수
  const age = 20;

  const myStyle = { color: 'red', backgroundColor: 'yellow', fontSize: 15 };

  return (
    <Fragment>
      <ul>
        <li> 1. 주석 alt+ shift + a{/* 주석 */}</li>
        <li> 2. return 구문은 반드시 1개여야 합니다. 반드시 하나의 태그를 리턴해야 합니다.</li>
        <li> 3. div를 사용하고 싶지 않다면 Fragment 컴포넌트를 사용합니다.</li>
        <li> 4. 함수 안에서 변수를 만들고 사용하고 싶으면 {name}를 사용합니다.</li>
        <li> 5. if문 대신에 3항 연산자를 사용합니다.</li>
        <li> 6. 화면에 그리고 싶은 내용이 없다면 null을 반환 합니다.</li>
        <li> 7. undefined을 반환하는 상황을 만들면 안됩니다.</li>
        <li> 8. dom에 직접 스타일을 하고 싶은 경우는 객체로 묶고 속성은 카멜 표기법(단위 생략시 px)</li>
        <li> 9. class속성 대신에 className을 사용합니다. </li>
        <li> 10. 홀로 사용하는 태그는 반드시 닫는 태그를 작성합니다. (예: {/* <input /> <br/> */}) </li>
      </ul>


      {/* <div style={{color: 'red', backgroundColor : 'yellow'}}> */}
      <div className ="App" style={myStyle}>
        {name === '홍길동' ? '홍길동입니다.' : '홍길동이 아닙니다.'}
        {name === '이순신' ? <h3>이순신입니다</h3> : <h3>이순신이 아닙니다.</h3>}
        {age === 30 ? <h3>20입니다</h3> : null}
      </div>
    


    <div className="App">
      <header className="App-header">
        <img src={logo} className="App-logo" alt="logo" />
        <p>
          안녕하세요~
        </p>
        <a
          className="App-link"
          href="https://reactjs.org"
          target="_blank"
          rel="noopener noreferrer"
        >
          Learn React
        </a>
      </header>
    </div>
</Fragment>
  );
}


export default App;

 

2. 리액트의 components와 props

 

1) 컴포넌트는 함수형, 클래스형 2가지입니다.

- 함수형

function Welcome(props) {
  return <h1>Hello, {props.name}</h1>;
}

- 클래스형

class Welcome extends React.Component {
  render() {
    return <h1>Hello, {this.props.name}</h1>;
  }
}

* 수업에서는 함수형 컴포넌트를 사용합니다.

- 어떻게?

모듈내보내기 - 외부에서 사용할 모듈 이름을 지정합니다.
- export default 이름 
모듈불러오기 - 부모컴포넌트에서 사용
import 이름 from 경로;

이렇게 이해하면 쉬움

 

* 컴포넌트 합성

- 예를 들어 Welcome을 여러 번 렌더링하는 App 컴포넌트를 만들 수 있습니다.

//상위
function App() {
  return (
    <div>
      <Welcome name="Sara" />
      <Welcome name="Cahal" />
      <Welcome name="Edite" />
    </div>
  );
}

//하위
function Welcome(props) {
  return <h1>Hello, {props.name}</h1>;
}

 

2) props(매우 중요)

- 상위 컴포넌트에서 하위컴포넌트로 전달하는 매개변수 입니다. (부모에서 자식으로 데이터를 전달한다)

- 하위 컴포넌트에서 사용할 때는 {}를 이용해서 값을 받을 수 있습니다.

- 상위 컴포넌트에서는 컴포넌트의 속성값을 동일이름으로 지정합니다.

* MyComponent.js, app.js

/* 
p.87p
컴포넌트 선언 방법은 크게 2가지(함수형, 클래스)
컴포넌트는 여러개 일 수 있습니다.
모듈 내보내기 export defalut
모듈 가져오기 import ~~ from 경로

p.96(프롭스)
1. 상위 컴포넌트에서 하위 컴포넌트로 전달하는 매개변수
2. 객체 형태로 전달되기 때문에 {}로 값을 받습니다.
3. props은 읽기 전용입니다. (값은 부모에서 바꿔서 전달합니다.)
*/

import { Fragment } from "react";

const MyComponent = (/* props */ {name, age, email}) => {

    //1st
    // console.log(props);
    // const a = props.name;
    // const b = props.age;
    // const c = props.email; 
    
    //2nd
    // const {name, age, email}= props;

    
    return (
        <Fragment>
        <div>나의 첫번째 컴포넌트</div>
        <div>props값: {name}</div>
        <div>props값: {age}</div>
        <div>props값: {email}</div>
        </Fragment>
    )
}

export default MyComponent;
import { Fragment } from "react";
import MyComponent from "./component/MyComponent";
import MyComponent2 from "./component/MyComponent2";
import MyComponent3 from "./component/MyComponent3";

const App = () => {

    return (
        <Fragment>
            <h3>나의 App.JS</h3>
            {/* props */}
            <MyComponent name={'홍길동'} age={20} email={"aa@naver.com"}/>
            <MyComponent2/>
            <MyComponent3/>
        </Fragment>
    )
}

export default App; //내보내기

 

- props의 기본값 설정하기 (주의 - 대소문자 정확하게 구분함  )

app.js에서 name과 age를 빼면 MyComponent의 기본값으로 나옴

ex. {<MyComponent name={'홍길동'} age={20} email={"aa@naver.com"}/>}

컴포넌트명.defaultProps = {}

MyComponent.defaultProps = {
    addr: '서울시',
    age: 0    
}

 

- props의 타입검증 (주의 - 대소문자 정확하게 구분함  )

컴포넌트명.propTypes = {}

MyComponent.propTypes = {
    name: PropsTypes.string,
    age: PropsTypes.number,
    email: PropsTypes.string.isRequired //필수값(상위컴포넌트에서 반드시 전달)

}

 

* 예제 - myComponent.js, app.js

/* 
p.87p
컴포넌트 선언 방법은 크게 2가지(함수형, 클래스)
컴포넌트는 여러개 일 수 있습니다.
모듈 내보내기 export defalut
모듈 가져오기 import ~~ from 경로

p.96(프롭스)
1. 상위 컴포넌트에서 하위 컴포넌트로 전달하는 매개변수
2. 객체 형태로 전달되기 때문에 {}로 값을 받습니다.
3. props은 읽기 전용입니다. (값은 부모에서 바꿔서 전달합니다.)
*/

import PropTypes from 'prop-types'; //프롭스 타입 검증
import { Fragment } from "react";

const MyComponent = (/* props */ {name, age, email, addr}) => {

    //1st
    // console.log(props);
    // const a = props.name;
    // const b = props.age;
    // const c = props.email; 
    
    //2nd
    // const {name, age, email}= props;

    
    return (
        <Fragment>
        <div>나의 첫번째 컴포넌트</div>
        <div>props값: {name}</div>
        <div>props값: {age}</div>
        <div>props값: {email}</div>
        <div>default props값: {addr}</div>
        </Fragment>
    )
}

/* props의 기본값 지정하기 컴포넌트명.defaultProps = {} */
MyComponent.defaultProps = {
    name: "이름 없음",
    age: 0,
    // email : "지정 안됨",
    addr : "서울시" //addr은 전달되지 않지만 기본값
}

/* props의 타입 검증 propsTypes={} */
MyComponent.propTypes = {
    name : PropTypes.string,
    age : PropTypes.number,
    email : PropTypes.string.isRequired //문자열 타입, 반드시 전달
}

export default MyComponent;
import { Fragment } from "react";
import MyComponent from "./component/MyComponent";
import MyComponent2 from "./component/MyComponent2";
import MyComponent3 from "./component/MyComponent3";

const App = () => {

    return (
        <Fragment>
            <h3>나의 App.JS</h3>
            {/* props */}
            {/* name, age를 빼면 MyComponent의 기본값으로 나옴 */}
            <MyComponent name={"홍길동"} age={20} />
            <MyComponent2/>
            <MyComponent3/>
        </Fragment>
    )
}

export default App; //내보내기

'TIL > React' 카테고리의 다른 글

day70-react  (0) 2023.01.19
day69-react  (0) 2023.01.18
day68-react  (0) 2023.01.18
day67-react  (0) 2023.01.17
day66-react  (0) 2023.01.16
profile

mjeongriver

@mjeongriver

포스팅이 좋았다면 "좋아요❤️" 또는 "구독👍🏻" 해주세요!

검색 태그