Javascript Functions, Ready, Click, Each, Next, This, and Toggle - javascript

I just started learning web development and someone gave me this code to use. However, I want to understand it so that I can change it the way that I would like. However, I am having some trouble understanding it completely. I have the basics of computer programming. I just am having a hard time understanding what this code here is doing. I've done some research here https://api.jquery.com/. I understand the individual concepts kind of, but can't put them together. So here is what I understand so far:
.ready(): It makes sure that the page is loaded and is ready for use. And I'm assuming the following code won't execute unless the page is fully loaded and ready for interaction.
.click(): Basically responds to a click.
.each(): Kind of a like a for loop.
.next(): Goes to the next element.
.hide(): Hides the element (which is kind of confusing, because it doesn't actually hide it, it just makes it jump up)?
.toggle(): It reveals a hidden element?
Here is the code:
$(document).ready(function(){
$('.info').click(function(){
$('.info').each(function(){
$(this).next().hide();
});
$(this).next().toggle();
});
});
I think that's it. But I'm not sure how it all fits in. Could someone please explain it to me?
Also, why doesn't the code above work without this line:
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.3/jquery.min.js"></script>

The line
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.3/jquery.min.js"></script>
loads the jQuery library from the CDN URL above. This Javascript file contains the definition of all the above functions you're using as well as many other useful functions. You can read more on the official docs. https://api.jquery.com/
Code Explanation
$(document).ready(function () {
This registers a ready event on document. In other words, the callback anonymous function is called when the DOM is completely loaded and is ready to be manipulated.
$('.info').click(function () {
Just like the ready event handler, this code binds a click event on all the elements having class of info.
$('.info').each(function () {
$(this).next().hide();
});
This part of code will loop over all the elements having the class of info and hides the next element of each element one by one.'
$(this).next().toggle();
This will toggle the visibility of the next element of the clicked-$(this) element. Not really, this is showing the next element as in the above each loop, you've hide all the next elements of .info class.
}); // End of click
}); // End of ready
Your code can also written without loop as
$(document).ready(function () {
$('.info').click(function () {
$('.info').not(this).next().hide();
// Hide all elements that are nextSibling of the elements having class info other than the clicked one
$(this).next().show();
// Show the next element of the clicked element
});
});

First of all, you should know js is a language, and most of the functions you mentioned here are jQuery functions.
jQuery is a library written in js which has a lot of functions and options to support development.
So the line of script you included, loads the jQuery library in to the page.
As for the other questions:
.ready(): It makes sure that the page is loaded and is ready for use. And I'm assuming the following code won't execute unless the page is fully loaded and ready for interaction.
As you wrote - this is a function to deal with page loading, although the following code will execute before page is done loading, and that is because js is a non-blocking script
so the proper use of .ready() is:
$(document).ready(function(){
....//all code you need after page is fully ready goes here
});
.click(): Basically responds to a click.
Correct. this responds to a DOM event of a DOM element. It is really impotent to understand what is DOM and how to use it when developing for web.
$(element).click(function(){
....//all code you need after clicking element goes here
});
.each(): Kind of a like a for loop.
Correct. this loops through DOM elements, and in each iteration you get a reference to the current one
$(elements).each(function(){
var element = $(this) //jquery wrapper of current iterated DOM element. this refers to current iterated DOM element
});
.next(): Goes to the next element.
this is a way of "walking" through the DOM tree, to manipulate elements in it
.hide(): Hides the element (which is kind of confusing, because it doesn't actually hide it, it just makes it jump up)?
this does actually hide the element. This would probably be done using css to hide the element
.toggle(): It reveals a hidden element?
this is a shortcut for hide() and show(). It checks if element is hidden, and if it is, it uses show(), otherwise, it uses hide(). as mentioned, this would also probably be done with css

Related

Jquery Onclick functionality not working for div, as specific loaded after sometime

For <div class="editdiv">Test</div>. Jquery click functionality is added in document.ready function . But editdiv loading in page dynamically with delay.
So when I click on the div. Function is not calling. By using timeout function is working fine.
I need a different approach to solve this functionality.
If your .editdiv is loaded dynamically after your js loading so your click event can't detect it and it will not work, instead you should use event delegation on() to deal with fresh DOM :
$('body').on('click', '.editdiv', function(){
//Your click event code
})
If you want to avoid setTimeout you could use delay with queue callback method :
$('div.scroll-area-blue')
.delay(5000)
.queue(function() {
$(this).enscroll({
showOnHover: false,
verticalScrolling: true,
verticalTrackClass: 'vertical-track-blue',
verticalHandleClass: 'vertical-handle-blue'
});
});
If you will use setTimeout better to use it like :
setTimeout( enscrollDiv, 5000);
function enscrollDiv(){
$('div.scroll-area-blue').enscroll({
showOnHover: false,
verticalScrolling: true,
verticalTrackClass: 'vertical-track-blue',
verticalHandleClass: 'vertical-handle-blue'
});
}
Hope this helps.
It is really difficult to understand whats going wrong from your question. What I guess is you are loading a specific div using Ajax or similar technologies - meaning the div is not available initially.
The way jQuery works is that, it only binds the event to the elements only available at the time the part is executed.
If a <div id='myDiv'></div> is not present when $('#myDiv').click(function(){}) is called, it won't work.
One workaround is to do it like this:
$('body').on('click','#myDiv',function(){});
This registers the click on body and then checks if the clicked element is having a id 'myDiv' or not. We can expect the <body></body> to be present always. So the problem we had with previous code won't happen here.
maybe you're loading the javascript codes before the html elements(tags) are loaded.
try adding the script which includes "document.ready()" before the end tag of the body when all html tags have already finished loading.
I'm hitting targets in the dark. Hope it works for you. It's difficult to generate any solution without analyzing the problematic code......

jQuery scripts on ajax content WITHOUT using $(document).on

I am using an infinite scroll plugin which uses ajax.
When the 'next page' is loaded via ajax, all other ajax related scripts that are on the next page do not work. I have been told that I have to use 'delegated events'(ie change $(id).click() to $(document).on) - problem is that means editing multiple plugins and changing dozens of function calls.
Is there any way I can avoid changing everything to $(document).on and do something cool with the infinite scroll?????
I'd much rather modify the infinite scroll plugin rather than modifying other ajax related plugins to make them fit.
Unfortunately you have very few options here, and switching to delegated events is by far the best of them.
The problem is that your old code was assigning behaviour to "particular elements" when what it should really have been doing is creating page-wide responses to "certain types of actions".
I see 3 possibilities, and only one of them is guaranteed to work.
Run any scripts that are needed on new pages each time a new page is loaded. The downside here being that unless you are careful about also "tearing down" between content loads you will have behaviours repeating or colliding with each other (eg: double popups, broken animations).
Encapsulate the dynamic areas in <iframe>s. Depending on your architecture this may or may not be possible, and certainly won't be easy to integrate with some kind of infinite scrolling plugin which already expects a certain page structure.
Bite the bullet and fix the crappy code.
Loading scripts inside your ajax loaded content is a bad way to start with anyway. What you need is event delegation to attach itself to any dynamically added elements.
$("body").on("click", ".yourclass", function() {
//This function will run for every element with `yourclass` class you load via ajax
});
If you must keep using .click() then you must have a function you can call on the new content to re-hook the events every time you add more content to the page.
e: though it is worth noting that a change from .click to .on can often be handled by a properly structured find/replace
Event delegation is the correct solution. The issue is that the HTML elements on the "next page" were not part of the DOM when the page loaded. Therefore, if you did something like:
$(function() {
$('#some-element-on-the-next-page').click(function() {
foo();
});
});
Your handler did not bind.
I wouldn't attach the events to $(document). I would attach them to the closest parent which is available when the DOM loads. For example, the body tag or the fixed width wrapper which is the first child of the body (assuming your layout uses this type of structure.)
Make sure that the element that you attach to is not emptied with .empty() or repopulated with .html() as that will break the binding. Attaching the delegated handlers lower down on the DOM tree will give you better performance since the events will not have to bubble all the way up to the document node to fire your methods.
You shouldn't need to rewrite all of your functions and plugins, just the bindings to the events that fire them.
I typically use the module pattern and de-couple my method definitions from the click handlers. All of my methods are defined in the outer closure. I'll have a "document ready" section where I bind user events like clicks.
For example:
var myModule = (function() {
var public = {};
public.foo = function() {
// do something cool here
};
// document ready
$(function () {
$('#site-container').on('click', '.js-foo', function() {
public.foo();
});
});
return public;
})();
If you need to change the bindings in the future you will only need to change the call inside the document ready section.

jQuery after ajax call, events with the same Ids stopped working

Not sure if this is a bug or I am not suppose be doing this.
I have a page with sidebars that loads the main body dynamically.
For page1, I have a callback for an element #id1, which works on initial load.
After the user navigates to page2, the main content will get replaced by contents of page2, which also has an element with #id1, they serve the same purpose. events are initialized there as well.
The problem is that everything on page 2 would work except the event associated with #id1.
If navigating back to page 1, #id1 wouldn't work as well.
After looking at the console, I found that when calling $("#id1") sometimes give me the initial load element (not destroyed?), which is probably the reason.
The ajax load simply uses:
$.get(path, function(data) {$('#main').html(data)});
Any idea what's going on here?
If the old elements are not 'properly destroyed in jquery', what is suppose to be done here.
While it's not clear exactly what you're binding, the solution is to use (depending on your jQuery version) live() or on() to ensure that you bind to elements that aren't in the DOM at execution time.
jQuery 1.7+: on()
$(document).on('click', '.selector', function() { ... });
jQuery <1.7: live()
$('.selector').live('click', function() { ... });
Remember that an ID should only occur once
Because you don't know what elements with ID's may still be living in the DOM after the Ajax call you should stick with classname's instead.
With that you can use jQuery's .live() to bind to elements that have been dynamically loaded.
You have to generate dynamic id for that. When you click the right bar option the id will generated and place the id in the body element "id" tag.So you know that which id is generated for which page. Call a javascript function on "onclick" event and pass that id to this function then call the body element as $("#id"+that generated_id).something;
I think this will help.

jQuery functions only work inside .ready()

I'm still new to jQuery and I'm wondering how come the jQuery functions called inside .ready() work just fine but not outside?
For example, this would work:
$(document).ready(function() {
$('#field1').click(function() {
$('#result').load('/random_post #post');
});
});
But this won't:
$('#field1').click(function() {
$('#result').load('/random_post #post');
});
You cannot access the DOM until the document is fully parsed and the DOM constructed. That includes modifying any elements – such as #field1 and #result.
Since $(document).ready(..) is long and may be hard to remember, you can also use the short form $(onReadyFunction), i.e.
$(function() {
$('#field1').click(function() {
$('#result').load('/random_post #post');
});
});
By the way, jQuery does no magic here: It just registers your function to be called when DOMContentLoaded (or equivalent) event is triggered by the parsing and construction of the DOM tree.
How and if it works will depend on the order of which scripts and elements are laid out in your HTML, and it might also be affected by parameters outside your control (e.g. how the browser is programmed to behave).
I 'd hazard a guess that this script appears in your page before the element with id="field1" that gets a click handler added; this causes the script to run and find no such element in the document tree (yet). The element gets added after the script runs, which is why jQuery finds it just fine after the whole document has loaded.
If you move this script at the very end of your page it should work (although of course the correct solution is to use the document ready event, as in your first snippet).
The ready function is executed when the dom tree has been created. You get an error in your second piece of code because the dom tree element with id filed1 has not been created yet, i.e. the page hasn't loaded yet.

Calling a function as soon as an element is encountered

Suppose I have an element on my page with id "some_id". I want to call a function as soon as I encounter this element. Something like following.
$("#some_id").call_a_function(function () {
// do stuff
});
Not sure what you mean by "encounter this element". If you mean as soon as the element is parsed, you could always inline some script right after it:
<div id="some_id">Hello</div>
<script type="text/javascript">
$("#some_id").call_a_function(function () {
// do stuff
});
</script>
The javascript code will be parsed right after the div. Of course, this wouldn't be much quicker than using $(document).ready() on small pages.
Checkout this jquery plugin as an alternative to $(document).ready()
http://plugins.jquery.com/project/available
Allows you to specify a handler to a DOM element as soon as it becomes available.

Categories