출처: https://bumcrush.tistory.com/182 [맑음때때로 여름]

구글링 해보니까 이게 제일 비슷한 것 같아서 이걸로 퍼옴

 

생성과정(start) / 갱신과정(props changed & state changed) / 소멸과정 (componentWillUnmount)

shouldComponentUpdate 함수의 반환값(true/false)에 따라 갱신과정은 생략되기도 한다. (갱신과정생략)

 

 

 

생성 과정의 생명주기 함수들 실행해보기

 

1. constructor(props)함수

맨 처음에 생성될 때 한번만 호출되며 상태(state)를 선언할 떄 사용된다.

항상 super()함수를 가장 위에 호출해야 한다.

=> super() 함수에는 프로퍼티와 생명 주기 상태등을 초기화하는 과정을 포함하고 있기 때문.

 

2. render()함수

데이터가 변경되어 새 화면을 그려야 할 때 자동으로 호출되는 함수

render()가 반환하는 JSX를 화면에 그려준다.

 

3. static getDerivedStateFromProps(props, state)함수 (이름왜케길어)

정적 함수로, 함수안에서 this.props나 this.state와 같은 방법으로 값에 접근이 불가하다.

만약 값에 접근하려면 인자로 전달된 props, state를 이용해야 하는데,

이때 props는 상위 컴포넌트에서 전달된 값이며, state는 현재 컴포넌트의 state값이다.

> 이 함수는 상위 컴포넌트에서 전달받은 프로퍼티로 state값을 연동할 때 주로 사용하며,

   반환 값으로 state를 변경한다.

 

4. componentDidMount()함수

render함수가 JSX를 화면에 그린 이후 호출되는 함수

=> 컴포넌트가 화면에 모두 표횬된 이후에 해야 하는 작업들은 여기서하면 된다.

 

 

 

 

[그림에서는 START부분]

import React from "react";

class LifecycleExample extends React.Component {
  static getDerivedStateFromProps() {
    console.log("getDerivedStateFromProps 호출");
    return {};
  }

  constructor(props) {
    super(props);
    //getDerivedStateFromProps()함수를 사용하므로
    //경고메세지를 건너뛰기 위해 state 초기값 설정

    this.state = {};
    console.log("constructor 호출");
  }

  componentDidMount() {
    console.log("ComponentDidMount 호출");
  }

  componentDidUpdate() {
    console.log("ComponentDidUpdate 호출");
  }

  componentWillUnmount() {
    console.log("ComponentWillUnmount 호출");
    return {};
  }

  getSnapshotBeforeUpdate() {
    console.log("getSnapshotBeforeUpdate 호출");
    return {};
  }

  shouldComponentUpdate() {
    console.log("shouldComponentUpdate 호출");
    return true;
  }

  render() {
    console.log("render 호출");
    return null;
  }
}

export default LifecycleExample;

 

 

변경 과정의 생명주기 함수들 실행해보기

상위 컴포넌트의 프로퍼티나 state의 변화가 생기면 실행된다.

 

1. shouldComponentUpdate(nextProps, nextState)

프로퍼티를 변경하거나, setState()함수를 호출하여 state값을 변경하면 '화면을 새로 출력해야하는지' 판단하는 함수

** 이 함수는 화면을 새로 출력할지 말지 판단하며, 데이터 변화를 비교하는 작업을 포함하므로 리액트 성능에 영향을 많이 준다.

forceUpdate()함수를 호출하여 강제로 화면을 출력하면 이함수는 호출되지 않는다.

 

2. getSnapshotBeforeUpdate(prevProps, prevState)

컴포넌트의 변경된 내용이 가상화면에 완성된 이후에 호출되는 함수

컴포넌트가 화면에 실제로 출력되기 전에 호출되므로 화면에 출력될 엘리먼트의 크기, 또는 스크롤 위치등의 DOM정보에 접근할 때 사용된다.

 

3. componentDidUpdate(prevProps, PrevState, snapshot)함수

실제 화면에 출력된 이후 호출되는 함수

부모 컴포넌트로부터 전달된 이전 프로퍼티(prevProps)와 이전 state값(prevState)과 함께, getSnapshotBeforeUpdate() 함수에서 반환된 값(snapshot)을 인자로 전달 받는다.

이 값들을 이용하여 스크롤의 위치를 옮기거나 커서를 옮기는 등의 DOM정보를 변경할 때 사용된다.

 

 

  componentDidMount() {
    console.log("ComponentDidMount 호출");
    // state값을 변경
    this.setState({updated : true});
  }

 

shouldComponentUpdate() 반환값을 false로 하면

-> 리액트 엔진은 데이터 비교 후 변경 사항이 없다고 판단하므로, 변경과정의 생명주기 함수가 실행되지 않는다.

  shouldComponentUpdate() {
    console.log("shouldComponentUpdate 호출");
    // false로 변경
    return false;
  }

결과값과 상관없이 화면 동기화를 진행하고 싶다면 forceUpdate()함수를 사용해야 한다.

  componentDidMount() {
    console.log("ComponentDidMount 호출");
    this.forceUpdate();
  }

 

소멸 과정의 생명주기 함수들 실행해보기

컴포넌트가 화면에서 생략되면 시작

 

componentWillUnmount()

컴포넌트가 소멸되기 직전에 호출되는 함수

보통 컴포넌트에서 감시하고 있는 작업들을 해제할 때 필요한 함수이다 (뭔말이지?)

예를 들어 컴포넌트에 setInterval()함수가 사용되었다면 이 함수에서 setInterval()함수를 clearInterval()함수로 해제해야 한다. (그렇군..)

이러한 해제 작업이 생략되면 메모리 누수현상이 발생하여 브라우저가 멈추기도 하기 때문이다.

 

 

 

App 컴포넌트에서 LifecycleExample 컴포넌트를 그리지 않도록(null) 코드를 작성

/// app.jsx


import React from "react";
import LifecycleExample from "./03/LifecycleExample";

class App extends React.Component {
  constructor(props) {
    super(props);
    this.state = { hadDestroyed: false };
  }
  componentDidMount() {
    this.setState({ hadDestroyed: true });
  }

  render() {
    return (
      <div>
        <div>{this.state.hadDestroyed ? null : <LifecycleExample />}</div>
      </div>
    );
  }
}

export default App;

 

 

카운터 프로그램을 만들며 생명주기 함수 사용해보기

 

 

counter.jsx

: state의 초기값을 설정할 때 props.count와 같이 프로퍼티로 받은 값을 사용한다.

import React, { Component } from "react";

class Counter extends Component {
  constructor(props) {
    super(props);
    this.state = {
      // count 초기값을 프로퍼티에서 전달된 값으로 설정한다.
      count: props.count,
    };
    this.increaseCount = this.increaseCount.bind(this);
  }
  increaseCount() {
    this.setState(({ count }) => ({
      count: count + 1,
    }));
  }
  render() {
    return (
      <div>
        현재카운트 : {this.state.count}
        <button onClick={this.increaseCount}>카운트증가</button>
      </div>
    );
  }
}

export default Counter;

NewCount.jsx

gerDerfivedStateFromProps() 함수를 사용하여 변경된 프로퍼티 값으로 state값을 갱신한다.

app컴포넌트가 전달한 최초의 프로퍼티 값은 state.count에 저장되며,

NewCounter 컴포넌트는 state.newCount로 증가값을 따로 분리하여 관리

=> state.count가 아니라 state.newCount로 증가값을  관리하는 이유는,

getDerivedStateFromProps()함수는 다른 프로퍼티가 변경되어도 호출되기 때문이다.

import React, { Component } from "react";

class NewCounter extends Component {
  constructor(props) {
    super(props);
    this.state = {};
    this.increaseCount = this.increaseCount.bind(this);
  }

  static getDerivedStateFromProps(props, state) {
    const { count } = props;
    return {
      //프로퍼티에서 전달된 count값을 보관한다
      count,
      newCount:
        count === state.count
          ? //프로퍼티가 변경되지 않았다면 기존state값으로 설정
            state.newCount
          : //변경되었다면 변경된 값으로 설정
            count,
    };
  }

  increaseCount() {
    this.setState(({ newCount }) => ({
      newCount: newCount + 1,
    }));
  }
  render() {
    return (
      <div>
        현재카운트 : {this.state.newCount}
        <button onClick={this.increaseCount}>카운트증가</button>
      </div>
    );
  }
}

export default NewCounter;

 

 

import React from "react";
import Counter from "./03/Counter";
import NewCount from "./03/NewCounter";

class App extends React.Component {
  constructor(props) {
    super(props);
    this.state = { count: 10 };
    this.resetCount = this.resetCount.bind(this);
  }

  resetCount() {
    this.setState(({ count }) => ({ count: count + 10 }));
  }

  render() {
    return (
      <div>
        <div>
          <Counter count={this.state.count} />
        </div>
        <div>
          <NewCount count={this.state.count} />
        </div>
        <button onClick={this.resetCount}>
          {this.state.count + 10}으로 초기화
        </button>
      </div>
    );
  }
}

export default App;

 

 

NewCounter 컴포넌트만 gerDerivedStateFromProps()함수로 App 컴포넌트부터 갱신된 프로퍼티 값을 동기화 했기 때문에 초기화버튼은 NewCounter에만 적용된다.

Counter 컴포넌트는 처음 생성될때만 프로퍼티 값을 설정하므로 갱신 과정에서는 변경X

 

 

 

 

 

 

 

 

 

 

 

 

 

 

 

CRA (create-react-app)

- 리액트 개발 환경을 직접 구축하려면 많은 지식과 노력이 필요한데 자동으로 구축해준다.

(webpack, babel, jest, eslint, polyfill, hmr, css후처리)

- 페이스북에서 관리하는 공식 툴이라 믿고 사용할만 하다~

- 서버사이드 렌더링을 지원하지 않음. (할수있지만 깔끔한 방법이없음)

 => 서버사이드 렌더링이 필요하다면 Next.js를 사용하자

 

 

참고 : (왜냐면 서버사이드 렌더링이 뭔지모르니깐..ㅎ)

 

[주니어탈출기] 서버사이드렌더링(SSR) & 클라이언트사이드렌더링(CSR)

서버사이드렌더링 & 클라이언트사이드렌더링 왜 모바일의 시대에 등장한 클라이언트사이드렌더링 Single Page Application(SPA)! 고려해야할 점들이 있다. SPA는 최초 한 번 페이지 전체를 로딩한 후 데

velog.io

 

 

인강버전은 뭔가 자꾸 에러가나서 책에 나온 버전으로 cra설치함

npm install -g yarn // yarn설치

npm install -g create-react-app // cra설치

create-react-app cra-test // cra-test라는 app 만들어줌

yarn start // 시작

3000번 포트로 들어가서 리액트앱화면뜨면 성공

 

[리액트] 개발환경 설치하기

1. 노드 버전 매니저로 노드JS설치하기 1-1. NVM 설치하기 github.com/coreybutler/nvm-windows/releases 1-2 nvm이 잘 설치 됐는지 cmd로 확인해보기 1-3 NVM으로 노드제이에스 설치하기 (주의 10.16.2 버전으..

javappo.tistory.com

 

 

cra버전이 올라가면 대부분 react-scripts를 수정해주면 된다고 한다.

browerslist의 0.2는 0.2퍼센트 이상의 점유율을 가진 브라우저를 대상으로 하겠다는 뜻

(자세한 문법은 브라우저 리스트에 대해서 검색해보면 자세히 알 수 있다)

 

CRA의 4가지 명령어

 

start

: 개발모드로 실행할떄 사용, 여러가지 최적화가 적용이 안된 상태로 실행 (배포할때 사용X)

: 기본적으로 http로 실행된다.

: https로실행하고싶다면? => set HTTPS=true&&npm start  (혹은 yarn start).. (ㅡㅡ맥북이랑 윈도우랑다름..)

create-react-app.dev/docs/using-https-in-development/

 

Using HTTPS in Development | Create React App

Note: this feature is available with react-scripts@0.4.0 and higher.

create-react-app.dev

 

build

: 배포할 때 사용

: npm run build  or yarn run build => 빌드를 하면 정적 파일 생성

: 별도로 서버에 애플리케이션을 실행하지않기때문에 서버사이드 렌더링으로 동작할 수 없다함..(아직뭔말인지ㅎ)

: 빌드 시 작은 이미지는 base64로 자바스크립트에 저장 => 빠르게 하려고

\\react developer tools

 

test

npm test => app.test.js

__test__ 폴더에 넣으면 다 테스트파일로 인식

 

eject

: react scripts를 사용하지 않고, 모든 설정 파일을 추출하는 명령어 

: cra를 기반으로 직접 개발환경을 구축하고 싶을때 사용

: 추출을 하지 않으면 cra 에 기능이 추가됐을때 react scripts 버전만 올리면 되지만, 추출하면 직접 수정해야함

 

caniuse.com

브라우저별로 지원여부나옴 => 특정기능 중 사용하고 싶은 것입력 (ex: padStart)

지원하지 않는 브라우저에서도 지원하고 싶다 ==> polyfill 추가해야함 => 보통 core-js라는 것을 많이 사용함

cra에는 기본적으로 core-js가 내장되어있으므로 (원래는 설치해야하지만)

core-js에서 padstart를 검색하고 import해서 사용 import 'core-js/~!##$#' (복사내용)

 

환경변수

개발, 테스트 환경별로 다른값을 쓸때 유용

process.env.{변수 이름}

process.env.NODE_ENV [기본]

npm start로 실행하면 development , npm test로실행하면 test 

 

웹팩은 오픈 소스 자바스크립트 모듈 번들러로써 여러개로 나누어져 있는 파일들을 하나의 자바스크립트 코드로 압축하고 최적화하는 라이브러리입니다.

 

웹팩의 기본 개념 이해하기

: 다양한 기능 제공

- 파일 내용을 기반으로 파일 이름에 해시값 추가 => 효율적으로 브라우저 캐싱 이용

- 사용되지 않은 코드 제거

- JS에서 CSS,JSON, 텍스트 파일 등을 일반 모듈처럼 불러오기

 (자바스크립트 안에서 여러가지를 처리할 수 있다)

- 환경변수 주입

 

* 웹펙을 사용하는 가장 큰 이유 => 모듈 시스템(ESM, commonJS)을 사용하고 싶어서

 

- 웹사이트가 점점 동적으로 변하면서 많은 js파일이 필요하게 됨

=> 선언된 자바스크립트 파일의 순서에 따라서 동작이 달라질 수 있다.

=> 외부라이브러리와 내부의 파일들이 서로 싱크가 맞아야 하는데 그 문제를 해결해준다.

  (변수 이름 충돌 같은 것은 빌드단계에서 잡아낼 수 있고 외부라이브러리는 npm으로 관리를 할 수가 있다고 함..)

- 요즘 브라우저는 ESM을 지원해서 웹팩을 사용하지 않고도 서비스 할수 있지만 오래된 브라우저도 서비스를 해야하고, 많은 오픈 소스가 commonJS로 작성되어있고, 요즘 브라우저는 commonJS를 처리를 못한다.

 

웹팩에 필요한 패키지 설치

npm install webpack wepack-cli react react-dom

 

npx 실행

 

 

 

나중에 읽어볼 링크

 

[JS][WEBPACK] 1. 웹팩이란 무엇인가

웹팩은 오픈 소스 자바스크립트 모듈 번들러로써 여러개로 나누어져 있는 파일들을 하나의 자바스크립트 코드로 압축하고 최적화하는 라이브러리입니다.

medium.com

 

바벨 (Babel)

 : ES6 문법을 ES5 문법으로 변환해주는 용도로 주로 사용

 : 리액트에서는 jsx 문법을 createElement 함수로 호출하는 코드로 변환하기 위해 사용한다.

 

최근) 코드에서 주석을 제거하거나, 코드를 압축하는 용도로 사용되기도 한다.

 

 

// 바벨설치하기 

 

package.json 파일생성

(npm은 node.js를 설치하면 알아서 설치됨.. 노드 패키지 매니저)

 

npm init -y를 하면 생성

npm install @babel/core @babel/cli @babel/preset-react 설치

(강의에선 npm install @~~ @~~ @~~ 해서 한방에 설치했으나 나는 안되서 한개씩..)

 

core : 바벨의 핵심 기능을 가지고 있는 패키지

cli : cli에서 사용할 바이너리가 들어있음

preset-react : 리액트를 위한 플러그인 여러개를 모아놓은 것

 

바벨에는 프리셋과 플러그인이라는 개념이있고

플러그인 : 하나의 변환하는 기능을 의미

프리셋 : 그런 여러개의 플러그인을 모아놓은 것 (특정 목적을 위해)

npx babel --watch src --out-dir . --presets @babel/preset-react 

(watch모드로 동작을 시킴 / src폴더에 있는 것을 현재 폴더로 출력을 해줌

/ 프리셋으로 이전에 설치했던 preset-react를 쓰겠다는뜻..)

npx를 명령어를 사용하면 노드모듈안의 바벨 바이너리를 실행해준다.

(바벨을 설치하지 않았다면 npx가 알아서 바벨을 설치해주는 똑똑이짓을함)

simple1.js복사~

 

복사된 simple1.js는 원본이 바뀔때마다 컴파일해서 createElement코드로 변환된다.

 

 

 

<!DOCTYPE html>
<html lang="">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title></title>
</head>

<body>
    <h2>안녕하세요</h2>    
    <div id="root"></div>

    <h3>root1</h3>
    <div id="root1"></div>
    <h3>root2</h3>
    <div id="root2"></div>
    <h3>root3</h3>
    <div id="root3"></div>

    
    <script src="react.develpment.js"></script>
    <script src="react-dom.development.js"></script>    
    <script src="simple1.js"></script>

</body>
</html>
function LikeButton(){
    // likebutton에 liked라는 상태값을 추가
    const [liked, setLiked] = React.useState(false);
    const text = liked ? '좋아요 취소' : '좋아요';

    return React.createElement(
        'button',
        { onClick: () => setLiked(!liked)},
        text,     
    )
}

// const domContainer = document.getElementById('root');
// ReactDOM.render(React.createElement(LikeButton), domContainer);

const domContainer = document.getElementById('root');
ReactDOM.render(
    React.createElement(
        'div',
        null,
        React.createElement(LikeButton),
        React.createElement(LikeButton),
        React.createElement(LikeButton),
    ),
    domContainer
);



const domContainer1 = document.getElementById('root1');
ReactDOM.render(React.createElement(LikeButton), domContainer1);
const domContainer2 = document.getElementById('root2');
ReactDOM.render(React.createElement(LikeButton), domContainer2);
const domContainer3 = document.getElementById('root3');
ReactDOM.render(React.createElement(LikeButton), domContainer3);


// React.createElement(
//     'div',
//     null,
//     React.createElement('p',null,'hello'),
//     React.createElement('p',null,'world'),
// );

 

ithub.tistory.com/264

 

React Error Target container is not a DOM element

안녕하세요. 오늘은 웹 작업을 할때 발생하는 Target container is not a DOM element 에러에 대해서 알아보겠습니다. 리액트를 사용할때, (리액트를 사용하지 않을때도 발생할 수 있습니다.) UInvariant

ithub.tistory.com

 

 

javascript 파일을 head에서 불러올 경우 하단에 있는 body 엘리먼트가 읽혀지지 않은 상태에서 javascript 파일이 호출되어 DOM element를 참조할 경우 에러가 발생하게 된다

 

해결 방법
1.  javascript 파일을 body 하단부에 등록해주는 방법
2. javascript의 실행을 DOM이 load 되고 난 이후에 발생하도록 하는 방법

 

 

나는 빨간 표시를 아랫부분으로 내려줌! (해결방법1)

 

 

 

왜그런가했네..

 

 

컴포넌트에 데이터를 전달하는 프로퍼티

- 프로퍼티 기초 알아보기

import React from 'react';
import PropTypes from 'prop-types';

class PropsComponent extends React.Component {
  render() {
    return <div className="message-container">{this.props.name}</div>;
  }
}

// 자료형을 선언하는 예제
PropsComponent.propTypes = {
  name: PropTypes.string,
};

export default PropsComponent;
import './App.css';
import { Component } from 'react';
import PropsComponent from './03/PropsComponent';

class App extends Component{
  render(){
    return(
      
      <PropsComponent name="두잇 리액트"/>
    )
  }
}

export default App;

 

- 다양한 프로퍼티 사용하기

import React, { Component } from 'react';
import PropTypes from 'prop-types';

