[스터디]리액트를 다루는 기술 – 이벤트 핸들링

리액트에서 이벤트를 사용할 때 주의점

  • 이벤트 이름은 카멜 표기법으로 작성한다.
  • 이벤트를 전달할 땐 함수 형태로 전달한다.
  • DOM 요소에만 이벤트를 설정할 수 있다.(사용자가 만든 컴포넌트에는 이벤트를 설정할 수 없다)

이벤트의 종류

  • Clipboard
  • Touch
  • Composition
  • UI
  • keyboard
  • wheel
  • Form
  • Image
  • Mouse 등

컴포넌트 생성 및 불러오기

사용자가 입력한 내용을 콘솔에 출력한다.

// EventPractice.js
import React, { Component } from 'react';

class EventPractice extends Component {
    render() {
        return (
            <div>
                <h1>이벤트 연습</h1>
                <input
                    type="text"
                    name="message"
                    placeholder="아무거나 입력해 보세요"
                    onChange={e => {
                        console.log(e.target.value);
                    }}
                />
            </div>
        );
    }
}

export default EventPractice;

// App.js
import React, {Component} from 'react';

class EventPractice extends Component {
    render() {
        return (
            <div>
                <h1>이벤트 연습</h1>
            </div>
        )
    }
}

export default EventPractice

사용자가 입력한 값을 state에 저장한다.

// EventPractice.js
import React, { Component } from 'react';

class EventPractice extends Component {
    state = {
        message: '',
    };

    render() {
        return (
            <div>
                <h1>이벤트 연습</h1>
                <input
                    type="text"
                    name="message"
                    placeholder="아무거나 입력해 보세요"
                    value={this.state.message}
                    onChange={e => {
                        this.setState({
                            message: e.target.value,
                        });
                    }}
                />
            </div>
        );
    }
}

export default EventPractice;

확인버튼을 누르면 현재 state값을 보여주고, 공백으로 초기화한다.

// EventPractice.js
import React, { Component } from 'react';

class EventPractice extends Component {
    state = {
        message: ''
    };

    render() {
        return (
            <div>
                <h1>이벤트 연습</h1>
                <input
                    type="text"
                    name="message"
                    placeholder="아무거나 입력해 보세요"
                    value={this.state.message}
                    onChange={e => {
                        this.setState({
                            message: e.target.value
                        });
                    }}
                />
                <button
                    onClick={() => {
                        alert(this.state.message);
                        this.setState({
                            message: ''
                        });
                    }}
                >
                    확인
                </button>
            </div>
        );
    }
}

export default EventPractice;

이벤트를 별도의 메서드로 분리하는 예제

// EventPractice.js
import React, { Component } from 'react';

class EventPractice extends Component {
    state = {
        message: ''
    };

    // 함수가 호출될 때, this는 호출부에 따라 결정되므로, 클래스의 임의 메서드가 특정 html요소의 이벤트로 등록되는 과정에서 메서드와 this간의 관계가 끊어진다. 
    // 이를 막고자 this를 생성자에서 바인딩 해주고 있다.
    constructor(props) {
        super(props);
        this.handleChange = this.handleChange.bind(this);
        this.handleClick = this.handleClick.bind(this);
    }

    handleChange(e) {
        this.setState({
            message: e.target.value
        });
    }

    handleClick() {
        alert(this.state.message);
        this.setState({
            message: ''
        });
    }

    render(onClick = this.handleClick) {
        return (
            <div>
                <h1>이벤트 연습</h1>
                <input
                    type="text"
                    name="message"
                    placeholder="아무거나 입력해 보세요"
                    value={this.state.message}
                    onChange={this.handleChange}
                />
                <button onClick={this.handleClick}>확인</button>
            </div>
        );
    }
}

export default EventPractice;

Property Initializer Syntax를 사용한 메서드 작성

// EventPractice.js
import React, { Component } from 'react';

class EventPractice extends Component {
    state = {
        message: ''
    };

    // 바벨의 transform-class-properties 문법을 이용하면 생성자를 이용하지 않고 이벤트를 등록해줄 수 있어 편리하다.
    handleChange = e => {
        this.setState({
            message: e.target.value
        });
    };

