fix: Reimplement the HeatMap

pull/34316/head
Bouncey 2018-11-08 13:43:36 +00:00 committed by mrugesh mohapatra
parent f5ae5027cc
commit d686b32d9d
5 changed files with 108 additions and 169 deletions

View File

@ -14378,6 +14378,25 @@
"prop-types": "^15.6.0"
}
},
"react-calendar-heatmap": {
"version": "1.7.0",
"resolved": "https://registry.npmjs.org/react-calendar-heatmap/-/react-calendar-heatmap-1.7.0.tgz",
"integrity": "sha512-stPZSm07l3mZmj/MXOD+feHM2ZWY4Jb8fn06O+OeMFMasRCuiB2ZjBgCnCLb0BZ4hHh8vHNQ9v7wapiMcVgU0g==",
"requires": {
"prop-types": "^15.6.2"
},
"dependencies": {
"prop-types": {
"version": "15.6.2",
"resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.6.2.tgz",
"integrity": "sha512-3pboPvLiWD7dkI3qf3KbUe6hKFKa52w+AE0VCqECtf+QHAKgOL37tTaNCnuX1nAAQ4ZhyP+kYVKf8rLmJ/feDQ==",
"requires": {
"loose-envify": "^1.3.1",
"object-assign": "^4.1.1"
}
}
}
},
"react-dev-utils": {
"version": "4.2.3",
"resolved": "https://registry.npmjs.org/react-dev-utils/-/react-dev-utils-4.2.3.tgz",

View File

@ -40,6 +40,7 @@
"prismjs": "^1.15.0",
"query-string": "^6.1.0",
"react": "^16.4.2",
"react-calendar-heatmap": "^1.7.0",
"react-dom": "^16.4.2",
"react-freecodecamp-search": "^2.0.2",
"react-ga": "^2.5.3",

View File

@ -1,9 +1,15 @@
import React, { Component } from 'react';
import React from 'react';
import PropTypes from 'prop-types';
import { Helmet } from 'react-helmet';
import CalendarHeatMap from 'react-calendar-heatmap';
import startOfMonth from 'date-fns/start_of_month';
import startOfDay from 'date-fns/start_of_day';
import format from 'date-fns/format';
import FullWidthRow from '../../helpers/FullWidthRow';
import Spacer from '../../helpers/Spacer';
import 'react-calendar-heatmap/dist/styles.css';
import './heatmap.css';
const propTypes = {
@ -14,44 +20,72 @@ const propTypes = {
})
};
class HeatMap extends Component {
constructor(props) {
super(props);
const now = Date.now();
const today = new Date(now);
const sixMonthsInMillseconds = 15780000000;
const sixMonthsAgoInMilliseconds = now - sixMonthsInMillseconds;
const sixMonthsAgo = startOfMonth(sixMonthsAgoInMilliseconds);
this.renderMap = this.renderMap.bind(this);
}
function HeatMap({ calendar, streak }) {
const dateValueMap = Object.keys(calendar)
.map(ts => Number(ts * 1000) || null)
.filter(Boolean)
.reduce((map, current) => {
const startOfCurrent = format(startOfDay(current), 'YYYY-MM-DD');
if (startOfCurrent in map) {
map[startOfCurrent] = map[startOfCurrent] + 1;
} else {
map[startOfCurrent] = 1;
}
return map;
}, {});
render() {
const { streak = {} } = this.props;
return (
<FullWidthRow id='cal-heatmap-container'>
<Helmet>
<script
src='https://cdnjs.cloudflare.com/ajax/libs/d3/5.7.0/d3.min.js'
type='text/javascript'
/>
<link href='/css/cal-heatmap.css' rel='stylesheet' />
</Helmet>
<FullWidthRow>
<h3>This needs a refactor to use something like</h3>
<a href='https://www.npmjs.com/package/react-calendar-heatmap'>
react-calendar-heatmap
</a>
</FullWidthRow>
<FullWidthRow>
<div className='streak-container'>
<span className='streak'>
<strong>Longest Streak:</strong> {streak.longest || 1}
</span>
<span className='streak'>
<strong>Current Streak:</strong> {streak.current || 1}
</span>
</div>
</FullWidthRow>
<hr />
const calendarValues = Object.keys(dateValueMap).map(key => ({
date: key,
count: dateValueMap[key]
}));
return (
<FullWidthRow id='cal-heatmap-container'>
<Helmet>
<script
src='https://cdnjs.cloudflare.com/ajax/libs/d3/5.7.0/d3.min.js'
type='text/javascript'
/>
<link href='/css/cal-heatmap.css' rel='stylesheet' />
</Helmet>
<FullWidthRow>
<CalendarHeatMap
classForValue={value => {
if (!value) {
return 'colour-empty';
}
console.log(value);
if (value.count > 4) {
return 'colour-scale-a-lot';
}
return `colour-scale-${value.count}`;
}}
endDate={today}
startDate={sixMonthsAgo}
values={calendarValues}
/>
</FullWidthRow>
);
}
<Spacer />
<FullWidthRow>
<div className='streak-container'>
<span className='streak'>
<strong>Longest Streak:</strong> {streak.longest || 1}
</span>
<span className='streak'>
<strong>Current Streak:</strong> {streak.current || 1}
</span>
</div>
</FullWidthRow>
<Spacer />
<hr />
</FullWidthRow>
);
}
HeatMap.displayName = 'HeatMap';

View File

@ -13,3 +13,21 @@
.night .streak strong {
color: #ccc;
}
.react-calendar-heatmap .colour-empty {
fill: #eee;
}
.react-calendar-heatmap .colour-scale-1 {
fill: #d6e685;
}
.react-calendar-heatmap .colour-scale-2 {
fill: #8cc665;
}
.react-calendar-heatmap .colour-scale-3 {
fill: #44a340;
}
.react-calendar-heatmap .colour-scale-4 {
fill: #1e6823;
}
.react-calendar-heatmap .colour-scale-a-lot {
fill: #006400;
}

View File

@ -1,133 +0,0 @@
/* Cal-HeatMap CSS */
.cal-heatmap-container {
display: block;
}
.cal-heatmap-container .graph {
font-family: 'Lucida Grande', Lucida, Verdana, sans-serif;
}
.cal-heatmap-container .graph-label {
fill: #999;
font-size: 10px;
}
.cal-heatmap-container .graph,
.cal-heatmap-container .graph-legend rect {
shape-rendering: crispedges;
}
.cal-heatmap-container .graph-rect {
fill: #ededed;
}
.cal-heatmap-container .graph-subdomain-group rect:hover {
stroke: #000;
stroke-width: 1px;
}
.cal-heatmap-container .subdomain-text {
font-size: 8px;
fill: #999;
pointer-events: none;
}
.cal-heatmap-container .hover_cursor:hover {
cursor: pointer;
}
.cal-heatmap-container .qi {
background-color: #999;
fill: #999;
}
/*
Remove comment to apply this style to date with value equal to 0
.q0
{
background-color: #fff;
fill: #fff;
stroke: #ededed
}
*/
.cal-heatmap-container .q1 {
background-color: #dae289;
fill: #dae289;
}
.cal-heatmap-container .q2 {
background-color: #cedb9c;
fill: #9cc069;
}
.cal-heatmap-container .q3 {
background-color: #b5cf6b;
fill: #669d45;
}
.cal-heatmap-container .q4 {
background-color: #637939;
fill: #637939;
}
.cal-heatmap-container .q5 {
background-color: #3b6427;
fill: #3b6427;
}
.cal-heatmap-container rect.highlight {
stroke: #444;
stroke-width: 1;
}
.cal-heatmap-container text.highlight {
fill: #444;
}
.cal-heatmap-container rect.now {
stroke: red;
}
.cal-heatmap-container text.now {
fill: red;
font-weight: 800;
}
.cal-heatmap-container .domain-background {
fill: none;
shape-rendering: crispedges;
}
.ch-tooltip {
padding: 10px;
background: #222;
color: #bbb;
font-size: 12px;
line-height: 1.4;
width: 140px;
position: absolute;
z-index: 99999;
text-align: center;
border-radius: 2px;
box-shadow: 2px 2px 2px rgba(0, 0, 0, 0.2);
display: none;
box-sizing: border-box;
}
.ch-tooltip::after {
position: absolute;
width: 0;
height: 0;
border-color: transparent;
border-style: solid;
content: '';
padding: 0;
display: block;
bottom: -6px;
left: 50%;
margin-left: -6px;
border-width: 6px 6px 0;
border-top-color: #222;
}