๋ณธ๋ฌธ ๋ฐ”๋กœ๊ฐ€๊ธฐ
IT/React

[react] CKEditor ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ ํ™œ์šฉํ•˜์—ฌ ๊ฒŒ์‹œํŒ ๊ตฌ์„ฑํ•˜๊ธฐ (์ตœ์†Œ ๋†’์ด ์„ค์ •ํ•˜๊ธฐ, CSS Module)

by ITyranno 2024. 1. 9.
728x90
๋ฐ˜์‘ํ˜•

 

 

 

 

 

 

 

ํ”„๋กœ๊ทธ๋ž˜๋ฐ ์„ธ๊ณ„๋ฅผ ํƒ๊ตฌํ•ฉ์‹œ๋‹ค.

 

 

 

 

 

 

CKEditor ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ ํ™œ์šฉํ•˜์—ฌ ๊ฒŒ์‹œํŒ ๊ตฌ์„ฑํ•˜๊ธฐ

 

 

 

CKEditor ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ๋ฅผ ํ™œ์šฉํ•˜์—ฌ ๊ฒŒ์‹œํŒ์„ ํšจ๊ณผ์ ์œผ๋กœ ๊ตฌ์„ฑํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

HTML, CSS๋ฅผ ์ „๋ถ€ ํ™œ์šฉํ•ด์„œ ๊ตฌํ˜„ํ•˜๋ ค๋ฉด ์–ด๋ ค์šด ๊ฒŒ์‹œํŒ ์š”์†Œ๋ฅผ ๊ฐ„ํŽธํ•˜๊ฒŒ ์ถœ๋ ฅํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์•„๋ž˜๋Š” ๊ตฌํ˜„ ์˜ˆ์‹œ์ž…๋‹ˆ๋‹ค.

 

 

 

 

 

 

 

 

 

CKEditor ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ

 

 

1. CKEditor ๋ž€?

 

 

CKEditor๋Š” ์›น ๊ธฐ๋ฐ˜์˜ ํ…์ŠคํŠธ ์—๋””ํ„ฐ๋กœ, HTML๋กœ ์ž‘์„ฑ๋œ ๋ฌธ์„œ๋ฅผ ํŽธ์ง‘ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์ด๋Š” ์›น์‚ฌ์ดํŠธ์˜ ์‚ฌ์šฉ์ž๊ฐ€ ๋ธŒ๋ผ์šฐ์ €์—์„œ ์ง์ ‘ ์ฝ˜ํ…์ธ ๋ฅผ ํŽธ์ง‘ํ•  ์ˆ˜ ์žˆ๊ฒŒ ํ•ด์ค๋‹ˆ๋‹ค.

์ด ์—๋””ํ„ฐ๋Š” JavaScript๋กœ ์ž‘์„ฑ๋˜์—ˆ์œผ๋ฉฐ, ๋‹ค์–‘ํ•œ ์›น ๋ธŒ๋ผ์šฐ์ €์™€ ํ˜ธํ™˜๋ฉ๋‹ˆ๋‹ค.

 

 

CKEditor ์‚ฌ์ดํŠธ URL

 

https://ckeditor.com/ckeditor-5/

 

CKEditor 5 | Powerful Framework with Modular Architecture

Easy to customize RichText Editor with a powerful framework, a modular architecture, and modern features like Collaborative Editing.

ckeditor.com

 

 

 

 

CKEditor ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ ์ฃผ์š” ๊ธฐ๋Šฅ

 

 

CKEditor๋Š” ํ…์ŠคํŠธ ์Šคํƒ€์ผ๋ง, ๊ธ€๋จธ๋ฆฌ ๊ธฐํ˜ธ์™€ ๋ฒˆํ˜ธ ๋งค๊ธฐ๊ธฐ, ํ‘œ ์‚ฝ์ž…, ๋งํฌ์™€ ์ด๋ฏธ์ง€ ์‚ฝ์ž… ๋“ฑ๊ณผ ๊ฐ™์€ ํ’๋ถ€ํ•œ ํ…์ŠคํŠธ ํŽธ์ง‘ ๊ธฐ๋Šฅ์„ ์ œ๊ณตํ•ฉ๋‹ˆ๋‹ค.

๋˜ํ•œ, HTML ์ฝ”๋“œ๋ฅผ ์ง์ ‘ ํŽธ์ง‘ํ•˜๋Š” '์†Œ์Šค' ๋ชจ๋“œ๋„ ์žˆ์Šต๋‹ˆ๋‹ค.