class ChildComponent extends Component {
  render() {
    const { boolValue, numValue, arrayValue, objValue, nodeValue, funcValue } = this.props;

    return (
      <div>
        <span>불리언 값 : {boolValue}</span>
        <span>숫자값 : {numValue}</span>
        <span>배열값 : {arrayValue}</span>
        <span>객체값 : {String(objValue)}</span>
        <span>노드값 : {nodeValue}</span>
        <span>함수값 : {String(funcValue)}</span>
      </div>
    );
  }
}
ChildComponent.propTypes = {
  boolValue: PropTypes.bool,
  numValue: propTypes.number,
  arrayValue: PropTypes.arrayOf(PropTypes.number),
  objValue: PropTypes.object,
  nodeValue: PropTypes.node,
  funcValue: PropTypes.func,
};

export default ChildComponent;
import './App.css';
import { Component } from 'react';
import ChildComponent from './03/ChildComponent';

class App extends Component{
  render(){
    return(
      <ChildComponent
        boolValue={true}
        numValue={1}
        arrayValue={[1,2,3]}
        objValue={{ name : '제목', age : 30}}
        nodeValue={<h1>노드</h1>}
        funcValue={()=> { console.log('메시지'); }}
        />
    )
  }
}

export default App;

결과값은 같지만 개발자간의 실수를 줄이기 위해 변수에 객체를 담아 전달하는 아랫 방식을 선호한다.

import './App.css';
import { Component } from 'react';
import ChildComponent from './03/ChildComponent';

class App extends Component{
  render(){
    const array=[1,2,3];
    const obj = {name : '제목', age:30};
    const node = <h1>노드</h1>;
    const func = () => { console.log('메시지'); };
    return(
      <ChildComponent
        boolValue={true}
        numValue={1}
        arrayValue={array}
        objValue={obj}
        nodeValue={node}
        funcValue={func}
        />
    )
  }
}

export default App;

 

- 불리언 프로퍼티 사용하기

=> 실무에서 자주 사용하므로 알아두기

import React, { Component } from 'react';

class BooleanComponent extends Component {
  render() {
    const message = this.props.bored ? '놀러가자' : '하던 일 열심히 마무리하기';
    return <div className="message-container">{message}</div>;
  }
}

export default BooleanComponent;
import { Component } from 'react';
import BooleanComponent from './03/BooleanComponent';

class App extends Component {
  render() {
    return (
      <div>
        <div>
          <b>지루할 때 :</b>
          <BooleanComponent bored />
        </div>
        <div>
          <b>즐거울 때 :</b>
          <BooleanComponent />
        </div>
      </div>
    );
  }
}

export default App;

 

- 객체형 / 필수 프로퍼티 사용하기

 

import React from 'react';
import PropTypes from 'prop-types';

class ChildComponent2 extends React.Component {
  render() {
    const { objValue, requiredStringValue } = this.props;

    return (
      <div>
        <div>객체값: {String(Object.entries(objValue))}</div>
        <div>필수값: {requiredStringValue}</div>
      </div>
    );
  }
}

ChildComponent2.propTypes = {
  // 객체형 프로퍼티
  objValue: PropTypes.shape({
    name: PropTypes.string,
    age: PropTypes.number,
  }),
  // 필수 프로퍼티
  requiredStringValue: PropTypes.string.isRequired,
};

export default ChildComponent2;
import { Component } from 'react';
import BooleanComponent from './03/BooleanComponent';
import ChildComponent2 from './03/ChildComponent2';

class App extends Component {
  render() {
    return (
      <div>
        <ChildComponent2 objValue={{ age: '20살' }} />
      </div>
    );
  }
}

export default App;

age에 number가 아닌 String을 대입한 에러1과, 필수 프로퍼티로 지정한 RequiredStringVaule에 값이 전달되지 않아서 에러가 나게 됐다.

import { Component } from 'react';
import BooleanComponent from './03/BooleanComponent';
import ChildComponent2 from './03/ChildComponent2';

class App extends Component {
  render() {
    return (
      <div>
        <ChildComponent2 objValue={{ age: 20 }} requiredStringValue="문자" />
      </div>
    );
  }
}

export default App;

수정해주니까 에러 사라짐~

 

 

컴포넌트 상태 관리하기

 

1. state로 상태관리하기.

import React from "react";

class StateExample extends React.Component {
  constructor(props) {
    super(props);
    // 상태 정의
    this.state = {
      loading: true,
      formData: "no data",
    };
    // 이후 콜백 함수를 다룰때 bind를 선언하는 부분에 대해 다룹니다
    this.handleData = this.handleData.bind(this);
    // 생성 후 4초 후에 handleData를 호출합니다.
    setTimeout(this.handleData, 4000);
  }
  handleData() {
    const data = "new data";
    const { formData } = this.state;
    // 상태 변경
    this.setState({
      loading: false,
      formData: data + formData,
    });
    // this.state.loading 은 현재 true 입니다.
    // 이후 호출될 출력함수에서의 this.state.loading은 false입니다.
  }
  // 다음과 같이 setState함수를 사용할 수 있습니다.
  // handleData(data) {
  //   this.setState(function(prevState) {
  //     const newState = {
  //       loading : false,
  //       formData: data + prevState.formData,
  //     };
  //     return newState;
  //   });
  // }
  render() {
    return (
      <div>
        {/* 상태 데이터는 this.state로 접근 가능합니다. */}
        <span>로딩중: {String(this.state.loading)}</span>
        <span>결과: {this.state.formData}</span>
      </div>
    );
  }
}

export default StateExample;

왼쪽 => 4초뒤 => 오른쪽

 

state를 사용할 떄 주의점

: 생성자에서 반드시 초기화 해야 한다.

: state값을 변경할 떄는 setState()함수(상태관리함수)를 반드시 사용해야함

: setState()함수는 비동기로 처리되며, setState() 코드 이후로 연결된 함수들의 실행이 완료된 시점에

  화면 동기화 과정을 거친다.

 

 

2. 클래스 인스턴스 변수와 forceUpdate()함수로 State관리하기

import React from "react";

class ForceUpdateExample extends React.Component {
  constructor(props) {
    super(props);
    //state 정의
    this.loading = true;
    this.formData = "no data";

    //이후 콜백 함수를 다룰 때 bind를 선언하는 부분에 대해 다룹니다
    this.handleData = this.handleData.bind(this);
    // 4초후 호출
    setTimeout(this.handleData, 4000);
  }
  handleData() {
    const data = "new data, ";
    //state 변경
    this.loading = false;
    this.formData = data + this.formData;
    // 컴포넌트 내장 함수 forceUpdate()를 호출하여 강제로 화면을 새로고침 한다.
    this.forceUpdate;
  }
  render() {
    return (
      <div>
        {/* 상태 데이터는 this.state로 접근 가능합니다. */}
        <span>로딩중: {String(this.state.loading)}</span>
        <span>결과: {this.state.formData}</span>
      </div>
    );
  }
}

export default ForceUpdateExample;
C;

  

 

위에 것과 결과는 같지만 리액트 성능에 제약이 있으므로, 매번 새롭게 화면을 출력해야 되는 경우가 아니라면

가급적 사용하지 않기를 권한다고 한다

'front-end > react' 카테고리의 다른 글

[리액트] create-react-app  (0) 2021.03.15
[리액트] 웹팩 webpack  (0) 2021.03.15
[리액트] 바벨 babel  (0) 2021.03.14
[리액트] 기본 렌더링  (0) 2021.03.14
[리액트] Target container is not a DOM element. 에러  (0) 2021.03.14
[리액트] 개발환경 설치하기  (0) 2021.03.12
[리액트] 기본  (0) 2021.03.12

1. 노드 버전 매니저로 노드JS설치하기

1-1. NVM 설치하기

github.com/coreybutler/nvm-windows/releases

1-2 nvm이 잘 설치 됐는지 cmd로 확인해보기

1-3 NVM으로 노드제이에스 설치하기

(주의 10.16.2 버전으로 설치하자)

책에서처럼 8.버전으로 설치했더니 10이하에서는 create-react-app이안됐다. 

1-4 nvm이 설치한 노드제이에스 사용 설정하기

nvm ls를 사용하면 설치된 node버전들을 볼 수있다.

(역시 사용도 use 10.16.2로하자...)

 

 

2. yarn과 create-react-app 설치하기

2-1 yarn 설치하기

2-2 create-react-app 설치하기 및 생성

(10 버전 이상을 써야 설치가능.. 책에선 8도됐지만^^....) 참고 참고!

그리고 global add하니까 안댐 ㅎ.. 휴 옛날책이네..

npm install -g create-react-app 했다..

(아래링크 참고!)

ssungkang.tistory.com/entry/React-React-%EC%8B%9C%EC%9E%91%ED%95%98%EA%B8%B0-create-react-app

 

2-3 리액트 앱 구동하기

이 화면이 뜨면 성공 !

나같은 경우 바로안뜨고 좀 걸렸다..

 

 

루트 폴더에 package.json을 필요에 맞게 수정하고

루트폴더에서 cmd 실행시키고 yarn을 입력하면 라이브러리들을 설치한다.

warning메세지는 버전의 호환성에 대해 제작 당시 명시된 버전과 다르다는 것을 알려주는 내용이라함

리액트 : 페이스북에서 개발하고 관리하는 라이브러리

앵글러와 달리 UI기능만 제공

=> 전역상태 관리, 라우팅, 빌드시스템을 직접 구축해야함

=> 자유도는 높지만 개발환경을 직접 구축해야하는 번거로움이 있다

=> create-react-app을 이용해서 이 단점을 보완함

 

프론트엔드 라이브러리나 프레임워크를 사용하는 이유

: UI를 자동으로 업데이트 해준다

: 브라우저의 돔을 직접 수정 하지 않아도 되어서 좋다.

 

 

- 자동으로 업데이트 되는 UI

- UI = render(state)

- render 함수는 순수 함수로 작성

 > 랜덤 함수 사용(X)

 > 외부 상태 변경(X)

- state는 불변 변수로 관리 => 복잡도가 낮아지고, 버그 발생확률로 낮아짐 / 렌더링 성능 향상

- 가상돔(Virtual DOM)

=> 변경된 부분만 실제 DOM에 반영 해줌

=> 그렇다고 무조건 자바스크립트나 다른 것보다 무조건 빠른 것은 아니다.

 

 

 

나중에 정리할 것

 

data.html

<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>

	<table border="1">
		<tr>
			<td>우유</td>
			<td>2000</td>			
		</tr>
		<tr>
			<td>홍차</td>
			<td>5000</td>			
		</tr>
		<tr>
			<td>커피</td>
			<td>5000</td>			
		</tr>
		
		
	</table>

</body>
</html>

ajax-1.html

<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>

<!-- 제이쿼리 DSK로드 -->
<script src="https://code.jquery.com/jquery-1.12.4.min.js"></script>
<script>
	$(document).ready(function(){
		//alert('onload');
		$.ajax('data.html',{
			success : function(data){
				$('body').append(data);	
			}
			
		});
		
	});

</script>
</head>
<body>
	<h1>가격표</h1>
</body>
</html>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>

<!-- 제이쿼리 DSK로드 -->
<script src="https://code.jquery.com/jquery-1.12.4.min.js"></script>
<script>
	$(document).ready(function() {
		$.ajax({
			url : 'data.html',
			success : function(data) {
				$('body').append(data);
			}
		});
	});
</script>
</head>
<body>
	<h1>가격표</h1>
</body>
</html>

 

parameter.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>

<div> 이름 : ${param.pname} </div>
<div> 가격 : ${param.price} </div>
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>

<!-- 제이쿼리 DSK로드 -->
<script src="https://code.jquery.com/jquery-1.12.4.min.js"></script>
<script>
	$(document).ready(function() {	
		$.ajax({
			url : 'parameter.jsp',
			type : 'GET', // get post put delete
			data : {
				pname : '우유',
				price : 2000,
				
			},
			success : function(data){
				$('body').append(data);
			}
			
		});
	});
</script>
</head>
<body>
	<h1>가격표</h1>
</body>
</html>

 

위에것을 동적으로 만들기

<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>

<!-- 제이쿼리 DSK로드 -->
<script src="https://code.jquery.com/jquery-1.12.4.min.js"></script>
<script>

$(document).ready(function(){
    //alert('onload');
    $('input:button').click(function(){
  	  $.ajax({
  	    	url : 'parameter.jsp',
  	    	type : 'get', // http method get, post, put, delete
  	    	data : {	
  	    		pname: $('#pname').val(),
  	    		price: $('#price').val()
  	    	},
  	    	success : function(data) {
  				$('body').append(data);
  			}
  	     }); 
    });     
  
 });


</script>
</head>
<body>
	<h3>제품등록</h3>
	이름 <input type="text" id="pname"><br>
	가격 <input type="number" id="price"><br><br>
	<input type="button" value="등록"><br>
	<hr>
	<br>
	<h1> 가격표</h1>
</body>
</html>

 

idcheck.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<%@ page trimDirectiveWhitespaces="true" %>
<!-- 공백제거 -->
${param.uid eq 'cool'? 'N' : 'Y'}
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>

<!-- Jquery SDK 로드 -->
<script src="https://code.jquery.com/jquery-1.12.4.min.js"></script>

<script>

	$(document).ready(function(){
		$('#uid').focusin(function(){
			//alert('focusin');
			//$('#msg').html('사용할수 있는 아이디 입니다.');
			$('#msg').addClass('display_none');
			$('#msg').removeClass('color_blue');
			$('#msg').removeClass('color_red');
			
		});
		
	//$('#idChkBtn').click(function(){
		
		$('#uid').focusout(function(){
			$.ajax({
				url : 'idcheck.jsp',
				type : 'post',
				data : {
					uid: $('#uid').val()
				}, 
				beforeSend : function(){
					console.log('beforeSend');
					$('#loaddingImg').removeClass('display_none');
				},
				success : function(data){
					
					//alert(data);
					if(data == 'Y') {						
						$('#msg').html('사용할수 있는 아이디 입니다.');
						$('#msg').removeClass('display_none');
						$('#msg').addClass('color_blue');
					} else {
						$('#msg').html('사용할수 없는 아이디 입니다.');
						$('#msg').removeClass('display_none');
						$('#msg').addClass('color_red');
					}
					
					
				},
				error : function(request, status, error){
					console.log('request', request);
					console.log('status', status);
					console.log('error', error);
				},
				complete : function(){
					
				setTimeout(function(){
						$('#loaddingImg').addClass('display_none');
					}, 3000);
					
				}
			});
			
		});
		
	});

</script>

<style>
	
	.display_none {
		display: none;
	}
	
	.display_block {
		display: block;
	}
	
	.color_red {
		color : red;
	}
	.color_blue {
		color: blue;
	}
	
	/* #msg {
		display: none;
	} */
	 
</style>
</head>
<body>

	id <input type="text" id="uid"> 
	<input type="button" id="idChkBtn" value="아이디 체크">
	<div id="msg"  class="display_none"></div><br>
	<img id="loaddingImg" class="display_none" alt="loadding" src="loading.gif">
 
</body>
</html>

 

serialize / serializeArray

- 입력받는 값이 많을수록 편리하며 id가 아닌 name으로 캐스팅 한다.

 

- parameter.jsp는 위에 있음

<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>

<!-- 제이쿼리 DSK로드 -->
<script src="https://code.jquery.com/jquery-1.12.4.min.js"></script>
<script>

$(document).ready(function(){
	
		     
	     $('#myform').submit(function(event){
	    	 
	    	 console.log($(this).serialize()); // input 파라미터 쿼리스트림을 문자열로 처리
	    	 console.log($(this).serializeArray());
	    	 
	    	 //입력받는게 많을수록 더 편리하다. id가아닌 name으로 캐스팅한다.
	    	 $.ajax({
	    		 url : 'parameter.jsp',
	    		 data : $(this).serialize(),
                 // data : data : $(this).serializeArray()로 받아도 괜찮음
	    		 success : function(data){
	    			  $('body').append(data)
	    			 
	    		 }
	    	
	    	 });
	 		return false;
	     });
  
 });


</script>
</head>
<body>
	<h3>제품등록</h3>
	<form id="myform">
	이름 <input type="text" id="pname" name="pname"><br>
	가격 <input type="number" id="price" name="price"><br><br>
	<input type="submit" value="등록"><br>
	</form>
	<hr>
	<br>
	<h1> 가격표</h1>
	
</body>
</html>

 

 

 

http://coderap.tistory.com/539

<input type="text" id="pnum" name="pnum" required
onKeyup="this.value=this.value.replace(/[^0-9]/g,'');" />

숫자 이외에 다른 키 입력이 되지 않는다.

 

마우스이벤트

'

 

키보드이벤트

<!DOCTYPE html>
<html lang="">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>제이쿼리 키보드 이벤트</title>
    <!--제이쿼리 라이브러리 로드-->
    <script src="https://code.jquery.com/jquery-1.12.4.min.js" integrity="sha256-ZosEbRLbNQzLpnKIkEdrPv7lOy9C27hHQ+Xp8a4MxAQ=" crossorigin="anonymous"></script>

    <style>
    
        .rudrh{
            color:red;
        }
    </style>

    <script>
    
        $('document').ready(function(){
            
            $('textarea').keyup(function(){
                
                //현재 입력 문자열의 길이
                var inputStrLen = $(this).val().length;                
                
                
                if(inputStrLen>50){
                    $('span').addClass('rudrh');
                    alert('50자까지만 입력가능!');                    
                    var userInput = $(this).val().substr(0,50);
                    $(this).val(userInput);
                    userInput = 50;                    
                }else{
                    $('span').removeClass('rudrh');
                }
                
                $('span').text(inputStrLen);
                
            })        
                        
        });
        
    </script>
    
</head>
    
    

<body>
    
    <textarea rows="10" cols="50"></textarea>
    <h1><span>0</span>/50</h1>
    
</body>
</html>

 

 

윈도우이벤트

윈도 이벤트는 윈도 객체만 사용할 수 있는 이벤트가 아니라

window 객체와 document 객체 이외에 img 태그 등이 사용할 수 있는 이벤트

 

 

입력 양식 이벤트

<!DOCTYPE html>
<html lang="">

<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>체크박스</title>

    <!--jQuery 라이브러리 로드-->
    <script src="https://code.jquery.com/jquery-1.12.4.min.js" integrity="sha256-ZosEbRLbNQzLpnKIkEdrPv7lOy9C27hHQ+Xp8a4MxAQ=" crossorigin="anonymous"></script>
    
        <script>
        $('document').ready(function(){
           
            // 체크박스 이벤트 처리 : change() 메소드 사용
            $('#check-all').change(function(){
                if(this.checked){
                    $('#check-item').children().prop('checked',true);
                }else {
                    $('#check-item').children().prop('checked',false);
                }
            });
        
            
        });
    </script>
    
</head>

<body>
    
    개인정보활용 동의 <input type="checkbox" id="agree"><br>.
    <input type="checkbox" id="check-all"><label> 전체선택</label>
    <br><br>
    <div id="check-item">
        <input type="checkbox"> 게시물 1 <br>
        <input type="checkbox"> 게시물 2 <br>
        <input type="checkbox"> 게시물 3 <br>
        <input type="checkbox"> 게시물 4 <br>
        <input type="checkbox"> 게시물 5 <br>        
    </div>
</body>

</html>

이벤트를 연결할 때 on ( ) 메서드를 사용

 

 

on( ) 메서드를 사용하지 않은 기본 이벤트 연결

    <script>
        
        $('document').ready(function(){
        
        
           $('h1').click(function(){
               var length = $('h1').length;
               var html = $(this).html();
               
               $('#wrap').append('<h1>'+length+' - '+html+'</h1>');
           });
            
            
        });
    </script>

</head>

<body>


    <div id="wrap">
        <h1> HEADER 1 </h1>
    </div>

 

 

 

- delegate 방식을 사용하는 on( ) 메서드

- 이벤트 리스너에서 this 키워드가 #wrap 태그가 아니라 h1 태그라는 것을 주의

        
        $('document').ready(function(){

            // 범위를 지정하고 해당 범위안의 엘리먼트를 지정해서 이벤트 적용
            // 해당 범위에 특정 엘리먼트가 추가되어도 이벤트를 적용.
           $('#wrap').on('click','h1',function(){
               
               var length = $('h1').length;
               var html = $(this).html();
               
               $('#wrap').append('<h1>'+length+' - '+html+'</h1>');
               
               
           });
            
        });           

 

                // 제거
                $('#wrap').off('click', 'h1');

1) $(this).html($(this).html()+'+');
2) $(this).html(function(index, html){return html+'+'});

