From 5576bf2251e97b1db8f33dba130e8bbccea370ac Mon Sep 17 00:00:00 2001 From: notnull Date: Sat, 13 Jul 2019 07:56:55 -0400 Subject: [PATCH 1/4] WIP recursion --- .gitignore | 2 + src/App.js | 31 +++++------- src/Components/AllComments/AllCommentsView.js | 12 ----- src/Components/AllComments/CommentList.js | 15 ------ src/Components/AllComments/CommentRow.js | 33 ------------- src/Components/AllComments/Replies.js | 20 -------- src/Components/AllComments/SingleComment.js | 10 ---- .../SingleComment}/CollapsedComment.js | 4 +- .../SingleComment}/ExpandedComment.js | 5 +- .../Comments/SingleComment/index.js | 12 +++++ src/Components/Comments/index.js | 47 +++++++++++++++++++ .../Navbar/{NavbarView.js => index.js} | 0 src/Components/index.js | 4 +- 13 files changed, 80 insertions(+), 115 deletions(-) delete mode 100644 src/Components/AllComments/AllCommentsView.js delete mode 100644 src/Components/AllComments/CommentList.js delete mode 100644 src/Components/AllComments/CommentRow.js delete mode 100644 src/Components/AllComments/Replies.js delete mode 100644 src/Components/AllComments/SingleComment.js rename src/Components/{AllComments => Comments/SingleComment}/CollapsedComment.js (88%) rename src/Components/{AllComments => Comments/SingleComment}/ExpandedComment.js (91%) create mode 100644 src/Components/Comments/SingleComment/index.js create mode 100644 src/Components/Comments/index.js rename src/Components/Navbar/{NavbarView.js => index.js} (100%) diff --git a/.gitignore b/.gitignore index 4d29575..56e27d6 100644 --- a/.gitignore +++ b/.gitignore @@ -21,3 +21,5 @@ npm-debug.log* yarn-debug.log* yarn-error.log* + +old diff --git a/src/App.js b/src/App.js index 7aed175..dd2d6b7 100644 --- a/src/App.js +++ b/src/App.js @@ -1,5 +1,5 @@ import React from 'react' -import { NavbarView, CommentsView } from './Components' +import { Navbar, Comments } from './Components' import axios from 'axios' const API = 'http://localhost:5555' @@ -13,15 +13,6 @@ const comments = [ replies: [ { id: 3, text: 'c3', replies: [] }, { id: 4, text: 'c4', replies: [] }, - { id: 5, text: 'c5', replies: [] }, - ], - }, - { - id: 6, - text: 'c6', - replies: [ - { id: 7, text: 'c7', replies: [] }, - { id: 8, text: 'c8', replies: [] }, ], }, ] @@ -37,14 +28,14 @@ class App extends React.Component { } async fetchComments() { - // try { - // const { data } = await axios.get(API + '/api/comments') - // return data - // } catch (error) { - // console.log(error) - // this.setState({ error }) - // } - return comments + try { + const { data } = await axios.get(API + '/api/comments') + return data + } catch (error) { + console.log(error) + this.setState({ error }) + } + //return comments } async fetchData() { @@ -67,8 +58,8 @@ class App extends React.Component { renderApp() { return (
- - + +
) } diff --git a/src/Components/AllComments/AllCommentsView.js b/src/Components/AllComments/AllCommentsView.js deleted file mode 100644 index 6b0947a..0000000 --- a/src/Components/AllComments/AllCommentsView.js +++ /dev/null @@ -1,12 +0,0 @@ -import React from 'react' -import CommentList from './CommentList' -import { Container } from 'react-bootstrap' - -const AllCommentsView = props => { - return ( - - - - ) -} -export default AllCommentsView diff --git a/src/Components/AllComments/CommentList.js b/src/Components/AllComments/CommentList.js deleted file mode 100644 index 2026fc7..0000000 --- a/src/Components/AllComments/CommentList.js +++ /dev/null @@ -1,15 +0,0 @@ -import React from 'react' -import CommentRow from './CommentRow' - -const CommentList = props => { - const { comments } = props - return ( - - ) -} - -export default CommentList diff --git a/src/Components/AllComments/CommentRow.js b/src/Components/AllComments/CommentRow.js deleted file mode 100644 index 003d810..0000000 --- a/src/Components/AllComments/CommentRow.js +++ /dev/null @@ -1,33 +0,0 @@ -import React from 'react' -import SingleComment from './SingleComment' -import Replies from './Replies' - -//todo: rename to 'thread' -class CommentRow extends React.Component { - constructor() { - super() - this.state = {} - this.toggleCollapse = this.toggleCollapse.bind(this) - } - - toggleCollapse() { - this.setState({ collapsed: !this.state.collapsed }) - } - - render() { - const { text, replies } = this.props - - return ( -
- - -
- ) - } -} - -export default CommentRow diff --git a/src/Components/AllComments/Replies.js b/src/Components/AllComments/Replies.js deleted file mode 100644 index 9622cd4..0000000 --- a/src/Components/AllComments/Replies.js +++ /dev/null @@ -1,20 +0,0 @@ -import React from 'react' -import CommentList from './CommentList' - -class Replies extends React.Component { - constructor() { - super() - this.state = {} - } - - render() { - const { replies } = this.props - return ( -
- -
- ) - } -} - -export default Replies diff --git a/src/Components/AllComments/SingleComment.js b/src/Components/AllComments/SingleComment.js deleted file mode 100644 index 6b88047..0000000 --- a/src/Components/AllComments/SingleComment.js +++ /dev/null @@ -1,10 +0,0 @@ -import React from 'react' -import ExpandedComment from './ExpandedComment' -import CollapsedComment from './CollapsedComment' - -export default props => { - const { text, collapsed, toggleCollapse } = props - if (collapsed) - return - return -} diff --git a/src/Components/AllComments/CollapsedComment.js b/src/Components/Comments/SingleComment/CollapsedComment.js similarity index 88% rename from src/Components/AllComments/CollapsedComment.js rename to src/Components/Comments/SingleComment/CollapsedComment.js index 8f02b22..f6ff902 100644 --- a/src/Components/AllComments/CollapsedComment.js +++ b/src/Components/Comments/SingleComment/CollapsedComment.js @@ -1,6 +1,6 @@ import React from 'react' -export default props => { +const CollapsedComment = props => { return (
  • @@ -22,3 +22,5 @@ export default props => {
  • ) } + +export default CollapsedComment diff --git a/src/Components/AllComments/ExpandedComment.js b/src/Components/Comments/SingleComment/ExpandedComment.js similarity index 91% rename from src/Components/AllComments/ExpandedComment.js rename to src/Components/Comments/SingleComment/ExpandedComment.js index dfdd36f..92f8c83 100644 --- a/src/Components/AllComments/ExpandedComment.js +++ b/src/Components/Comments/SingleComment/ExpandedComment.js @@ -1,6 +1,5 @@ import React from 'react' - -export default props => { +const ExpandedComment = props => { const { text } = props return ( @@ -30,3 +29,5 @@ export default props => { ) } + +export default ExpandedComment diff --git a/src/Components/Comments/SingleComment/index.js b/src/Components/Comments/SingleComment/index.js new file mode 100644 index 0000000..d6738f2 --- /dev/null +++ b/src/Components/Comments/SingleComment/index.js @@ -0,0 +1,12 @@ +import React from 'react' +import ExpandedComment from './ExpandedComment' +import CollapsedComment from './CollapsedComment' + +const SingleComment = props => { + console.log(props) + const { collapsed } = props + if (collapsed) return + return +} + +export default SingleComment diff --git a/src/Components/Comments/index.js b/src/Components/Comments/index.js new file mode 100644 index 0000000..90fbe6e --- /dev/null +++ b/src/Components/Comments/index.js @@ -0,0 +1,47 @@ +import React from 'react' +import SingleComment from './SingleComment' +import uuid from 'uuid' + +class ThreadList extends React.Component { + constructor() { + super() + this.state = { collapsed: false } + this.toggleCollapse = this.toggleCollapse.bind(this) + } + + toggleCollapse() { + this.setState({ collapsed: !this.state.collapsed }) + } + + render() { + const { comments } = this.props + console.log(comments) + + return ( +
      + {comments.map(comment => { + return ( +
      + + + {comment.replies && ( + + )} +
      + ) + })} +
    + ) + } +} + +export default ThreadList diff --git a/src/Components/Navbar/NavbarView.js b/src/Components/Navbar/index.js similarity index 100% rename from src/Components/Navbar/NavbarView.js rename to src/Components/Navbar/index.js diff --git a/src/Components/index.js b/src/Components/index.js index 6f8970f..aa234d8 100644 --- a/src/Components/index.js +++ b/src/Components/index.js @@ -1,2 +1,2 @@ -export { default as NavbarView } from './Navbar/NavbarView' -export { default as CommentsView } from './AllComments/AllCommentsView' +export { default as Navbar } from './Navbar' +export { default as Comments } from './Comments' From 23144bc1806fb481ae2cf84598613d2085c1167e Mon Sep 17 00:00:00 2001 From: data Date: Fri, 12 Jul 2019 12:56:40 +0200 Subject: [PATCH 2/4] fix toggling and thread view - pass all comments to ThreadList - filter comments based on threadLevel === parentId - pass comment id to toggleCollapse() --- server/db/seed.js | 3 +- src/App.js | 12 ---- .../SingleComment/CollapsedComment.js | 4 +- .../Comments/SingleComment/ExpandedComment.js | 29 +++++---- .../Comments/SingleComment/index.js | 4 +- src/Components/Comments/index.js | 63 ++++++++++++------- 6 files changed, 61 insertions(+), 54 deletions(-) diff --git a/server/db/seed.js b/server/db/seed.js index 35380f8..73b8769 100755 --- a/server/db/seed.js +++ b/server/db/seed.js @@ -22,7 +22,8 @@ async function runSeed() { await c1.addReply(2) - await c2.addReplies([c3, c4, c5]) + await c2.addReplies([c3, c4]) + await c5.setParent(c4) await c6.setParent(c1) diff --git a/src/App.js b/src/App.js index dd2d6b7..4629786 100644 --- a/src/App.js +++ b/src/App.js @@ -5,18 +5,6 @@ import axios from 'axios' const API = 'http://localhost:5555' console.log('Using API at ' + API) -const comments = [ - { id: 1, text: 'c1', replies: [] }, - { - id: 2, - text: 'c2', - replies: [ - { id: 3, text: 'c3', replies: [] }, - { id: 4, text: 'c4', replies: [] }, - ], - }, -] - class App extends React.Component { constructor() { super() diff --git a/src/Components/Comments/SingleComment/CollapsedComment.js b/src/Components/Comments/SingleComment/CollapsedComment.js index f6ff902..cc712fb 100644 --- a/src/Components/Comments/SingleComment/CollapsedComment.js +++ b/src/Components/Comments/SingleComment/CollapsedComment.js @@ -2,7 +2,7 @@ import React from 'react' const CollapsedComment = props => { return ( -
  • +
  • profile username @@ -14,7 +14,7 @@ const CollapsedComment = props => { color: 'blue', cursor: 'pointer', }} - onClick={props.toggleCollapse} + onClick={() => props.toggleCollapse(props.id)} > expand diff --git a/src/Components/Comments/SingleComment/ExpandedComment.js b/src/Components/Comments/SingleComment/ExpandedComment.js index 92f8c83..6954424 100644 --- a/src/Components/Comments/SingleComment/ExpandedComment.js +++ b/src/Components/Comments/SingleComment/ExpandedComment.js @@ -1,26 +1,29 @@ import React from 'react' const ExpandedComment = props => { const { text } = props - return ( -
  • +
  • profile
    username
    July 9 2019, 01:32:27 UTC - - collapse - + {props.replies.length > 0 ? ( + props.toggleCollapse(props.id)} + > + collapse + + ) : ( + '' + )}
    diff --git a/src/Components/Comments/SingleComment/index.js b/src/Components/Comments/SingleComment/index.js index d6738f2..1b4417b 100644 --- a/src/Components/Comments/SingleComment/index.js +++ b/src/Components/Comments/SingleComment/index.js @@ -3,9 +3,7 @@ import ExpandedComment from './ExpandedComment' import CollapsedComment from './CollapsedComment' const SingleComment = props => { - console.log(props) - const { collapsed } = props - if (collapsed) return + if (props.collapsed) return return } diff --git a/src/Components/Comments/index.js b/src/Components/Comments/index.js index 90fbe6e..21d4076 100644 --- a/src/Components/Comments/index.js +++ b/src/Components/Comments/index.js @@ -5,39 +5,56 @@ import uuid from 'uuid' class ThreadList extends React.Component { constructor() { super() - this.state = { collapsed: false } this.toggleCollapse = this.toggleCollapse.bind(this) } - toggleCollapse() { - this.setState({ collapsed: !this.state.collapsed }) + toggleCollapse(id) { + // select passed comment from the state, toggle it and put it all back + const otherComments = this.props.comments.filter(c => c.id !== id) + const comment = this.props.comments.find(c => c.id === id) + comment['collapsed'] = !comment.collapsed + console.log('toggled: ', comment) + this.setState({ comments: otherComments.concat(comment) }) } render() { - const { comments } = this.props - console.log(comments) - + const comments = this.props.comments.filter( + // only show comments for this parent / thread + c => + (!c.parentId && !this.props.threadLevel) || + c.parentId === this.props.threadLevel + ) + console.log('showing comments for thread', this.props.threadLevel, comments) return (
      {comments.map(comment => { - return ( -
      - - - {comment.replies && ( - 0) { + return ( +
      + + ) + } else { + return ( +
      + - )} -
      - ) + {!comment.collapsed && ( + + )} +
      + ) + } })}
    ) From 3186a1f8ca7b1a19c43233705001dfe3cc0a8265 Mon Sep 17 00:00:00 2001 From: data Date: Sat, 13 Jul 2019 18:52:48 +0200 Subject: [PATCH 3/4] view changes to ExpendedComments.js, show Collapse/Expand on hover --- .../Comments/SingleComment/ExpandedComment.js | 61 ++++++++++++------- src/Components/Comments/index.js | 19 +++++- 2 files changed, 56 insertions(+), 24 deletions(-) diff --git a/src/Components/Comments/SingleComment/ExpandedComment.js b/src/Components/Comments/SingleComment/ExpandedComment.js index 6954424..275fdd6 100644 --- a/src/Components/Comments/SingleComment/ExpandedComment.js +++ b/src/Components/Comments/SingleComment/ExpandedComment.js @@ -1,34 +1,49 @@ import React from 'react' + const ExpandedComment = props => { - const { text } = props return ( -
  • +
  • props.showCollapseLink(props.id, true)} + onMouseLeave={() => props.showCollapseLink(props.id, false)} + >
    profile +
    - username -
    - July 9 2019, 01:32:27 UTC - {props.replies.length > 0 ? ( - props.toggleCollapse(props.id)} - > - collapse - - ) : ( - '' - )} -
    + + username + +
    +
    + {props.createdAt} + {props.replies.length > 0 ? ( + props.toggleCollapse(props.id)} + > + collapse + + ) : ( + '' + )} + + reply +
    -
    {text}
    - reply +
    {props.text}
  • ) } diff --git a/src/Components/Comments/index.js b/src/Components/Comments/index.js index 21d4076..a429c9f 100644 --- a/src/Components/Comments/index.js +++ b/src/Components/Comments/index.js @@ -6,6 +6,16 @@ class ThreadList extends React.Component { constructor() { super() this.toggleCollapse = this.toggleCollapse.bind(this) + this.showCollapseLink = this.showCollapseLink.bind(this) + } + + showCollapseLink(id, collapsed) { + this.setState({ displayCollapse: 'block' }) + const otherComments = this.props.comments.filter(c => c.id !== id) + const comment = this.props.comments.find(c => c.id === id) + comment['displayCollapse'] = collapsed + //console.log('displayed collapse for: ', comment) + this.setState({ comments: otherComments.concat(comment) }) } toggleCollapse(id) { @@ -24,18 +34,23 @@ class ThreadList extends React.Component { (!c.parentId && !this.props.threadLevel) || c.parentId === this.props.threadLevel ) + if (comments.length === 0) { + return '' + } console.log('showing comments for thread', this.props.threadLevel, comments) return (
      {comments.map(comment => { // TODO comments aren't sorted by time - if (!comment.replies.length > 0) { + if (comment.replies && comment.replies.length === 0) { return (
      ) } else { @@ -43,12 +58,14 @@ class ThreadList extends React.Component {
      {!comment.collapsed && ( )} From e8e3729f5ff155cb2262029ad7a152972f33b74b Mon Sep 17 00:00:00 2001 From: data Date: Sat, 13 Jul 2019 20:38:09 +0200 Subject: [PATCH 4/4] show nested collapsed comments (#3) --- .../Comments/SingleComment/ExpandedComment.js | 10 ++--- .../Comments/SingleComment/index.js | 2 +- src/Components/Comments/index.js | 37 +++++++++++++------ 3 files changed, 29 insertions(+), 20 deletions(-) diff --git a/src/Components/Comments/SingleComment/ExpandedComment.js b/src/Components/Comments/SingleComment/ExpandedComment.js index 275fdd6..5ad89cf 100644 --- a/src/Components/Comments/SingleComment/ExpandedComment.js +++ b/src/Components/Comments/SingleComment/ExpandedComment.js @@ -27,18 +27,14 @@ const ExpandedComment = props => { cursor: 'pointer', display: props.displayCollapse || 'none', }} - onClick={() => props.toggleCollapse(props.id)} + onClick={() => props.toggleCollapse(props.id, !props.collapsed)} > - collapse + {props.collapsed ? 'expand' : 'collapse'} ) : ( '' )} - + reply
      diff --git a/src/Components/Comments/SingleComment/index.js b/src/Components/Comments/SingleComment/index.js index 1b4417b..fd1ba90 100644 --- a/src/Components/Comments/SingleComment/index.js +++ b/src/Components/Comments/SingleComment/index.js @@ -3,7 +3,7 @@ import ExpandedComment from './ExpandedComment' import CollapsedComment from './CollapsedComment' const SingleComment = props => { - if (props.collapsed) return + if (props.hidden) return return } diff --git a/src/Components/Comments/index.js b/src/Components/Comments/index.js index a429c9f..11a3edf 100644 --- a/src/Components/Comments/index.js +++ b/src/Components/Comments/index.js @@ -18,13 +18,28 @@ class ThreadList extends React.Component { this.setState({ comments: otherComments.concat(comment) }) } - toggleCollapse(id) { - // select passed comment from the state, toggle it and put it all back + toggleCollapse(id, collapsed) { const otherComments = this.props.comments.filter(c => c.id !== id) - const comment = this.props.comments.find(c => c.id === id) - comment['collapsed'] = !comment.collapsed - console.log('toggled: ', comment) + var parent = this.props.comments.find(c => c.id === id) + console.log('toggling', parent) + parent['collapsed'] = collapsed + if (!collapsed) { + // when parent was a reply in a previously collapsed thread + // and is to be expanded it will be marked hidden + // and needs to be unhidden + parent['hidden'] = false + } + this.setState({ comments: otherComments.concat(parent) }) + parent.replies.map(comment => this.toggleReplies(comment.id, collapsed)) + } + toggleReplies(id, collapsed) { + const otherComments = this.props.comments.filter(c => c.id !== id) + var comment = this.props.comments.find(c => c.id === id) + comment['hidden'] = collapsed this.setState({ comments: otherComments.concat(comment) }) + if (comment.replies) { + comment.replies.map(c => this.toggleReplies(c.id, collapsed)) + } } render() { @@ -62,13 +77,11 @@ class ThreadList extends React.Component { toggleCollapse={this.toggleCollapse} {...comment} /> - {!comment.collapsed && ( - - )} + ) }