์ด ์™ธ์—๋„ CKEditor๋Š” ํ”Œ๋Ÿฌ๊ทธ์ธ ์•„ํ‚คํ…์ฒ˜๋ฅผ ํ†ตํ•ด ์‚ฌ์šฉ์ž๊ฐ€ ์›ํ•˜๋Š” ๊ธฐ๋Šฅ์„ ์ถ”๊ฐ€๋กœ ๊ฐœ๋ฐœํ•˜๊ณ  ์ ์šฉํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

 

 

 

 

 

CKEditor ๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ ์‚ฌ์šฉ ๋ฐฉ๋ฒ•

 

์ €๋Š” react ํ”„๋กœ์ ํŠธ์—์„œ ์‚ฌ์šฉํ•˜์˜€์Šต๋‹ˆ๋‹ค.

 

 

 1.  ์„ค์น˜

 

 

๋ผ์ด๋ธŒ๋Ÿฌ๋ฆฌ ์„ค์น˜๋ฅผ ์ง„ํ–‰ํ•ฉ๋‹ˆ๋‹ค.

 

npm install --save @ckeditor/ckeditor5-react @ckeditor/ckeditor5-build-classic

 

 

 

documentation ์—์„œ ๋‹ค๋ฅธ ์—๋””ํ„ฐ์˜ ์ข…๋ฅ˜๋ฅผ ํ™•์ธํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

https://ckeditor.com/docs/ckeditor5/latest/builds/guides/overview.html

 

Predefined builds | CKEditor 5 documentation

Learn how to install, integrate and configure CKEditor 5 Builds and how to work with CKEditor 5 Framework, customize it, create your own plugins and custom editors, change the UI or even bring your own UI to the editor. API reference and examples included.

ckeditor.com

 

 

 

 2.  ์ฝ”๋“œ ์ž‘์„ฑ

 

์•„๋ž˜ ์ฝ”๋“œ๋ฅผ ์ ์ ˆํ•œ ์œ„์น˜์— ์ž…๋ ฅํ•ฉ๋‹ˆ๋‹ค.

 

import React, { Component } from 'react';
import { CKEditor } from '@ckeditor/ckeditor5-react';
import ClassicEditor from '@ckeditor/ckeditor5-build-classic';



<CKEditor
                        editor={ClassicEditor}
                        data="<p>Hello from CKEditor 5!</p>"
                        onReady={editor => {
                            // You can store the "editor" and use when it is needed.
                            console.log('Editor is ready to use!', editor);
                        }}
                        onChange={(event, editor) => {
                            const data = editor.getData();
                            console.log({ event, editor, data });
                            setMountainContent({
                                ...mountainContent,
                                content: data
                            })
                            console.log(mountainContent);
                        }}
                        onBlur={(event, editor) => {
                            console.log('Blur.', editor);
                        }}
                        onFocus={(event, editor) => {
                            console.log('Focus.', editor);
                        }}
                    />
                </div>

 

 

 

์ƒ์„ธํ•œ ์„ค๋ช…์€ ์•„๋ž˜ ๊ณต์‹๋ฌธ์„œ ์ฐธ๊ณ  ๋ฐ”๋ž๋‹ˆ๋‹ค.

https://ckeditor.com/docs/ckeditor5/latest/installation/integrations/react.html

 

React rich text editor component | CKEditor 5 documentation

Learn how to install, integrate and configure CKEditor 5 Builds and how to work with CKEditor 5 Framework, customize it, create your own plugins and custom editors, change the UI or even bring your own UI to the editor. API reference and examples included.

ckeditor.com

 

 

 

 

 

 

 

 3.  ์ตœ์†Œ ๋†’์ด CSS ์ ์šฉ

 

์ œ ํ”„๋กœ์ ํŠธ์— ์‚ฌ์šฉํ•œ ์ฝ”๋“œ์ž…๋‹ˆ๋‹ค.

 

 

Board.jsx

import Nav from '../nav/Nav';
import style from './Board.module.css';
import { CKEditor } from '@ckeditor/ckeditor5-react';
import ClassicEditor from '@ckeditor/ckeditor5-build-classic';
import { useState } from 'react';

function Board() {

    const [mountainContent, setMountainContent] = useState({
        title: '',
        content: ''
    })

    const [viewContent, setViewContent] = useState([]);

    const getValue = e => {
        const { name, value } = e.target;
        setMountainContent(prevContent => ({
            ...prevContent,
            [name]: value
        }));
    };


    return (
        <>
            <div className={style.homepage_nav}>
                <Nav />
            </div>

            <div className={style.board}>
                <h1>๋“ฑ์‚ฐ ํ›„๊ธฐ</h1>
                <div className={style.mountain_container}>
                    {viewContent.map(element =>
                        <div>
                            <h2>{element.title}</h2>
                            <div>{element.content}</div>
                        </div>)}
                </div>
                <div className={style.form_wrapper}>
                    <input className={style.title_input}
                        type='text'
                        placeholder='์ œ๋ชฉ'
                        onChange={getValue}
                        name='title' />
                    <CKEditor
                        editor={ClassicEditor}
                        data="<p>Hello from CKEditor 5!</p>"
                        onReady={editor => {
                            // You can store the "editor" and use when it is needed.
                            console.log('Editor is ready to use!', editor);
                        }}
                        onChange={(event, editor) => {
                            const data = editor.getData();
                            console.log({ event, editor, data });
                            setMountainContent({
                                ...mountainContent,
                                content: data
                            })
                            console.log(mountainContent);
                        }}
                        onBlur={(event, editor) => {
                            console.log('Blur.', editor);
                        }}
                        onFocus={(event, editor) => {
                            console.log('Focus.', editor);
                        }}
                    />
                </div>
                <button className={style.submit_button}
                    onClick={() => {
                        setViewContent(prevContent => prevContent.concat(mountainContent));
                    }}
                >์ž…๋ ฅ</button>
            </div>

        </>
    )
}
export default Board;

 

 

 

Board.module.css

 

.board {
    text-align: center;
    height: 100vh;
    width: 100vw;
    display: flex;
    flex-direction: column;
    align-items: center;
    padding-top: 7rem;

}

.mountain_container {
    margin: 0 auto;
    width: 80%;
    border: 1px solid #333;
    padding: 10px 0 30px 0;
    border-radius: 5px;
    margin-bottom: 50px;
}

.form_wrapper {
    width: 60%;
    margin: 0 auto;
}

.title_input {
    width: 500px;
    height: 40px;
    margin: 10px;
}

.text_area {
    width: 80%;
    min-height: 500px;
}

.submit_button {
    width: 200px;
    height: 50px;
    font-size: 20px;
    padding: 20px;
    border: none;
    background: indianred;
    border-radius: 5px;
    margin-top: 40px;
    vertical-align: middle;
}

 

 

 

 

์œ„ ์ฝ”๋“œ๋ฅผ ๊ทธ๋Œ€๋กœ ์‚ฌ์šฉํ•˜๋ฉด ์•„๋ž˜์™€ ๊ฐ™์€ ํ˜•ํƒœ๊ฐ€ ์ถœ๋ ฅ๋ฉ๋‹ˆ๋‹ค.

 

 

 

 

 

 

๊ฒŒ์‹œํŒ์˜ ๊ธฐ๋ณธ ์˜์—ญ์ด ๋„ˆ๋ฌด ์ž‘์Šต๋‹ˆ๋‹ค.

Board.css ๋“ฑ ๋ฐฉ์‹์„ ์‚ฌ์šฉํ•œ ๊ฒฝ์šฐ๋ผ๋ฉด css ํŒŒ์ผ์— ์•„๋ž˜ ์ฝ”๋“œ๋ฅผ ์ž…๋ ฅํ•˜๋ฉด ์ตœ์†Œ ๋†’์ด๊ฐ€ ์„ค์ •๋ฉ๋‹ˆ๋‹ค.

 

.ck-editor__editable {
  min-height: 30rem;
}

 

 

 

๊ทธ๋Ÿฌ๋‚˜ ์ €๋Š” module.css ํ˜•์‹์„ ์‚ฌ์šฉํ•˜์˜€๊ธฐ ๋•Œ๋ฌธ์— CSS๊ฐ€ ์ ์šฉ๋˜์ง€ ์•Š๋Š” ๋ฌธ์ œ๊ฐ€ ์ƒ๊ฒผ์Šต๋‹ˆ๋‹ค.

 

๊ทธ๋ž˜์„œ board.module.css ํŒŒ์ผ์ด ์•„๋‹Œ index.css์™€ ๊ฐ™์€ ๊ธ€๋กœ๋ฒŒ ์Šคํƒ€์ผ์‹œํŠธ ํŒŒ์ผ์— ์œ„ ์ฝ”๋“œ๋ฅผ ์ž…๋ ฅํ•˜์—ฌ ์ตœ์†Œ ๋†’์ด๋ฅผ ์„ค์ •ํ•˜๋Š” ๋ฐฉ์‹์œผ๋กœ ์œ„ ๋ฌธ์ œ๋ฅผ ํ•ด๊ฒฐํ•˜์˜€์Šต๋‹ˆ๋‹ค.

 

 

index.css

/* ๊ธ€๋กœ๋ฒŒ ์Šคํƒ€์ผ์‹œํŠธ ํŒŒ์ผ์— ์ถ”๊ฐ€ */
.ck-editor__editable {
  min-height: 30rem;
}

 

 

 

๊ตฌํ˜„ ํ™”๋ฉด

 

 

 

 

 

728x90
๋ฐ˜์‘ํ˜•

loading