Let's say I have a color of #404040. How can I generate a new color hex code which is either lighter or darker by 20% (or another given percentage)? I need this for generating a color to apply on hover.
The color being applied changes based on the chosen theme, therefore it is not possible to use another class or :hover
with a predefined color value.
Approach: We can dynamically change the color of any element by percentage using the filter property in CSS. The brightness() function of the filter property is used to dynamically change color by percentage. The brightness function takes a value in percentage to set the brightness of that color.
CSS has a filter property that can be used with a variety of filter functions. One of them is the brightness() filter. By feeding a percentage less than 100% to brightness() , the target element will be made darker.
Tints are lighter versions of the color that are made by mixing a color with white, whereas shades are darker versions of the color that are made by mixing a color with black. For example, pink is a tint of red, while maroon is a shade of red.
var pad = function(num, totalChars) { var pad = '0'; num = num + ''; while (num.length < totalChars) { num = pad + num; } return num; }; // Ratio is between 0 and 1 var changeColor = function(color, ratio, darker) { // Trim trailing/leading whitespace color = color.replace(/^\s*|\s*$/, ''); // Expand three-digit hex color = color.replace( /^#?([a-f0-9])([a-f0-9])([a-f0-9])$/i, '#$1$1$2$2$3$3' ); // Calculate ratio var difference = Math.round(ratio * 256) * (darker ? -1 : 1), // Determine if input is RGB(A) rgb = color.match(new RegExp('^rgba?\\(\\s*' + '(\\d|[1-9]\\d|1\\d{2}|2[0-4][0-9]|25[0-5])' + '\\s*,\\s*' + '(\\d|[1-9]\\d|1\\d{2}|2[0-4][0-9]|25[0-5])' + '\\s*,\\s*' + '(\\d|[1-9]\\d|1\\d{2}|2[0-4][0-9]|25[0-5])' + '(?:\\s*,\\s*' + '(0|1|0?\\.\\d+))?' + '\\s*\\)$' , 'i')), alpha = !!rgb && rgb[4] != null ? rgb[4] : null, // Convert hex to decimal decimal = !!rgb? [rgb[1], rgb[2], rgb[3]] : color.replace( /^#?([a-f0-9][a-f0-9])([a-f0-9][a-f0-9])([a-f0-9][a-f0-9])/i, function() { return parseInt(arguments[1], 16) + ',' + parseInt(arguments[2], 16) + ',' + parseInt(arguments[3], 16); } ).split(/,/), returnValue; // Return RGB(A) return !!rgb ? 'rgb' + (alpha !== null ? 'a' : '') + '(' + Math[darker ? 'max' : 'min']( parseInt(decimal[0], 10) + difference, darker ? 0 : 255 ) + ', ' + Math[darker ? 'max' : 'min']( parseInt(decimal[1], 10) + difference, darker ? 0 : 255 ) + ', ' + Math[darker ? 'max' : 'min']( parseInt(decimal[2], 10) + difference, darker ? 0 : 255 ) + (alpha !== null ? ', ' + alpha : '') + ')' : // Return hex [ '#', pad(Math[darker ? 'max' : 'min']( parseInt(decimal[0], 10) + difference, darker ? 0 : 255 ).toString(16), 2), pad(Math[darker ? 'max' : 'min']( parseInt(decimal[1], 10) + difference, darker ? 0 : 255 ).toString(16), 2), pad(Math[darker ? 'max' : 'min']( parseInt(decimal[2], 10) + difference, darker ? 0 : 255 ).toString(16), 2) ].join(''); }; var lighterColor = function(color, ratio) { return changeColor(color, ratio, false); }; var darkerColor = function(color, ratio) { return changeColor(color, ratio, true); }; // Use var darker = darkerColor('rgba(80, 75, 52, .5)', .2); var lighter = lighterColor('rgba(80, 75, 52, .5)', .2);
Now handles RGB(A) input, as well as hex (3 digit or 6).
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With