Динамический прогресс бар с датой и наложением цвета на дату

Задача сделать динамический progress bar.

Во первых должно изменяться время, которое осталось до определённой даты. С этим проблем нет. Основной вопрос - как сделать так, чтобы цифры заливались по контуру? (этот контур тоже считается динамически от остaвшегося).

Нужен совет в какую сторону вообще смотреть, ибо у меня в голове не совсем понятно как это реализовать. В теории должно быть какое-то перекрытие между 2 текстурами - текстом и белым прямоугольником. Но ничего похожего я не нашёл. Интересует подход к решению на чистом canvas или three.js или pixi.js. Спасибо!

Скриншот


Ответы (3 шт):

Автор решения: Александр

Вариант на чистом css:

body{
  display: flex;
  align-items: center;
  justify-content: center;
  flex-direction: column;
  width: 100%;
  text-align: center;
  min-height: 100vh;
  font-size: 16px;
  background: black;
}

h1 {
  background: linear-gradient(to right, tomato 17%,  transparent 17%);
  background-clip: text;
  -webkit-background-clip: text;
  color: transparent;
  -webkit-text-stroke: 1px #ffffff
}
<body>
  <h1>Text Transparent</h1>
</body>

→ Ссылка
Автор решения: NoSkill

Регулируется с помощью background-position от 0% до -100%... Но к сожалению работает только в webkit-браузерах. Для остальных браузеров можно сделать fallback.

div {
  height: 200px;
  background-image: linear-gradient(0deg, yellow 0%, green 100%);
}

h1 {
  display: inline-block;
  font-variant: small-caps;
  font-size: 70px;
  font-weight: 800;
  text-align: center;
  background-image: linear-gradient(90deg, transparent 50%, red 50%);
  background-size: 200% 200%;
  background-position: -43% center;
  background-clip: text;
  -webkit-text-fill-color: transparent;
  -webkit-text-stroke: 1px rgb(0, 0, 0);
}
<div>
  <h1>Character</h1>
</div>

→ Ссылка
Автор решения: prisoner849

Голый canvas с отрисовкой:

var text = "6D:20:50:17";
var ctx = c.getContext("2d");
ctx.font = "bold 96px Times New Roman";
ctx.textAlign = 'center';

function drawText() {
  ctx.clearRect(0, 0, 512, 128);
  ctx.fillStyle = "gray";
  ctx.fillRect(0, 0, Math.floor(Math.floor(Math.random() * 10) * 51.2), 128);
  ctx.globalCompositeOperation = "destination-in";
  ctx.fillText(text, 256, 96);

  ctx.globalCompositeOperation = "source-over";

  ctx.strokeStyle = "maroon";
  ctx.lineWidth = 3;
  ctx.strokeText(text, 256, 96);
}

drawText();

setInterval(drawText, 1000);
canvas {
  border: 1px solid red;
  background-color: pink;
}
<canvas id="c" width="512" height="128"></canvas>

→ Ссылка