| 1 | // Vanilla solution |
| 2 | let format = require('util').format; |
| 3 | |
| 4 | const COLORS = [ |
| 5 | { stop: 0, rgb: [35, 198, 161] }, |
| 6 | { stop: 6, rgb: [245, 235, 73] }, |
| 7 | { stop: 48, rgb: [245, 51, 0] }, |
| 8 | ]; |
| 9 | |
| 10 | function getRGBColor (hours) { |
| 11 | // ordering of max and min IS IMPORTANT as we're mutating the colors array with reverse |
| 12 | let colors = COLORS.slice(0), |
| 13 | min = colors.reduce((min, color) => color.stop <= hours ? color : min), |
| 14 | max = colors.reverse().reduce((max, color) => color.stop >= hours ? color : max), |
| 15 | normalizationFactor; |
| 16 | |
| 17 | // control for out of bounds, use the same value twice in such an event |
| 18 | max = max || min; |
| 19 | min = min || max; |
| 20 | |
| 21 | // calculate the normalization factor, should always be between 0 - 1 |
| 22 | normalizationFactor = (hours - min.stop) / (max.stop - min.stop); |
| 23 | |
| 24 | // at this point we don't care about the stops anymore, just the rgb and factor |
| 25 | // calculate and return one RGB array |
| 26 | return min.rgb.map((c, i) => { |
| 27 | let rgb1 = min.rgb[i], |
| 28 | rgb2 = max.rgb[i], |
| 29 | normalizedDiff = (rgb2 - rgb1) * normalizationFactor, |
| 30 | |
| 31 | return Math.round(rgb1 + normalizedDiff); |
| 32 | }); |
| 33 | } |
| 34 | |
| 35 | // Timer logic |
| 36 | // Pretty shitty but just playing around |
| 37 | function simulateTime () { |
| 38 | const NOW = Date.now(); |
| 39 | const eventDate = NOW + (1000 * 60 * 60 * 24 * 2); // 2 days from now |
| 40 | |
| 41 | let currentTime = NOW; |
| 42 | |
| 43 | let interval = setInterval(() => { |
| 44 | if (currentTime < eventDate) { |
| 45 | let duration = eventDate - currentTime, |
| 46 | hours = Math.ceil(duration / 1000 / 60 / 60), |
| 47 | color = getRGBColor(hours); |
| 48 | |
| 49 | console.log(`${format(color)} ${new Date(currentTime).toString()} ${hours} hours before the event`); |
| 50 | |
| 51 | currentTime += 1000 * 60 * 60 * 2; // increment by 2 hours |
| 52 | } |
| 53 | else if (currentTime >= eventDate + 3000) { |
| 54 | clearInterval(interval); |
| 55 | } |
| 56 | }, 1000); |
| 57 | } |
| 58 | |
| 59 | simulateTime(); |
curiouser / color-graduation.js
Last active 3 days ago
An update to the first solution here: https://gist.github.com/jayzawrotny/3079b17004a5237910a58f877bac1d58f