0

I've got a list of items that have different data values that I'm trying to return on a click event. I can't seem to pass the value from the click event to the parent function. I may just be doing this all wrong. I just need the data value from each click event to replace the value of my systemName variable. Can someone help me out here?

function getSystemName(){
var systemName = '';
$('.pulldown li').bind('click', function(){
    var systemName = '';
    var systemName = $(this).find('a').data('value');
    console.log(systemName);
});
return systemName;
}

// Edit: I should probably explain that I'm trying to get that value from the click event to update content on the page via jquery .load so perhaps like mentioned below....I'm not doing this properly because I can log the systemName properly on click but it doesn't seem to update the page content. Here is the entire code block.

$.ajaxSetup ({  
    cache: false  
});  
var ajax_load = "<img src='.../images/130.gif' alt='loading...' align='middle' />";
var loadUrl = ".../content.php";  

var getSystemName = (function(){
var systemName = '';
$('.pulldown li').bind('click', function(){
   systemName = $(this).find('a').data('value');
   console.log(systemName);
});
return function() { return systemName };
})();

$("#results")  
    .html(ajax_load)  
    .load(loadUrl, "ki_systems=" +getSystemName());
5
  • What's wrong? You're declaring systemName three times. Is that intended? Commented Jan 6, 2012 at 13:53
  • No that is me trying a bunch of different things and not cleaning up the code. Commented Jan 6, 2012 at 13:56
  • From your update, are you saying that you want to load content via ajax in direct response to a user clicking? If so, forget the getSystemName() function: just put your .load() statement inside the click event handler and run the .bind() in your document.ready. (Man did I ever guess wrong what you were talking about, though I think my answer is reasonable for your original question as asked.) Commented Jan 6, 2012 at 14:31
  • So are you saying put the three lines: $("#results") .html(ajax_load) .load(loadUrl, "ki_systems=" +getSystemName()); into the the click event handler? Commented Jan 6, 2012 at 14:33
  • That did the trick. Thanks!!! Just needed to post the entire code so you all could see what I was trying to accomplish. That's my bad. Commented Jan 6, 2012 at 14:42

6 Answers 6

2

In the code in the question, each time you call getSystemName() it will bind a click handler again (resulting in multiple click handlers) and then just return the local systemName variable that will always be blank.

If you are saying that each time you call getSystemName() you want it to return the system name associated with whichever li element was most recently clicked then you can declare the systemName variable as a global variable and bind the event handler (once) outside getSystemName():

var systemName = '';

$('.pulldown li').bind('click', function(){
   systemName = $(this).find('a').data('value');
   console.log(systemName);
});

function getSystemName() {
   return systemName;
}

But that makes the function rather redundant: you could just refence the global variable directly.

On the other hand you could declare just the function and use a closure to avoid the need for global variables, something like this:

var getSystemName = (function(){
    var systemName = '';
    $('.pulldown li').bind('click', function(){
       systemName = $(this).find('a').data('value');
       console.log(systemName);
    });
    return function() { return systemName };
})();

// if no items have been clicked yet it will return an empty string by default
console.log( getSystemName() ); // ""
// click on an item with name "red"
console.log( getSystemName() ); // "red"
// click on an item with name "green"
console.log( getSystemName() ); // "green"

That last block could be a little confusing to the uninitiated. It is setting getSystemName to whatever is returned from an anonymous function expression that is executed immediately (note the extra empty parentheses at the end). And what is returned is a simple function that when called itself will return systemName, which is declared in the outer scope. The click handler also updates this same systemName. So when you actually call getSystemName() you are calling the little one-liner function from the return statement.

Sign up to request clarification or add additional context in comments.

Comments

1

I think the problem here is that you're missing synchronous and asynchronous programming - you probably want a callback on the getSystemName() function. I expect there's something more architecturally wrong with the approach you're taking.

However, this is what it'd look like if I wrote that using your style:

function getSystemName(callback) {
    $('.pulldown li').bind('click', function(){
        console.log(systemName);
        callback( $(this).find('a').data('value') );
    });
}

So instead of this sort of code:

console.log("System Name: ", getSystemName())

You would have:

getSystemName( function (name) { console.log("System Name: ", name); } );

1 Comment

I think you're probably right and that I'm not approaching this properly. I am using the jquery .load to try to update my results based on the value returned from the function above.
0

Remove the var from the second and third definitions. If you use var before the variable name a new local instance will be created.

 systemName = '';
 systemName = $(this).find('a').data('value');
console.log(systemName);

2 Comments

That won't work. The return statement will still fire before the element is clicked to fire the code in the click handler.
Yes you are right... that's the second error there. He should do something with it before. +1.
0

Consider this, on the second line you're only binding a callback function to the click event, not executing the code inside that function.

Comments

0

You can't.

Look at the code.

  1. Set systemName to an empty string
  2. When a list item is clicked set systemName to something else
  3. Return systemName

You can't make 3 wait for 2. You need to do something with the data in the click handler and not try to return it.

Comments

-1

Well, i suppose you are trying to set a value to see which node has been click, thus you need to change the scope of your systemName variable. Move it out so it will be global, like so:

var systemName = '';
$('.pulldown li').bind('click', function(){
    systemName = $(this).find('a').data('value');
    console.log(systemName);
});

2 Comments

The code that sets systemName still won't fire before the returnstatement does.
And the value won't be set without the user clicking it. Calling the function will only bind the event, the event will set the value.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.