проблема с глобальными областями, возвращающими значения и ajax? - PullRequest
0 голосов
/ 19 августа 2011

Заголовок является предположением относительно того, что происходит с моим скриптом:

Это в моем global.js скрипте:

alert(search.getLabelsNames(); //alerts as undefined.
$('#search').autocomplete({
    source: function( request ) {
        search.getLabelsNames();
    },
    minLength:1
});

Это в моем functions.js скрипте:

var search;
window.search = {
    getLabelsNames:function( search ) {
        $.ajax({
            url : '../db_scripts/get_labels_names.php',
            type: "POST",
            data: { id: search }, //this defaults to nothing. not a problem
            success : function( data ) {
                var dataObj = jQuery.parseJSON( data );
                $.each(dataObj, function() {
                    alert(this.name);
                    return this.name;
                })
            }
        });
    }
}

В каждой функции this.name правильно возвращает каждое из имен меток из базы данных.Но когда я звоню из globals.js, он возвращается как undefined.Если я верну число 1, search.getLabelsNames() предупреждает 1 .., поэтому у него нет проблем с поиском глобальной функции.

что не так с этим скриптом и почему global.js не может найти this.name, который возвращается?

Ответы [ 3 ]

3 голосов
/ 19 августа 2011

У вас есть две проблемы:

  1. Невозможно вернуть данные из jQuery.each обратного вызова.Возвращаемое значение указывает, остановить ли итерацию или нет.Из документации :

    Мы можем разорвать цикл $.each() на определенной итерации, заставив функцию обратного вызова вернуть false.Возвращение non-false - это то же самое, что и оператор continue в цикле for;он сразу перейдет к следующей итерации.

  2. Невозможно вернуть данные из обратного вызова Ajax.Ajax асинхронный , что означает, что в вашем случае getLabelsNames возвращает до , ответ получен и обработан.

К счастью, автозаполнениеПлагин принимает функцию в качестве источника.Вы уже используете его, но не правильно.Заставьте его принять второй аргумент, который является обратным вызовом.Из документации :

Третий вариант, обратный вызов, обеспечивает наибольшую гибкость и может использоваться для подключения любого источника данных к автозаполнению.Обратный вызов получает два аргумента :

  • Объект запроса с единственным свойством под названием «term», который ссылается на значение, которое в настоящее время находится в текстовом вводе.Например, когда пользователь ввел «новое йо» в поле города, термин «автозаполнение» будет равен «новый йо».

  • ответный обратный вызов , который ожидаетодин аргумент, содержащий данные для предложения пользователю.Эти данные должны быть отфильтрованы на основе предоставленного термина и могут быть в любом из форматов, описанных выше для простых локальных данных (String-Array или Object-Array с меткой / значением / обоими свойствами).Это важно при предоставлении пользовательского обратного вызова источника для обработки ошибок во время запроса.Вы всегда должны вызывать ответный обратный вызов, даже если вы столкнулись с ошибкой.Это гарантирует, что виджет всегда имеет правильное состояние.

Итак, вам нужно передать этот обратный вызов на getLabelsNames, чтобы его можно было вызватьsuccess метод вызова Ajax:

$('#search').autocomplete({
    source: function(request, callback) {
        // pass the callback along
        search.getLabelsNames(request.term, callback);
    },
    minLength:1
});

window.search = {
    getLabelsNames:function(search, callback) { // accept callback as argument
        $.ajax({
            url : '../db_scripts/get_labels_names.php',
            type: "POST",
            data: { id: search }, //this defaults to nothing. not a problem
            success : function( data ) {
                // format the data
                data = $.map(jQuery.parseJSON(data), function(obj) {
                    return obj.name;
                });
                // pass the data to the callback
                callback(data);
            }
        });
    }
}

Обратите внимание, что я использую jQuery.map [docs] здесь, гдевозврат значения из обратного вызова имеет другое значение.Не путайте это с jQuery.each.

0 голосов
/ 19 августа 2011

AJAX-вызовы являются асинхронными, что означает, что вы запускаете их, а они отвечают ПОЗЖЕ.Вы не можете просто «вернуть» значение из вызова ajax - вам нужно передать значение другой функции в «success».

0 голосов
/ 19 августа 2011

this зависит от контекста вызова. ТАК в вашей внутренней функции, this не то же самое.

В зависимости от структуры вашего dataObj вы можете сделать что-то вроде:

$.each(dataObj, function(key, value) {
                alert(value.name);  // value will correspond to the current item being looped over
                return value.name;
            })
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...