React 2일차

지나가는 행인·2024년 1월 19일

React

목록 보기
2/11

Web Component (웹 표준)

원하는 내용을 담은 html 코드를 태그 하나로 축약할 수 있음

HTML

<hello-p name="song"></hello-p>

JS

// connectedCallback() 함수는 컴포넌트가 html에 적용될 때 실행됨

if ('customElements' in globalThis) {
  customElements.define("hello-p", class extends HTMLElement {
    connectedCallback() {
      let name = this.getAttribute('name');
      this.innerHTML = `<p>${name} 입니다. 잘 부탁드립니다!</p>`
    }
  });
}
/* 풀어서 작성  위 코드와 의미 같음 */
class hello extends HTMLElement {
  connectedCallback() {
    let name = this.getAttribute('name');
    this.innerHTML = `<p>${name} 입니다. 잘 부탁드립니다!</p>`
  }
}

if ('customElements' in globalThis) {
  customElements.define("hello-p", hello);
}

출력



단점

스타일을 넣으면 오염됨

<p>왜 나도 색이 변해?</p>
<hello-p name="song"></hello-p>
class hello extends HTMLElement {
  connectedCallback() {
    let name = this.getAttribute('name');
    this.innerHTML = `
      <p>${name} 입니다. 잘 부탁드립니다!</p>
      <style>p{color : skyblue}</style>
    `
  }
}

if ('customElements' in globalThis) {
  customElements.define("hello-p", hello);
}

해결법

스타일을 shadow DOM에 넣으면 됨

<p>왜 나도 색이 변해?</p>
<hello-p name="song"></hello-p>
class hello extends HTMLElement {
  connectedCallback() {
    let name = this.getAttribute('name');
    this.attachShadow({ mode: 'open' });
    this.shadowRoot.innerHTML = `
      <p>${name} 입니다. 잘 부탁드립니다!</p>
      <style>p{color : skyblue}</style>
    `
  }
}

if ('customElements' in globalThis) {
  customElements.define("hello-p", hello);
}



slot 사용해 보기

  • slot은 웹 컴포넌트에서 특별한 역할을 하는 태그
  • 부모 컴포넌트에서 자식 컴포넌트로 콘텐츠를 전달하는 데 사용
<euid-stack>
  <span slot="headline">슬롯(Slot)</span>
  <span slot="description">슬롯! 나를 넣어줘</span>
</euid-stack>
if ('customElements' in globalThis) {
  customElements.define('euid-stack', class extends HTMLElement {
    constructor() {
      super();
      this.attachShadow({ mode: 'open' });
      this.shadowRoot.innerHTML = `
        <div class="euid-stack">
            <h2><slot name="headline"></slot></h2>
            <p><slot name="description"></slot></p>
        </div>
        <style>h2 {color : skyblue}</style>
        <style>p {color : pink}</style>
      `;
    }
  });
}



JSX에서 slot (슬롯)

: JSX에 데이터를 끼워 넣으려면 슬롯을 사용 (React에서 slot이라는 명칭은 공식적이지 않음)

📍주의) JSX 내부 슬롯 { } 안에 문을 사용할 수 없음

HTML

<div id="root"></div>
<button type="button">대답</button>

JS

import React from 'https://esm.sh/react';
import ReactDOM from 'https://esm.sh/react-dom';


const question = '지금 무슨 노래 듣고 계세요? '
const answer = '뉴진스의 하입보이요'
const button = document.querySelector('button');

const creatApp = (data) => {
  return (
    <div id="app">
      <h1>
        {data}
      </h1>
    </div>
  )
}

function render(mode = 'question') {
  reactDomRoot.render(creatApp(mode === 'question' ? question : answer));
}

const handleChangeMent = () => {
  if (mode.includes('question')) {
    mode = 'answer';
    button.textContent = '질문'

  }
  else {
    mode = 'question';
    button.textContent = '대답'
  }

  render(mode);
}


const root = document.getElementById('root');
const reactDomRoot = ReactDOM.createRoot(root);
let mode = 'question';

render()

button.addEventListener('click', handleChangeMent)



HTML vs JSX

  • JSX는 예약어 사용 x
    • class, for, while, if ....

  • JSX는 대소문자를 구분한다

  • aria-속성, data-작명은 '-'을 사용해도 됨
    • aria-label, aria-hidden, data-index ...

  • JSX는 style 속성을 설정할 때는 JavaScript 객체로 설정
    • style={{ color: 'blue'}}
    • style={{ color: 'green', fontSize: '20px' }}
// ex)
<div id="app">
  <h1 style={{ color: 'blue', fontSize: '20px' }}>
    안녕하시오
  </h1>
</div>

  • 공백 추가 시
    • HTML - &nbsp;
    • JSX - {' '}

0개의 댓글