1

What I want to do is to change the default jquery method of a specific element.

For example, I want to change the method val() of some (not all) select list. And after that revert back if necessary.

My first attempt is the following but not work.

$('#list').val = function(){ alert('toto'); };
//and then
$('#list').val()  //not work

SOLUTION

var old_val = $.fn.val;
$.fn.val = function(value){
    //some condition to trigger
    if (this.hasClass('someclass')){
        //getter
        if (value===undefined){
            //do something to get the values
            return val;
        }
        //setter
        else {
            //do something with the value
            return this;
        }
    }

    return old_val.apply(this, arguments);
};
6
  • This is a bad idea and won't work. Commented Aug 1, 2013 at 15:41
  • @MightyPork What does it mean,changing method val()? Commented Aug 1, 2013 at 15:43
  • 1
    possible duplicate of stackoverflow.com/questions/5760599/… Commented Aug 1, 2013 at 15:43
  • What's your ultimate purpose? Commented Aug 1, 2013 at 15:44
  • As in the duplicate listed, you need to cache the element if you want to change it just for that element. It's probably better to write a small plugin that does whatever functionality you want to do and do that instead. Commented Aug 1, 2013 at 15:45

2 Answers 2

4

Each time you call $('#list') you're creating a new jQuery object. So when you do $('#list').val = function(){ alert('toto'); };, you have overwritten the val() method for only that instance. If you cache that object, you could continue to use the overwritten val() method:

var list = $('#list');
list.val = function(){ alert('toto'); };
list.val(); //alerts 'toto'

HOWEVER, this is a bad practice, since you don't know what else will be depending on val() working correctly. The better approach would be to create your own plugin:

$.fn.totoVal = function() {
    alert('toto');
    return this;
};

You could then call this as $('#list').totoVal()

EDIT

If you really, really want to do this (again it is a bad idea), you can override the native val() implementation this way:

var originalValueFunct = $.fn.val;

//update value function
$.fn.val = function () {
    return "custom value";
}

//do something with val()

//restore value function
$.fn.val = originalValueFunct;

See this working demo for an example of overriding and restoring the native val() function.

I strongly advise against doing this as you will create side-effects in your code or any libraries you use that rely on the val() method. These side-effects will be very hard to debug because they will only be present in your environment and it won't always be obvious that you have changed a piece of core jQuery functionality.

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

7 Comments

As I was saying, it's the best way to achieve that ! ;)
This answered my first part. But I really want to modify the default behavior, globally and not just cached jquery object, of val() of some jquery elements.
A plugin is the best way to do that. If you change the behavior of a standard jQuery function, you could have unintended side-effects in other places in your code or in any libraries you use. These side-effects will appear as bugs that will be very hard to debug.
I added an example to show how you could override val() if you really wanted to. Use it wisely.
To filter out custom element, can I just do, inside $.fn.val: return $(this).hasClass('someclass') ? 'custom' : $.fn.val ?
|
1

jquery provides the valHooks object to which you can attach whatever function you would like to attach to the .val() function. Your example would look something like this, to put it in one line.

$.valHooks.select = {get: function( elem ) { if($(elem).attr('id') == 'list') alert('toto') }}

For more detail on valHooks you can look at the jquery api documentation at http://api.jquery.com/val/

2 Comments

I like this idea. So all I need to do is to make a test if ($(elem).hasClass('someclass') || $(elem).is('#list')) to achieve what I want to filter out. But how do you return the value of the original function for other element?
When I tested out the above code it was still returning the value of the original function, in addition to throwing the alert. You can also access the element through the elem parameter.

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.