Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
30 changes: 24 additions & 6 deletions doc/src/components/common/componentData/Table/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -64,6 +64,12 @@ export const componentData = {
defaultValue: 'false',
description: 'Prop to be sent, If sorting functionality is required.',
},
{
prop: 'sortByTitle',
type: 'Boolean',
defaultValue: 'false',
description: 'Prop to be sent, If sorting functionality by clicking column header is required.',
},
],
themesData: [
{
Expand Down Expand Up @@ -106,6 +112,10 @@ export const componentData = {
name: 'sortArrow',
description: 'Class used for the sorting arrows in table header cells.',
},
{
name: 'sortableTitle',
description: 'Class used for the title when sortByTitle is enabled.',
},
],
basicComponent: `
class Demo extends React.Component {
Expand Down Expand Up @@ -163,7 +173,7 @@ export const componentData = {
render() {
const columns = [
{ title: 'Name', key: 'name', colWidth: '150px' },
{ title: 'Default Value', key: 'defaultValue' },
{ title: 'Default Value', key: 'defaultValue', colWidth: '180px' },
{ title: 'Description', key: 'description' },
];
const data = [
Expand Down Expand Up @@ -194,12 +204,20 @@ export const componentData = {
},
];
return (
<PreviewElements>
<div>
<PreviewBlock header="Table, Sortable with buttons">

{/* Default table component with sort functionality */}
<Table columns={columns} data={data} sort />

</PreviewElements>
{/* Default table component with sort functionality */}
<Table columns={columns} data={data} sort />

</PreviewBlock>
<PreviewBlock header="Table, sortable by clicking header cell">

{/* Default table component with sort functionality on clicking header */}
<Table columns={columns} data={data} sortByTitle />

</PreviewBlock>
</div>
)
}
}
Expand Down
60 changes: 58 additions & 2 deletions lib/table/index.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
/* eslint-disable react/destructuring-assignment */
import React from 'react';
import classnames from 'classnames';
import { themr } from 'react-css-themr';
import { FaArrowDown } from 'react-icons/fa';
import PropTypes from 'prop-types';
import defaultTheme from './theme.module.scss';

Expand All @@ -12,6 +14,14 @@ class Table extends React.Component {
};
}

componentDidMount() {
const { columns } = this.props;
this.setState({
sortTitle: columns[0].key,
[`${columns[0].key}Ascending`]: true,
});
}

componentDidUpdate() {
const { data } = this.props;
const { tableData } = this.state;
Expand Down Expand Up @@ -80,13 +90,57 @@ class Table extends React.Component {
);
}

handleTitleSort = (key) => {
// eslint-disable-next-line react/destructuring-assignment
this.setState(prevState => ({
[`${key}TitleToggle`]: !prevState[[`${key}TitleToggle`]],
}));
if (this.state[`${key}TitleToggle`]) {
this.sortAscending(key);
} else {
this.sortDescending(key);
}
}

renderArrowIcon = (isCurrentKey, key) => {
const { theme } = this.props;
return (
<FaArrowDown
className={classnames(
theme.arrow,
!isCurrentKey && theme.hidden,
this.state[`${key}Ascending`] ? theme.downArrow : theme.upArrow,
)}
/>
);
}

renderSortableTitle = (title, key) => {
const { sortTitle } = this.state;
const { theme } = this.props;
const isCurrentKey = sortTitle === key;
return (
<div
className={theme.sortableTitle}
onClick={() => this.handleTitleSort(key)}
>
{title}
<span className={theme.sortableTitleIcon}>
{this.renderArrowIcon(isCurrentKey, key)}
</span>
</div>
);
}

/*
* the table header content will be rendered from accepting columns prop as array,
* the number of columns in table is directly proportional to
* length of columns array from prop
*/
renderTableHeader = () => {
const { columns, theme, sort } = this.props;
const {
columns, theme, sort, sortByTitle,
} = this.props;
return (
<div className={theme.tableHeader} aria-label="table-header">
{ columns && columns.map(({
Expand All @@ -99,7 +153,7 @@ class Table extends React.Component {
{...other}
>
<div className={theme.tableHeadCellContent}>
{title}
{sortByTitle ? this.renderSortableTitle(title, key) : title}
{sort && this.renderSortArrow(key)}
</div>
</div>
Expand Down Expand Up @@ -170,11 +224,13 @@ Table.propTypes = {
columns: PropTypes.oneOfType([PropTypes.array]).isRequired,
data: PropTypes.oneOfType([PropTypes.array]).isRequired,
sort: PropTypes.bool,
sortByTitle: PropTypes.bool,
};

Table.defaultProps = {
theme: defaultTheme,
sort: false,
sortByTitle: false,
};

export default themr('CBTable', defaultTheme)(Table);
28 changes: 28 additions & 0 deletions lib/table/theme.module.scss
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,35 @@
}
:local(.tableHeadCellContent) {
justify-content: space-between;
:local(.sortableTitle) {
cursor: pointer;
:local(.hidden) {
opacity: 0;
}
&:hover {
:local(.hidden) {
opacity: 1;
}
}
}
:local(.sortableTitleIcon) {
font-size: 0.8em;
margin-left: 0.7em;
}
}

:local(.arrow) {
transition: all 0.2s linear;
}

:local(.upArrow) {
transform: rotate(0deg);
}

:local(.downArrow) {
transform: rotate(180deg);
}

:local(.sortArrow) {
position: relative;
width: 12px;
Expand Down