Home > Software design >  Two clocks side by side
Two clocks side by side

Time:03-19

Sorry if this has been asked a million times already, i'm quite new with this so it's difficult for me to understand some of the responses. I am trying to have two analog clocks side by side, ticking away. I am not sure why this code isn't showing that.

I would like to make a simple website of multiple timezones shown on each clock, but for now they can all be the same time.

const secondHand = document.querySelector('.second-hand');
const minsHand = document.querySelector('.min-hand');
const hourHand = document.querySelector('.hour-hand');

function setDate() {
  const now = new Date();
  const seconds = now.getSeconds();
  const secondsDegrees = ((seconds / 60) * 360)   90;
  secondHand.style.transform = `rotate(${secondsDegrees}deg)`;
  const mins = now.getMinutes();
  const minsDegrees = ((mins / 60) * 360)   ((seconds / 60) * 6)   90;
  minsHand.style.transform = `rotate(${minsDegrees}deg)`;
  const hour = now.getHours();
  const hourDegrees = ((hour / 12) * 360)   ((mins / 60) * 30)   90;
  hourHand.style.transform = `rotate(${hourDegrees}deg)`;
}
setInterval(setDate, 1000);
setDate();
html {
  background: #018DED url(https://unsplash.it/1500/1000?image=881&blur=5);
  background-size: cover;
  font-family: 'helvetica neue';
  text-align: center;
  font-size: 10px;
}

body {
  margin: 0;
  font-size: 2rem;
  display: flex;
  flex: 1;
  min-height: 100vh;
  align-items: center;
}

.clock,
.clocktwo {
  width: 30rem;
  height: 30rem;
  border: 20px solid white;
  border-radius: 50%;
  margin: 50px auto;
  position: relative;
  padding: 2rem;
  box-shadow: 0 0 0 4px rgba(0, 0, 0, 0.1), inset 0 0 0 3px #EFEFEF, inset 0 0 10px black, 0 0 10px rgba(0, 0, 0, 0.2);
}

.clock-face,
.clock-facetwo {
  position: relative;
  width: 100%;
  height: 100%;
  transform: translateY(-3px);
  /* account for the height of the clock hands */
}

.hand,
.handtwo {
  width: 50%;
  height: 6px;
  background: black;
  position: absolute;
  top: 50%;
  /* transform-origin will allow us to rotate the clock hands along the x axis, so it */
  transform-origin: 100%;
  transform: rotate(90deg);
  transition: all 0.5s;
  transition-timing-function: cubic-bezier(0.1, 2.7, 0.58, 1);
}
<div >
  <div >
    <div ></div>
    <div ></div>
    <div ></div>
  </div>
</div>
<div >
  <div >
    <div ></div>
    <div ></div>
    <div ></div>
  </div>
</div>

CodePudding user response:

The problem is that you have multiple (two to be exact) of each (second, min, hour) clock 'hands'. But you use querySelector which will only select the first (from top to bottom of the HTML structure) element it finds.

What you need to do, is to select all of them using e.g. querySelectorAll and then loop over them.

const secondHand = document.querySelectorAll('.second-hand');
const minsHand = document.querySelectorAll('.min-hand');
const hourHand = document.querySelectorAll('.hour-hand');

function setDate() {
  const now = new Date();
  const seconds = now.getSeconds();
  const secondsDegrees = ((seconds / 60) * 360)   90;
  secondHand.forEach(sec => sec.style.transform = `rotate(${secondsDegrees}deg)`);
  const mins = now.getMinutes();
  const minsDegrees = ((mins / 60) * 360)   ((seconds / 60) * 6)   90;
  minsHand.forEach(min => min.style.transform = `rotate(${minsDegrees}deg)`);
  const hour = now.getHours();
  const hourDegrees = ((hour / 12) * 360)   ((mins / 60) * 30)   90;
  hourHand.forEach(hour => hour.style.transform = `rotate(${hourDegrees}deg)`);
}
setInterval(setDate, 1000);
setDate();
html {
  background: #018DED url(https://unsplash.it/1500/1000?image=881&blur=5);
  background-size: cover;
  font-family: 'helvetica neue';
  text-align: center;
  font-size: 10px;
}

body {
  margin: 0;
  font-size: 2rem;
  display: flex;
  flex: 1;
  min-height: 100vh;
  align-items: center;
}

.clock,
.clocktwo {
  width: 30rem;
  height: 30rem;
  border: 20px solid white;
  border-radius: 50%;
  margin: 50px auto;
  position: relative;
  padding: 2rem;
  box-shadow: 0 0 0 4px rgba(0, 0, 0, 0.1), inset 0 0 0 3px #EFEFEF, inset 0 0 10px black, 0 0 10px rgba(0, 0, 0, 0.2);
}

.clock-face,
.clock-facetwo {
  position: relative;
  width: 100%;
  height: 100%;
  transform: translateY(-3px);
  /* account for the height of the clock hands */
}

.hand,
.handtwo {
  width: 50%;
  height: 6px;
  background: black;
  position: absolute;
  top: 50%;
  /* transform-origin will allow us to rotate the clock hands along the x axis, so it */
  transform-origin: 100%;
  transform: rotate(90deg);
  transition: all 0.5s;
  transition-timing-function: cubic-bezier(0.1, 2.7, 0.58, 1);
}
<div >
  <div >
    <div ></div>
    <div ></div>
    <div ></div>
  </div>
</div>
<div >
  <div >
    <div ></div>
    <div ></div>
    <div ></div>
  </div>
</div>

CodePudding user response:

You need to use querySelectorAll to get reference to all elements.

Then you can set the transform values for each element like this:

const bothSecondHands = document.querySelectorAll('.second-hand');
bothSecondHands.forEach(secondHand => secondHand.style.transform = `rotate(${secondsDegrees}deg)`);
  • Related