JQuery select data attributes with a common keyword

I have two elements with the following setting:

<span data-placeholder-class="test-class"></span> <span data-placeholder-template="/some/template.hbs"></span> 

I use underscore to iterate over all elements containing any of these attributes, and then perform the appropriate actions if they do.

This is currently being done like this

 _.each($('[data-placeholder-class], [data-placeholder-template]'), function cb(element) { // code goes here }) 

Instead of defining each data attribute for the loop, I wondered if there was a way to select all attributes that contain a common keyword, in this case a placeholder. eg.

 _.each($('[data-placeholder-*]'), function cb(element) { // code goes here }) 

Does anyone know if this is possible at all?

+7
javascript jquery html5 custom-data-attribute
source share
5 answers

You can use a separate function that creates your selector, so you won’t need to enter the selector in its entirety (but you, of course, have to write a function).

eq :.

 function getSelector() { return Array.prototype.map.call(arguments, function(key) { return '[data-placeholder-' + key + ']'; }).join(','); } 

This will return the desired selector and will work with arguments 1 ... N.

 getSelector('class', 'template') // returns "[data-placeholder-template],[data-placeholder-class]" _.each($(getSelector('class', 'template')), function cb(element) { // code goes here }); 
+3
source share

You can iterate the attributes set of elements, direct the element to an array if the .attributes.name element matches the provided string variable

 var spans = document.querySelectorAll("span"); function filterAttrs(elems, attr, matches = []) { for (var elem of elems) { for (var attrs of elem.attributes) { // alternatively use `.indexOf()` or `RegExp()` // to match parts of string of `.name` or `.value` // of `.attributes` `NamedNodeMap` if (attrs.name.slice(0, attr.length) === attr) { matches.push({ "element": elem, "attr": { "name": attrs.name, "value": attrs.value } }) } } } return matches } var matches = filterAttrs(spans, "data-placeholder"); console.log(matches); matches.forEach(function(match) { match.element.textContent = "matches:" + JSON.stringify(match.attr); match.element.style.color = "green"; }); 
 <span data-placeholder-class="test-class"></span> <span data-placeholder-template="/some/template.hbs"></span> <span data-not-placeholder-template="/some/template.hbs"> data-not-placeholder-template </span> <span data-not-placeholder-template="/some/template.hbs"> data-not-placeholder-template </span> 
+1
source share

I know this is a jquery question, but there is a vanilla way to do this thanks to XPath requests:

starts-with() The XPath function does just that.

Thus, the request //*[@*[starts-with(name(), 'data-placeholder')]] will give you what you need.

deployed:

  '//' + // from root to anywhere in the tree '*' + // any kind of node '[@*' + // with any attribute '[starts-with(name(), "data-placeholder")]' + // which starts with "data-" ']' 

 function getElementsByStartOfAttribute(start_of_attr) { var query = document.evaluate("//*[@*[starts-with(name(), '" + start_of_attr + "')]]", document, null, XPathResult.ANY_TYPE, null); var elements = []; var el; while (el = query.iterateNext()) { elements.push(el); } return elements; } var placehodlers = getElementsByStartOfAttribute('data-placeholder'); console.log(placehodlers); $(placehodlers).css('background', 'green'); 
 <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> <span data-placeholder-class="test-class">should find me</span> <span data-placeholder-template="/some/template.hbs">me too</span> <span data-not-placeholder-template="/some/template.hbs"> data-not-placeholder-template </span> <span data-not-placeholder-template="/some/template.hbs"> data-not-placeholder-template </span> 
+1
source share
  var eles = $('span').filter(function() { for (var attrName in $(this).data()) { if (attrName.indexOf('placeholder') == 0) { return true; } } return false; }); console.log(eles); 

Hope this helps you :)

0
source share

HTML SAMPLE:

 <span data-placeholder-class="test-class">test</span> <span data-placeholder-template="/some/template.hbs">hahaha</span> <span>hahahahaha</span> <span data-test="/some/template.hbs">hahahahaha</span> 

JS:

 $('span').filter(function(ndx, item){ var data = Object.keys($(item).data())[0]; // gets data name if (data === undefined) { return; } // checks if data starts with placeholder if (~(data.indexOf('placeholder'))) { // do anything to that item here return item; } }).css('color', 'green'); 

Fiddle: here

Hope this helps! :)

0
source share

All Articles