Skip to content

Instantly share code, notes, and snippets.

@macbookandrew
Last active March 30, 2024 15:24
Show Gist options
  • Save macbookandrew/f33dbbc0aa582d0515919dc5fb95c00a to your computer and use it in GitHub Desktop.
Save macbookandrew/f33dbbc0aa582d0515919dc5fb95c00a to your computer and use it in GitHub Desktop.
List unique CSS properties for all DOM elements
/**
* List unique CSS properties for all DOM elements
* Initially created to list unique font stacks on a page
* @see {@link http://stackoverflow.com/a/35022690/ Inspired by this StackOverflow answer}
*
* @see {@link https://gist.github.com/macbookandrew/f33dbbc0aa582d0515919dc5fb95c00a/ URL for this file}
*
* @author AndrewRMinion Design (https://andrewrminion.com)
* @version 1.1
*
* @license MIT
* @copyright AndrewRMinion Design
*
* @example Show all unique font stacks in use on the current page
* console.log(styleInPage('fontFamily'));
*
* @example Show a list of all DOM elements with their computed font stack
* console.log(styleInPage('fontFamily', true));
*
* @example Highlight all DOM elements using a particular font stack (pass in the array key from styleInPage)
* var fontStacksInUse = styleInPage('fontFamily');
* console.log(fontStacksInUse);
* highlightInPage(8);
*/
/**
* Get an array of elements with their computed styles
* @param {string} css CSS property, camelCased for JS
* @param {boolean} verbose whether to output an array of all elements with their style properties
* @returns {array} array of unique properties, or if verbose is true, array of all elements with their properties
*/
function styleInPage(css, verbose) {
// polyfill getComputedStyle
if (typeof getComputedStyle == "undefined") {
getComputedStyle = function (elem) {
return elem.currentStyle;
}
}
// set vars
var style,
thisNode,
styleId,
allStyles = [],
nodes = document.body.getElementsByTagName('*');
// loop over all elements
for (var i = 0; i < nodes.length; i++) {
thisNode = nodes[i];
if (thisNode.style) {
styleId = '#' + (thisNode.id || thisNode.nodeName + '(' + i + ')');
style = thisNode.style.fontFamily || getComputedStyle(thisNode, '')[css];
// get element’s style
if (style) {
if (verbose) {
allStyles.push([styleId, style]);
} else if (allStyles.indexOf(style) == -1) {
allStyles.push(style);
}
// add data-attribute with key for allStyles array
thisNode.dataset.styleId = allStyles.indexOf(style);
}
// get element:before’s style
styleBefore = getComputedStyle(thisNode, ':before')[css];
if (styleBefore) {
if (verbose) {
allStyles.push([styleId, styleBefore]);
} else if (allStyles.indexOf(styleBefore) == -1) {
allStyles.push(styleBefore);
}
// add data-attribute with key for allStyles array
thisNode.dataset.styleId = allStyles.indexOf(styleBefore);
}
// get element:after’s style
styleAfter = getComputedStyle(thisNode, ':after')[css];
if (styleAfter) {
if (verbose) {
allStyles.push([styleId, styleAfter]);
} else if (allStyles.indexOf(styleAfter) == -1) {
allStyles.push(styleAfter);
}
// add data-attribute with key for allStyles array
thisNode.dataset.styleId = allStyles.indexOf(styleAfter);
}
}
}
return allStyles;
}
/**
* Highlight elements with the specified style
* @param {integer} styleId data-style-id to highlight
*/
function highlightInPage(styleId) {
var thisNode,
allNodes = document.body.getElementsByTagName('*'),
nodes = document.body.querySelectorAll('[data-style-id="' + styleId + '"]');
// remove previous highlights
for (var i = 0; i < allNodes.length; i++) {
allNodes[i].classList.remove('style-highlight');
}
// add highlight to specified nodes
for (var i = 0; i < nodes.length; i++) {
thisNode = nodes[i];
thisNode.classList.add('style-highlight');
}
}
/**
* Clear all highlights
*/
function clearHighlights() {
highlightInPage();
}
/**
* Add blank stylesheet for highlight rule
* @returns {CSSStyleSheet} new blankstylesheet
*/
var sheet = (function() {
// Create the <style> tag
var style = document.createElement("style");
// WebKit hack :(
style.appendChild(document.createTextNode(""));
// Add the <style> element to the page
document.head.appendChild(style);
return style.sheet;
})();
/**
* Add specified CSS rule to the specified stylesheet
* @param {CSSStyleSheet} sheet a CSSStyleSheet object
* @param {string} selector CSS selector rule; include “.” for classes or “#” for IDs
* @param {string} rules CSS properties for this selector
* @param {integer} index index detailing where to add the new rule
*/
function addCSSRule(sheet, selector, rules, index = 0) {
if ("insertRule" in sheet) {
sheet.insertRule(selector + "{" + rules + "}", index);
} else if ("addRule" in sheet) {
sheet.addRule(selector, rules, index);
}
}
// add a yellow background to highlighted elements
addCSSRule(sheet, ".style-highlight", "background-color: yellow");
@Darrel-Collinsworth
Copy link

Heyo! This is awesome! Thank you for creating it, I did have one question. Do you know if there is a way to show the font weights being used?

My problem is that the design has lots of calls for all the font weights and all the fonts to be used on a site, however, not all the weights are used, so I want to prune them for faster load time.

I hope that makes sense, I look forward to tinkering!
-Darrel

@kunwardeep
Copy link

Try this console.log(styleInPage('fontWeight')); Darrel-Collinsworth

@obliviga
Copy link

obliviga commented Jul 26, 2021

Does this still work? I tried pasting the contents of the file into the browser console, and it returns undefined.

@macbookandrew
Copy link
Author

Does this still work? I tried pasting the contents of the file into the browser console, and it returns undefined.

@obliviga It should still work, but you need to call one of the functions in order to actually do anything. See the examples for usage.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment