diff --git a/.eslintrc.js b/.eslintrc.js index a16f10b9..2f87a271 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -10,6 +10,13 @@ module.exports = { rules: { 'jsx-a11y/href-no-hash': ['off'], 'react/jsx-filename-extension': ['warn', { extensions: ['.js', '.jsx'] }], + 'react/destructuring-assignment': [ + 'warn', + 'always', + { + ignoreClassFields: false, + }, + ], 'max-len': [ 'warn', { diff --git a/src/components/PatternFrequencies/index.js b/src/components/PatternFrequencies/index.js new file mode 100644 index 00000000..040a08f0 --- /dev/null +++ b/src/components/PatternFrequencies/index.js @@ -0,0 +1,74 @@ +import { Badge } from 'reactstrap'; +import React from 'react'; +// eslint-disable-next-line import/no-extraneous-dependencies +import PropTypes from 'prop-types'; +import './styles.scss'; + +const PatternFrequencies = ({ filters, rows }) => { + const patternsMap = rows.reduce((acc, row) => { + for (let i = 0; i < row.original.pattern.length; i += 1) { + const pattern = row.original.pattern[i]; + acc[pattern] = acc[pattern] + 1 || 1; + } + return acc; + }, Object.create(null)); + const sortedPatternsByFrequency = Object.keys(patternsMap).sort( + (a, b) => patternsMap[b] - patternsMap[a], + ); + const showComponent = filters.find(filter => + ['companies', 'difficulty'].includes(filter.id), + ); + + const getFrequencyClass = rate => { + const highestFrequency = Math.round( + patternsMap[sortedPatternsByFrequency[0]], + ); + + if (highestFrequency / 3 < 1) { + return ''; + } + + const frequencyRate = { + easy: Math.round(highestFrequency / 3), + medium: Math.round((highestFrequency / 3) * 2), + hard: highestFrequency, + }; + + return Object.keys(frequencyRate).find(key => rate <= frequencyRate[key]); + }; + + return showComponent ? ( +
+
Problems pattern frequency
+ {sortedPatternsByFrequency.map((pattern, index) => ( + + + {pattern} : {patternsMap[pattern]} + + + ))} +
+ ) : null; +}; + +PatternFrequencies.propTypes = { + filters: PropTypes.arrayOf( + PropTypes.shape({ id: PropTypes.string, value: PropTypes.string }), + ).isRequired, + rows: PropTypes.arrayOf( + PropTypes.shape({ + original: PropTypes.shape({ + pattern: PropTypes.arrayOf(PropTypes.string), + }), + }), + ).isRequired, +}; + +export default PatternFrequencies; diff --git a/src/components/PatternFrequencies/styles.scss b/src/components/PatternFrequencies/styles.scss new file mode 100644 index 00000000..7276352b --- /dev/null +++ b/src/components/PatternFrequencies/styles.scss @@ -0,0 +1,11 @@ +.pattern-count { + padding: 0.75em; + + h5 { + font-weight: bold; + } + + .badge { + margin: 0.25em 0.25em; + } +} diff --git a/src/components/Table/index.js b/src/components/Table/index.js index e892834a..b79cf123 100644 --- a/src/components/Table/index.js +++ b/src/components/Table/index.js @@ -22,6 +22,7 @@ import questions from '../../data'; import 'react-toggle/style.css'; import './styles.scss'; +import PatternFrequencies from '../PatternFrequencies'; const iconPath = `${process.env.PUBLIC_URL}/assets/icons/`; @@ -328,6 +329,8 @@ const Table = () => { getTableProps, getTableBodyProps, headerGroups, + filteredRows, + state: { filters }, rows, prepareRow, } = useTable( @@ -343,6 +346,7 @@ const Table = () => { return ( + {headerGroups.map(headerGroup => (