ngscheurich/fresh-pots

View on GitHub
app/frontend/js/components/Clock.js

Summary

Maintainability
C
1 day
Test Coverage
import React, { Component } from "react";
import PropTypes from "prop-types";

class Clock extends Component {
  constructor(props) {
    super(props);
    this.tick =
      typeof this.props.tick === "undefined" ? false : this.props.tick;
    this.state = { date: props.date };
  }

  rotation(hand) {
    const date = this.state.date;
    let degrees = 0;
    switch (hand) {
      case "hour":
        degrees = 30 * (date.getHours() % 12) + date.getMinutes() / 2;
        break;
      case "minute":
        degrees = 6 * date.getMinutes();
    }
    return degrees;
  }

  hourStyle() {
    return {
      transform: `rotate(${this.rotation("hour")}deg)`,
      transformOrigin: `${this.props.size}px ${this.props.size}px`
    };
  }

  minuteStyle() {
    return {
      transform: `rotate(${this.rotation("minute")}deg)`,
      transformOrigin: `${this.props.size}px ${this.props.size}px`
    };
  }

  tick() {
    this.setState(
      Object.assign(...this.state, {
        date: new Date()
      })
    );
  }

  componentDidMount() {
    if (this.tick) {
      this.timerID = setInterval(() => this.tick(), 1000);
    }
  }

  componentWillUnmount() {
    if (typeof this.timerID !== "undefined") {
      clearInterval(this.timerID);
    }
  }

  render() {
    const size = this.props.size;
    const strokeWidth = this.props.strokeWidth;
    const hourHandWidth = this.props.hourHandWidth;
    const hourHandLength = this.props.hourHandLength;
    const minuteHandWidth = this.props.minuteHandWidth;
    const minuteHandLength = this.props.minuteHandLength;

    return (
      <svg viewBox={`0 0 ${size * 2} ${size * 2}`}>
        <circle
          cx={size}
          cy={size}
          r={size - strokeWidth / 2}
          fill="transparent"
          stroke={this.props.color}
          strokeWidth={strokeWidth}
        />
        <rect
          x={size - hourHandWidth / 2}
          y={size - size * hourHandLength}
          width={hourHandWidth}
          height={size * hourHandLength}
          fill={this.props.color}
          style={this.hourStyle()}
        />
        <rect
          x={size - minuteHandWidth / 2}
          y={size - size * minuteHandLength}
          width={minuteHandWidth}
          height={size * minuteHandLength}
          fill={this.props.color}
          style={this.minuteStyle()}
        />
        <circle
          className="clock__anchor"
          cx={size}
          cy={size}
          r={
            minuteHandWidth > hourHandWidth
              ? minuteHandWidth * 0.375
              : hourHandWidth * 0.375
          }
          fill={this.props.color}
        />
      </svg>
    );
  }
}

Clock.propTypes = {
  color: PropTypes.string.isRequired,
  date: PropTypes.object.isRequired,
  hourHandLength: PropTypes.number.isRequired,
  hourHandWidth: PropTypes.number.isRequired,
  minuteHandWidth: PropTypes.number.isRequired,
  minuteHandLength: PropTypes.number.isRequired,
  size: PropTypes.number.isRequired,
  strokeWidth: PropTypes.number.isRequired
};

export default Clock;