1)

    <script>

        $('documnet').ready(function() {

            // 이벤트 연결
            $('h1').on('click',function(){
                
                // 클릭이 발생하면 이벤트가 발생한 객체의 문자열을 변경
                // this는 이벤트가 발생한 객체
                $(this).html($(this).html()+'+');
            });

        });

    </script>

</head>

<body>


    <h1> CLICK1 </h1>

</body>

2)

        $('documnet').ready(function() {
        
            // 이벤트 연결
            $('h1').on('click',function(){
                 $(this).html(function(index, html){                     
                        return html+'+'; 
                 });
            });
        });

둘다 실행 결과는 같다 // 클릭할때 마다 +가 생김

 

 

 

이벤트 연결 

1) 기본


- on ( ) 메서드의 매개변수에 객체를 넣어줌
- 속성 이름과 속성 값에 이벤트 이름과 이벤트 리스너를 넣으면 이벤트를 쉽게 연결

 

        $('documnet').ready(function() {
            
            // 여러개의 이벤트를 등록할 때 객체 형식으로 정의
            $('h1').on({
                mouseenter:function(){
                    $(this).addClass('h1over'); // style에 .h1over만들어놓음
                },
                mouseleave:function(){
                    $(this).removeClass('h1over');
                },
                click : function(){
                    console.log(event);
                    $(this).html(function(index, html){
                        return html + '*'
                    })
                }
            })
            
            
        });

        $('documnet').ready(function(){
            $('h2').hover(function(){
                $(this).addClass('over');       
            }, function(){
                $(this).removeClass('over');
            })
            
        });

 

이벤트 연결 제거

 

- off ( ) 메서드는 다음 형태로 사용
- 1번 형태는 해당 문서 객체와 관련된 모든 이벤트를 제거
- 2번 형태는 해당 문서 객체의 특정 이벤트와 관련된 모든 이벤트를 제거
- 3번 형태는 특정 이벤트 리스너를 제거

        $('documnet').ready(function() {

            // 여러개의 이벤트를 등록할 때 객체 형식으로 정의
            $('h1').on({
                mouseenter: function() {
                    $(this).addClass('over'); // style에 .h1over만들어놓음
                },
                mouseleave: function() {
                    $(this).removeClass('over');
                },
                click: function() {
                    console.log(event);
                    $(this).html(function(index, html) {
                        return html + '*'
                    });
                    $(this).off('click');
                }
            })
        });


        $('documnet').ready(function() {
            $('h2').hover(function() {
                $(this).addClass('over');
            }, function() {
                $(this).removeClass('over');
                $('h2').off();
            })

        });

처음 한번만 실행되고 두번째부터는 실행되지 않는다.

1) hover는 테두리가 처음 한번만 생기고 다음엔 안생김

2) 눌러도 별표 한개이상 안생김

 

 

매개변수 context

- 특정 부분에 선택자를 적용하고 싶을 때 사용하는 것이 매개변수 context

- 매개변수 context는 selector가 적용하는 범위를 한정

    <script>
        $('documnet').ready(function() {

            $('div').click(function(){

                var header = $('h1', this).text();
                var paragraph = $('p', this).text();

                alert(header + ' : ' + paragraph);


            });
        });
    </script>

</head>

<body>

    <div>
        <h1> header - 1 </h1>
        <p> paragraph - 1 </p>
    </div>
    <div>
        <h1> header - 2 </h1>
        <p> paragraph - 2 </p>
    </div>
    <div>
        <h1> header - 2 </h1>
        <p> paragraph - 2 </p>
    </div>
</body>

 

 

이벤트 강제발생

 

        $(document).ready(function() {

            $('h1').on({
                mouseenter: function() {
                    $(this).addClass('over');
                },
                mouseleave: function() {
                    $(this).removeClass('over');
                },
                click: function(event) {
                    console.log(event);
                    $(this).html(function(index, html) {
                        return html + '+';
                    });
                }
            });

            setInterval(function(){
            	// h1의 마지막에 click 이벤트 강제발생
                $('h1').last().trigger('click');
            }, 1000);           
        });

계속해서 +가 발생한다.

 

 

버블링 막기

 

자바스크립트의 버블링에 대해서 알기쉬운 티스토리

http://programmingsummaries.tistory.com/313

 

 

[JavaScript] JavaScript에서 이벤트 전파를 중단하는 네가지 방법

자바스크립트 이벤트 리스너에서 preventDefault() 와 stopPropagation()  그리고 return false 는 자바스크립트 프로그래밍을 할 때 이벤트 중단을 위해 자주 사용되는 코드들이다. 이벤트 중단 시에 사용되

programmingsummaries.tistory.com

 

 

1) 버블링을 막지 않으면 <a>태그부분을 눌러도 div부분의 이벤트(alert)가 같이 실행된 후 네이버로 이동한다.

    </script>
		$('div').click(function() {

                var header = $('h1', this).text();
                var paragraph = $('p', this).text();

                alert(header + ' : ' + paragraph);
            });


            $('a').click(function(event) {
                //event.preventDefault();
                //return false;
            });

        });

    </script>

</head>

<body>
    <div>
        <h1>Header 1</h1>
        <p>paragraph 1</p>

        <h3>
            <a href="http://www.naver.com">네이버</a>
        </h3>

    </div>

</body>

</html>

 

2) preventDefault ( ) 메서드로 a 태그의 기본 이벤트를 제거하면,

 a 태그의 네이버로 이동하는 이벤트는 작동하지 않아서 네이버로 가지지는 않지만,

여전히 div의 이벤트인 alert는 작동한다.

 

            $('a').click(function(event) {
                event.preventDefault();
                //return false;
            });

 

 

 

 

3) return false;를 해주면 <a>태그 네이버를 눌러도 아무런 일도 일어나지 않는다.

return false

stopPropagation ( ) 메서드와 preventDefault ( ) 메서드를 함께 사용하는 경우가 많으므로, 

jQuery는 간단하게 return false를 사용하면 이 두 가지를 함께 적용하는 것으로 인식

            $('a').click(function(event) {
                //event.preventDefault();
                return false;
            });

 

 

 

 

1) appendTo

 

문서 객체 생성 , 문서 객체 연결

    <script>
        $(document).ready(function() {

            $('input[type=button]').click(function(){
                
                
                $('<h1></h1>').html('<i>새로운 태그 추가</i>').appendTo('div');
                
            });
            
        });
    </script>
</head>

<body>

    <div></div>
    
    <input type="button" value="동적tag추가">

</body></html>

더보기

이런 경우(아래코드)에는 생성 시점이 달라서 글씨색이 변경되지 않고 그냥 나온다.

- 코드가 같은 {} 곳에 삽입되어있다면 버튼을 누르면 원래 글씨색은 검정에서 빨간색으로 바뀌고,

  새로운 태그 추가부터 블루 초록 빨강 이런식으로 나옴

 

    <script>
        $(document).ready(function() {

            $('input[type=button]').click(function() {

                $('<h1></h1>').html('<i>새로운 태그 추가</i>').appendTo('div');

                //            var h1='<h1>안<h1>';
                //            var h2='<h1>녕<h1>';
                //            var h3='<h1>하<h1>';
                //            var h4='<h1>세<h1>';
                //            var h5='<h1>요<h1>';
                //            
                //            $('div').append(h1, h2, h3, h4, h5);

            });

        });

        $(document).ready(function() {
            var colors = ['red', 'blue', 'green'];

            $('h1').css('color', function(index) {
                return colors[index];
            });
        });
        
    </script>

</head>

<body>

    <div>
        <h1>원래있던태그</h1>
    </div>

    <input type="button" value="동적tag추가">

</body></html>

 

 

 

텍스트 노드를 갖지 않는 문서 객체를 생성하는 방법

- img 태그를 생성할 때는 $ ( ) 메서드로 문서 객체를 생성하고 attr ( ) 메서드로 속성을 입력

 

        $(document).ready(function() {

        $('input[type=button]').click(function(){
        
        $('<img>').attr({
        src:'../tae6.jpg',
        height:100
        }).appendTo('div');

        });

        });

 

 

2) append

- append ( ) 메서드의 사용 형태

 

- 여러 개의 문서 객체를 한꺼번에 입력할 수 있음

        $('input[type=button]').click(function(){

            var h1='<h1>안<h1>';
            var h2='<h1>녕<h1>';
            var h3='<h1>하<h1>';
            var h4='<h1>세<h1>';
            var h5='<h1>요<h1>';
            
            $('div').append(h1, h2, h3, h4, h5);
        });

- 배열을 사용한 문서 객체 생성과 추가

    <script>
        $(document).ready(function() {

            $('input[type=button]').click(function() {

                var links = [
                    {name:'네이버', url:'http://www.naver.com'},
                    {name:'다음', url:'http://www.daum.net'},
                    {name:'구글', url:'http://www.google.com'},
                ];
                
                $('h1').append(function(index){
                    var item = links[index];
                    var output = '<a href="'+item.url+'">'+item.name+'</a>';
                    
                    return output;
                    
                });

            });

        });
    </script>

</head>

<body>

    <div>
        <h1> 네이버 </h1>
        <h1> 카카오 </h1>
        <h1> 페이스북 </h1>
    </div>

    <input type="button" value="동적tag추가">

</body></html>

 

3) 문서 객체 이동

    <script>
        $(document).ready(function(){
           
            setInterval(function(){
                // 첫번째 이미지를 마지막으로 보낸다.
                 $('img').first().appendTo('div');
            },2*1000);
            
            
            
        });
    </script>
    <style>
        
        div {
            width: 150px;
            height: 150px;
            
            border: 2px solid black;
            
            overflow: hidden;
        }
        img {
            width: 150px;
            height: 150px;
        }
    </style>

</head>

<body>

    <div>
        <img src="/image/tae1.jpg">
        <img src="/image/tae2.jpg">
        <img src="/image/tae3.png">
        <img src="/image/tae4.jpg">
        <img src="/image/tae5.jpg">
    </div>

</body></html>

 

 

1) 문서 객체의 내부 검사

    <script>
        $(document).ready(function() {
            //html( ) 메서드 - Getter
            console.log('div->', $('div').html());
            //text( ) 메서드 - Getter
            console.log('div->', $('div').text());
        });
    </script>

</head>

<body>

    <div>

        <h1> 네이버 </h1>
        <h1> 카카오 </h1>
        <h1> 페이스북 </h1>

    </div>

 

