Виктор Т.
1036 повідомлень
#15 років тому
Есть вот такой код:
function DataView(ItemNumber){
this.ItemNumber = ItemNumber;
this.Visible = false;
//Всякая ерунда для отображения
this.Height = 0;
this.Width = 0;
}

DataView.prototype = {
//Получение новых данных
GetData: function(){
var url = "localhost/api.php?xid=" + this.Id;
if (window.XMLHttpRequest) {
var req = new XMLHttpRequest();
if (req){
req.open("GET", url, false);
req.send(null);
}
} else if (window.ActiveXObject) {
var req = new ActiveXObject("Microsoft.XMLHTTP");
if (req) {
req.open("GET", url, false);
req.send();
}
}
//обработка результата
if (req.status == 200){
}
}
};


Сейчас запросы отсылаются в синхронном режиме. Как переписать этот код так, чтобы запросы отсылались в асинхронном режиме, но не возникало нехороших бяк, типа конкуренции? Объектов DataView порядка 10-15 штук.

Заранее спасибо.
Виктор Т.
1036 повідомлень
#15 років тому
Переписал код так:
function DataView(ItemNumber){
this.ItemNumber = ItemNumber;
this.Visible = false;
//Всякая ерунда для отображения
this.Height = 0;
this.Width = 0;

this.req = new XMLHttpRequest();
this.req.onreadystatechange = this.ProcessData;
}

DataView.prototype = {
GetData: function(){
var url = "localhost/api.php?xid=" + this.Id;
if (this.req){
this.req.open("GET", url, true);

this.req.send(null);
}
},
ProcessData: function(){
if (this.req.readyState == 4) {
if (this.req.status == 200){

}
}
}
};


Теперь на строке "(this.req.readyState == 4)" вываливается ошибка 'this.req.ReadyState' - есть null или не является объектом.
Но ЧСХ - this.req.open отрабатывает нормально.

Господа, хелп! Мозг кипит.
Владимир М.
578 повідомлень
#15 років тому
Аякс по пределению асинхронен.
--------------------------------------------
вообще не понял, как у вас согласуются

function DataView(ItemNumber){
и
DataView.prototype = {


есть же более классический, безкостыльный метод записи аякса
-------------------------------------------
Владимир М.
578 повідомлень
#15 років тому
А поттом вот еще начиная отсюда -
Цитата ("Sivis"):
this.req = new XMLHttpRequest();

у вас какой ДОМ-объект вызывает DataView(..)?
вы уверены что у него может быть свойство, которое можно объявить экземпляром класса ХМЛ-риквест? ))
Виктор Т.
1036 повідомлень
#15 років тому
vladmax, спасибо за отклик. Делов том, что я очень плохо знаком с JavaScript, поэтому я ни в чем не уверен. То что я там наваял - это все под влиянием Delphi)))
Задача передо мной стоит такая - Есть некая область данных, которую нужно обновлять с сервера через определенные промежутки времени. Таких областей может быть несколько, причем заранее не известно сколько. Собственно я поступил так, как поступил бы если бы писал на delphi - создал "класс", отвечающий за загрузку и отображение данных. И при работе динамически создаю нужное число экземпляров этого "класса".
Если кто-то готов помочь довести это до ума (за вознаграждение разумеется) - буду только рад))
Виктор Т.
1036 повідомлень
#15 років тому
Если в последнем образце заменить вызов на синхронный, то все нормально работает.
this.req.open("GET", url, false);
this.req.send(null);
this.ProcessData;


Итог: При синхронном последовательном вызове GetData и ProcessData все нормально. При асинхронном вызове ProcessData назначается в качестве обработчика, при этом this.req почему-то null
Евгений О.
2989 повідомлень
#15 років тому
Вы неправильно подходите. readyState - это фунция вызывается самим объектом reg по его внутреннему событию с передачей соотвествующих параметров. С точки зрения Delphi это даже не функция, а событие. Здесь надо не синхронизировать, а организовывать очередь. Например что-то вроде такого:

var массив_запросов = new Array();
var executing = false;

function обращение_к_ajax(value) {
if (value) массив_запросов = value;
if (executing) {
setTimeout('обращение_к_ajax("")', 1000);
} else {
if (массив_запросов.length > 0) {
var cur_value = массив_запросов.shift();
//здесь вызываем собственно ajax
ajaxExecute(cur_value);
}
}

function ajaxExecute(value) {
executing = true;
......
reg = new ...
......
......
if (req.readyState == 4) {
......
executing= false;
}
}

И еще. В javascript нет таких понятий как overload, owerride, переприсвоение обработчиков событий и т.п. Когда Вы пишите this.req.onreadystatechange = this.ProcessData; - это не присвоение, а просто вызов на выполнение функции this.ProcessData. Все что Вы можете - это переопределить свойство, функцию, событие так, как Вы делали для DataView.prototype = {....