    handleClick = () => {
        alert(this.state.message);
        this.setState({
            message: ''
        });
    };

    render(onClick = this.handleClick) {
        return (
            <div>
                <h1>이벤트 연습</h1>
                <input
                    type="text"
                    name="message"
                    placeholder="아무거나 입력해 보세요"
                    value={this.state.message}
                    onChange={this.handleChange}
                />
                <button onClick={this.handleClick}>확인</button>
            </div>
        );
    }
}

export default EventPractice;

Input 여러개 사용하기

// EventPractice.js
import React, { Component } from 'react';

class EventPractice extends Component {
    state = {
        message: '',
        username: '',
    };

    // [] 안에 사용된 변수 이름으로 key값이 치환된다. 
    // e.target.name이 message 경우 {message : e.target.value}
    // e.target.name이 username인 경우 {username : e.target.value}
    handleChange = e => {
        this.setState({
            [e.target.name] : e.target.value
        });
    };

    handleClick = () => {
        alert(this.state.username + "님 : " + this.state.message);
        this.setState({
            message: '',
            username: '',
        });
    };

    render(onClick = this.handleClick) {
        return (
            <div>
                <h1>이벤트 연습</h1>
                <input
                    type="text"
                    name="username"
                    placeholder="사용자명"
                    value={this.state.username}
                    onChange={this.handleChange}
                />
                <input
                    type="text"
                    name="message"
                    placeholder="아무거나 입력해 보세요"
                    value={this.state.message}
                    onChange={this.handleChange}
                />
                <button onClick={this.handleClick}>확인</button>
            </div>
        );
    }
}

export default EventPractice;

함수형 컴포넌트로 구현

// EventPractice.js
import React, { useState } from 'react';

const EventPractice = () => {
    const [username, setUsername] = useState('');
    const [message, setMessage] = useState('');
    const onChangeUsername = e => setUsername(e.target.value);
    const onChangeMessage = e => setMessage(e.target.value);

    const onClick = () => {
        alert(username + ' : ' + message);
        setUsername('');
        setMessage('');
    };

    const onKeyPress = e => {
        if (e.key === 'Enter') {
            onClick();
        }
    };

    return (
        <div>
            <h1>이벤트 연습</h1>
            <input
                type="text"
                name="username"
                placeholder="사용자명"
                value={username}
                onChange={onChangeUsername}
            />
            <input
                type="text"
                name="message"
                placeholder="아무거나 입력해 보세요"
                value={message}
                onChange={onChangeMessage}
                onKeyPress={onKeyPress}
            />
            <button onClick={onClick}>확인</button>
        </div>
    );
};

export default EventPractice;

useState에 객체를 넣는 형태로 변경

// EventPractice.js
import React, { useState } from 'react';

const EventPractice = () => {
    // 객체를 넣어준다. useState()함수는 배열을 반환하기 때문에 []를 사용했다.
    const [form, setForm] = useState({
        username: '',
        message: ''
    });

    // form 은 object이므로 {}를 사용했다.
    const {username, message} = form;

    const onChange = e => {
        const nextForm = {
            ...form,  // form 내용을 복사한다는 의미
            [e.target.name]: e.target.value   // 원하는 값으로 덮어 씌운다.
        };
        setForm(nextForm);
    };

    const onClick = () => {
        alert(username + ' : ' + message);
        setForm({
            username: '',
            message: ''
        });
    };

    const onKeyPress = e => {
        if (e.key === 'Enter') {
            onClick();
        }
    };

    return (
        <div>
            <h1>이벤트 연습</h1>
            <input
                type="text"
                name="username"
                placeholder="사용자명"
                value={username}
                onChange={onChange}
            />
            <input
                type="text"
                name="message"
                placeholder="아무거나 입력해 보세요"
                value={message}
                onChange={onChange}
                onKeyPress={onKeyPress}
            />
            <button onClick={onClick}>확인</button>
        </div>
    );
};

export default EventPractice;

You may also like...

답글 남기기

이메일 주소는 공개되지 않습니다. 필수 항목은 *(으)로 표시합니다