所以我创建了一个反应记事本。我使用react
作为前端,node js
+ mongodb
作为后端。然后我添加了react-quill以在我的应用程序中包含富文本编辑器。
问题是我将这个文本编辑器集成到我的项目中,现在我可以将html样式的数据输入到我的数据库中,但是我不知道我应该使用哪个部分react-quill
来显示我的记录从服务器提取到我的应用程序的数据。
你可以帮帮我吗?
以下是react-quill github page,此处为react-quill documentation。
我很难在本文档中找到特定的信息,也许我的经验不足。
现在,我坚持这个:
这是我的NoteNew
组件:
import React, { Component } from 'react';
import ReactQuill from 'react-quill';
import { Field, reduxForm } from 'redux-form';
import { Link } from 'react-router-dom';
import { connect } from 'react-redux';
import { addNote } from '../actions/actions';
class NoteNew extends Component {
constructor(props) {
super(props);
this.state = {
content: '',
};
}
handleContentChange(value) {
this.setState({ content: value });
}
onSumbit(values) {
const content = this.state.content;
const currentTime = this.formatDateAndHour();
const currentTimeRaw = new Date();
this.props.addNote(
{ ...values, content, createTime: currentTime, timeRaw: currentTimeRaw },
() => this.props.history.push('/')
);
}
formatDateAndHour() {
const monthNames = [
'January',
'February',
'March',
'April',
'May',
'June',
'July',
'August',
'September',
'October',
'November',
'December',
];
const date = new Date();
const day = date.getDate();
const monthIndex = date.getMonth();
const year = date.getFullYear();
const hour = date.getHours();
const minutes = date.getMinutes();
const dayShow = day < 10 ? `0${day}` : day;
const hourShow = hour < 10 ? `0${hour}` : hour;
const minutesShow = minutes < 10 ? `0${minutes}` : minutes;
return `${dayShow} ${
monthNames[monthIndex]
} ${year} ${hourShow}:${minutesShow}`;
}
errorView() {
const { addNoteStatus } = this.props;
if (addNoteStatus === 'error') {
return (
<div className="error-del">
Sorry, something went wrong. Please try again later.
</div>
);
}
return <div />;
}
renderFieldTitle(field) {
const className = `form-group ${
field.meta.touched && field.meta.error ? 'has-danger' : ''
}`;
return (
<div className={className}>
<label className="form-title" htmlFor="title">
{field.labelToShow}
</label>
<br />
<input className="form-control-title" type="text" {...field.input} />
<div className="text-help">
{field.meta.touched ? field.meta.error : ''}
</div>
</div>
);
}
render() {
const { handleSubmit } = this.props;
return (
<div className="row form-fields text-center">
<form onSubmit={handleSubmit(this.onSumbit.bind(this))}>
<Field
name="title"
labelToShow="Note title"
component={this.renderFieldTitle}
/>
<ReactQuill
value={this.state.content}
onChange={this.handleContentChange.bind(this)}
name="content"
labelToShow="content"
component={this.renderFieldContent}
/>
<button type="submit" className="btn btn-secondary submit-button">
<i className="fa fa-check" aria-hidden="true" />
</button>
<Link to="/" className="btn btn-secondary back-button">
<i className="fa fa-times" aria-hidden="true" />
</Link>
{this.errorView()}
</form>
</div>
);
}
}
function validate(values) {
const errors = {};
if (!values.title || values.title.length < 3) {
errors.title = 'Enter note title that is at least 3 characters long!';
}
return errors;
}
function mapStateToProps(state) {
return {
addNoteStatus: state.addNoteStatus,
};
}
export default reduxForm({
validate,
form: 'NoteNewFormUnique',
})(connect(mapStateToProps, { addNote })(NoteNew));
这是我的NoteShow
组件:
import React, { Component } from 'react';
import { connect } from 'react-redux';
import { withRouter } from 'react-router-dom';
import { prepareEdit, deleteOneNote } from '../actions/actions';
class NoteShow extends Component {
onEditClick() {
const { selectedNoteFromState } = this.props;
this.props.prepareEdit(selectedNoteFromState, () => {
this.props.history.push('/notes/edit');
});
}
onDeleteClick() {
const { selectedNoteFromState } = this.props;
this.props.deleteOneNote(selectedNoteFromState, () => {
this.props.history.push('/');
});
}
errorView() {
const { delNoteStatus } = this.props;
if (delNoteStatus === 'error') {
return (
<div className="col-sm-3 col-md-3 col-lg-3 col-xl-3 error-del text-center">
Sorry, something went wrong. Please try again later.
</div>
);
}
return <div />;
}
timeView() {
const { selectedNoteFromState } = this.props;
const { allNotesFromStateObj } = this.props;
const noteToView = allNotesFromStateObj[selectedNoteFromState];
if (noteToView.editTime) {
return (
<p className="text-center date-time">
Last edited: {noteToView.editTime}
</p>
);
}
return (
<p className="text-center date-time">Created: {noteToView.createTime}</p>
);
}
renderNoteDetail() {
const { selectedNoteFromState } = this.props;
const { allNotesFromStateObj } = this.props;
const noteToView = allNotesFromStateObj[selectedNoteFromState];
return (
<div className="col-sm-8 col-md-7 col-lg-8 col-xl-8 pull-sm-right text-justify note-show">
<h2 className="text-center">{noteToView.title}</h2>
<p className="note-text">{noteToView.content}</p>
<hr />
{this.timeView()}
<button
className="btn btn-secondary pull-xs-left small-buttons"
onClick={this.onEditClick.bind(this)}
>
<i className="fa fa-pencil" aria-hidden="true" />
</button>
<button
className="btn btn-secondary pull-xs-right small-buttons"
onClick={this.onDeleteClick.bind(this)}
>
<i className="fa fa-trash-o" aria-hidden="true" />
</button>
</div>
);
}
render() {
const { statusFromState } = this.props;
const { selectedNoteFromState } = this.props;
if (
statusFromState === 'fetch_all_notes_success' &&
selectedNoteFromState !== null
) {
return (
<div>
{this.renderNoteDetail()}
{this.errorView()}
</div>
);
}
return <div />;
}
}
function mapStateToProps(state) {
return {
selectedNoteFromState: state.selectedNote,
statusFromState: state.fetchAllStatus,
allNotesFromStateObj: state.notes,
delNoteStatus: state.delNoteStatus,
};
}
export default withRouter(
connect(mapStateToProps, { prepareEdit, deleteOneNote })(NoteShow)
);