Add sorting functionality to people page

This commit is contained in:
2017-02-18 14:12:30 +00:00
parent 1ce3673896
commit ac5fb8c987
3 changed files with 173 additions and 10 deletions

View File

@@ -4,6 +4,7 @@ import s from './Button.css';
class Button extends React.Component {
static propTypes = {
to: PropTypes.string,
children: PropTypes.node,
onClick: PropTypes.func,
};
@@ -12,6 +13,10 @@ class Button extends React.Component {
if (this.props.onClick) {
this.props.onClick(event);
}
if (this.props.to) {
window.location.href = this.props.to;
}
};
render() {

View File

@@ -11,6 +11,15 @@
max-width: var(--max-content-width);
}
table {
border-spacing: 0;
}
td {
position: relative;
padding: 0 14px;
}
.formGroup {
position: relative;
margin-bottom: 15px;
@@ -44,3 +53,23 @@
border-color: var(--colour-tertiary);
box-shadow: inset 0 1px 1px rgba(0, 0, 0, 0.075), 0 0 8px rgba(0, 116, 194, 0.6);
}
.personForm {
display: none;
}
.personFormVisible {
display: block;
}
.sortIcon {
display: none;
position: absolute;
top: 50%;
left: 0;
transform: translateY(-50%);
}
.showSortIcon {
display: inline-block;
}

View File

@@ -19,31 +19,149 @@ class AdminPeople extends React.Component {
})).isRequired,
};
constructor(props) {
super(props);
this.state = {
people: this.props.people,
personFormVisible: false,
sortDirection: false,
};
}
sortPeople = (event, sortedBy) => {
event.preventDefault();
const sortDirection = (sortedBy === this.state.sortedBy) ? !this.state.sortDirection : true;
this.setState({
sortedBy,
sortDirection,
people: this.props.people.sort((a, b) => {
if (a[sortedBy] > b[sortedBy]) {
return sortDirection ? 1 : -1;
}
return sortDirection ? -1 : 1;
}),
});
}
togglePersonForm = (event) => {
event.preventDefault();
this.setState({ personFormVisible: !this.state.personFormVisible });
}
render() {
return (
<div className={s.root}>
<div className={s.container}>
<h1>{this.props.title}</h1>
{this.props.people.length === 0 ? <p> No people yet ☹️</p> :
{this.state.people.length === 0 ? <p> No people yet ☹️</p> :
<table>
<thead>
<tr>
<td>Name</td>
<td>Email</td>
<td>Password</td>
<td>Ceremony</td>
<td>Responded</td>
<td>
<span
className={[
s.sortIcon,
this.state.sortedBy === 'firstname' && this.state.sortDirection ? s.showSortIcon : null,
].join(' ')}
>⬇</span>
<span
className={[
s.sortIcon,
this.state.sortedBy === 'firstname' && !this.state.sortDirection ? s.showSortIcon : null,
].join(' ')}
>⬆</span>
<a href="#sortcolumn" onClick={event => this.sortPeople(event, 'firstname')}>First name</a>
</td>
<td>
<span
className={[
s.sortIcon,
this.state.sortedBy === 'lastname' && this.state.sortDirection ? s.showSortIcon : null,
].join(' ')}
>⬇</span>
<span
className={[
s.sortIcon,
this.state.sortedBy === 'lastname' && !this.state.sortDirection ? s.showSortIcon : null,
].join(' ')}
>⬆</span>
<a href="#sortcolumn" onClick={event => this.sortPeople(event, 'lastname')}>Last name</a>
</td>
<td>
<span
className={[
s.sortIcon,
this.state.sortedBy === 'email' && this.state.sortDirection ? s.showSortIcon : null,
].join(' ')}
>⬇</span>
<span
className={[
s.sortIcon,
this.state.sortedBy === 'email' && !this.state.sortDirection ? s.showSortIcon : null,
].join(' ')}
>⬆</span>
<a href="#sortcolumn" onClick={event => this.sortPeople(event, 'email')}>Email</a>
</td>
<td>
<span
className={[
s.sortIcon,
this.state.sortedBy === 'password' && this.state.sortDirection ? s.showSortIcon : null,
].join(' ')}
>⬇</span>
<span
className={[
s.sortIcon,
this.state.sortedBy === 'password' && !this.state.sortDirection ? s.showSortIcon : null,
].join(' ')}
>⬆</span>
<a href="#sortcolumn" onClick={event => this.sortPeople(event, 'password')}>Password</a>
</td>
<td>
<span
className={[
s.sortIcon,
this.state.sortedBy === 'ceremony' && this.state.sortDirection ? s.showSortIcon : null,
].join(' ')}
>⬇</span>
<span
className={[
s.sortIcon,
this.state.sortedBy === 'ceremony' && !this.state.sortDirection ? s.showSortIcon : null,
].join(' ')}
>⬆</span>
<a href="#sortcolumn" onClick={event => this.sortPeople(event, 'ceremony')}>Ceremony</a>
</td>
<td>
<span
className={[
s.sortIcon,
this.state.sortedBy === 'completed' && this.state.sortDirection ? s.showSortIcon : null,
].join(' ')}
>⬇</span>
<span
className={[
s.sortIcon,
this.state.sortedBy === 'completed' && !this.state.sortDirection ? s.showSortIcon : null,
].join(' ')}
>⬆</span>
<a href="#sortcolumn" onClick={event => this.sortPeople(event, 'completed')}>Responded</a>
</td>
</tr>
</thead>
<tbody>
{this.props.people.map(person => (
{this.state.people.map(person => (
<tr key={person.key}>
<td><Link to={`/admin/person/${person.key}`}>{person.firstname} {person.lastname}</Link></td>
<td>{person.firstname}</td>
<td>{person.lastname}</td>
<td>{person.email}</td>
<td><Link to={`/rsvp/${person.password}`}>{person.password}</Link></td>
<td>{person.ceremony ? 'Full day' : 'Evening only'}</td>
<td>{person.completed ? 'Yes' : 'No'}</td>
<td>
<Button to={`/admin/person/${person.key}`}>Edit</Button>
</td>
<td>
<form method="post" action="/admin/person/delete">
<input type="hidden" name="key" value={person.key} />
@@ -57,8 +175,19 @@ class AdminPeople extends React.Component {
</tbody>
</table>
}
<h2>Add Person</h2>
<form method="post" action="/admin/person">
<h2>
<a href="#sortcolumn" onClick={this.togglePersonForm}>
<span>{this.state.personFormVisible ? '-' : '+'}</span> Add Person
</a>
</h2>
<form
method="post"
action="/admin/person"
className={[
s.personForm,
this.state.personFormVisible ? s.personFormVisible : null,
].join(' ')}
>
<div className={s.formGroup}>
<label className={s.label} htmlFor="firstname">
First name: