Слава Україні
Glory to Ukraine
Save the World
Жыве Беларусь
Live Belarus



Урок - Метод jQuery.proxy().

Группа вКонтакте
Лицензия: Лицензия Creative Commons.

Метод jQuery.proxy() возвращает функцию с измененным контекстом this.

Синтаксис метода jQuery.proxy().

Метод jQuery.proxy() может выполнять празличные действия, в зависимости от количества передаваемых аргументов:

  • jQuery.proxy( function, context)
  • jQuery.proxy( context, name)
  • jQuery.proxy( function, context, additionalArguments)
  • jQuery.proxy( context, name, additionalArguments)

где

  • function - функция, контекст которой должен быть изменен.
  • context - объект, на который должен указывать контекст (this).
  • name - строка, имя метода чей контекст должен быть изменён (должен быть свойством объекта контекста).
  • additionalArguments - любое число аргументов, для передачи в качестве аргументов функции.

Описание метода jQuery.proxy().

Метод jQuery.proxy() полезен для назначения обработчиков событий к элементу, когда контекст указывает на другой элемент. Кроме того, jQuery гарантирует правильное удаление функции назначенной jQuery.proxy(), если она указана с оригинальным контекстом.

Необходимо понимать, что jQuery, при назначении подсистемы, присваивает уникальный идентификатор каждой функции, чтобы отслеживать её, для определения самой функции, которая назначается. Функция в jQuery.proxy() рассматриваются как функции из подсистемы событий, даже когда разные контексты.  Чтобы избежать не правильного удаления обработчика, используйте уникальное пространство имен для назначения и удаления обработчиков (например: 'click.myproxy1') вместо указания прокси функции во время назначения.

Начиная с версии jQuery 1.6, любое количество дополнительных аргументов может быть передано в jQuery.proxy() и они будут переданы функции контекст которой был изменен.

Наичная с версии jQuery 1.9, когда контекст является null или не определен, то функция будет вызвана с тем же объектом в качестве контекста, для которого вызвается метод jQuery.proxy(). Это позволяет использовать метод jQuery.proxy() частично применять аргументы функции, без изменения контекста.

Примеры использования метода jQuery.proxy().

Пример 1: Изменить контекст функции связанный с обработчиком click используя "function, contexts". Первый обработчик отключается после первого клика.

<!DOCTYPE html>
<html>
<head>
    <meta charset=utf-8>
    <script src="http://code.jquery.com/jquery-1.10.0.min.js"></script>
    <script>
        jQuery(function(){

            var me = {
                type: "zombie",
                test: function(event) {
                    //    без использования jQuery.proxy() контекст this должен указывать на элемент события.
                    //    что бы получить элемент необходимо использовать event.target
                    var element = event.target;
                    $(element).css("background-color", "red");
                    
                    //    при использовании jQuery.proxy() контекст this меняется.
                    $("#log").append( "From me.test. this type: " + this.type + "<br>" );
                    
                    //    удаляем текущий обработчик
                    $("#test").off("click", this.test);
                }
            };
            var you = {
                type: "person",
                test: function(event) {
                    $("#log").append('From you.test(). this.type: ' + this.type + "<br>" );
                }
            };
            /* execute you.test() in the context of the `you` object */
            /* no matter where it is called */
            /* i.e. the `this` keyword will refer to `you` */
            var youClick = $.proxy( you.test, you );
            
            
            //    назначем обработчики для кнопки
            $("#test")
                //    в этом обработчике, основаном на me.test(), this будет указывать на me.
                //    this.type равен "zombie"
                //    обработчик будет удален после первого клика
                .on( "click", $.proxy( me.test, me ) )
                //    в этом обработчике, основаном на you.test(), this будет указывать на you.
                //    т.е. this.type равен "person"
                .on( "click", youClick )
                //    в этом обработчике, основаном на you.test(), this будет указывать на me.
                //    т.е. this.type равен "zombie"
                .on( "click", $.proxy( you.test, me ) )
                //    в этом обработчике, основаном на you.test(), this будет указывать на элемент к которому прикреплен обработчик.
                //    т.е. this.type равен "button"
                .on( "click", you.test )
            ;
            
        });
    </script>
</head>
<body>
    <p><button type="button" id="test">Test</button></p>
    <div id="log"></div>
</body>
</html>

Пример 2: принудительный контекст функции с помощью "context, function name". Отключение обработчика после первого клика.

<!DOCTYPE html>
<html>
<head>
    <meta charset=utf-8>
    <script src="http://code.jquery.com/jquery-1.10.1.min.js"></script>
    <script>
        jQuery(function(){

            var obj = {
                name: "John",
                test: function() {
                    $("#log").append( this.name );
                    $("#test").off("click", obj.test);
                }
            };
            $("#test").on( "click", jQuery.proxy( obj, "test" ) );
            
        });
    </script>
</head>
<body>
    <p><button id="test">Test</button></p>
    <p id="log"></p>
</body>
</html>

Пример 3: Изменить контекст функции с вязанный с обработчиком click.

<!DOCTYPE html>
<html>
<head>
    <meta charset=utf-8>
    <script src="http://code.jquery.com/jquery-1.10.1.min.js"></script>
    <script>
        jQuery(function(){
            var main = {
                type: "mainType",
                //    Обратите внимание, что событие задано после аргументов one и two
                test: function(one, two, event) {
                    //    после выполнения команды var proxy = jQuery.proxy( main.test, main, first, second );
                    //    контекст this будет указывать на main
                    //    аргумент one указывает на first
                    //    аргумент two указывает на second
                    jQuery("#log")
                        //    выводим информацию о контексте this
                        .append( "this.type: " + this.type + "<br>")
                        //    выводим информацию из первого аргумента
                        .append( "one.type: " + one.type + "<br>")
                        //    выводим информацию из второго аргумента
                        .append( "two.type: " + two.type + "<br>")
                        //    выводим информацию о типе события
                        .append( "event.type: " + event.type + "<br>")
                        //    информация о элементе к которому привязано событие
                        .append( "event.target.type: " + event.target.type + "<br>")
                    ;
                }
            };
            var first = {
                type: "firstType"
            };
            var second = {
                //    тип "рыб"
                type: "secondType"
            };
            //    первый аргумент - обработчик у которого заменяем контекст this: main.test()
            //    второй аргумент - переменная на которую будет указывать контекст this: main
            //    третий и четвертый аргументы - дполнительные параметры передаваемые в обработчик: first и second
            var proxy = jQuery.proxy( main.test, main, first, second );
            jQuery("#test").on( "click", proxy );
        });
    </script>
</head>
<body>
    <button type="button" id="test">Test</button>
    <div id="log"></div>
</body>
</html>