2) 문서 객체의 내부 추가

            $('button').first().click(function() {
                $('div>h1').html('<h4>html</h4>');
            });

            $('button').first().click(function() {
                $('div>h1').text('<h4>text</h4>');
            });

 

 

 

            $('button').first().click(function() {
                $('div>h1').html(function(index){
                    return '<h'+(index+2)+'>안녕!</h'+(index+2)+'>';            
                });

            $('button').first().click(function() {
                $('div>h1').text(function(index){
                    return '<h'+(index+2)+'>안녕!</h'+(index+2)+'>';            
                });              
            });

 

3) 문서 객체 제거

            $('button').first().click(function() {
                $('div').empty();
            });

            $('button').first().click(function() {
                $('div>h1:first').remove();
            });

addClass() removeClass() / c대문자

문서 객체에 클래스 속성 추가 / 제거

<!DOCTYPE html>
<html lang="">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>jquery_DOM / 문서객체 컨트롤</title>


    <!--제이쿼리 라이브러리 로드-->
    <script src="https://code.jquery.com/jquery-1.12.4.min.js" integrity="sha256-ZosEbRLbNQzLpnKIkEdrPv7lOy9C27hHQ+Xp8a4MxAQ=" crossorigin="anonymous"></script>

    <script>
        $(document).ready(function() {

            $('button').first().click(function() {

                $('h1').addClass('float_left');

            });
            $('button').last().click(function() {
                $('h1').removeClass('float_left');
            });



        });
    </script>
    <style>
        h1 {
            border: 5px solid #ddd;
        }

        .float_left {
            float: left;
            widows: 32%;
        }
    </style>
</head>

<body>

    <h1> 네이버 </h1>
    <h1> 카카오 </h1>
    <h1> 페이스북 </h1>

    <button>변경</button><button>초기화</button>
</body></html>

 

 

attr()

문서 객체의 클래스 속성 검사 및 추가 ( 반환 & 설정 / get & set )

 

        $(document).ready(function() {
            $('button').first().click(function() {                
            	$('img').attr('src', '../image/tae2.jpg')
            });
            $('button').last().click(function() {          
                $('img').attr('src', '../image/tae1.jpg')
            });
            
            // 속성값을 반환 : get > attr('속성이름)
            var img_path = $('img').attr('src');
            console.log('img_path >', img_path);
            
            // 속성값을 설정 : set > attr('속성이름', 속성값)
            $('img').attr('width', 300);
            
        });

 

        $(document).ready(function() {
            // 속성값을 설정 : set > attr('속성이름', 함수())
            // 함수의 반환값은 속성에 적용할 데이터를 반환
            $('img').attr('width', function(index) {
                return (index + 1) * 100;
            });

        });

 

 

        $(document).ready(function() {
            // 속성값을 설정 : set > attr({속성이름:속성값 , 속성이름:속성값...})
            $('img').attr({
               width : function(index){
                   return (index+1)*100;
               },
                height:100
                                
            });
            
        });

 

 

 

removeAttr()

 

        $(document).ready(function() {

            $('button').first().click(function() {
                $('img').removeAttr('height');
                

            });
            $('button').last().click(function() {
            
            });
        });

css()

문서 객체의 스타일 검사 및 추가

    <script>
        $(document).ready(function() {

            var colors= ['red', 'blue','green'];
            
            $('h1').css('color',function(index){
                return colors[index];    
            });
            
        });
    </script>
    <style>
        h1 {
            border: 5px solid #ddd;
        }

        .float_left {
            float: left;
            widows: 32%;
        }
    </style>
</head>

<body>    
    <h1> 네이버 </h1>
    <h1> 카카오 </h1>
    <h1> 페이스북 </h1>
</body></html>

 

html = 1 > 2 > 3이라면 

                $('body').html($('body').html()+html); 

 

1) 뒤에 차례로 붙이기

[ body ] +  1 2 3

 

                $('body').html(html+$('body').html());

2) 역순으로 넣기 (위에 생김)

3 2 1  + [ body ]

- $.parseXML( ) 메서드와 each( ) 메서드, find() 메서드

 

        $(document).ready(function() {
            
            // xml 문서 구조의 문자열 
            var xmlStr = '';
            xmlStr += '<links>';
            xmlStr += '     <link>';
            xmlStr += '         <name>네이버</name>';            
            xmlStr += '         <url>http://www.naver.com</url>';            
            xmlStr += '     </link>';
            xmlStr += '     <link>';
            xmlStr += '         <name>구글</name>';            
            xmlStr += '         <url>http://www.google.com</url>';            
            xmlStr += '     </link>';
            xmlStr += '     <link>';
            xmlStr += '         <name>다음</name>';            
            xmlStr += '         <url>http://www.daum.net</url>';            
            xmlStr += '     </link>';
            xmlStr += '</links>';
            
            // 문자열 > xml 문서 객체로 만듦
            var xmlDoc = $.parseXML(xmlStr);
            
            // xml문서 객체 > 제이쿼리 객체로 만듦 > find() 사용 가능
            $(xmlDoc).find('link').each(function(index){
                // <link></link>가 하나의 this가 된다.
                var name = $(this).find('name').text();
                var url = $(this).find('url').text();
                
                var html ='';
                html += '<div class="card">';
                html += '   <h2>'+name+'</h2>';
                html += '   <a href="'+url+'">방문하기</a>';
                html += '</div>';
                
                $('body').html(html+$('body').html());
            });
            
      
        });
    <style>
        *{
            margin: 0px;
            padding: 0px;
        }
        div.card{
            border : 1px solid #aaa;
            width: 30%;
            float : left;
            margin: 5px;
        }
        
        
        div.card > h2 {
            background-color: palevioletred;            
            text-align: center;
        }
        
        div.card > a{
            display: block;
            text-align: center;
            height: 30px;
            line-height: 30px;
            text-decoration: none;
            color : black;
            background-color: pink;
        }
    </style>

기본 필터 메서드 filter(), filter(function(){})

    <script>
        $(document).ready(function() {

//            $('h3:even').css({
//                background: 'black',
//                color: 'orange'
//            });

            $('h3').filter(':even').css({
                background: 'black',
                color: 'orange'
            })

        });
    </script>


</head>

<body>

    <h3> header3-0 </h3>
    <h3> header3-1 </h3>
    <h3> header3-2 </h3>
    <h3> header3-3 </h3>
    <h3> header3-4 </h3>
    <h3> header3-5 </h3>
    <h3> header3-6 </h3>
    <h3> header3-7 </h3>


</body></html>

 

        $(document).ready(function() {

            $('h3').filter(':even').css({
                background: 'black',
                color: 'orange'
            })

            $('h3').filter(function(index) {
                return index % 3 == 0;
            }).css({
                background: 'black',
                color: 'red'
            });

        });

 

 

end()

	<script>
		$(document).ready(function() {

            //end (), filter를 이용한 선택의 한단계 위로 이동.
            $('h1').css('background-color','orange')
            .filter(':even').css('color','white')
            .end().filter(':odd').css('color','red');
            
        });
    </script>


</head>

<body>

    <h1> header1-0 </h1>
    <h1> header1-1 </h1>
    <h1> header1-2 </h1>
    <h1> header1-3 </h1>
    <h1> header1-4 </h1>
    <h1> header1-5 </h1>
    <h1> header1-6 </h1>
    <h1> header1-7 </h1>

 

특정 위치의 문서 객체 선택 eq(), first(), last()

 

        $(document).ready(function() {
            
            $('h1').eq(0).css('background','orange');
            $('h1').eq(-3).css('background','orange');
            $('h1').last().css('background','orange');

        });

 

add()

- add ( ) 메서드를 사용하면 현재 선택한 문서 객체의 범위를 확장할 수 있음

        $(document).ready(function() {

            $('h1').css('border','5px solid #333')
            .add('h3').css('color','blue');

        });

each$.each( ) 메서드의 콜백 함수

each() > 하나의 행을 다루는 핸들러 / 함수

        $(document).ready(function() {
            // 배열의 반복 처리를 위한 each 메소드
            // $.each(배열의 원본, callbck : 하나의 행을 처리하는 함수)
            
            // 배열 생성
            var links = [
                {name:'네이버', url:'http://www.naver.com'},
                {name:'다음', url:'http://www.daum.net'},
                {name:'구글', url:'http://www.google.com'},
            ];
            
            var output='';
            
            $.each(links, function(index,item){
                console.log(index, item);
                
                output += '<h1><a href="'+item.url+'">'+item.name+'</a></h1>';
            })     
                document.body.innerHTML +=output;
           
            
        });

 

addclass() 메서드

 

        $(document).ready(function() {
            $('h1').addClass('title');

            $('h1').each(function(index, item) {
                if (index % 2 == 0) {
                    $(item).css('color', 'red');
                }
            });

        });
    </script>
    <style>
        .title {
            background-color: beige;
            font-style: italic;
        }
    </style>
</head>

<body>

    <h1> h1 - 1 </h1>
    <h1> h1 - 2 </h1>
    <h1> h1 - 3 </h1>
    <h1> h1 - 4 </h1>
    <h1> h1 - 5 </h1>

        $(document).ready(function() {
//            $('h1').addClass('title');

            $('h1').each(function(index, item) {
                if (index % 2 == 0) {
                    /*$(item).css('color', 'red');*/
                    $(item).addClass('title')
                }
            });

        });
    </script>
    <style>
        .title {
            background-color: beige;
            font-style: italic;
        }
    </style>
</head>

<body>

    <h1> h1 - 1 </h1>
    <h1> h1 - 2 </h1>
    <h1> h1 - 3 </h1>
    <h1> h1 - 4 </h1>
    <h1> h1 - 5 </h1>

minified

 

jQuery Core – All Versions | jQuery CDN

jQuery Core – All Versions jQuery Core & Migrate - Git Builds UNSTABLE, NOT FOR PRODUCTION jQuery Core - All 3.x Versions jQuery Core 3.5.1 - uncompressed, minified, slim, slim minified jQuery Core 3.5.0 - uncompressed, minified, slim, slim minified jQue

code.jquery.com

 

 

***

            $('body').html('abc') 
            // abc만 출력됨(덮어쓰기)
            
            $('body').html(
                $('body').html()+output
            );            
            //document.body.innerHTML +=output;와 같다
           

 

 

 

$(document).ready( )

- jQuery를 사용한 모든 웹 페이지는 다음 코드로 시작

 

