Last active
December 28, 2017 14:09
-
-
Save tomhodgins/8adce21101badac36f36c9205dd93f3b to your computer and use it in GitHub Desktop.
Skopein - Scoped CSS Stylesheets with element queries and a $this selector
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
:self { | |
background: lime; | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<!DOCTYPE html> | |
<meta charset="utf-8"> | |
<meta name="viewport" content="width=device-width, initial-scale=1"> | |
<title>Skopein - Scoped Stylesheets</title> | |
<link rel="scoped" href="skopein.css" data-selector="input" data-test="this.value.length > 5"> | |
<p>Input tags will go green when their value has more than 5 characters:</p> | |
<input> | |
<input> | |
<input> | |
<script src="skopein.js"></script> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
var skopein = {} | |
skopein.load = function() { | |
var link = document.querySelectorAll('link[rel="scoped"]') | |
for (i = 0; i < link.length; i++) { | |
var currentLink = link[i] | |
var stylesheet = '' | |
if (currentLink.href) { | |
(function() { | |
var xhr = new XMLHttpRequest | |
xhr.open('GET', currentLink.href, true) | |
xhr.send(null) | |
xhr.onreadystatechange = function() { | |
skopein.process(currentLink, xhr.responseText) | |
} | |
})() | |
} | |
} | |
} | |
skopein.process = function(link, stylesheet) { | |
if (stylesheet) { | |
var event = link.getAttribute('data-event') | |
? link.getAttribute('data-event').replace(/ /g, '').split(',') | |
: ['load', 'resize', 'input', 'click'] | |
for (var j=0; j < event.length; j++) { | |
if (!link.getAttribute('data-populated')) { | |
var style = document.createElement('style') | |
link.parentNode.insertBefore(style, link) | |
link.setAttribute('data-populated', true) | |
} | |
window.addEventListener(event[j], function(e) { | |
var tag = document.querySelectorAll(link.getAttribute('data-selector')) | |
var func = new Function('return ' + link.getAttribute('data-test')) | |
var selector = [] | |
var count = 0 | |
for (var k=0; k<tag.length; k++) { | |
// process selectors | |
if (func.call(tag[k])) { | |
var attr = link.getAttribute('data-selector').replace(/\W+/g, '') | |
tag[k].setAttribute('data-scoped-' + attr, count) | |
selector.push('[data-scoped-' + attr + '="' + count + '"]') | |
count++ | |
} else { | |
tag[k].removeAttribute('data-scoped-' + attr) | |
} | |
} | |
if (style) { | |
var css = stylesheet.replace(/:self|\$this/g, selector) | |
style.innerHTML = css | |
} | |
}) | |
} | |
} | |
} | |
window.addEventListener('load', skopein.load) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment