Reputation: 3
function TopicsTable(props) {
return (
<Table className="tablecss">
<thead>
<tr>
<th>
<button type="button">
{props.getHeader[0]}
</button>
</th>
<th>
<button type="button">
{props.getHeader[1]}
</button>
</th>
<th>
<button type="button">
{props.getHeader[2]}
</button>
</th>
<th>
<button type="button">
{props.getHeader[3]}
</button>
</th>
<th>
<button type="button">
{props.getHeader[4]}
</button>
</th>
<th>
<button type="button">
{props.getHeader[5]}
</button>
</th>
</tr>
</thead>
<TableBody>
{(props.getRowInfo)}
</TableBody>
</Table>
);
}
getRowsData = () => {
var rowContents = this.state.data;
return rowContents.map((rowContent, index) => {
this.state.rowCount = this.state.rowCount + 1;
return <React.Fragment><TableRow key={index} onClick={() => this.handleClick(index)}>{this.RenderCell(rowContent)}</TableRow> {this.state.show && this.state.id === index ? <ChildComponent/>:""} </React.Fragment>
})
}
render() {
return (
<div className="Main">
<header className="App-header">
<h2 className="hdr"><i>Openion</i></h2>
</header>
<h4><Actionunit /></h4>
<br />
<TopicsTable getHeader={this.getHeader()} getRowInfo={this.getRowsData()}/>
</div>
);
}
Sort the table ascending & descending order when i click on button in reactjs
Upvotes: 0
Views: 7813
Reputation: 15031
I think the requirements you're looking for is:
My solution doesn't use <table>
but that is something you can manage easily...
Relevant component which gets headers, rows... sorts and prints data:
import React, { useState, useEffect } from "react";
export const MyTable = props => {
const { header, data } = props;
const [sortedRows, setSortedRows] = useState([]);
const [headers, setHeaders] = useState([]);
useEffect(() => {
setSortedRows(data);
setHeaders(header);
}, []);
const Sorter = fieldToSort => {
let sortedArray = sortedRows;
if(fieldToSort.dir === 'asc' ){
sortedArray.sort((a, b) =>
a[fieldToSort.label] > b[fieldToSort.label] ? 1 : b[fieldToSort.label] > a[fieldToSort.label] ? -1 : 0
);
} else {
sortedArray.sort((a, b) =>
a[fieldToSort.label] < b[fieldToSort.label] ? 1 : b[fieldToSort.label] < a[fieldToSort.label] ? -1 : 0
);
}
(fieldToSort.dir === 'asc') ? fieldToSort.dir = 'dsc' : fieldToSort.dir = 'asc';
let newHeaders = header;
newHeaders[fieldToSort.dir] = fieldToSort.dir;
setHeaders([...newHeaders]);
setSortedRows([...sortedArray]);
};
return (
<>
<h2>Actual Table</h2>
{headers.map((val, ind) => {
return (
<button type="button" key={ind} onClick={() => Sorter(val)}>
{val.label} ({val.dir})
</button>
);
})}
{sortedRows.length > 0 ? (
<ul>
{sortedRows.map((val, ind) => {
return (
<li>
{val.name} - {val.age}{" "}
</li>
);
})}{" "}
</ul>
) : (
"no data available"
)}
</>
);
};
complete working stackblitz here
Upvotes: 1
Reputation: 1001
First, define your state, to save your current sort order:
state = {
sortedBy: '',
sortDirection: 0
}
Then, define constants, to show the order direction (outside of your class):
const sortAsc = 1;
const sortDesc = -1;
Then, define your sort function:
sortTable = (columnName) => {
let sortDirection = sortAsc;
if (this.state.columnName === columnName) {
if (this.state.sortDirection === sortAsc) {
sortDirection = sortDesc;
}
}
this.s.TableData.sort((x1, x2) => x1[columnName] < x2[columnName] ? -1 * sortDirection : sortDirection )
this.setState({
columnName, sortDirection, data: this.state.data
})
};
Then, attach this function to each table header:
<th>
<button type="button" onClick={() => props.sortTable(props.getHeader[0])> // <-- here you pass the header NAME (Upvote, Downvote, Comment and etc.)
{props.getHeader[0]}
</button>
</th>
Keep in mind, that this code is taken out of context, and you may face errors with naming, parameters passing and etc, in general it is a basic abstraction. The sort function was tested out and working. I hope you will manage to integrate it in your application. Good luck!
Upvotes: 0