Creating, Operating, and Adding HTML On the Fly
You can create HTML markup on the fly by passing the jQuery function a string of raw HTML.
<!DOCTYPE html> <html lang="en"> <body> <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script> <script> (function($){ alert($('<div><a></a></div>').get(0).nodeName); // Alerts "DIV" alert($('<div><a></a></div>').length); // Alerts "1" <div> is in the wrapper set alert($('<div><a></a></div><div><a></a></div>').length); // Alerts "2" <div> are in the set })(jQuery); </script> </body> </html>
It is important to note that when creating DOM structures using the jQuery function, only root elements in the structure are added to the wrapper set. In the previous code example, the <div>
elements will be the only elements in the wrapper set.
We can use the find()
method to operate on any element in the HTML structure once it is created.
<!DOCTYPE html> <html lang="en"> <body> <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script> <script> (function ($) { $('<div><a></a></div>') .find('a') .text('jQuery') .attr('href', 'http://www.jquery.com'); })(jQuery); </script> </body> </html>
After operating on the newly created HTML, it is also possible to add it into the DOM using one of jQuery's manipulation methods. Below we use the appendTo()
method to add the markup to the page.
<!DOCTYPE html> <html lang="en"> <body> <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script> <script> (function($){ $('<div><a></a></div>') .find('a') .text('jQuery') .attr('href', 'http://www.jquery.com') .end().appendTo('body'); // end() is used to exit the find() method })(jQuery); </script> </body> </html>
Notes: Simple elements that do not contain attributes - e.g. $('<div></div>')
- are created via the document.createElement
DOM method, while all other cases rely on the innerHTML
property. In fact, you can directly pass the jQuery function an element created with document.createElement
-e.g. $(document.createElement('div'))
.
The HTML string passed to jQuery cannot contain elements that might be considered invalid inside of a <div>
element.
The HTML string passed to the jQuery function must be well formed.
You should open and close all HTML elements when passing jQuery HTML. Not doing so could result in bugs, mostly in Internet Explorer. Just to be safe, always close your HTML elements and avoid writing shortcut HTML - e.g. $(<div />)
.
Grokking the index() Method
You can determine the index of an element in the wrapper set by passing that element to the index()
method. As an example, suppose you have a wrapper set containing all the <div>
elements in a Web page, and you would like to know the index of the last <div>
element.
<!DOCTYPE html> <html lang="en"> <body> <div>0</div> <div>1</div> <div>2</div> <div>3</div> <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script> <script> (function ($) { // Alerts "3" alert($('div').index($('div:last'))); })(jQuery); </script> </body> </html>
The use of index()
does not really hit home until we consider how it can be used with events. As an example, by clicking the <div>
elements in the code below, we can pass the clicked <div>
element (using the keyword this
) to the index()
method to determine the clicked <div>
's index.
<!DOCTYPE html> <html lang="en"> <body> <div id="nav"> <div>nav text</div> <div>nav text</div> <div>nav text</div> <div>nav text</div> </div> <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script> <script> (function ($) { // Alert index of the clicked div amongst all div's in the wrapper set $('#nav div').click(function () { alert($('#nav div').index(this)); // or, a nice trick... alert($(this).prevAll().length); }); })(jQuery); </script> </body> </html>
Grokking the text() Method
One might incorrectly assume that the text()
method only returns the text node of the first element in a wrapper set. However, it will actually join the text nodes of all elements contained in a wrapper set and then return the concatenated value as a single string. Make sure you are aware of this functionality, or you might get some unexpected results.
<!DOCTYPE html> <html lang="en"> <body> <div>1,</div> <div>2,</div> <div>3,</div> <div>4</div> <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script> <script> (function ($) { alert($('div').text()); // Alerts "1,2,3,4" })(jQuery); </script> </body> </html>
Update Or Remove Characters Using a Regular Expression
Using the JavaScript replace()
method combined with some jQuery functionality, we can very easily update or remove any pattern of characters from the text contained within an element.
<!DOCTYPE html> <html lang="en"> <body> <p> I really hate using JavaScript. I mean really hate it! It is the best twister ever! </p> <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script> <script> (function ($) { var $p = $('p'); // Replace 'hate' with 'love' $p.text($p.text().replace(/hate/ig, 'love')); // Remove 'twister' and replace it with nothing $p.text($p.text().replace(/twister/ig, '')); // Keep in mind that text() returns a string, not the jQuery object. // That is how the replace() string method is chained after using text() })(jQuery); </script> </body> </html>
You could also update any characters that are contained in a string returned from html()
. This means you can not only update text, but also update and replace DOM elements via a regular expression.
Grokking the .contents() Method
The .contents()
method can be used to find all the child element nodes, including text nodes contained inside of an element. However, there is a catch. If the retrieved contents contain only text nodes, the selection will be placed inside the wrapper set as a single text node. However, if the contents you are retrieving have one or more element nodes amongst the text nodes, then the .contents()
method will contain text nodes and element nodes. Examine the code below to grasp this concept.
<!DOCTYPE html> <html lang="en"> <body> <p>I love using jQuery!</p> <p>I love <strong>really</strong> using jQuery!</p> <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script> <script> (function ($) { // Alerts "I love using jQuery!" because no HTML elements exist alert($('p:first').contents().get(0).nodeValue); // Alerts "I love" alert($('p:last').contents().get(0).nodeValue); // Alerts "really" but is an HTML element, not a text node alert($('p:last').contents().eq(1).text()); // Alerts "using jQuery!" alert($('p:last').contents().get(2).nodeValue); })(jQuery); </script> </body> </html>
Notice that when an item in the wrapper set is a text node, we have to extract the value by using .get(0).nodeValue
. The contents()
method is handy for extracting text node values. It is possible to extract only the text nodes from a DOM structure using contents()
.
<!DOCTYPE html> <html lang="en"> <body> <p>jQuery gives me <strong>more <span>power</span></strong> than any other web tool! </p> <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script> <script> (function($){ $('p') .find('*') // Select all nodes .andSelf() // Include <p> .contents() // Grab all child nodes, including text .filter(function() {return this.nodeType == Node.TEXT_NODE;}) // Remove non-text nodes .each(function (i, text) { alert(text.nodeValue) }); // Alert text contained in wrapper set })(jQuery); </script> </body> </html>
Using remove() Does Not Remove Elements From Wrapper Set
When you use remove()
, a DOM snippet from the DOM the elements contained in the removed DOM structure are still contained within the wrapper set. You could remove an element, operate on that element, and then actually place that element back into the DOM, all within a single jQuery chain.
<!DOCTYPE html> <html lang="en"> <body> <div>remove me</div> <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script> <script> (function ($) { $('div') .remove().html('<a href="http://www.jQuery.com">jQuery</a>') .appendTo('body'); })(jQuery); </script> </body> </html>
The point here is that just because you remove()
elements does not mean they are removed from the jQuery wrapper set.
Comments