반응형
이번 시간에는 클릭 이벤트에 대해 Content가 변경되도록 App을 구성해보겠습니다.
1. 아래 화면에서 WEB을 클릭하면 그 아래 HTML / HTML is HyperText Markup Language 부분이 그에 맞는 내용으로 변경되게 할 것입니다.
우선 WEB 부분에 해당하는 <h1> 영역에 링크를 달아줍니다.
Subject.js
import React, { Component } from 'react';
class Subject extends Component {
render() {
return (
<div>
<header>
<h1><a href="/">{this.props.title}</a></h1>
{this.props.sub}
</header>
</div>
);
}
}
export default Subject;
페이지 첫 로딩시와 WEB을 클릭하면 웰컴페이지가 나타나도록 하기 위해 state에 'mode'를 생성하고,
welcome 모드에서 보여줄 내용을 'welcome' 인자를 생성합니다.
render()함수 내부에 _title, _desc 변수를 선언해주고 모드에 따른 내용이 변경되도록 할당해줍니다.
그리고 <Content> 컴포넌트의 내용에 전달되도록 코드를 수정해줍니다.
App.js
<Subject> 태그 내부에 onChangePage 속성을 선언하고 실행할 함수를 정의해줍니다. 이 함수는 mode를 'welcome'으로 변경해줍니다.
import React, { Component } from 'react';
import Subject from './components/Subject';
import TOC from './components/TOC';
import Content from './components/Content';
//import logo from './logo.svg'; 삭제
import './App.css';
class App extends Component {
constructor(props) {
super(props);
this.state = {
mode: 'read', // 읽기모드인지 welcome모드인지 구분하는 '모드' 설정
welcome: { title: 'welcom', desc: 'Hello, React!!' }, // welcome모드에서 표시할 내용 선언
subject: { title: 'WEB', sub: 'world wide web!' },
contents: [
{ id: 1, title: 'HTML', desc: 'HTML is HyperText ...' },
{ id: 2, title: 'CSS', desc: 'CSS is for design' },
{ id: 3, title: 'Javascript', desc: 'JavaScript is for interactive' }
]
}
}
render() {
var _title, _desc = null;
if (this.state.mode === 'welcome') { // welcome 모드일 경우
_title = this.state.welcome.title; // welcome 의 title
_desc = this.state.welcome.desc; // welcome 의 desc
} else if (this.state.mode === 'read') { // read 모드일 경우
_title = this.state.contents[0].title; // 1번째 content의 title: 추후 개선 예정
_desc = this.state.contents[0].desc; // 1번째 content의 desc: 추후 개선 예정
}
return (
<div className="App">
<Subject
title={this.state.subject.title}
sub={this.state.subject.sub}
onChangePage={function () {
this.setState({ mode: 'welcome' });
}.bind(this)}
/>
<TOC data={this.state.contents} />
<Content title={_title} desc={_desc} /> {/* mode에 따라 타이틀과 desc를 전달받는다. */}
</div>
);
}
}
export default App;
Subject.js
<a> 태그 내부에 클릭 이벤트 속성인 onClick으로 onChangePage()함수를 연결해줍니다.
import React, { Component } from 'react';
class Subject extends Component {
render() {
return (
<div>
<header>
<h1><a href="/" onClick={function (e) {
e.preventDefault();
this.props.onChangePage();
}.bind(this)}>{this.props.title}</a></h1>
{this.props.sub}
</header>
</div>
);
}
}
export default Subject;
2. 다음으로 HTML / CSS / JavaScript부분을 클릭하면 역시 내용이 변경되도록 해보겠습니다.
App.js
<TOC> 태그 내부에 마찬가지로 onChangePage 함수를 선언해줍니다.
import React, { Component } from 'react';
import Subject from './components/Subject';
import TOC from './components/TOC';
import Content from './components/Content';
import './App.css';
class App extends Component {
constructor(props) {
super(props);
this.state = {
mode: 'read',
selected_content_id: 2, // 기본적으로 2번이 선택되도록 함
welcome: { title: 'welcom', desc: 'Hello, React!!' },
subject: { title: 'WEB', sub: 'world wide web!' },
contents: [
{ id: 1, title: 'HTML', desc: 'HTML is HyperText ...' },
{ id: 2, title: 'CSS', desc: 'CSS is for design' },
{ id: 3, title: 'Javascript', desc: 'JavaScript is for interactive' }
]
}
}
render() {
var _title, _desc = null;
if (this.state.mode === 'welcome') {
_title = this.state.welcome.title;
_desc = this.state.welcome.desc;
} else if (this.state.mode === 'read') { // read 모드일 경우
var i = 0; // 반복을 위한 i 변수를 선언하고
while (i < this.state.contents.length) { // i 가 content의 요소 갯수만큼 반복하며
var data = this.state.contents[i]; // i 번째 content를 data 라고 정의한다.
if (data.id === this.state.selected_content_id) { // data의 id와 현재 선택된 content의 id가 일치할 경우
_title = data.title; // content의 title을 다음 진행(출력)으로 넘겨준다.
_desc = data.desc; // content의 desc을 다음 진행(출력)으로 넘겨준다.
break;
}
i = i + 1;
}
}
return (
<div className="App">
<Subject
title={this.state.subject.title}
sub={this.state.subject.sub}
onChangePage={function () {
this.setState({ mode: 'welcome' });
}.bind(this)}
/>
<TOC
onChangePage={function (id) { // 몇번째 요소인지를 id로 넘겨받아서 실행한다.
this.setState({
mode: 'read', // 모드를 read로 바꿔준다.
selected_content_id: Number(id) // selected_content_id에 넘겨받은 id값을 할당하면서 숫자형으로 변환한다.
});
}.bind(this)}
data={this.state.contents} />
<Content title={_title} desc={_desc} />
</div>
);
}
}
export default App;
TOC.js
<a> 태그 내부에 onClick 이벤트 함수를 지정해줍니다.
import React, { Component } from 'react';
class TOC extends Component {
render() {
var lists = [];
var data = this.props.data;
var i = 0;
while (i < data.length) {
lists.push(
<li key={data[i].id}>
<a
href={"/content/" + data[i].id}
data-id={data[i].id} // 몇번째 요소의 이벤트인지를 나타내는 id
// 'data-XXX'접두사로 시작하는 속성은 e.target.dataset.XXX으로 접근가능하다.
onClick={function (e) {
e.preventDefault();
// onChangePage()함수를 연결하면서 id값을 넘겨준다.
this.props.onChangePage(e.target.dataset.id);
}.bind(this)}
>{data[i].title}</a></li>);
i = i + 1;
}
return (
<div>
<nav>
<ul>
{lists}
</ul>
</nav>
</div>
);
}
}
export default TOC;
반응형
'Programming > React' 카테고리의 다른 글
React기초- 8.Update (0) | 2020.07.29 |
---|---|
React기초- 7.Create (0) | 2020.07.29 |
React기초-5.state2 (0) | 2020.07.27 |
React기초-4.state (0) | 2020.07.25 |
React기초-3.props (0) | 2020.07.25 |