$(document).ready( )

- 이벤트 연결

 

        // 제이쿼리 객체를 만들고 객체의 메소드를 사용하는 형태
        // jquery(자바스크립트 객체 또는 선택자) : jquery 객체 생성
        $(document).ready(function(){
            alert('1');
        });
        
        $(document).ready(function(){
            alert('2');
        });
        
        $(document).ready(function(){
            alert('3');
        });
        

 

 

기본 선택자

- jQuery 메서드의 가장 기본적인 형태
- 선택자는 jQuery에서 가장 중요한 역할

 

    <script>
        //선택자로 제이쿼리 객체 생성 : $('선택자')
        $(document).ready(function(){
            console.log('onload=ready()')
            $('*').css('color','red');            
        });
        
                        
    </script>
</head>

<body>
    
    <h1>jquery test</h1>
    <p>제이쿼리 테스트</p>   
    
    
    
    
</body>

</html>

 

 

속성 선택자

		$(document).ready(function(){
            // 속성타입으로 선택
            $('input[type=text]').css('padding',10);
            $('input:text').css('color','pink');
            
            $('input:button').css('background-color', 'black');
        });
        
        //
        
    <input type="text"><br><br>
    <input type="button" value="버튼"><br>

 

필터 선택자

입력 양식 필터 선택자 - 필터 선택자는 기본 선택자 뒤에 사용

<script>
        $(document).ready(function() {
            // select에서 선택한 항목
            var value = $('select>option:selected').val(); // get 기능
            console.log(value);

            setTimeout(function() {
                var value = $('select>option:selected').val();
                console.log(value);
            }, 3 * 1000)
        });
    </script>
</head>

<body>

    <select>
        <option>2021</option>
        <option>2020</option>
    </select>

 

위치 필터 선택자

 <script>
        $(document).ready(function() {
            $('table tr:odd').css('background','pink');
            $('table tr:even').css('background','black');
            
            $('table tr:first').css('background','blue');
            $('table tr:last').css('background','green');            
        });
    </script>
</head>

<body>

    <table border="1" style="width: 400px">
        <tr>
            <td>1</td>
            <td>1</td>
        </tr>
        <tr>
            <td>2</td>
            <td>2</td>
        </tr>
        <tr>
            <td>3</td>
            <td>3</td>
        </tr>
        <tr>
            <td>4</td>
            <td>4</td>
        </tr>
        <tr>
            <td>5</td>
            <td>5</td>
        </tr>
        <tr>
            <td>6</td>
            <td>6</td>
        </tr>
        <tr>
            <td>7</td>
            <td>7</td>
        </tr>
        <tr>
            <td>8</td>
            <td>8</td>
        </tr>
        

    </table>

<!DOCTYPE html>
<html lang="">

<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Javascript Window Object</title>

    <script>

        window.onload = function() {
            
            // 삭제버튼 : 이벤트 설정
            document.querySelector('input[type=submit]').onclick = function(){
               
                alert('h1');
                
                // 삭제 대상 
                var remove_h1 = document.getElementById('header-1');
                
                // 삭제 대상을 포함하는 문서객체
                var parent = document.body;
                
                parent.removeChild(remove_h1);
                
                
            };
        };
    </script>


</head>

<body>

    <div id="header-1">1</div>
    <div id="header-2">2</div>

    <br>
    
    <input type="submit" value="H1-0 삭제">



</body></html>

문제발생, h1을 누르면 div영역도 같이 눌려진다.

<!DOCTYPE html>
<html lang="">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>이벤트 전달</title>
    
    <style>
    
        div{
            height: 300px;
            background-color: black;
        }
        
        h1{
            background-color: pink;
        }
    </style>
    
    <script>
    
        window.onload = function(){
            
            var div = document.querySelector('div');
            var h1 = document.querySelector('h1');
            
            div.onclick = function(){
                console.log('div 영역에 클릭이벤트 발생!');
            }
            h1.onclick = function(){
                console.log('h1 영역에 클릭이벤트 발생!');
            }
            
            
        };
    </script>
</head>

<body>
    
    <div>
    
        <h1> 클릭하세요 :) </h1>
    </div>
</body>
</html>

 

 

 

이벤트 객체의 stopPropagation() 메서드 사용!

익스플로러는 cancelBubble 속성을 true로 변경하는데 잘안쓰니까 패스..

<!DOCTYPE html>
<html lang="">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>이벤트 전달</title>
    
    <style>
    
        div{
            height: 300px;
            background-color: black;
        }
        
        h1{
            background-color: pink;
        }
    </style>
    
    <script>
    
        window.onload = function(){
            
            var div = document.querySelector('div');
            var h1 = document.querySelector('h1');
            
            div.onclick = function(){
                console.log('div 영역에 클릭이벤트 발생!');
            }
            h1.onclick = function(){
                console.log('h1 영역에 클릭이벤트 발생!');
            }
            
            h1.onclick = function(e){
                
                var event = e || window.event;
                console.log('h1 영역에 클릭이벤트 발생쓰!!!!!')
                
                if(event.stopPropagation){
                    event.stopPropagation();
                }
                
            };
            
        };
    </script>
</head>

<body>
    
    <div>
    
        <h1> 클릭하세요 :) </h1>
    </div>
</body>
</html>

<!DOCTYPE html>
<html lang="">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>유효성 검사</title>
</head>

<body>
    
    <form id="myform">
    
        <h1> 회원가입</h1>
        <hr>
        <table>
            <tr>
                <td><label for="uesrid">아이디(이메일)</label></td>
                <td><input type="text" name="userid" id="userid"></td>
            </tr>
            <tr>
                <td><label for="pw">비밀번호</label></td>
                <td><input type="password" name="pw" id="pw"></td>
            </tr>
            <tr>
                <td><label for="pw-check">비밀번호 번호 확인</label></td>
                <td><input type="password" name="pw-check" id="pw-check"></td>
            </tr>
            <tr>
                <td><label for="username">이름</label></td>
                <td><input type="text" name="username" id="username"></td>
            </tr> 
            <tr>
                <td></td>
                <td><input type="submit" value="회원가입">
                    <input type="reset" value="초기화"></td>
            </tr>
        
        
        </table>
    </form>
</body>
</html>
<!DOCTYPE html>
<html lang="">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>유효성 검사</title>
    
    <script>
    
        window.onload = function(){
            
            document.querySelector('#myform').onsubmit = function(){               
                var userid = document.querySelector('#userid');
                var pw = document.getElementById('pw');
                var pwcheck = document.getElementById('pw-check');
                var username = document.querySelector('#username');
                
                // 유효성 검사 1: 공백이 없어야 한다.
                if(userid.value.trim().length < 1){
                    alert ('id는 필수 항목입니다.');
                    userid.value='';
                    userid.focus(); //커서를 userid로 이동시키는 함수
                    return false;
                }
                
                if(pw.value.trim()<1){
                    alert('비밀번호는 필수항목입니다.');
                    pw.value='';
                    pw.focus();
                    return false;
                }
                
                // pw == pwcheck 이어야 한다.
                if(pwcheck.value.trim()<1 || pw.value!=pwcheck.value){
                    alert('비밀번호 확인이 일치하지 않습니다.');
                    pwcheck.value='';
                    pwcheck.focus();
                    return false;
                }
                
                 if(username.value.trim()<1){
                    alert('이름 항목은 필수항목입니다.');
                    username.value='';
                    username.focus();
                    return false;
                }
        };
            
        };
    
    </script>
</head>

<body>
    
    <form id="myform" action="http://www.naver.com">
    
        <h1> 회원가입</h1>
        <hr>
        <table>
            <tr>
                <td><label for="uesrid">아이디(이메일)</label></td>
                <td><input type="text" name="userid" id="userid"></td>
            </tr>
            <tr>
                <td><label for="pw">비밀번호</label></td>
                <td><input type="password" name="pw" id="pw"></td>
            </tr>
            <tr>
                <td><label for="pw-check">비밀번호 번호 확인</label></td>
                <td><input type="password" name="pw-check" id="pw-check"></td>
            </tr>
            <tr>
                <td><label for="username">이름</label></td>
                <td><input type="text" name="username" id="username"></td>
            </tr> 
            <tr>
                <td></td>
                <td><input type="submit" value="회원가입">
                    <input type="reset" value="초기화"></td>
            </tr>
        
        
        </table>
    </form>
</body>
</html>

 

다 입력하면 action = > naver로 가짐

 

 

클릭 이벤트 / this 키워드

<!DOCTYPE html>
<html lang="">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>event</title>
</head>

<style>
    h1 {
        border: 1px solid #999;
    }
</style>

<script>
    
    window.onload = function(){
        
        // 캐스팅_변수선언
        var hearder = document.getElementById('header');
        
        // 클릭하면 Click hearder :)♡가 뜨는 onclick 이벤트 연결
        header.onclick = function(){
            alert('Click header :)♡ '+this.innerHTML); 
            // this > 이벤트가 발생한 header를 가리키고 있다 
            // 여기서 this.innerHTML는 C L I C K! 이다          
            
        // 이벤트 제거 > 한번 클릭하고 나면 창이 다시뜨지 않는다.
        header.onclick = null;
            
        }
        
    };
    
</script>

<body>

    <h1 id="header"> C L I C K ! </h1>

</body></html>

 

이벤트 강제실행

 

<!DOCTYPE html>
<html lang="">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>event</title>
</head>

<style>
    h1 {
        border: 1px solid #999;
    }
</style>

<script>
    
    window.onload = function(){
        
    
        
        // 캐스팅
        var btn1 = document.getElementById('btn1'); //버튼id
        var btn2 = document.getElementById('btn2');
        
        var cnt1 = document.getElementById('count-a');
        var cnt2 = document.getElementById('count-b');
        
        // btn 문서객체에 클릭이벤트 적용
        btn1.onclick = function(){
            // 클릭하면 숫자증가 
            cnt1.innerHTML = Number(cnt1.innerHTML)+1;
            // a를 누르면 b 버튼 카운트도 같이 증가하고 싶다면
            //btn2.onclick();
            
        };
        
        btn2.onclick = function(){     //inner나 text나 둘다상관없음
            cnt2.innerHTML = Number(cnt2.textContent)+1;            
        };
        
        
        
    };
    
</script>

<body>
        
    <button id="btn1">Button-A</button>
    <button id="btn2">Button-B</button>
    <h1>Button-A : <span id="count-a">0</span></h1>
    <h1>Button-B : <span id="count-b">0</span></h1>
    

</body></html>

 

인라인 이벤트 모델

<!DOCTYPE html>
<html lang="">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>event</title>
</head>

<style>
    h1 {
        border: 1px solid #999;
    }
</style>

<script>
    
    function clickH1(){
        alert('인라인 방식으로 이벤트 처리');
    }
</script>

<body>
    
    <h1 onclick="clickH1();">인라인 방식의 이벤트 정의</h1>


</body></html>

문서 객체의 스타일 변경

- style 속성 사용
- getElementById ( ) 메서드로 문서 객체를 가져옴
- style 속성에 있는 border, color, fontFamily 속성을 지정
- CSS에 입력하는 것과 같은 형식으로 입력

 

<!DOCTYPE html>
<html lang="">
 
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>문서객체 동적 생성</title>

    <script>
        window.onload = function() {
            
            // 태그이름으로 문서객체 생성 > 배열로 반환
            var divs = document.getElementsByTagName('div'); // div 아래두개모두선택
            divs[0].innerHTML='By tagname - 0 ';
            divs[1].innerHTML='By tagname - 1 ';
            
            // style
            divs[0].style.color = 'pink';       

        };
    </script>

</head>

<body>

    <div id="header-1">1</div>
    <div id="header-2">2</div>

</body></html>


<!DOCTYPE html>
<html lang="">

<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Javascript Window Object</title>

    <script>
        window.onload = function() {

            document.getElementById('go_naver_btn').onclick = function() {
                
                var alink = document.querySelector('a');
                alink.style.display='block';
                alink.style.backgroundColor='blue';
                alink.style.fontSize=32;
                alink.style.color='yellow';
                alink.style.fontWeight='bold';
                alink.style.textAlign='center';

            };         


        };
    </script>

</head>

<body>


    <a href="http://www.naver.com">네이버로 이동</a>

</body></html>

 

HTML 태그를 자바스크립트로 가져오는 방법

 

<!DOCTYPE html>
<html lang="">
 
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>문서객체 동적 생성</title>

    <script>
        window.onload = function() {

            //html 문서의 요소를 문서 객체로 만들기
            // id 속성값으로 문서 객체 생성 : 캐스팅
            // document.getElementById('아이디속성값');

            var header1 = document.getElementById('header-1');
            var header2 = document.getElementById('header-2');

            // 문서 객체의 속성 변경
            header1.innerHTML = '<i>문서객체 생성</i>';
            header2.textContent = '<i>문서객체 생성</i>';


        };
    </script>

</head>

<body>

    <div id="header-1">1</div>
    <div id="header-2">2</div>

</body></html>


 

여러 개의 문서 객체 가져오는 방법

- document 객체의 getElementById( )메서드는 한 번에 한 가지 문서 객체만 가져올 수 있음
- 아래 메서드를 이용해서 여러 개의 객체를 가져올 수 있음

 

getElementsByName(name) : 태그의 name 속성이 name과 일치하는 문서 객체를 배열로 가져온다.

getElementsByTagName(tagname) : tagName과 일치하는 문서 객체를 배열로 가져온다.

 

<!DOCTYPE html>
<html lang="">
 
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>문서객체 동적 생성</title>

    <script>
        window.onload = function() {
            
            // 태그이름으로 문서객체 생성 > 배열로 반환
            var divs = document.getElementsByTagName('div'); // div 아래두개모두선택
            divs[0].innerHTML='By tagname - 0 ';
            divs[1].innerHTML='By tagname - 1 ';

        };
    </script>

</head>

<body>

    <div id="header-1">1</div>
    <div id="header-2">2</div>

</body></html>


 

HTML 5에서 추가된 메서드

querySelector / querySelectorAll 예제1)

<!DOCTYPE html>
<html lang="">
 
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>문서객체 동적 생성</title>

    <script>
        window.onload = function() {
			// CSS의 선택자로 선택할수 있는 메소드
			
            
            var div1 = document.querySelector('div'); // 가장 첫번째거 가져옴.
            alert(div1.innerHTML) // 1
            
            var divs = document.querySelectorAll('div');
            alert(divs[0].innerHTML+' : querySelectorAll'); // 1 : que~


        };
    </script>

</head>

<body>

    <div id="header-1">1</div>
    <div id="header-2">2</div>

</body></html>


 

querySelector / querySelectorAll 예제2)

<!DOCTYPE html>
<html lang="">
 
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>문서객체 동적 생성</title>

    <script>
        window.onload = function() {


            var input = document.querySelector('input[type=button]');
            alert(input.value);

            var input2 = document.querySelector('input[type=text]');
            alert(input2.value);

        };
    </script>

</head>

<body>

    <input type="button" value="네이버로 이동" id="go_naver_btn">
    <input type="text" value="텍스트">

</body></html>

 

 

querySelector / querySelectorAll 예제3)

> 유효성 검사

<!DOCTYPE html>
<html lang="">

<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Javascript Window Object</title>

    <script>

        window.onload = function() {
            document.getElementById('go_naver_btn').onclick = function() {

                var userid = document.querySelector('#userid');

                var uid = userid.value;

                if (uid.length < 1) {
                    alert('아이디는 필수 입력항목입니다.');
                } else {
                    alert('사용자가 입력한 아이디는 ' + userid.value + '입니다.');
                }

            };

        };
    </script>
    <style>

    </style>

</head>

<body>

    <input type="text" value="test" id="userid">
    <br>
    <input type="button" value="확인" id="go_naver_btn">



</body></html>

 

 

 

문서 객체 생성


정적으로 문서 객체를 생성 : 처음 HTML 페이지에 적혀 있는 태그들을 읽으며 생성
- 동적으로 문서 객체를 생성 : 자바스크립트로 원래 HTML 페이지에는 없던 문서 객체를 생성

 

createElement(tagName) > 요소 노드를 생성

createTextNode(text)      > 텍스트 노드 생성

appendchild(node))        > 객체에 노드를 연결

 

텍스트 노드를 갖는 문서 객체

*<h1></h1>이 body에 생성됨 (createElement)

<!DOCTYPE html>
<html lang="">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>문서객체 동적 생성</title>
    
    <script>
    
    
        window.onload = function(){
            
            // 태그 요소 생성
            var header = document.createElement('h1');
            
            // 텍스트 요소 생성
            
            // 태그 요소에 텍스트 요소 추가
            
            // 새로운 문서객체를  body 요소에 추가
            document.body.appendChild(header);
        }
    </script>
    
</head>

<body>
    
</body>
</html>

 

 

 

 

*<h1></h1> 사이에 하이! 뽀선뽀선!을 넣어줌 (createtextNode)

<!DOCTYPE html>
<html lang="">
<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>문서객체 동적 생성</title>
    
    <script>
    
    
        window.onload = function(){
            
            // 태그 요소 생성
            var header = document.createElement('h1');
            
            // 텍스트 요소 생성
            var textNode = document.createTextNode('하이! 뽀선뽀선!');
            // 태그 요소에 텍스트 요소 추가
            header.appendChild(textNode);
            
            // 새로운 문서객체를  body 요소에 추가
            document.body.appendChild(header);
        }
    </script>
    
</head>

<body>
    
</body>
</html>

 

 

 

텍스트가 없는 요소 : img

<!DOCTYPE html>
<html lang="">

<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>문서객체 동적 생성</title>

    <script>
        window.onload = function() {


            // 텍스트가 없는 요소 : img
            var img = document.createElement('img');
            document.body.appendChild(img);
        }
    </script>

</head>

<body>

</body>

</html>

<!DOCTYPE html>
<html lang="">

<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>문서객체 동적 생성</title>

    <script>
        window.onload = function() {


            // 텍스트가 없는 요소 : img
            var img = document.createElement('img');
            img.src = 'tae6.jpg';
            img.width = 300; //px
            img.height = 300;
            document.body.appendChild(img);
        }
    </script>

</head>

<body>

</body>

</html>

 

두개 합친 것! TEST

<!DOCTYPE html>
<html lang="">

<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>문서객체 동적 생성</title>

    <script>
        window.onload = function() {
                        
            // 태그 요소 생성
            var header = document.createElement('h1');
            
            // 텍스트 요소 생성
            var textNode = document.createTextNode('하이! 뽀선뽀선!');
            // 태그 요소에 텍스트 요소 추가
            header.appendChild(textNode);
            
            // 새로운 문서객체를  body 요소에 추가
            document.body.appendChild(header);


            // 텍스트가 없는 요소 : img
            var img = document.createElement('img');
            img.src = 'tae6.jpg';
            img.width = 300; //px
            img.height = 300;
            document.body.appendChild(img);
            
            //밑에 있는 h1에 추가한다
            document.getElementById('pposeon').appendChild(img);
        }
    </script>

</head>

<body>
    
    <h1 id="pposeon">새로운 문서객체를 추가합니다.</h1>

</body>

</html>

// 하이 뽀선뽀선은 바디에 추가된것 > document.body.appendChild(header);

 

 

 

텍스트 노드를 갖지 않는 문서 객체 / 속성 지정

 

<!DOCTYPE html>
<html lang="">

<head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>문서객체 동적 생성</title>

    <script>
        window.onload = function() {
            var pposeon = document.getElementById('pposeon');
            console.log('h1#pposeon id->', pposeon.getAttribute('data-brackets-id')); //1087

            var link = document.getElementById('link_naver');

            // text 노드 생성 
            //var str = document.createTextNode('-' + link.getAttribute('href')); // 아래랑 같음
            var str = document.createTextNode('-' + link.href);
            link.appendChild(str);

            
            
          	// 속성 지정
            var img1 = document.createElement('img');
            img1.setAttribute('src', 'tae6.jpg');
            img1.setAttribute('width', 200);
            img1.setAttribute('height', 200);
            document.body.appendChild(img1);
            
            

        };
    </script>

</head>

<body>

    <h1 id="pposeon">새로운 문서객체를 추가합니다.</h1>

    <a href="http://www.naver.com" id="link_naver"> 네이버 </a>

</body></html>

 

 

innerHTML과 textContent의 차이.

            pposeon.innerHTML = '<i>안녕하세요</i>';
            alert(pposeon.innerHTML);
            alert(pposeon.textContent);
            // html 인식이 아닌 순수한 문자로 인식
            pposeon.textContent = '<i>안녕하세요</i>';

+ Recent posts