I don't want to know if an element contains a specific class, but just if it's loaded in DOM:
$(myObject).attr("class").length;
or
if($t.classList.length) {
var classSUP = $t.attr("class");
} else {
var classSUP = $t.attr("id");
};
Or how about just
(myObject.className != '')
or, just to be sure about possible additional spaces
(myObject.className.replace(' ', '') != '')
This is no job for a framework ;)
The easiest way to check would be:
if($("element").attr("class")) {
return true;
}
Example shown here: http://jsfiddle.net/Skooljester/XpUJA/
You don't need jQuery to do this:
if (element.className) {
// element has a class
}
or, if you really want to use jQuery:
if ($('#elementID').attr('class')) {
// element has a class
}
Try this:
var containsClass = $t.attr("class") !== "" && $t.attr("class") !== undefined;
Here is as a function:
function containsClass($t)
{
return $t.attr("class") !== "" && $t.attr("class") !== undefined;
}
The easiest way to detect if particular object loaded in DOM is:
if ( $('.className').length ) {
alert('.className is on DOM')
}
Related
Currently, my javascript is creating pages dynamically, so when the user clicks X, the new html code is generated for that option, if B then vice versa.
Although, I'm getting "undefined" errors. Even though I do check for the variables before they're passed into the function.
My current non-working prototype looks like this
var appName;
if(evt.target.getAttribute("appName") != "" || evt.target.getAttribute("appName") != null){
appName = evt.target.getAttribute("appName");
}
Before that, I've tried using something which looks like this
var appName = evt.target.get("appName");
if (typeof appName != typeof undefined && appName !== false) {
appName = evt.target.getAttribute("appName");
}
else appName = 'boo';
That still returns undefined.
Lastly, I tried more or less the same approach but it still returns
Uncaught TypeError: Cannot read property 'getAttribute' of undefined
The code for the following looks like that :
var appName = '';
if(evt.target.hasAttribute("appName")){
appName = evt.target.getAttribute("appName");
}
else appName = 'boo';
How would I check if the attribute is actually set and I can proceed if not then I would like to pick alternate course for the code.
Thanks for your help and time spent.
evt.target is undefined, which means that you need to check for that before trying getAttribute(). This is one of the options you have, mostly depending on what your "alternate course for the code" is:
var appName;
if(evt && evt.target && ( evt.target.getAttribute("appName") != "" || evt.target.getAttribute("appName") != null )){
appName = evt.target.getAttribute("appName");
}
You could check if something is undefined by doing this (Copied from here):
if(typeof obj !== "undefined") {
// obj is a valid variable, do something here.
}
Note that typeof always returns a string. Also, there's a difference between comparing with "double equals" and "triple equals" so you might want to check this out.
I have provided the sample snippet.
you have tried evt.target.getAttribute instead try evt.getAttribute
Try like this.
function findAttr(e){
if (!e.hasAttribute("appName")) {
console.log("No attribute");
} else {
console.log(e.getAttribute("appName"));
}
}
<div onclick="findAttr(this)">is attr present?</div>
<div onclick="findAttr(this)" appName="test">is attr present?</div>
If you have an alternate state for your element determined by the presence/absence of an attribute then use .toggleAttribute()
function editMode(e) {
const clicked = e.target;
const editor = document.querySelector('.editor');
if (clicked.matches('.mode')) {
clicked.classList.toggle('on');
clicked.classList.toggle('off');
editor.toggleAttribute('contenteditable');
if (clicked.matches('.off')) {
editor.focus();
} else {
editor.blur();
}
}
return false;
}
document.querySelector('.mode').onclick = editMode;
.editor {
min-height: 32px
}
.mode {
float: right;
display: inline-block;
width: 100px;
}
.on::before {
content: 'READ/WRITE';
}
.off::before {
content: 'READ ONLY';
}
<fieldset class='editor'></fieldset>
<button class='mode on'></button>
I am looking for a way to get all the attributes of an element that begins with "on" using jQuery or Vanilla JS. I am currently getting all attributes and then looping through them to get the ones I want using the method proposed by #primvdb on this post: Get all attributes of an element using jQuery.
My code looks like this:
/* Expanding .attr as proposed by #primvdb */
(function(old) {
$.fn.attr = function() {
if(arguments.length === 0) {
if(this.length === 0) {
return null;
}
var obj = {};
$.each(this[0].attributes, function() {
if(this.specified) {
obj[this.name] = this.value;
}
});
return obj;
}
return old.apply(this, arguments);
};
})($.fn.attr);
/* And then my function */
$.fn.attrThatBeginWith = function(begins){
var attributes = this.attr();
var attrThatBegin = {};
for(var attr in attributes){
if(attr.indexOf(begins)==0){
attrThatBegin[attr] = attributes[attr];
}
}
return attrThatBegin;
};
/* Usage */
var onAttributes = $("#MyElement").attrThatBeginWith("on");
And this works but is very "dirty". It's seems like with all the vast features of jQuery there should be a better "cleaner" way to do this. Does anybody have any suggestions?
You can get all attributes attached to an element with element.attributes.
The native attributes object can be converted to an array and then filtered based on the given string.
A plugin that does the above would look like
$.fn.attrThatBeginWith = function(begins){
return [].slice.call(this.get(0).attributes).filter(function(attr) {
return attr && attr.name && attr.name.indexOf(begins) === 0
});
};
FIDDLE
If I set a function under an object i can use it once only like
function handle(selector)
{
return{
elem:selector,
next:function(){
return (this.nextSibling.nodeType==1) ? this.nextSibling : this.nextSibling.nextSibling;
}
}
}
here i can say handle.next() this will work but if I want to say handle.next().next().next() my question is how I can use in this way as jquery does?
Speaking about your function you can modify it like this to make it work:
function handle(selector)
{
if (typeof selector === 'string') {
selector = document.querySelector(selector);
}
return{
elem:selector,
next:function(){
return handle(selector.nextElementSibling);
}
}
}
See jsfiddle.
UPD: Modified the code to support both elements and string selectors as a parameter.
UPD 2: Came out with an alternative variant. In this case we extend the native html element object and add new next method:
function handle(selector)
{
if (typeof selector === 'string') {
selector = document.querySelector(selector);
}
selector.next = function() {
return handle(selector.nextElementSibling);
};
return selector;
}
Fiddle is here.
Is there a pure JS equivalent of jQuery .is() on modern browsers?
I know there is the querySelector method, but I want to check the node itself, rather than finding child nodes.
Looks like matchesSelector is what I want.
https://developer.mozilla.org/en-US/docs/Web/API/Element.matches
Polyfill is here:
https://gist.github.com/jonathantneal/3062955
this.Element && function(ElementPrototype) {
ElementPrototype.matchesSelector = ElementPrototype.matchesSelector ||
ElementPrototype.mozMatchesSelector ||
ElementPrototype.msMatchesSelector ||
ElementPrototype.oMatchesSelector ||
ElementPrototype.webkitMatchesSelector ||
function (selector) {
var node = this, nodes = (node.parentNode || node.document).querySelectorAll(selector), i = -1;
while (nodes[++i] && nodes[i] != node);
return !!nodes[i];
}
}(Element.prototype);
You've already answered your own question, but as per my comment above I looked through the jQuery.fn.is function. This isn't a strip from the source, because the function they're using is more generalized so it can be used across multiple other functions, But I've boiled it down to this function:
function is(elem, selector){ //elem is an element, selector is an element, an array or elements, or a string selector for `document.querySelectorAll`
if(selector.nodeType){
return elem === selector;
}
var qa = (typeof(selector) === 'string' ? document.querySelectorAll(selector) : selector),
length = qa.length,
returnArr = [];
while(length--){
if(qa[length] === elem){
return true;
}
}
return false;
}
DEMO
Another approach: Wrap the element you're testing in a parent then run querySelector from that
function is(el, selector) {
var div = document.createElement('div');
div.innerHTML = el.outerHTML;
return div.querySelector(selector);
}
I ran one test and it worked:
JS
var a = document.querySelector('a');
if(is(a, '.foo[name=foo]')) {
console.log('YES');
} else {
console.log('Nope');
}
HTML
Meow
I am sure this can be done a lot prettier.
According to youmightnotneedjquery.com depending on your IE compatibility requirement, you can even end up with simpler version:
var is = function(element, selector) {
return (element.matches || element.matchesSelector || element.msMatchesSelector ||
element.mozMatchesSelector || element.webkitMatchesSelector ||
element.oMatchesSelector).call(element, selector);
};
is(element, '.my-class');
With ES6 this would be:
const is = (element, selector) =>
(element.matches || element.matchesSelector || element.msMatchesSelector ||
element.mozMatchesSelector || element.webkitMatchesSelector ||
element.oMatchesSelector).call(element, selector);
};
is(element, '.my-class');
Following the concept from #AdamMerrifield it could be useful building the method is on any element through the Element.prototype chain by doing:
Element.prototype.is = function(match) {
...
};
Element is supported by all major browsers, even by IE 8+.
Here is a DEMO.
var myElement = document.querySelector('div.example');// <div..></div>
/*
* A lot time after, codes executed, whatever
*/
if( myElement.isInDocument )
{
// Do something
}
Is there a easy way to know if 'myElement' still in document?
From Mozilla:
function isInPage(node) {
return (node === document.body) ? false : document.body.contains(node);
}
Since every element in the document is a child of the document, check to see if your element is:
function isInDocument(e) {
while( e.parentNode) e = e.parentNode;
return e === document;
}
One way is to use contains()
var myElement = document.querySelector('div.example');
console.log("elment ", myElement);
console.log("contains before ", document.body.contains(myElement));
myElement.parentNode.removeChild(myElement);
console.log("contains after ", document.body.contains(myElement));
JSFiddle
You can first see if the .contains() method exists and use it if available. If not, walk the parent chain looking for the document object. From a prior project using code like this, you can't just rely on parentNode being empty (in some versions of IE) when you get to document so you have to also explicitly check for document like this:
function isInDocument(e) {
if (document.contains) {
return document.contains(e);
} else {
while (e.parentNode && e !== document) {
e = e.parentNode;
}
return e === document;
}
}
For modern browsers the answer is myElement.isConnected
https://developer.mozilla.org/en-US/docs/Web/API/Node/isConnected