]> Untitled Git - lemmy-ui.git/blob - src/shared/components/person/person-details.tsx
Fixing nav-link
[lemmy-ui.git] / src / shared / components / person / person-details.tsx
1 import { Component } from "inferno";
2 import {
3   CommentView,
4   GetPersonDetailsResponse,
5   PersonViewSafe,
6   PostView,
7   SortType,
8 } from "lemmy-js-client";
9 import { PersonDetailsView } from "../../interfaces";
10 import { commentsToFlatNodes, setupTippy } from "../../utils";
11 import { CommentNodes } from "../comment/comment-nodes";
12 import { Paginator } from "../common/paginator";
13 import { PostListing } from "../post/post-listing";
14
15 interface PersonDetailsProps {
16   personRes: GetPersonDetailsResponse;
17   admins: PersonViewSafe[];
18   page: number;
19   limit: number;
20   sort: SortType;
21   enableDownvotes: boolean;
22   enableNsfw: boolean;
23   view: PersonDetailsView;
24   onPageChange(page: number): number | any;
25 }
26
27 enum ItemEnum {
28   Comment,
29   Post,
30 }
31 type ItemType = {
32   id: number;
33   type_: ItemEnum;
34   view: CommentView | PostView;
35   published: string;
36   score: number;
37 };
38
39 export class PersonDetails extends Component<PersonDetailsProps, any> {
40   constructor(props: any, context: any) {
41     super(props, context);
42     this.handlePageChange = this.handlePageChange.bind(this);
43   }
44
45   // TODO needed here?
46   componentDidMount() {
47     setupTippy();
48   }
49
50   // TODO wut?
51   // componentDidUpdate(lastProps: UserDetailsProps) {
52   //   for (const key of Object.keys(lastProps)) {
53   //     if (lastProps[key] !== this.props[key]) {
54   //       this.fetchUserData();
55   //       break;
56   //     }
57   //   }
58   // }
59
60   render() {
61     return (
62       <div>
63         {this.viewSelector(this.props.view)}
64
65         <Paginator page={this.props.page} onChange={this.handlePageChange} />
66       </div>
67     );
68   }
69
70   viewSelector(view: PersonDetailsView) {
71     if (
72       view === PersonDetailsView.Overview ||
73       view === PersonDetailsView.Saved
74     ) {
75       return this.overview();
76     } else if (view === PersonDetailsView.Comments) {
77       return this.comments();
78     } else if (view === PersonDetailsView.Posts) {
79       return this.posts();
80     } else {
81       return null;
82     }
83   }
84
85   renderItemType(i: ItemType) {
86     switch (i.type_) {
87       case ItemEnum.Comment: {
88         let c = i.view as CommentView;
89         return (
90           <CommentNodes
91             key={i.id}
92             nodes={[{ comment_view: c }]}
93             admins={this.props.admins}
94             noBorder
95             noIndent
96             showCommunity
97             showContext
98             enableDownvotes={this.props.enableDownvotes}
99           />
100         );
101       }
102       case ItemEnum.Post: {
103         let p = i.view as PostView;
104         return (
105           <PostListing
106             key={i.id}
107             post_view={p}
108             admins={this.props.admins}
109             showCommunity
110             enableDownvotes={this.props.enableDownvotes}
111             enableNsfw={this.props.enableNsfw}
112           />
113         );
114       }
115       default:
116         return <div />;
117     }
118   }
119
120   overview() {
121     let id = 0;
122     let comments: ItemType[] = this.props.personRes.comments.map(r => ({
123       id: id++,
124       type_: ItemEnum.Comment,
125       view: r,
126       published: r.comment.published,
127       score: r.counts.score,
128     }));
129     let posts: ItemType[] = this.props.personRes.posts.map(r => ({
130       id: id++,
131       type_: ItemEnum.Post,
132       view: r,
133       published: r.post.published,
134       score: r.counts.score,
135     }));
136
137     let combined = [...comments, ...posts];
138
139     // Sort it
140     if (this.props.sort === SortType.New) {
141       combined.sort((a, b) => b.published.localeCompare(a.published));
142     } else {
143       combined.sort((a, b) => b.score - a.score);
144     }
145
146     return (
147       <div>
148         {combined.map(i => [this.renderItemType(i), <hr class="my-3" />])}
149       </div>
150     );
151   }
152
153   comments() {
154     return (
155       <div>
156         <CommentNodes
157           nodes={commentsToFlatNodes(this.props.personRes.comments)}
158           admins={this.props.admins}
159           noIndent
160           showCommunity
161           showContext
162           enableDownvotes={this.props.enableDownvotes}
163         />
164       </div>
165     );
166   }
167
168   posts() {
169     return (
170       <div>
171         {this.props.personRes.posts.map(post => (
172           <>
173             <PostListing
174               post_view={post}
175               admins={this.props.admins}
176               showCommunity
177               enableDownvotes={this.props.enableDownvotes}
178               enableNsfw={this.props.enableNsfw}
179             />
180             <hr class="my-3" />
181           </>
182         ))}
183       </div>
184     );
185   }
186
187   handlePageChange(val: number) {
188     this.props.onPageChange(val);
189   }
190 }