Показать содержимое массива в рендере - PullRequest
0 голосов
/ 06 августа 2020

Я использую стек MERN и Redux. Я создал массив в комментариях состояния, который обновляется с помощью функции clickHandler элементами из глобального состояния (доступ к которому осуществляется через реквизиты). Когда я пытаюсь показать содержимое массива в рендере, я просто получаю его длину. Как мне показать свойства элементов, например заголовок.

import React, { Component } from "react";
import PropTypes from "prop-types";
import GoogleSearch from "./GoogleSearch";
import { connect } from "react-redux";
import { fetchSubjects } from "../../actions/subject";
import { fetchComments } from "../../actions/comment";
import store from "../../store";

class Subject extends Component {
  // on loading the subjects and comments
  // are fetched from the database
  componentDidMount() {
    this.props.fetchSubjects();
    this.props.fetchComments();
  }

  constructor(props) {
    super(props);
    this.state = {
      // set inital state for subjects description
      // and summary to invisible
      viewDesription: -1,
      viewSummary: -1,
      comments: [],
    };
  }

  componentWillReceiveProps(nextProps) {
    // new subject and comments are added to the top
    if (nextProps.newPost) {
      this.props.subjects.unshift(nextProps.newPost);
    }
    if (nextProps.newPost) {
      this.props.comments.unshift(nextProps.newPost);
    }
  }

  clickHandler = (id) => {
    // when a subject title is clicked pass in its id
    // and make the desciption visible
    const { viewDescription } = this.state;
    this.setState({ viewDescription: viewDescription === id ? -1 : id });
    // clear the existing comments in state
    this.setState({
      comments: [],
    });
    // loop through the comment items in the global state
    // and add any with the same subjects id passed in to the array
    var i;
    for (i = 0; i < this.props.comments.length; i++) {
      if (this.props.comments[i].subject == id) {
        console.log(this.props.comments[i]);
        this.setState({
          comments: this.state.comments.unshift(this.props.comments[i]),
        });
      }
    } // set local storage to the id for the subject that has been clicked
    localStorage.setItem("passedSubject", id);
  };

  // hovering on and off subjects toggles the visibility of the summary
  hoverHandler = (id) => {
    this.setState({ viewSummary: id });
  };
  hoverOffHandler = () => {
    this.setState({ viewSummary: -1 });
  };

  render() {
    const subjectItems = this.props.subjects.map((subject) => {
      // if the state equals the id set to visible if not set to invisible
      var view = this.state.viewDescription === subject._id ? "" : "none";
      var hover = this.state.viewSummary === subject._id ? "" : "none";
      var comments = this.state.comments;
      return (
        <div key={subject._id}>
          <div
            className="subjectTitle"
            onClick={() => this.clickHandler(subject._id)}
            onMouseEnter={() => this.hoverHandler(subject._id)}
            onMouseLeave={() => this.hoverOffHandler()}
          >
            <p className="title">{subject.title}</p>
            <p className="rating">Rating: {subject.rating}</p>
            <p className="summary" style={{ display: hover }}>
              {subject.summary}
            </p>
          </div>

          <div className="subjectBody " style={{ display: view }}>
            <div className="subjectAuthor">
              <p className="author">
                Subject created by: {subject.author} on {subject.date}
              </p>
              <a href="">
                <div className="buttonRateSubject">RATE SUBJECT</div>
              </a>
            </div>

            <div className="subjectDescription">
              <p className="description">{subject.description}</p>
            </div>

            <div className="subjectLinks">Links:</div>

            <div className="subjectComments">
              <p>Comments:</p>
              {/* ************HERE*********** */}
              <p>{comments}</p>
              {/* ********************************* */}
              <a href="/addcomment">
                <div className="buttonAddComment">ADD COMMENT</div>
              </a>
            </div>
          </div>
        </div>
      );
    });

    return (
      <div id="Subject">
        <GoogleSearch />
        {subjectItems}
      </div>
    );
  }
}

Subject.propTypes = {
  fetchSubjects: PropTypes.func.isRequired,
  fetchComments: PropTypes.func.isRequired,
  subjects: PropTypes.array.isRequired,
  comments: PropTypes.array.isRequired,
  newPost: PropTypes.object,
};

const mapStateToProps = (state) => ({
  subjects: state.subjects.items,
  newSubject: state.subjects.item,
  comments: state.comments.items,
  newComment: state.comments.item,
});

// export default Subject;
export default connect(mapStateToProps, { fetchSubjects, fetchComments })(
  Subject,
  Comment
);

Ответы [ 2 ]

1 голос
/ 06 августа 2020

Думаю, я знаю вашу проблему. Вы хотите визуализировать элементы массива.

Позвольте мне дать вам краткий обзор.

Javascript:

this.setState({
  comments: data
});

render (){
  return (
    <div>
    { this.state.comments.map(c=> <div>{c.body}</div> ) }
    </div>
  )
}
0 голосов
/ 06 августа 2020

Спасибо, ребята, я изменил для l oop в clickHandler на это, в котором теперь есть рендеринг данных, ему почему-то не нравились объекты в массиве.

 var temp = [];
    for (i = 0; i < this.props.comments.length; i++) {
      if (this.props.comments[i].subject == id) {
        console.log(this.props.comments[i]);
        temp.unshift(this.props.comments[i].comment);
        temp.unshift(this.props.comments[i].title);
    
      }
    }
    this.setState({
      comments: temp,
    });
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...