I have the following HTML:
<ul actualpage=0>
<li/>
<li/>
....
</ul>
<ul actualpage=0>
<li/>
<li/>
....
</ul>
Im trying to get the value of actualpage of each ul and create a new attribute. Its easy but not in one jquery sentence... Its possible? Until now i have the following line (between ## simbols the missing part that i need.
/*
select all uls with attribute actualpage and create a new attribute on each with the current actualpage value
*/
$('ul[actualpage]').attr('newactualpage',##Current value of actualpage attr of UL##);
Well maybe this isn't as nice as you'd like, but
$('ul[actualpage]').each(function(_, ul) { $(ul).attr('newactualpage', $(ul).attr('actualpage')); });
One might think that
$('ul[actualpage]').attr('newactualpage',$(this).attr('actualpage'))
is the answer.
However, this is evaluated before the call to attr, so it's going to equal whatever this equals in the calling context.
You could use:
$('ul[actualpage]').attr('newactualpage',function(){
return $(this).attr('actualpage');
});
or this:
$('ul[actualpage]').each(function()
{
$(this).attr('newactualpage',$(this).attr('actualpage'));
};
In both, this refers to the element that your selector matched.
You can use function as second argument for .attr(), eliminating the need of .each():
$('ul[actualpage]').attr('newactualpage', function() { return $(this).attr('actualpage') });
Related
what I want to achieve is setting all occurences of a class to their designated data - except the particular occurence clicked, which is to be set to something unique. My code below gives an undefined error on the "y" variable. How would I go about contextualizing the dataset?
<div id="menu">
<ul>
<li id="menu-tos" data-info="TERMS OF SERVICE">TERMS OF SERVICE</li>
<li id="menu-contact" data-info="CONTACT">CONTACT</li>
<li id="menu-signup" data-info="SIGN UP">SIGN UP</li>
<li id="menu-login" data-info="LOG IN">LOGIN</li>
</ul>
</div>
<script>
$('#menu ul li').click(function() {
i = $(this.id);
y = dataset.info;
$('#menu ul li').not(i).html(y);
$(i).html('Something unique');
});
</script>
(to skip the explanation and see a working version, scroll to the bottom)
Your undefined error is because you trying to access dataset as if it is a variable, when it is actually a property of DOM element objects (details here).
Also, if I'm understanding your desired functionality correctly, there are a couple other issues you'll run into with your code:
i = $(this.id); this will resolve to $('menu-tos'). To select via ID, you'd need a #, like this: $('#menu-tos'). In your case, though, there's really no reason to set the current element to a variable anyway, because it is already available via $(this).
As mentioned above, y = dataset.info; won't work because dataset is a property on HTML Element objects, not a variable. Since you're using jQuery, it'd be easier to use $(this).data('info').
$('#menu ul li').not(i).html(y); this will not do what you said you're trying to do. This will set the HTML of all other <li> elements to the value of the one you just clicked. To set each one to its own value, you'll need to loop through them using .each()
$(i).html('Something unique'); assuming i was set correctly as a jQuery object, you don't need the jQuery wrapper here, you can just use i.html('Something unique');
A couple other things that would help your code:
The way you are setting your variables now (without using var), it will set them on the global scope. This may work, but it can cause collisions, and is generally avoided. Use var like var i = $(this);, and it will keep that variable only within the scope of your click() function.
When using jQuery, you should wrap your code in a $(document).ready() callback. This will ensure that the DOM is loaded before jQuery tries to bind any event handlers (such as your click handler).
After fixing the issues mentioned here, the javascript code ends up looking like:
$(document).ready(function() { // ensure document is loaded before running code
$('#menu ul li').click(function() {
// set all other elements to their own data-info attribute value
$('#menu ul li').not(this).each(function() {
var info = $(this).data('info');
$(this).html(info);
});
// set the clicked item to 'Something unique'
$(this).html('Something unique');
});
});
Checkout the working code on this JSFiddle.
Try like this:
$('#menu ul li').click(function() {
$(this).siblings().each(function() {
var info = $(this).data('info');
$(this).html(info);
});
$(this).html('Something unique');
});
Full example here https://jsfiddle.net/_jakob/q49kq3c5/1/
Here is my HTML and when tag was click I want to know that what is its <li> siblings number was. Please Advice me please.
<div id="tabs">
<ul>
<li class="select" >Hotel</li>
<li >Airfare</li>
<li >Package</li>
</ul>
</div>
and here is my javascript.
// I don't want to input 1 in the function tabSelector
// I want to get parent's sibling value automatic and
// change somthing in li class.
$('#tabHotel').click(function(){
tabSelector(1);
});
you could use index().
$("#tabs").on("click", "li", function(){
alert($(this).index());
});
in your case:
tabSelector($(this).index() + 1 );
Demo:
http://jsfiddle.net/P3KjZ/1/
You can use jQuery's index() method to achieve this I believe.
index() - If no argument is passed to the .index() method, the return value is
an integer indicating the position of the first element within the
jQuery object relative to its sibling elements.
If .index() is called on a collection of elements and a DOM element or
jQuery object is passed in, .index() returns an integer indicating the
position of the passed element relative to the original collection
Here's a jsFiddle example.
For the technical number (first is equal to 0) you'd use:
$('li').on('click', function(){
console.log($(this).index());
});
For the literal number (first element is equal to one) you'd just add one to the index instead:
$('li').on('click', function(){
console.log($(this).index()+1);
});
to get exact number you will be required to add 1 to the index. please try below one
$("#tabs").on("click", "li", function(){
alert($(this).index()+1)
})
I'm plucking my brain away at this but was hoping someone could help after several failed attempts.
I have an HTML list like this:
<ul>
<li><span class="current"></span></li>
<li><span class="normal"></span></li>
</ul>
I'm trying to figure out a way to find the li element in this list which has the span with the class current with the number it is at in the ul. So, in this case, it would be 1.
I tried using different jquery functions but I seem to be getting nowhere. This is what it looks like right now:
var list = $('ul li');
$.each(list, function(key, value) {
if( $(this).find('.current') ) {
alert(key);
}
});
This just alerts 0, and 1, essentially meaning that it doesn't work. Does anyone have any idea what is wrong with what I'm doing?
It would be 0 not 1 (JavaScript is zero-indexed), but:
$('li:has(span.current)').index();
JS Fiddle demo, and a larger-table example.
Or you could use:
$('span.current').parent().index();
JS Fiddle demo, and a larger-table example.
Or:
$('span.current').closest('li').index();
JS Fiddle demo, and a larger-table example.
References:
closest().
:has() selector.
index().
parent().
jQuery selectors (never) return a falsey value. So something like:
$(this).find('.current')
Will always return true in an if statement. An easy way to check for existence is with the length property, which says how many elements are found from the selector.
if ($(this).find('.current').length > 0) {
Your code loops through each item in the list and shows its key.
What you want is more like:
$('mylist').find('.current').each(function(key, value)
{
alert(key);
}
This will loop only through the items with class 'current'.
I have a list here
<ul id="demo2" data-name="demo2">
<li data-value="here">here</li>
<li data-value="are">are</li>
<li data-value="some...">some</li>
<!-- notice that this tag is setting a different value :) -->
<li data-value="initial">initial</li>
<li data-value="tags">tags</li>
</ul>
Where each li item has a custom data attribute. On JQuery how would get all of the values of each li element which has an attribute of data-value? I want to get their value.
but this code of mine doesn't seem to be working
$('#view-tags').click(function(){
$('li[data-value]').each(function(){
alert($(this).data("value"));
})
});
The whole code on jsfiddle: http://jsfiddle.net/Zn3JA/
You are pretty close. You can use jQuery's .data() method to read attributes that start with data-. So in your case .data("value") since your attribute is data-value="some".
This should do it:
$('li[data-value]').each(function(){
alert($(this).data("value"));
});
Here is a working fiddle as well: http://jsfiddle.net/nuphP/
$(this).attr('data-value')
should also work.
You can use in your case:
jQuery(this).data("value");
in order to retrieve the value.
$(this) refers to the current li element hence you get the element alerted.
You can try what the others have suggested i.e $(this).data("value")
$('#view-tags').click(function(){
$('li[data-value]').each(function(){
var value = $(this).attr('data-value');
alert(value);
})
}); // this work normally
Takes the attribute value and stores the variable value
var value = $ (this) .attr ('date value');
After this warning the variable value
alert (value);
The JQuery "has" method effectively selects all elements where they have particular descendants.
I want to select elements based on the fact they have particular ancestors. I know about parent([selector]) and parents([selector]) but these select the parents and not the children with the parents.
So is there an ancestor equivalent of "has"?
Note: I already have the context of an element further down the hierarchy and I will be selecting based on this so I can't do a "top down" query.
Update
I've obviously explained myself really badly here, so I'll try and clarify:
<ul class="x">
<li>1</li>
<li>2</li>
<li>3</li>
</ul>
<ul class="y">
<li>4</li>
<li>5</li>
<li>6</li>
</ul>
I have a jQuery object that already consists of elements 2,3,4 and 5. I want to select those elements who have a parent with the class = x.
Hope that makes more sense.
For a clean re-usable solution, consider extending the jQuery.fn object with a custom method used for determining the presence of a particular ancestor for any given element:
// Extend jQuery.fn with our new method
jQuery.extend( jQuery.fn, {
// Name of our method & one argument (the parent selector)
within: function( pSelector ) {
// Returns a subset of items using jQuery.filter
return this.filter(function(){
// Return truthy/falsey based on presence in parent
return $(this).closest( pSelector ).length;
});
}
});
This results in a new method, $.fn.within, that we can use to filter our results:
$("li").within(".x").css("background", "red");
This selects all list items on the document, and then filters to only those that have .x as an ancestor. Because this uses jQuery internally, you could pass in a more complicated selector:
$("li").within(".x, .y").css("background", "red");
This will filter the collection to items that descend from either .x or .y, or both.
Fiddle: http://jsfiddle.net/jonathansampson/6GMN5/
if ( $('.foo').parents('.parentSelector').length ) { // has parent }
If I understand your question correctly, this would do:
$.fn.hasAncestor = function(a) {
return this.filter(function() {
return !!$(this).closest(a).length;
});
};
$('.element').hasAncestor('.container').myAction();
<div class="container">
<span>
<strong class="element">strong</strong>
</span>
</div>
$('body').hasParent('html') //true
$('div#myDiv').hasParent($('body')) //true
#API:
// check if current element has parent element 'e'
$.fn.hasParent = function (e) {
return !!$(this).parents(e).length
}
You can actually use filter directly (without a function calling closest) and it will have better performance. Simply use a selector that matches elements contained within .x:
$("li").filter(".x *")
this also differs slightly from the closest solutions suggested by others in that it will not match if the element itself has the given class but only if it is within an element with that class.
If matching an element with the class is desired as well, this could be modified slightly:
$("li").filter(".x, .x *")
$("li").filter(".x *").css("background", "red");
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<ul class="x"><li>1</li><li>2</li><li>3</li></ul>
<ul class="y"><li>4</li><li>5</li><li>6</li></ul>
Try this
ul.myList > li > a
This selector selects only links that are direct children of list elements, which are
in turn direct children of elements that have the class myList.
object.each(function(){
element = $(this);
if(element.parent().hasClass("x")){
//do stuff
}
});
this will affect every item in your object that has parent .x
The easy way is this:
// all children of a specific parent match
$('parentSelector').children();
// All children matching a specific pattern, one level deep
$('parentSelector > childSelector');
// or
// $('parentSelector').children('childSelector');
// All children matching a specific pattern, multiple levels deep
$('parentSelector childSelector');
// or
// $('parentSelector').find('childSelector');
or did you really need something more complicated than that?
Edit: If you already have an element, you can combine this with the parent() command, like so:
myElement.parents('parentSelector').find('childSelector'); // Will include self
I realize this is an old question, but I'm leaving this here for future visitors looking for something similar;
There is a $.contains(container, contained) method which returns a boolean.
https://api.jquery.com/jQuery.contains/
Very simple way to do it
$('.x').find('li')